From patchwork Tue Feb 17 23:36:48 2015 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Viswas G X-Patchwork-Id: 9950973 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id D8D7E6038F for ; Wed, 13 Sep 2017 10:42:24 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id CA3E028F7A for ; Wed, 13 Sep 2017 10:42:24 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id BEF3F28FBD; Wed, 13 Sep 2017 10:42:24 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-3.5 required=2.0 tests=BAYES_00, DATE_IN_PAST_96_XX, DKIM_SIGNED,DKIM_VALID,RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id F080A28F7A for ; Wed, 13 Sep 2017 10:42:23 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1752278AbdIMKmW (ORCPT ); Wed, 13 Sep 2017 06:42:22 -0400 Received: from mail-sn1nam01hn0230.outbound.protection.outlook.com ([104.47.32.230]:65440 "EHLO NAM01-SN1-obe.outbound.protection.outlook.com" rhost-flags-OK-OK-OK-FAIL) by vger.kernel.org with ESMTP id S1751905AbdIMKmU (ORCPT ); Wed, 13 Sep 2017 06:42:20 -0400 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=mscc365.onmicrosoft.com; s=selector1-microsemi-com; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version; bh=zYVTrW9FK2L1zMYtb8/scEUFaHde4H3yLw1ZCRoGhw8=; b=FEQljxJWdgHFSvy5EQKn2Ack5MnM3hp5lBQ3DspVYH8sGg2aQSroHT9/yySAfSHBqIA10EjNDCUIq1kFEAWEdtGxlm3ffNr1RcTBevv6b6LRrbcHwZ+h3VkS3XeiquDKOBWDDBdLrdKr64s0BpqKdqz200cV1E4J9b/OuvI/A/Y= Received: from CY4PR02CA0004.namprd02.prod.outlook.com (10.169.188.14) by MWHPR02MB2207.namprd02.prod.outlook.com (10.168.243.13) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384_P256) id 15.20.35.12; Wed, 13 Sep 2017 10:42:18 +0000 Received: from BN1AFFO11FD021.protection.gbl (2a01:111:f400:7c10::139) by CY4PR02CA0004.outlook.office365.com (2603:10b6:903:18::14) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384_P256) id 15.20.56.8 via Frontend Transport; Wed, 13 Sep 2017 10:42:18 +0000 Received-SPF: Pass (protection.outlook.com: domain of microsemi.com designates 208.19.100.21 as permitted sender) receiver=protection.outlook.com; client-ip=208.19.100.21; helo=avsrvexchhts1.microsemi.net; Received: from avsrvexchhts1.microsemi.net (208.19.100.21) by BN1AFFO11FD021.mail.protection.outlook.com (10.58.52.81) with Microsoft SMTP Server (version=TLS1_0, cipher=TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA_P384) id 15.20.13.11 via Frontend Transport; Wed, 13 Sep 2017 10:42:17 +0000 Received: from localhost (10.187.72.81) by avsrvexchhts1.microsemi.net (10.100.34.105) with Microsoft SMTP Server id 14.3.361.1; Wed, 13 Sep 2017 03:42:13 -0700 From: Viswas G To: CC: , , , , , Subject: [PATCH V2 7/9] pm80xx : corrected SATA abort handling sequence. Date: Wed, 18 Feb 2015 05:06:48 +0530 Message-ID: <20150217233650.9091-8-Viswas.G@microsemi.com> X-Mailer: git-send-email 2.12.3 In-Reply-To: <20150217233650.9091-1-Viswas.G@microsemi.com> References: <20150217233650.9091-1-Viswas.G@microsemi.com> MIME-Version: 1.0 X-EOPAttributedMessage: 0 X-MS-Office365-Filtering-HT: Tenant X-Forefront-Antispam-Report: CIP:208.19.100.21; IPV:NLI; CTRY:US; EFV:NLI; SFV:SPM; SFS:(10009020)(6009001)(346002)(366002)(376002)(39860400002)(2980300002)(438002)(189002)(199003)(8676002)(104016004)(575784001)(81156014)(8936002)(50226002)(76176999)(5003940100001)(189998001)(4326008)(86362001)(50986999)(47776003)(5890100001)(69596002)(81166006)(36756003)(76506005)(106466001)(57986006)(2950100002)(6916009)(2351001)(50466002)(5660300001)(77096006)(316002)(478600001)(305945005)(2906002)(53936002)(356003)(97736004)(110136004)(6666003)(54906002)(1076002)(48376002)(68736007)(5530500006); DIR:OUT; SFP:1501; SCL:5; SRVR:MWHPR02MB2207; H:avsrvexchhts1.microsemi.net; FPR:; SPF:Pass; PTR:InfoDomainNonexistent; MX:1; A:1; LANG:en; X-Microsoft-Exchange-Diagnostics: 1; BN1AFFO11FD021; 1:JWD7wBpsJ5hfEQLFZejc8BmFwMB8liZWMzNrmP8Uvq90NTtmiENb3DraW80dMzFhNZGC6n2D9nycNHsLbZ7JhD3LZzQy6zVIEQvRFCLWfnpe7En7OENlmB9apAmYjVsb X-MS-PublicTrafficType: Email X-MS-Office365-Filtering-Correlation-Id: eb6ad098-3c7c-4741-4674-08d4fa941aed X-Microsoft-Antispam: UriScan:; BCL:0; PCL:0; RULEID:(300000500095)(300135000095)(300000501095)(300135300095)(22001)(300000502095)(300135100095)(2017030254152)(8251501002)(300000503095)(300135400095)(2017052603199)(201703131423075)(201703031133081)(201702281549075)(300000504095)(300135200095)(300000505095)(300135600095)(300000506095)(300135500095); SRVR:MWHPR02MB2207; X-Microsoft-Exchange-Diagnostics: 1; MWHPR02MB2207; 3:mkKZcVUjgRaXFWrYlkAeSMQmvX9SoauiM1VYjvESZSONul79BsQh0gMzANQQW4qmBGhIpRLRWr5vtjzNRrV7zk8RcRNF1Uuz2rQQzS+CMV0CGdw/mFFoqYHk+rdf3II8ENhPxpOu9t2cye/Ws7skSbZBIqFClqxn3AZCyPtrApDAtWz9MC+PpLeB+nwKmy1st95p4/3Kh56f7E/rsWgUvvC4HJU7skhRo5AI0DAgfprIeb6bPCG+r7Vb+RLdcGJtmAazQffYb1JmJY36NlNIDEKpzAun0pxs/KuxLWkVlR8K0bZZTBRCH+7fBXhAT+cV+/eZS3pPyd/br1q53qJzSXeYCsyrsyKd8nRruw8SMHE=; 25:COCiYey+Rsq7fYquOVpcQ4/hPG9VlcJsUFdBypb6DNQgxvMB4LVk5tam7jsqYeUOqN7wS5u/MJrKJx6/dUO+AlQ2u5Oi47ul/di38hsBlCChzJDMy7J/TW4vEdM8WSOYhvdZ596xiXsYm1F25y0JWFhSLSgFdReSVU65YJP6Ep0mMv9uITFC9wE1R4leNB2LwwnK7QURYqj5UFx4aHAmA4v94CAwoUHhxsdPsswGLIspTEzxnTEUYcQQLn3ZDrOeWrerqm2VQ/gZXu4RDOzQyNoBuq6XsC7fsDBjFa5ycHCVhq965L5j/5D4YE53NcylKkDWCUAfWYT62dYNRQas6A== X-MS-TrafficTypeDiagnostic: MWHPR02MB2207: X-Microsoft-Exchange-Diagnostics: 1; MWHPR02MB2207; 31:Ci4NhIBgSje9xPCGUbCSPSGO8h9Wh9HiSCZHexf4z5zXEDBhiv6MB1gpB+CFPXtgV6GmbBXyg4onN/ZUhOBURju8sCSJAdK80fxZXUAs7CrawgipjJNWsbDRk/Sr7wuBuFJoko53aIeoOjBXvh83iYxzxCu9KjvxsHI/xudB5yPxYrXfC11DzeRh1xNEOcIxa/fMcnNdt2rAoU+7Cpu3OE3ImBObKq5nvkcVyF6D4tg=; 20:FiRLrx1oWF1X8aa1Sr77bKd9Y1KjnPGuGPVbGQW4N7SewLkK7OMBu1gcLTO5RrHm8fQ9NY6mzarNYAG6R4FxNBeIC/kz7j7HgE0jvYpGEDdO6t7GcRMg3Q2/50D+amEj4nKAUjBA5PYLxQl6IpA3CUn2BrMJdjAPUFeEIp+SIDI+4v9wAqypIu+w/j1N+XYNpj1yosh6TVSsLKy/wPhfdVirBKEZrU7Ivrrp1aRXEgfz2uheMCRUIPDaed30jeZw4Zcg4D3wy1/Z7HDkcR7xeSXloXV7W5dDEliLMK7T16ZXtoFce5ATZ3UYGXb8LD/r8xp/7583+I4fjQeYa1+DH5gQj0GYqEiTE8cXcuSbQAmw4qlbwzk0usvBdWg2bwWMG3OlDXmm7tNPZwviT63GTSYW/YSMsW3B82+rdAiA62QllIgJ4rLRCxUajlPCsdO1gGeiiGoDqOlbBZmogxVfe8Dxe64Qyw/zlVhz1rKvPRntwF24v8raBBmSiqJnRRQv X-Exchange-Antispam-Report-Test: UriScan:(72170198267865); X-Microsoft-Antispam-PRVS: X-Exchange-Antispam-Report-CFA-Test: BCL:0; PCL:0; RULEID:(100000700101)(100105000095)(100000701101)(100105300095)(100000702101)(100105100095)(6040450)(2401047)(8121501046)(5005006)(3002001)(100000703101)(100105400095)(10201501046)(93006095)(93004095)(6055026)(6041248)(20161123564025)(20161123558100)(20161123562025)(20161123555025)(201703131423075)(201702281528075)(201703061421075)(201703061406153)(20161123560025)(6072148)(201708071742011)(100000704101)(100105200095)(100000705101)(100105500095); SRVR:MWHPR02MB2207; BCL:0; PCL:0; RULEID:(100000800101)(100110000095)(100000801101)(100110300095)(100000802101)(100110100095)(100000803101)(100110400095)(100000804101)(100110200095)(100000805101)(100110500095); SRVR:MWHPR02MB2207; X-Microsoft-Exchange-Diagnostics: 1; MWHPR02MB2207; 4:QlcAmSaMeCY/KoRZXTTql5JscyR2qkckN/9TftA7usFzDiAz1k4UroTsqGyB+i6DXHmNo8bfVURXDXpR9QJmF+LS7V2BGL8glFavbO8S5zpo/Iz5E6J+3yYO8j3ELabcTz0Rspbqg1966aRIw+Rvcn/huXuWAiBk9ASqHnjQhO8VULZ4pVgXRpBfbVqzAAKb73nc06PWdEmFR6nW9DVySgRSfvMR6L8WtfwRfd0JaCjUwDAnsY6sDtj5WLD3q1OXQmRwYMERZaqoAW4PbzTaAea+FrTsKZ8ITqpm4Ve/gT4= X-Forefront-PRVS: 042957ACD7 X-Microsoft-Exchange-Diagnostics: =?us-ascii?Q?1; MWHPR02MB2207; 23:Fe8pPoJLEwXHpXoR9maoDELjYGDqDLwQ6qvE4s1Nd?= =?us-ascii?Q?qnkhW37zyP+ezrGwsevUfoo/Uwqhl4P1lCZxo1P3Os0DPTt1Z/089wGNzxsv?= =?us-ascii?Q?0dU/Dh9bLco6Fu4cDMyyoCRnyf1+m4+CxVxZWxdYk8TteF55t+UlXJ8mt/+d?= =?us-ascii?Q?8+oP7edhBeSrfkVIvojuR183qtAoDiWaLJepnQ/G2pPBfO5sAWZlzQJOiwZc?= =?us-ascii?Q?Aa/37YJc/3fyiLBJ2nFUL/yuLD41VOCidDpn8sBrHnKcAt+A8/VCXSPIb1gg?= =?us-ascii?Q?/iwRqLjLt2nNKnkyKQX3ii+TAy7RRT5iWBTtSJrOOIEK2mUYMesUHy6RvpCC?= =?us-ascii?Q?G/HH53GEz3WWXFljH2A0lMAzQDT4sFTqsz2+Y44s+n46Rd1e4hckyZZ4kfO8?= =?us-ascii?Q?XfhATnfB95UDprvWVII8q/iCDTbJaBTL5kF+w6DkyxIriJthhpGcaKL4iwha?= =?us-ascii?Q?n1KrRcKII147Cr5we9RaRDbNeYsF/UcUA80gqFZKGGhXWwLuU5TvH7GOIO2x?= =?us-ascii?Q?Dv8FyTsQjGnYXvoWvVXNaitT/1vVNW+ZGcxzgP1M8h19cmNJInvTQaPt2hTU?= =?us-ascii?Q?Ir7iZ6kU0sCODn8p4SEpLTF3zENb1BZtXmDUeCrIq0qEGoIqJnTLLydqJtm4?= =?us-ascii?Q?SxLIwt+uF5vCNy65hSFVwAiqBV3zSC9QzdM8MkTPfhk4ETffTgGBVV1i7ovo?= =?us-ascii?Q?EqaDIwQPkZdDyYxJcq74WOaaSayjFvv4GkWIQ3/Ww2i8bbxNlg9R+Zj2O5iq?= =?us-ascii?Q?+9iZso+6465fI8QFNmWo5Qb80bLJgTzAJ5KHqGpzPrfNMrcierm4hogGKUa6?= =?us-ascii?Q?3gz5ADllHu9qcCH0MArBdblM4AznS47d9JyzZ8kIOiW2U9t/C68bbgFNvcli?= =?us-ascii?Q?Ogj6h35cOi1vO7xpotfs3icOr+6J2i422PkqogVEW1hi2/1YxPbHWin9PxMo?= =?us-ascii?Q?jcyi7I/P3wTUaYE3s6taFwzdt31IOs9Yb26WwUA0G7sLVdo+YtJsAc52ls8Z?= =?us-ascii?Q?bLv/5ehx3av9gsOGzgyuUQmcXJlTFqlFnpQZS55Wp3PBI9IfGs+acvqgXOT7?= =?us-ascii?Q?GmKAW9ZW3H+vtjrn25xR4Lz9aEJSGXklV2DQ7YaHvqg2ClSfPSOKjqpi7cuk?= =?us-ascii?Q?kFUBqbBZN946zUm+/X1RgUh7f9zjJn2s4h9nLsFhv0s+tX1UQQqYHvB9tXdp?= =?us-ascii?Q?KgrV9NtH5f/+lx5X0/ERMvo6yhs1W0Qk3YP?= X-Microsoft-Exchange-Diagnostics: 1; MWHPR02MB2207; 6:HXlhNOkMCVue6i8M1OOBiKI0DhGvrAVgTLi1BPGfynwINI4TwmcyYK/RHraiq8aQFUVqhyHKg4p7uHmPQv2toL81QeKGyQNahBJnn06dUT8LFg1VJH8+xMEi44owK7useiiyYdxhLCD1MlvGemQMY3SnTRGQD7W7qYqLqa8Qcol1o2F96UQnmXzfJC2L+8HhPjBQi1J8EqrtRxov7e/z46kH/7A/P8EtV3xb3SqC6p3j5nVHSfnrqfpWe8/ytyvsTmKok+FrKjG+5NRfA16xdfirFFEgS5kAQwkPt0QiFdQB6IrxB+umJDMW/rpsonbTUHkebMHxnku1Mu3ctQuwzw==; 5:E90VeOwp9kgQNSRnanFNSfcfNvBJUDX60hqQvVQYrS87IUPWjznYzeW4rjNewSlFCqW9No6xxpVBjH1GCGdZ64YYMaq/CBOEp5z0P0D2XRVoO0hgrbvbPNpCAUBgbXcVq+v15EY6vWIV5d5UPMCP9A==; 24:TDKeiLYpnytmj9vANcc2fsCydpDJC5gzUGnZlHHP5IduJPxW3JIkgz/AqGNc1D+1NA0ubFqAbd25gtH7dK5K4g==; 7:3URyF02bPWyHhgaek/TBgWz2+5n+htgKJ7AK/k79hPRhzR3wXi8F4huChxe4AIB6vs5F6g11eRwlA3SEmVSa1FONwPG0m1NJpkQRgL0XPXfrRxM2mi5GFSwVvVnFZV7QPpkbhBwnvr/4JqamQbF7K00t9qQOtSqKD3NQPm4mc8rWlvA4P+/dg8pEMwy8zRbIw6qOPy9gtw3nO4Kzf59g3MJQZqNqMz8lTYU30hFlMkM= SpamDiagnosticOutput: 1:22 X-OriginatorOrg: microsemi.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 13 Sep 2017 10:42:17.6668 (UTC) X-MS-Exchange-CrossTenant-Id: f267a5c8-86d8-4cc9-af71-1fd2c67c8fad X-MS-Exchange-CrossTenant-OriginalAttributedTenantConnectingIp: TenantId=f267a5c8-86d8-4cc9-af71-1fd2c67c8fad; Ip=[208.19.100.21]; Helo=[avsrvexchhts1.microsemi.net] X-MS-Exchange-CrossTenant-FromEntityHeader: HybridOnPrem X-MS-Exchange-Transport-CrossTenantHeadersStamped: MWHPR02MB2207 Sender: linux-scsi-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-scsi@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP Modified SATA abort handling with following steps: 1) Set device state as recovery. 2) Send phy reset. 3) Wait for reset completion. 4) After successful reset, abort all IO's to the device. 5) After aborting all IO's to device, set device state as operational. Signed-off-by: Deepak Ukey Signed-off-by: Viswas G Acked-by: Jack Wang --- drivers/scsi/pm8001/pm8001_hwi.c | 8 ++++- drivers/scsi/pm8001/pm8001_sas.c | 71 ++++++++++++++++++++++++++++++++++++++-- drivers/scsi/pm8001/pm8001_sas.h | 8 +++++ drivers/scsi/pm8001/pm80xx_hwi.c | 36 ++++++++++++++++---- 4 files changed, 113 insertions(+), 10 deletions(-) diff --git a/drivers/scsi/pm8001/pm8001_hwi.c b/drivers/scsi/pm8001/pm8001_hwi.c index bc4a6f649ec9..db88a8e7ee0e 100644 --- a/drivers/scsi/pm8001/pm8001_hwi.c +++ b/drivers/scsi/pm8001/pm8001_hwi.c @@ -3209,10 +3209,16 @@ int pm8001_mpi_local_phy_ctl(struct pm8001_hba_info *pm8001_ha, void *piomb) PM8001_MSG_DBG(pm8001_ha, pm8001_printk("%x phy execute %x phy op failed!\n", phy_id, phy_op)); - } else + } else { PM8001_MSG_DBG(pm8001_ha, pm8001_printk("%x phy execute %x phy op success!\n", phy_id, phy_op)); + pm8001_ha->phy[phy_id].reset_success = true; + } + if (pm8001_ha->phy[phy_id].enable_completion) { + complete(pm8001_ha->phy[phy_id].enable_completion); + pm8001_ha->phy[phy_id].enable_completion = NULL; + } pm8001_tag_free(pm8001_ha, tag); return 0; } diff --git a/drivers/scsi/pm8001/pm8001_sas.c b/drivers/scsi/pm8001/pm8001_sas.c index e80b0542a67f..60d5bec5c45e 100644 --- a/drivers/scsi/pm8001/pm8001_sas.c +++ b/drivers/scsi/pm8001/pm8001_sas.c @@ -1167,13 +1167,16 @@ int pm8001_abort_task(struct sas_task *task) struct scsi_lun lun; struct pm8001_device *pm8001_dev; struct pm8001_tmf_task tmf_task; - int rc = TMF_RESP_FUNC_FAILED; + int rc = TMF_RESP_FUNC_FAILED, ret; + u32 phy_id; + struct sas_task_slow slow_task; if (unlikely(!task || !task->lldd_task || !task->dev)) return TMF_RESP_FUNC_FAILED; dev = task->dev; pm8001_dev = dev->lldd_dev; pm8001_ha = pm8001_find_ha_by_dev(dev); device_id = pm8001_dev->device_id; + phy_id = pm8001_dev->attached_phy; rc = pm8001_find_tag(task, &tag); if (rc == 0) { pm8001_printk("no tag for task:%p\n", task); @@ -1184,6 +1187,11 @@ int pm8001_abort_task(struct sas_task *task) spin_unlock_irqrestore(&task->task_state_lock, flags); return TMF_RESP_FUNC_COMPLETE; } + task->task_state_flags |= SAS_TASK_STATE_ABORTED; + if (task->slow_task == NULL) { + init_completion(&slow_task.completion); + task->slow_task = &slow_task; + } spin_unlock_irqrestore(&task->task_state_lock, flags); if (task->task_proto & SAS_PROTOCOL_SSP) { struct scsi_cmnd *cmnd = task->uldd_task; @@ -1195,8 +1203,61 @@ int pm8001_abort_task(struct sas_task *task) pm8001_dev->sas_device, 0, tag); } else if (task->task_proto & SAS_PROTOCOL_SATA || task->task_proto & SAS_PROTOCOL_STP) { - rc = pm8001_exec_internal_task_abort(pm8001_ha, pm8001_dev, - pm8001_dev->sas_device, 0, tag); + if (pm8001_ha->chip_id == chip_8006) { + DECLARE_COMPLETION_ONSTACK(completion_reset); + DECLARE_COMPLETION_ONSTACK(completion); + struct pm8001_phy *phy = pm8001_ha->phy + phy_id; + /* 1. Set Device state as Recovery*/ + pm8001_dev->setds_completion = &completion; + PM8001_CHIP_DISP->set_dev_state_req(pm8001_ha, + pm8001_dev, 0x03); + wait_for_completion(&completion); + /* 2. Send Phy Control Hard Reset */ + reinit_completion(&completion); + phy->reset_success = false; + phy->enable_completion = &completion; + phy->reset_completion = &completion_reset; + ret = PM8001_CHIP_DISP->phy_ctl_req(pm8001_ha, phy_id, + PHY_HARD_RESET); + if (ret) + goto out; + PM8001_MSG_DBG(pm8001_ha, + pm8001_printk("Waiting for local phy ctl\n")); + wait_for_completion(&completion); + if (!phy->reset_success) + goto out; + /* 3. Wait for Port Reset complete / Port reset TMO*/ + PM8001_MSG_DBG(pm8001_ha, + pm8001_printk("Waiting for Port reset\n")); + wait_for_completion(&completion_reset); + if (phy->port_reset_status) + goto out; + /* 4. SATA Abort ALL + * we wait for the task to be aborted so that the task + * is removed from the ccb. on success the caller is + * going to free the task. + */ + ret = pm8001_exec_internal_task_abort(pm8001_ha, + pm8001_dev, pm8001_dev->sas_device, 1, tag); + if (ret) + goto out; + ret = wait_for_completion_timeout( + &task->slow_task->completion, + PM8001_TASK_TIMEOUT * HZ); + if (!ret) + goto out; + + /* 5. Set Device State as Operational */ + reinit_completion(&completion); + pm8001_dev->setds_completion = &completion; + PM8001_CHIP_DISP->set_dev_state_req(pm8001_ha, + pm8001_dev, 0x01); + wait_for_completion(&completion); + } else { + rc = pm8001_exec_internal_task_abort(pm8001_ha, + pm8001_dev, pm8001_dev->sas_device, 0, tag); + } + rc = TMF_RESP_FUNC_COMPLETE; } else if (task->task_proto & SAS_PROTOCOL_SMP) { /* SMP */ rc = pm8001_exec_internal_task_abort(pm8001_ha, pm8001_dev, @@ -1204,6 +1265,10 @@ int pm8001_abort_task(struct sas_task *task) } out: + spin_lock_irqsave(&task->task_state_lock, flags); + if (task->slow_task == &slow_task) + task->slow_task = NULL; + spin_unlock_irqrestore(&task->task_state_lock, flags); if (rc != TMF_RESP_FUNC_COMPLETE) pm8001_printk("rc= %d\n", rc); return rc; diff --git a/drivers/scsi/pm8001/pm8001_sas.h b/drivers/scsi/pm8001/pm8001_sas.h index c75de413e062..80b4dd6df0c2 100644 --- a/drivers/scsi/pm8001/pm8001_sas.h +++ b/drivers/scsi/pm8001/pm8001_sas.h @@ -263,8 +263,15 @@ struct pm8001_phy { u8 phy_state; enum sas_linkrate minimum_linkrate; enum sas_linkrate maximum_linkrate; + struct completion *reset_completion; + bool port_reset_status; + bool reset_success; }; +/* port reset status */ +#define PORT_RESET_SUCCESS 0x00 +#define PORT_RESET_TMO 0x01 + struct pm8001_device { enum sas_device_type dev_type; struct domain_device *sas_device; @@ -533,6 +540,7 @@ struct pm8001_hba_info { u32 smp_exp_mode; const struct firmware *fw_image; struct isr_param irq_vector[PM8001_MAX_MSIX_VEC]; + u32 reset_in_progress; }; struct pm8001_work { diff --git a/drivers/scsi/pm8001/pm80xx_hwi.c b/drivers/scsi/pm8001/pm80xx_hwi.c index 8f1f5dc77d71..92d2045dea68 100644 --- a/drivers/scsi/pm8001/pm80xx_hwi.c +++ b/drivers/scsi/pm8001/pm80xx_hwi.c @@ -1781,6 +1781,8 @@ mpi_ssp_completion(struct pm8001_hba_info *pm8001_ha , void *piomb) "task 0x%p done with io_status 0x%x resp 0x%x " "stat 0x%x but aborted by upper layer!\n", t, status, ts->resp, ts->stat)); + if (t->slow_task) + complete(&t->slow_task->completion); pm8001_ccb_task_free(pm8001_ha, t, ccb, tag); } else { spin_unlock_irqrestore(&t->task_state_lock, flags); @@ -3044,6 +3046,7 @@ hw_event_phy_down(struct pm8001_hba_info *pm8001_ha, void *piomb) struct pm8001_port *port = &pm8001_ha->port[port_id]; struct pm8001_phy *phy = &pm8001_ha->phy[phy_id]; + u32 port_sata = (phy->phy_type & PORT_TYPE_SATA); port->port_state = portstate; phy->identify.device_type = 0; phy->phy_attached = 0; @@ -3055,7 +3058,7 @@ hw_event_phy_down(struct pm8001_hba_info *pm8001_ha, void *piomb) pm8001_printk(" PortInvalid portID %d\n", port_id)); PM8001_MSG_DBG(pm8001_ha, pm8001_printk(" Last phy Down and port invalid\n")); - if (phy->phy_type & PORT_TYPE_SATA) { + if (port_sata) { phy->phy_type = 0; port->port_attached = 0; pm80xx_hw_event_ack_req(pm8001_ha, 0, HW_EVENT_PHY_DOWN, @@ -3077,7 +3080,7 @@ hw_event_phy_down(struct pm8001_hba_info *pm8001_ha, void *piomb) pm8001_printk(" Phy Down and PORT_LOSTCOMM\n")); PM8001_MSG_DBG(pm8001_ha, pm8001_printk(" Last phy Down and port invalid\n")); - if (phy->phy_type & PORT_TYPE_SATA) { + if (port_sata) { port->port_attached = 0; phy->phy_type = 0; pm80xx_hw_event_ack_req(pm8001_ha, 0, HW_EVENT_PHY_DOWN, @@ -3093,6 +3096,11 @@ hw_event_phy_down(struct pm8001_hba_info *pm8001_ha, void *piomb) break; } + if (port_sata && (portstate != PORT_IN_RESET)) { + struct sas_ha_struct *sas_ha = pm8001_ha->sas; + + sas_ha->notify_phy_event(&phy->sas_phy, PHYE_LOSS_OF_SIGNAL); + } } static int mpi_phy_start_resp(struct pm8001_hba_info *pm8001_ha, void *piomb) @@ -3195,12 +3203,14 @@ static int mpi_hw_event(struct pm8001_hba_info *pm8001_ha, void *piomb) case HW_EVENT_PHY_DOWN: PM8001_MSG_DBG(pm8001_ha, pm8001_printk("HW_EVENT_PHY_DOWN\n")); - if (phy->phy_type & PORT_TYPE_SATA) - sas_ha->notify_phy_event(&phy->sas_phy, - PHYE_LOSS_OF_SIGNAL); + hw_event_phy_down(pm8001_ha, piomb); + if (pm8001_ha->reset_in_progress) { + PM8001_MSG_DBG(pm8001_ha, + pm8001_printk("Reset in progress\n")); + return 0; + } phy->phy_attached = 0; phy->phy_state = 0; - hw_event_phy_down(pm8001_ha, piomb); break; case HW_EVENT_PORT_INVALID: PM8001_MSG_DBG(pm8001_ha, @@ -3307,9 +3317,17 @@ static int mpi_hw_event(struct pm8001_hba_info *pm8001_ha, void *piomb) case HW_EVENT_PORT_RESET_TIMER_TMO: PM8001_MSG_DBG(pm8001_ha, pm8001_printk("HW_EVENT_PORT_RESET_TIMER_TMO\n")); + pm80xx_hw_event_ack_req(pm8001_ha, 0, HW_EVENT_PHY_DOWN, + port_id, phy_id, 0, 0); sas_phy_disconnected(sas_phy); phy->phy_attached = 0; sas_ha->notify_port_event(sas_phy, PORTE_LINK_RESET_ERR); + if (pm8001_ha->phy[phy_id].reset_completion) { + pm8001_ha->phy[phy_id].port_reset_status = + PORT_RESET_TMO; + complete(pm8001_ha->phy[phy_id].reset_completion); + pm8001_ha->phy[phy_id].reset_completion = NULL; + } break; case HW_EVENT_PORT_RECOVERY_TIMER_TMO: PM8001_MSG_DBG(pm8001_ha, @@ -3334,6 +3352,12 @@ static int mpi_hw_event(struct pm8001_hba_info *pm8001_ha, void *piomb) case HW_EVENT_PORT_RESET_COMPLETE: PM8001_MSG_DBG(pm8001_ha, pm8001_printk("HW_EVENT_PORT_RESET_COMPLETE\n")); + if (pm8001_ha->phy[phy_id].reset_completion) { + pm8001_ha->phy[phy_id].port_reset_status = + PORT_RESET_SUCCESS; + complete(pm8001_ha->phy[phy_id].reset_completion); + pm8001_ha->phy[phy_id].reset_completion = NULL; + } break; case EVENT_BROADCAST_ASYNCH_EVENT: PM8001_MSG_DBG(pm8001_ha,