Re: [PATCH] ibmvfc: Avoid link down on FS9100 canister reboot

2020-09-21 Thread Martin K. Petersen
On Fri, 11 Sep 2020 16:28:26 -0500, Brian King wrote:

> When a canister on a FS9100, or similar storage, running in NPIV mode,
> is rebooted, its WWPNs will fail over to another canister. When this
> occurs, we see a WWPN going away from the fabric at one N-Port ID,
> and, a short time later, the same WWPN appears at a different N-Port ID.
> When the canister is fully operational again, the WWPNs fail back to
> the original canister. If there is any I/O outstanding to the target
> when this occurs, it will result in the implicit logout the ibmvfc driver
> issues before removing the rport to fail. When the WWPN then shows up at a
> different N-Port ID, and we issue a PLOGI to it, the VIOS will
> see that it still has a login for this WWPN at the old N-Port ID,
> which results in the VIOS simulating a link down / link up sequence
> to the client, in order to get the VIOS and client LPAR in sync.
> 
> [...]

Applied to 5.10/scsi-queue, thanks!

[1/1] scsi: ibmvfc: Avoid link down on FS9100 canister reboot
  https://git.kernel.org/mkp/scsi/c/4b29cb6197d9

-- 
Martin K. Petersen  Oracle Linux Engineering


Re: [PATCH] ibmvfc: Avoid link down on FS9100 canister reboot

2020-09-16 Thread Brian King
On 9/15/20 7:49 PM, Martin K. Petersen wrote:
> 
> Brian,
> 
>> When a canister on a FS9100, or similar storage, running in NPIV mode,
>> is rebooted, its WWPNs will fail over to another canister.
> 
> [...]
> 
> Applied to 5.10/scsi-staging, thanks! I fixed a bunch of checkpatch
> warnings.

Sorry about the checkpatch issues. Thanks for pulling this in.

-Brian

-- 
Brian King
Power Linux I/O
IBM Linux Technology Center



Re: [PATCH] ibmvfc: Avoid link down on FS9100 canister reboot

2020-09-15 Thread Martin K. Petersen


Brian,

> When a canister on a FS9100, or similar storage, running in NPIV mode,
> is rebooted, its WWPNs will fail over to another canister.

[...]

Applied to 5.10/scsi-staging, thanks! I fixed a bunch of checkpatch
warnings.

-- 
Martin K. Petersen  Oracle Linux Engineering


[PATCH] ibmvfc: Avoid link down on FS9100 canister reboot

2020-09-11 Thread Brian King
When a canister on a FS9100, or similar storage, running in NPIV mode,
is rebooted, its WWPNs will fail over to another canister. When this
occurs, we see a WWPN going away from the fabric at one N-Port ID,
and, a short time later, the same WWPN appears at a different N-Port ID.
When the canister is fully operational again, the WWPNs fail back to
the original canister. If there is any I/O outstanding to the target
when this occurs, it will result in the implicit logout the ibmvfc driver
issues before removing the rport to fail. When the WWPN then shows up at a
different N-Port ID, and we issue a PLOGI to it, the VIOS will
see that it still has a login for this WWPN at the old N-Port ID,
which results in the VIOS simulating a link down / link up sequence
to the client, in order to get the VIOS and client LPAR in sync.

The patch below improves the way we handle this scenario so as to
avoid the link bounce, which affects all targets under the virtual
host adapter. The change is to utilize the Move Login MAD, which
will work even when I/O is outstanding to the target. The change
only alters the target state machine for the case where the implicit
logout fails prior to deleting the rport. If this implicit logout fails,
we defer deleting the ibmvfc_target object after calling
fc_remote_port_delete. This enables us to later retry the implicit logout
after terminate_rport_io occurs, or to issue the Move Login request if
a WWPN shows up at a new N-Port ID prior to this occurring.

This has been tested by IBM's storage interoperability team
on a FS9100, forcing the failover to occur. With debug tracing enabled
in the ibmvfc driver, we confirmed the move login was sent
in this scenario and confirmed the link bounce no longer occurred.

Signed-off-by: Brian King 
---
 drivers/scsi/ibmvscsi/ibmvfc.c | 211 ++---
 drivers/scsi/ibmvscsi/ibmvfc.h |  38 +++-
 2 files changed, 232 insertions(+), 17 deletions(-)

diff --git a/drivers/scsi/ibmvscsi/ibmvfc.c b/drivers/scsi/ibmvscsi/ibmvfc.c
index 175a165..322bb30 100644
--- a/drivers/scsi/ibmvscsi/ibmvfc.c
+++ b/drivers/scsi/ibmvscsi/ibmvfc.c
@@ -134,6 +134,7 @@
 static void ibmvfc_tgt_query_target(struct ibmvfc_target *);
 static void ibmvfc_npiv_logout(struct ibmvfc_host *);
 static void ibmvfc_tgt_implicit_logout_and_del(struct ibmvfc_target *);
+static void ibmvfc_tgt_move_login(struct ibmvfc_target *);
 
 static const char *unknown_error = "unknown error";
 
@@ -431,7 +432,20 @@ static int ibmvfc_set_tgt_action(struct ibmvfc_target *tgt,
}
break;
case IBMVFC_TGT_ACTION_LOGOUT_RPORT_WAIT:
-   if (action == IBMVFC_TGT_ACTION_DEL_RPORT) {
+   if (action == IBMVFC_TGT_ACTION_DEL_RPORT ||
+   action == IBMVFC_TGT_ACTION_DEL_AND_LOGOUT_RPORT) {
+   tgt->action = action;
+   rc = 0;
+   }
+   break;
+   case IBMVFC_TGT_ACTION_LOGOUT_DELETED_RPORT:
+   if (action == IBMVFC_TGT_ACTION_LOGOUT_RPORT) {
+   tgt->action = action;
+   rc = 0;
+   }
+   break;
+   case IBMVFC_TGT_ACTION_DEL_AND_LOGOUT_RPORT:
+   if (action == IBMVFC_TGT_ACTION_LOGOUT_DELETED_RPORT) {
tgt->action = action;
rc = 0;
}
@@ -441,16 +455,18 @@ static int ibmvfc_set_tgt_action(struct ibmvfc_target 
*tgt,
tgt->action = action;
rc = 0;
}
+   break;
case IBMVFC_TGT_ACTION_DELETED_RPORT:
break;
default:
-   if (action >= IBMVFC_TGT_ACTION_LOGOUT_RPORT)
-   tgt->add_rport = 0;
tgt->action = action;
rc = 0;
break;
}
 
+   if (action >= IBMVFC_TGT_ACTION_LOGOUT_RPORT)
+   tgt->add_rport = 0;
+
return rc;
 }
 
@@ -548,7 +564,8 @@ static void ibmvfc_set_host_action(struct ibmvfc_host 
*vhost,
  **/
 static void ibmvfc_reinit_host(struct ibmvfc_host *vhost)
 {
-   if (vhost->action == IBMVFC_HOST_ACTION_NONE) {
+   if (vhost->action == IBMVFC_HOST_ACTION_NONE &&
+   vhost->state == IBMVFC_ACTIVE) {
if (!ibmvfc_set_host_state(vhost, IBMVFC_INITIALIZING)) {
scsi_block_requests(vhost->host);
ibmvfc_set_host_action(vhost, IBMVFC_HOST_ACTION_QUERY);
@@ -2574,7 +2591,9 @@ static void ibmvfc_terminate_rport_io(struct fc_rport 
*rport)
struct ibmvfc_host *vhost = shost_priv(shost);
struct fc_rport *dev_rport;
struct scsi_device *sdev;
-   unsigned long rc;
+   struct ibmvfc_target *tgt;
+   unsigned long rc, flags;
+   unsigned int found;
 
ENTER;
shost_for_each_device(sdev, shost) {
@@ -2588,6 +2607,25 @@ static void