From patchwork Sat Nov 9 04:45:22 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Himanshu Madhani X-Patchwork-Id: 13869242 Received: from mx0b-00069f02.pphosted.com (mx0b-00069f02.pphosted.com [205.220.177.32]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 7C0D613A89B for ; Sat, 9 Nov 2024 04:45:32 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=205.220.177.32 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1731127535; cv=none; b=o3X+DAq58FMeutwbc/JY8B9HmwrjGEuJ3fVGatvuJJltbgRQmYeayv3Ol2rvPtqHxUlc7k01I28yFkJZwscrO3VmMHjfJ0L4INQ6sf03BWjbzJFTDVn+nfhxWxAHxE1ru5fy72b8MWwEWaNI4c7KUfCLJKsVyg3t6aidXoCo4+o= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1731127535; c=relaxed/simple; bh=BLaDdgRfFUM588wy0p12T5Q1kij4RkekpGW9gKfae50=; h=From:To:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=iyvihMLEC4yMjcoHxP+dccrcA+rBySfZM5DeoAFTsjq/nUZJ0/1hiskQg8BPFmG6rxAd0/wS0wo7MSurdGb7QN9NqfI3HIdRb8FKwhdQnK1onQJ8dECeqoodVdr1EBY+jWbrr6BECxSJyaRHUZ4ZCCdWw686cE87ONKxgo5LajA= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=oracle.com; spf=pass smtp.mailfrom=oracle.com; dkim=pass (2048-bit key) header.d=oracle.com header.i=@oracle.com header.b=ZQTXXewN; arc=none smtp.client-ip=205.220.177.32 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=oracle.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=oracle.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=oracle.com header.i=@oracle.com header.b="ZQTXXewN" Received: from pps.filterd (m0246631.ppops.net [127.0.0.1]) by mx0b-00069f02.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id 4A94JDEF005644 for ; Sat, 9 Nov 2024 04:45:31 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=oracle.com; h= content-transfer-encoding:date:from:in-reply-to:message-id :mime-version:references:subject:to; s=corp-2023-11-20; bh=YeVHt uld5WncezmePkw/P2ZIM6RS83710TQscqSyfZQ=; b=ZQTXXewNlTexMRZ1uFKPu HTKc+ymN9kt+XBIMPQM6cUrk4hz+pi6nPrp07vswBFQWJT1t2Xh8fkRxW4MtXgB+ i2XdB43UgYACJJ2HudD8GHFDyZqS+w11RcefJAvR5QhiTMW26nXMPv22BJuOtEwL 34pQhXplItaCkEXUSbMD6vb/o5hAmbzemRWq/DBa7IJdqvIYXDkic409En9jgCEF IxQ3H6hLWUwEHUO9RS+WWlYb1aSqNHixerzc1yPz//EbTiAPhPXO1YKE6EIUOQn/ oWOa/RrBteuXYwNssR4aU7IZ+HINUq3M8fIFQMv3ThZZbOkk6rZoA1r/OstLVfcU g== Received: from iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (iadpaimrmta02.appoci.oracle.com [147.154.18.20]) by mx0b-00069f02.pphosted.com (PPS) with ESMTPS id 42t0k200a2-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK) for ; Sat, 09 Nov 2024 04:45:30 +0000 (GMT) Received: from pps.filterd (iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com [127.0.0.1]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (8.18.1.2/8.18.1.2) with ESMTP id 4A91Xu83034477 for ; Sat, 9 Nov 2024 04:45:30 GMT Received: from pps.reinject (localhost [127.0.0.1]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (PPS) with ESMTPS id 42sx65aj9t-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK) for ; Sat, 09 Nov 2024 04:45:30 +0000 Received: from iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com [127.0.0.1]) by pps.reinject (8.17.1.5/8.17.1.5) with ESMTP id 4A94jTdO001575 for ; Sat, 9 Nov 2024 04:45:29 GMT Received: from hmadhani-upstream.osdevelopmeniad.oraclevcn.com (hmadhani-upstream.allregionaliads.osdevelopmeniad.oraclevcn.com [100.100.255.48]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (PPS) with ESMTP id 42sx65aj9h-2; Sat, 09 Nov 2024 04:45:29 +0000 From: himanshu.madhani@oracle.com To: martin.petersen@oracle.com, linux-scsi@vger.kernel.org Subject: [RFC v1 1/8] scsi: Add multipath device support Date: Sat, 9 Nov 2024 04:45:22 +0000 Message-ID: <20241109044529.992935-2-himanshu.madhani@oracle.com> X-Mailer: git-send-email 2.41.0.rc2 In-Reply-To: <20241109044529.992935-1-himanshu.madhani@oracle.com> References: <20241109044529.992935-1-himanshu.madhani@oracle.com> Precedence: bulk X-Mailing-List: linux-scsi@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.293,Aquarius:18.0.1057,Hydra:6.0.680,FMLib:17.12.62.30 definitions=2024-11-09_03,2024-11-08_01,2024-09-30_01 X-Proofpoint-Spam-Details: rule=notspam policy=default score=0 mlxlogscore=999 malwarescore=0 adultscore=0 phishscore=0 bulkscore=0 suspectscore=0 spamscore=0 mlxscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.12.0-2409260000 definitions=main-2411090036 X-Proofpoint-ORIG-GUID: vqJjILdD9TFpMlSHmCa27Dm6rVJt1Cis X-Proofpoint-GUID: vqJjILdD9TFpMlSHmCa27Dm6rVJt1Cis From: Himanshu Madhani - Add multipath device support to scsi_device - Add multipath support to scsi_host - Add Kconfig and Makefile - Create new scsi_multipath.[ch] files Signed-off-by: Himanshu Madhani --- drivers/scsi/Kconfig | 12 + drivers/scsi/Makefile | 2 + drivers/scsi/scsi_multipath.c | 896 ++++++++++++++++++++++++++++++++++ include/scsi/scsi_device.h | 64 +++ include/scsi/scsi_host.h | 7 + include/scsi/scsi_multipath.h | 86 ++++ 6 files changed, 1067 insertions(+) create mode 100644 drivers/scsi/scsi_multipath.c create mode 100644 include/scsi/scsi_multipath.h diff --git a/drivers/scsi/Kconfig b/drivers/scsi/Kconfig index 37c24ffea65c..d1298fac774c 100644 --- a/drivers/scsi/Kconfig +++ b/drivers/scsi/Kconfig @@ -76,6 +76,18 @@ config SCSI_LIB_KUNIT_TEST If unsure say N. +config SCSI_MULTIPATH + bool "SCSI multipath support" + depends on SCSI + depends on SCSI_DH && SCSI_DH_ALUA + help + This option enables support for native SCSI multipath support for + SCSI host. This option depends on Asymmetric Logical Unit Access + support to be enabled on the device. If this option is enabled a + single /dev/mpathXsdY device will show up for each SCSI host. + + If unsure say N. + comment "SCSI support type (disk, tape, CD-ROM)" depends on SCSI diff --git a/drivers/scsi/Makefile b/drivers/scsi/Makefile index 1313ddf2fd1a..017795bc224d 100644 --- a/drivers/scsi/Makefile +++ b/drivers/scsi/Makefile @@ -154,6 +154,8 @@ obj-$(CONFIG_SCSI_ENCLOSURE) += ses.o obj-$(CONFIG_SCSI_HISI_SAS) += hisi_sas/ +obj-$(CONFIG_SCSI_MULTIPATH) += scsi_multipath.o + # This goes last, so that "real" scsi devices probe earlier obj-$(CONFIG_SCSI_DEBUG) += scsi_debug.o scsi_mod-y += scsi.o hosts.o scsi_ioctl.o \ diff --git a/drivers/scsi/scsi_multipath.c b/drivers/scsi/scsi_multipath.c new file mode 100644 index 000000000000..45684704b9e2 --- /dev/null +++ b/drivers/scsi/scsi_multipath.c @@ -0,0 +1,896 @@ +// SPDX-License-Indentifier: GPL-2.0 +/* + * Copyright (c) 2024 Himanshu Madhani + * + * SCSI Multipath support using ALUA (Asymmetric Logical Unit Access) + * capable devices. + */ + +#include +#include +#include +#include +#include +#include +#include +#include + +bool scsi_multipath = true; +module_param(scsi_multipath, bool, 0444); +MODULE_PARM_DESC(scsi_multipath, + "turn on native support for multiple scsi devices \n" + "set this value to false to disable multipath, \n"); + +static const char *scsi_iopolicy_names[] = { + [SCSI_MPATH_IOPOLICY_NUMA] = "numa", + [SCSI_MPATH_IOPOLICY_RR] = "round-robin", +}; + +static int iopolicy = SCSI_MPATH_IOPOLICY_NUMA; + +/* + * SCSI multipath will only allow 'NUMA' or 'round-robin' policy for IO. + * In Future, if more apropriate IO-policy is introduced will be added + * based on community feedback. + */ +static int scsi_set_iopolicy(const char *val, const struct kernel_param *kp) +{ + if (!val) + return -EINVAL; + if (!strncmp(val, "numa", 4)) + iopolicy = SCSI_MPATH_IOPOLICY_NUMA; + else if (!strncmp(val, "round-robin", 11)) + iopolicy = SCSI_MPATH_IOPOLICY_RR; + else + return -EINVAL; + + return 0; +} + +static int scsi_get_iopolicy(char *buf, const struct kernel_param *kp) +{ + return sprintf(buf, "%s\n", scsi_iopolicy_names[iopolicy]); +} + +module_param_call(iopolicy, scsi_set_iopolicy, scsi_get_iopolicy, + &iopolicy, 0644); +MODULE_PARM_DESC(iopolicy, + "Default multipath I/O policy; 'numa' (default) or 'round-robin'"); + +void scsi_mpath_default_iopolicy(struct scsi_device *sdev) +{ + sdev->mpath_iopolicy = iopolicy; +} + +void scsi_multipath_iopolicy_update(struct scsi_device *sdev, int iopolicy) +{ + struct Scsi_Host *shost = sdev->host; + struct scsi_mpath *mpath_dev = shost->mpath_dev; + int old_iopolicy = READ_ONCE(sdev->mpath_iopolicy); + + if (old_iopolicy == iopolicy) + return; + + WRITE_ONCE(sdev->mpath_iopolicy, iopolicy); + + /* iopoliocy changes clear the multipath */ + mutex_lock(&mpath_dev->mpath_lock); + list_for_each_entry_rcu(sdev, &shost->mpath_sdev, mpath_entry) + scsi_mpath_clear_paths(shost); + mutex_unlock(&mpath_dev->mpath_lock); + + sdev_printk(KERN_NOTICE, sdev, "Multipath iopolocy changed from %s to %s\n", + scsi_iopolicy_names[old_iopolicy], scsi_iopolicy_names[iopolicy]); +} + +bool scsi_mpath_clear_current_path(struct scsi_device *sdev) +{ + struct Scsi_Host *shost = sdev->host; + struct scsi_mpath *mpath_dev = shost->mpath_dev; + bool changed = false; + int node; + + if (!sdev) + return changed; + + for_each_node(node) { + if (sdev == rcu_access_pointer(mpath_dev->current_path[node])) { + rcu_assign_pointer(mpath_dev->current_path[node], NULL); + changed = true; + } + } + + return changed; +} +EXPORT_SYMBOL_GPL(scsi_mpath_clear_current_path); + +void scsi_mpath_clear_paths(struct Scsi_Host *shost) +{ + struct scsi_device *sdev; + int srcu_idx; + + srcu_idx = srcu_read_lock(&shost->mpath_dev->srcu); + list_for_each_entry_rcu(sdev, &shost->mpath_sdev, mpath_entry) { + scsi_mpath_clear_current_path(sdev); + kblockd_schedule_work(&shost->mpath_dev->mpath_requeue_work); + } + srcu_read_unlock(&shost->mpath_dev->srcu, srcu_idx); + +} + +static inline bool scsi_mpath_state_is_live(enum scsi_mpath_access_state state) +{ + if (state == SCSI_MPATH_OPTIMAL || + state == SCSI_MPATH_ACTIVE) + return true; + + return false; +} + +/* Check for path error */ +static inline bool scsi_is_mpath_error(struct scsi_cmnd *scmd) +{ + struct request *req = scsi_cmd_to_rq(scmd); + struct scsi_device *sdev = req->q->queuedata; + + if (sdev->handler && sdev->handler->prep_fn) { + blk_status_t ret = sdev->handler->prep_fn(sdev, req); + + if (ret != BLK_STS_OK) + return true; + } + + return false; +} + +static bool scsi_mpath_is_disabled(struct scsi_device *sdev) +{ + enum scsi_device_state sdev_state = sdev->sdev_state; + + /* + * if device multipath state is not set to LIVE + * then return true + */ + if (!scsi_mpath_state_is_live(sdev->mpath_state)) + return true; + + /* + * Do not treat DELETING as a disabled path as I/O should + * still be able to complete assuming that scsi_device is + * within timeout limit. + * Otherwise I/O will fail immeadiately and return to + * requeue list + */ + if (sdev_state != SDEV_RUNNING && sdev_state != SDEV_CANCEL) + return true; + + return false; +} + +/* handle failover request for path */ +void scsi_mpath_failover_req(struct request *req) +{ + struct scsi_cmnd *scmd = blk_mq_rq_to_pdu(req); + struct scsi_device *sdev = scmd->device; + struct Scsi_Host *shost = scmd->device->host; + struct scsi_mpath *mpath_dev = shost->mpath_dev; + unsigned long flags; + struct bio *bio; + + if (!scsi_device_online(sdev) || sdev->was_reset || sdev->locked) + return; + + scsi_mpath_clear_current_path(sdev); + + /* + * if we got device handler error, we know that device is alive but not + * ready to process command. kick off a requeue of scsi command and try + * other available path + */ + if (scsi_is_mpath_error(scmd)) { + /* + * Set flag as pending and requeue bio for retry on + * another path + */ + set_bit(SCSI_MPATH_DISK_IO_PENDING, &sdev->mpath_flags); + queue_work(shost->work_q, &mpath_dev->mpath_requeue_work); + } + + /* + * following logic tries to steal bio, check if the bio has polled + * operation, if yes, then clear polled reqeust and reqeue bio + */ + spin_lock_irqsave(&mpath_dev->mpath_requeue_lock, flags); + for (bio = req->bio; bio; bio = bio->bi_next) { + bio_set_dev(bio, req->q->disk->part0); + if (bio->bi_opf & REQ_POLLED) { + bio->bi_opf &= ~REQ_POLLED; + bio->bi_cookie = BLK_QC_T_NONE; + } + } + blk_steal_bios(&mpath_dev->mpath_requeue_list, req); + spin_unlock_irqrestore(&mpath_dev->mpath_requeue_lock, flags); + + scmd->result = 0; + + blk_mq_end_request(req, 0); + + kblockd_schedule_work(&mpath_dev->mpath_requeue_work); +} +EXPORT_SYMBOL_GPL(scsi_mpath_failover_req); + +static inline bool scsi_mpath_is_optimized(struct scsi_device *sdev) +{ + return (!scsi_device_online(sdev) && + ((sdev->mpath_state == SCSI_MPATH_OPTIMAL) || + (sdev->mpath_state == SCSI_MPATH_ACTIVE))); +} + +static struct scsi_device *scsi_next_mpath_sdev(struct Scsi_Host *shost, + struct scsi_device *sdev) +{ + sdev = list_next_or_null_rcu(&shost->mpath_sdev, &sdev->siblings, + struct scsi_device, siblings); + + if (sdev) + return sdev; + + return list_first_or_null_rcu(&shost->mpath_sdev, struct scsi_device, + siblings); +} + +static struct scsi_device *scsi_mpath_round_robin_path(struct Scsi_Host *shost, + int node, struct scsi_device *old_sdev) +{ + struct scsi_device *sdev, *found = NULL; + struct scsi_mpath *mpath_dev = shost->mpath_dev; + + if (list_is_singular(&shost->mpath_sdev)) { + if(scsi_mpath_is_disabled(old_sdev)) + return NULL; + return old_sdev; + } + + for (sdev = scsi_next_mpath_sdev(shost, old_sdev); + sdev && sdev != old_sdev; + sdev = scsi_next_mpath_sdev(shost, sdev)) { + if (scsi_mpath_is_disabled(sdev)) + continue; + if (sdev->mpath_state == SCSI_MPATH_OPTIMAL) { + found = sdev; + goto out; + } + if (sdev->mpath_state == SCSI_MPATH_ACTIVE) + found = sdev; + } + + if (!scsi_mpath_is_disabled(old_sdev) && + (old_sdev->mpath_state == SCSI_MPATH_OPTIMAL || + (!found && old_sdev->mpath_state == SCSI_MPATH_ACTIVE))) + return old_sdev; + + if (!found) + return NULL; +out: + rcu_assign_pointer(mpath_dev->current_path[node], found); + + return found; +} + +/* + * Search path based on iopolicy and numa node affinity + * and return the scsi_device for that path + */ +inline struct scsi_device *__scsi_find_path(struct Scsi_Host *shost, int node) +{ + struct scsi_mpath *mpath_dev = shost->mpath_dev; + int found_distance = INT_MAX, fallback_distance = INT_MAX, distance; + struct scsi_device *sdev_found = NULL, *sdev_fallback = NULL, *sdev; + + list_for_each_entry_rcu(sdev, &shost->mpath_sdev, mpath_entry) { + if (scsi_mpath_is_disabled(sdev)) + continue; + + if (sdev->mpath_numa_node != NUMA_NO_NODE && + (READ_ONCE(sdev->mpath_iopolicy) == SCSI_MPATH_IOPOLICY_NUMA)) + distance = node_distance(node, sdev->mpath_numa_node); + else + distance = LOCAL_DISTANCE; + + switch(sdev->mpath_state) { + case SCSI_MPATH_OPTIMAL: + if (distance < found_distance) { + found_distance = distance; + sdev_found = sdev; + } + break; + case SCSI_MPATH_ACTIVE: + if (distance < fallback_distance) { + fallback_distance = distance; + sdev_fallback = sdev; + } + break; + default: + break; + } + } + + if (!sdev_found) + sdev_found = sdev_fallback; + + if (sdev_found) + rcu_assign_pointer(mpath_dev->current_path[node], sdev_found); + + return sdev_found; +} + +inline struct scsi_device *scsi_find_path(struct Scsi_Host *shost) +{ + int node = numa_node_id(); + struct scsi_device *sdev; + + sdev = srcu_dereference(shost->mpath_dev->current_path[node], + &shost->mpath_dev->srcu); + + if (unlikely(!sdev)) + sdev = __scsi_find_path(shost, node); + + if (READ_ONCE(sdev->mpath_iopolicy) == SCSI_MPATH_IOPOLICY_RR) + return scsi_mpath_round_robin_path(shost, node, sdev); + + if (unlikely(!scsi_mpath_is_optimized(sdev))) + return __scsi_find_path(shost, node); + + return sdev; +} + +void scsi_mpath_requeue_work(struct work_struct *work) +{ + struct scsi_mpath *mpath_dev = + container_of(work, struct scsi_mpath, mpath_requeue_work); + struct bio *bio, *next; + + spin_lock_irq(&mpath_dev->mpath_requeue_lock); + next = bio_list_get(&mpath_dev->mpath_requeue_list); + spin_unlock(&mpath_dev->mpath_requeue_lock); + + while ((bio = next) != NULL) { + next = bio->bi_next; + bio->bi_next = NULL; + submit_bio_noacct(bio); + } +} + +void scsi_mpath_set_live(struct scsi_device *sdev) +{ + struct Scsi_Host *shost = sdev->host; + struct scsi_mpath *mpath_dev = shost->mpath_dev; + int ret; + + if (!sdev->mpath_disk) + return; + + if (!test_and_set_bit(SCSI_MPATH_DISK_LIVE, &sdev->mpath_flags)) { + ret = device_add_disk(&sdev->sdev_dev, sdev->mpath_disk, NULL); + if (ret) { + clear_bit(SCSI_MPATH_DISK_LIVE, &sdev->mpath_flags); + return; + } + } + + pr_info("Attached SCSI %s disk\n", sdev->mpath_disk->disk_name); + + mutex_lock(&mpath_dev->mpath_lock); + if (scsi_mpath_is_optimized(sdev)) { + int node, srcu_idx; + + srcu_idx = srcu_read_lock(&mpath_dev->srcu); + for_each_online_node(node) + __scsi_find_path(shost, node); + srcu_read_unlock(&mpath_dev->srcu, srcu_idx); + } + mutex_unlock(&mpath_dev->mpath_lock); + + synchronize_srcu(&mpath_dev->srcu); + kblockd_schedule_work(&mpath_dev->mpath_requeue_work); +} + +/** + * Callback function for activating multipath devices + */ +static void activate_mpath(void *data, int err) +{ + struct scsi_device *sdev = data; + struct scsi_mpath_dh_data *mpath_h = sdev->mpath_pg_data; + bool retry = false; + + if (!mpath_h) + return; + + switch (err) { + case SCSI_DH_OK: + break; + case SCSI_DH_NOSYS: + sdev_printk(KERN_ERR, sdev, + "Could not failover the device scsi_dh_%s, Error %d\n", + sdev->handler->name, err); + scsi_mpath_clear_current_path(sdev); + break; + case SCSI_DH_DEV_TEMP_BUSY: + sdev_printk(KERN_ERR, sdev, + "Device Handler Path Busy\n"); + break; + case SCSI_DH_RETRY: + sdev_printk(KERN_ERR, sdev, + "Device Handler Path Retry \n"); + retry = true; + fallthrough; + case SCSI_DH_IMM_RETRY: + case SCSI_DH_RES_TEMP_UNAVAIL: + sdev_printk(KERN_ERR, sdev, + "Device Handler Path Unavailable, Clear current path \n"); + if ((mpath_h->state == SCSI_ACCESS_STATE_OFFLINE) || + (mpath_h->state == SCSI_ACCESS_STATE_UNAVAILABLE)) + scsi_mpath_clear_current_path(sdev); + err = 0; + break; + case SCSI_DH_DEV_OFFLINED: + default: + sdev_printk(KERN_ERR, sdev, "Device Handler Path offlined \n"); + scsi_mpath_clear_current_path(sdev); + break; + } + + if (retry) + set_bit(SCSI_MPATH_DISK_IO_PENDING, &sdev->mpath_flags); + + if (scsi_mpath_state_is_live(sdev->mpath_state)) + scsi_mpath_set_live(sdev); +} + +void scsi_activate_path(struct scsi_device *sdev) +{ + struct request_queue *q = sdev->mpath_disk->queue; + struct scsi_mpath_dh_data *mpath_dh = sdev->mpath_pg_data; + + if (!mpath_dh) + return; + + if (!(scsi_mpath_state_is_live(sdev->mpath_state))) { + sdev_printk(KERN_INFO, sdev, "Path state is not live \n"); + return; + } + + if (!blk_queue_dying(q)) + scsi_dh_activate(q, activate_mpath, sdev); + else + activate_mpath(sdev, SCSI_DH_OK); +} + +static void scsi_activate_mpath_work(struct work_struct *work) +{ + struct scsi_device *sdev = container_of(work, + struct scsi_device, activate_mpath); + + if (!sdev) + return; + + scsi_activate_path(sdev); +} + +int scsi_mpath_add_disk(struct scsi_device *sdev) +{ + if (!sdev->mpath_pg_data) { + /* Re initialize ALUA */ + sdev->handler->rescan(sdev); + } else { + sdev->mpath_state = SCSI_MPATH_OPTIMAL; + scsi_mpath_set_live(sdev); + } + + return (test_bit(SCSI_MPATH_DISK_LIVE, &sdev->mpath_flags)); +} +EXPORT_SYMBOL_GPL(scsi_mpath_add_disk); + +int scsi_multipath_init(struct scsi_device *sdev) +{ + struct Scsi_Host *shost = sdev->host; + struct scsi_mpath_dh_data *h; + struct scsi_mpath *mpath_dev; + int ret = -ENOMEM; + + mpath_dev = kzalloc(sizeof(struct scsi_mpath), GFP_KERNEL); + if (!mpath_dev) + return ret; + + h = kzalloc(sizeof(struct scsi_mpath_dh_data), GFP_KERNEL); + if (!h) + goto out_mpath_dev; + + sdev->mpath_pg_data = h; + + ret = init_srcu_struct(&mpath_dev->srcu); + if (ret) { + cleanup_srcu_struct(&mpath_dev->srcu); + goto out_handler; + } + + shost->mpath_dev = mpath_dev; + + mutex_init(&mpath_dev->mpath_lock); + bio_list_init(&mpath_dev->mpath_requeue_list); + spin_lock_init(&mpath_dev->mpath_requeue_lock); + INIT_WORK(&mpath_dev->mpath_requeue_work, scsi_mpath_requeue_work); + INIT_LIST_HEAD(&mpath_dev->mpath_list); + INIT_WORK(&sdev->activate_mpath, scsi_activate_mpath_work); + INIT_LIST_HEAD(&sdev->mpath_entry); + sdev->mpath_numa_node = NUMA_NO_NODE; + sdev->is_shared = 1; + + return 0; + +out_handler: + kfree(h); +out_mpath_dev: + if (mpath_dev) + kfree(mpath_dev); + + return ret; +} +EXPORT_SYMBOL_GPL(scsi_multipath_init); + +static bool scsi_available_mpath(struct Scsi_Host *shost) +{ + struct scsi_device *sdev; + + list_for_each_entry_rcu(sdev, &shost->mpath_sdev, mpath_entry) { + if (scsi_device_online(sdev)) + return true; + } + return false; +} + +/* called when shost is being freed */ +void scsi_mpath_dev_release(struct scsi_device *sdev) +{ + struct Scsi_Host *shost = sdev->host; + struct scsi_mpath *mpath_dev; + + if (!shost->mpath_dev) + return; + + mpath_dev = shost->mpath_dev; + cancel_work_sync(&mpath_dev->mpath_requeue_work); + cleanup_srcu_struct(&mpath_dev->srcu); + + if (sdev->mpath_pg_data) + kfree(sdev->mpath_pg_data); +} +EXPORT_SYMBOL_GPL(scsi_mpath_dev_release); + +void scsi_put_mpath_sdev(struct scsi_device *sdev) +{ + scsi_device_put(sdev); +} + +void scsi_mpath_revalidate_path(struct gendisk *mpath_disk, sector_t capacity) +{ + struct Scsi_Host *shost = mpath_disk->private_data; + struct scsi_mpath *mpath_dev = shost->mpath_dev; + struct scsi_device *sdev; + int srcu_idx; + int node; + + if (!shost->mpath_dev) + return; + + srcu_idx = srcu_read_lock(&mpath_dev->srcu); + list_for_each_entry_rcu(sdev, &shost->mpath_sdev, mpath_entry) { + if (capacity != get_capacity(sdev->mpath_disk)) + clear_bit(SCSI_MPATH_DISK_LIVE, &sdev->mpath_flags); + } + srcu_read_unlock(&mpath_dev->srcu, srcu_idx); + + for_each_node(node) + rcu_assign_pointer(mpath_dev->current_path[node], NULL); + kblockd_schedule_work(&mpath_dev->mpath_requeue_work); +} +EXPORT_SYMBOL_GPL(scsi_mpath_revalidate_path); + +static int scsi_mpath_open(struct gendisk *disk, blk_mode_t mode) +{ + if (!scsi_get_device(disk->private_data)) + return -ENXIO; + + return 0; +} + +static void scsi_mpath_release(struct gendisk *disk) +{ + struct Scsi_Host *shost = disk->private_data; + struct scsi_device *sdev; + int srcu_idx; + + srcu_idx = srcu_read_lock(&shost->mpath_dev->srcu); + sdev = scsi_find_path(shost); + srcu_read_unlock(&shost->mpath_dev->srcu, srcu_idx); +} + +int scsi_mpath_failover_disposition(struct scsi_cmnd *scmd) +{ + struct request *req = scsi_cmd_to_rq(scmd); + + if (req->cmd_flags & REQ_SCSI_MPATH) { + if (scsi_is_mpath_error(scmd) || + blk_queue_dying(req->q)) { + return NEEDS_RETRY; + } + } else { + if (blk_queue_dying(req->q)) + return SUCCESS; + } + + return SUCCESS; +} +EXPORT_SYMBOL_GPL(scsi_mpath_failover_disposition); + +static void scsi_multipath_submit_bio(struct bio *bio) +{ + struct Scsi_Host *shost = bio->bi_bdev->bd_disk->private_data; + struct scsi_mpath *mpath_dev = shost->mpath_dev; + struct scsi_device *sdev; + int srcu_idx; + + /* + * The scsi device might be going away and the bio might be + * moved to a difference queue via blk_steal_bios(), so we + * need to use bio_split pool from the original queue to + * allocate the bvecs from. + */ + bio = bio_split_to_limits(bio); + if (!bio) + return; + + srcu_idx = srcu_read_lock(&mpath_dev->srcu); + sdev = scsi_find_path(shost); + if (likely(sdev)) { + bio_set_dev(bio, bio->bi_bdev->bd_disk->part0); + bio->bi_opf |= REQ_SCSI_MPATH; + submit_bio_noacct(bio); + } else if (scsi_available_mpath(shost)) { + sdev_printk(KERN_NOTICE, NULL, + "No Usable Path - Requeing I/O \n"); + + spin_lock_irq(&mpath_dev->mpath_requeue_lock); + bio_list_add(&mpath_dev->mpath_requeue_list, bio); + spin_unlock_irq(&mpath_dev->mpath_requeue_lock); + } else { + sdev_printk(KERN_NOTICE, NULL, + "No available path = Failing I/O \n"); + + bio_io_error(bio); + } + srcu_read_unlock(&mpath_dev->srcu, srcu_idx); +} + +static int scsi_mpath_get_unique_id(struct gendisk *disk, u8 id[16], + enum blk_unique_id type) +{ + struct Scsi_Host *shost = disk->private_data; + struct scsi_device *sdev; + int srcu_idx, ret = -EWOULDBLOCK; + + srcu_idx = srcu_read_lock(&shost->mpath_dev->srcu); + sdev = scsi_find_path(shost); + if (sdev) + ret = scsi_mpath_unique_id(sdev, id, type); + srcu_read_unlock(&shost->mpath_dev->srcu, srcu_idx); + + return ret; +} + +const struct block_device_operations scsi_mpath_ops = { + .owner = THIS_MODULE, + .submit_bio = scsi_multipath_submit_bio, + .open = scsi_mpath_open, + .release = scsi_mpath_release, + .get_unique_id = scsi_mpath_get_unique_id, +}; + +int scsi_mpath_unique_id(struct scsi_device *sdev, u8 id[16], + enum blk_unique_id type) +{ + struct scsi_mpath_dh_data *dh_data = sdev->mpath_pg_data; + + if (type != BLK_UID_NAA) + return -EINVAL; + + if (strncmp(dh_data->device_id_str, id, 16) == 0) + return dh_data->device_id_len; + + return -EINVAL; +} +EXPORT_SYMBOL_GPL(scsi_mpath_unique_id); + +int scsi_mpath_unique_lun_id(struct scsi_device *sdev) +{ + struct scsi_mpath_dh_data *dh_data = sdev->mpath_pg_data; + char device_id_str[20]; + int ret = -EINVAL; + + ret = scsi_vpd_lun_id(sdev, device_id_str, dh_data->device_id_len); + if (ret < 0) + return ret; + + if (strncmp(dh_data->device_id_str, device_id_str, + dh_data->device_id_len) == 0) + return -EINVAL; + + return 0; +} + +/* + * Allocate Disk for Multipath Device + */ +int scsi_mpath_alloc_disk(struct scsi_device *sdev) +{ + struct Scsi_Host *shost = sdev->host; + struct queue_limits lim; + + /* + * Don't allocate mpath disk if ALUA handler is not attached + */ + if (!sdev->handler || strncmp(sdev->handler->name, "alua", 4) != 0) { + sdev_printk(KERN_NOTICE, sdev, + "No Handler or correct handler attached for multipath \n"); + return 0; + } + + /* + * Add multipath disk only if scsi host supports multipath modparam + */ + if (!scsi_multipath) { + sdev_printk(KERN_NOTICE, sdev, + "%s Handler attached but modparam scsi_multipath is set to false \n", + sdev->handler->name); + return 0; + } + + if (scsi_mpath_unique_lun_id(sdev) == 0) { + sdev_printk(KERN_NOTICE, sdev, + "existing sdev with path, return\n"); + return 0; + } + + blk_set_stacking_limits(&lim); + + lim.features |= BLK_FEAT_IO_STAT | BLK_FEAT_NOWAIT | BLK_FEAT_POLL; + lim.max_zone_append_sectors = 0; + lim.dma_alignment = 3; + + sdev->mpath_disk = blk_alloc_disk(&lim, sdev->mpath_numa_node); + if (IS_ERR(sdev->mpath_disk)) + return PTR_ERR(sdev->mpath_disk); + + sdev->mpath_disk->private_data = shost; + sdev->mpath_disk->fops = &scsi_mpath_ops; + + list_add_tail(&shost->mpath_sdev, &sdev->mpath_entry); + + return 0; +} +EXPORT_SYMBOL_GPL(scsi_mpath_alloc_disk); + +void scsi_mpath_start_request(struct request *req) +{ + struct scsi_cmnd *cmd = blk_mq_rq_to_pdu(req); + struct scsi_device *sdev = cmd->device; + struct Scsi_Host *shost = sdev->host; + struct scsi_mpath *mpath_dev = shost->mpath_dev; + + if (!blk_queue_io_stat(sdev->mpath_disk->queue) || + blk_rq_is_passthrough(req)) + return; + + req->rq_flags |= SCSI_MPATH_IO_STATS; + mpath_dev->mpath_start_time = bdev_start_io_acct(sdev->mpath_disk->part0, + req_op(req), jiffies); +} + +void scsi_mpath_end_request(struct request *req) +{ + struct scsi_cmnd *cmd = blk_mq_rq_to_pdu(req); + struct scsi_device *sdev = cmd->device; + struct Scsi_Host *shost = sdev->host; + struct scsi_mpath *mpath_dev = shost->mpath_dev; + + if (!(req->rq_flags & SCSI_MPATH_IO_STATS)) + return; + + bdev_end_io_acct(sdev->mpath_disk->part0, req_op(req), + blk_rq_bytes(req) >> SECTOR_SHIFT, + mpath_dev->mpath_start_time); +} + +void scsi_mpath_kick_requeue_lists(struct Scsi_Host *shost) +{ + struct scsi_mpath *mpath_dev = shost->mpath_dev; + struct scsi_device *sdev; + int srcu_idx; + + srcu_idx = srcu_read_lock(&mpath_dev->srcu); + list_for_each_entry_rcu(sdev, &shost->mpath_sdev, mpath_entry) { + if (sdev->is_shared) + continue; + + kblockd_schedule_work(&mpath_dev->mpath_requeue_work); + if (sdev->sdev_state == SDEV_RUNNING) + disk_uevent(sdev->mpath_disk, KOBJ_CHANGE); + } + srcu_read_unlock(&mpath_dev->srcu, srcu_idx); +} + +void scsi_mpath_shutdown_disk(struct scsi_device *sdev) +{ + struct Scsi_Host *shost = sdev->host; + + if (!sdev->mpath_disk) + return; + + if (test_and_clear_bit(SCSI_MPATH_DISK_LIVE, &sdev->mpath_flags)) { + synchronize_srcu(&shost->mpath_dev->srcu); + kblockd_schedule_work(&shost->mpath_dev->mpath_requeue_work); + del_gendisk(sdev->mpath_disk); + } +} +EXPORT_SYMBOL_GPL(scsi_mpath_shutdown_disk); + +void scsi_mpath_remove_disk(struct scsi_device *sdev) +{ + struct Scsi_Host *shost = sdev->host; + + if (!sdev->mpath_disk) + return; + + if (!sdev->is_shared) + return; + + /* Make sure All pending bio's are cleaned up */ + kblockd_schedule_work(&shost->mpath_dev->mpath_requeue_work); + flush_work(&shost->mpath_dev->mpath_requeue_work); + put_disk(sdev->mpath_disk); +} +EXPORT_SYMBOL_GPL(scsi_mpath_remove_disk); + +int scsi_mpath_update_state(struct scsi_device *sdev) +{ + struct scsi_mpath_dh_data *mpath_h; + + mpath_h = sdev->mpath_pg_data; + if (!mpath_h) + return SCSI_MPATH_UNAVAILABLE; + + switch(mpath_h->state) { + case SCSI_ACCESS_STATE_OPTIMAL: + sdev->mpath_state = SCSI_MPATH_OPTIMAL; + break; + case SCSI_ACCESS_STATE_ACTIVE: + sdev->mpath_state = SCSI_MPATH_ACTIVE; + break; + case SCSI_ACCESS_STATE_STANDBY: + sdev->mpath_state = SCSI_MPATH_STANDBY; + break; + case SCSI_ACCESS_STATE_UNAVAILABLE: + sdev->mpath_state = SCSI_MPATH_UNAVAILABLE; + break; + case SCSI_ACCESS_STATE_TRANSITIONING: + sdev->mpath_state = SCSI_MPATH_TRANSITIONING; + break; + case SCSI_ACCESS_STATE_OFFLINE: + default: + sdev->mpath_state = SCSI_MPATH_OFFLINE; + break; + } + + return sdev->mpath_state; +} diff --git a/include/scsi/scsi_device.h b/include/scsi/scsi_device.h index 9c540f5468eb..b46e06a01179 100644 --- a/include/scsi/scsi_device.h +++ b/include/scsi/scsi_device.h @@ -9,6 +9,8 @@ #include #include #include +#include +#include struct bsg_device; struct device; @@ -100,6 +102,11 @@ struct scsi_vpd { unsigned char data[]; }; +/* + * Mark bio as coming from scsi multipath node + */ +#define REQ_SCSI_MPATH REQ_DRV + struct scsi_device { struct Scsi_Host *host; struct request_queue *request_queue; @@ -120,6 +127,7 @@ struct scsi_device { unsigned short last_queue_full_count; /* scsi_track_queue_full() */ unsigned long last_queue_full_time; /* last queue full time */ unsigned long queue_ramp_up_period; /* ramp up period in jiffies */ + #define SCSI_DEFAULT_RAMP_UP_PERIOD (120 * HZ) unsigned long last_queue_ramp_up; /* last queue ramp up time */ @@ -265,6 +273,25 @@ struct scsi_device { struct device sdev_gendev, sdev_dev; +#ifdef CONFIG_SCSI_MULTIPATH + int is_shared; /* Set Multipath flag */ + int mpath_first_path; /* Indicate if this was first path */ + struct gendisk *mpath_disk; /* Multipath disk */ + int mpath_numa_node; /* NUMA node for Path */ + enum scsi_mpath_access_state mpath_state; /* Multipath State */ + enum scsi_mpath_iopolicy mpath_iopolicy; /* IO Policy */ + struct list_head mpath_entry; /* list of all mpath_sdevs */ + struct scsi_mpath_dh_data *mpath_pg_data; /* Place holder for Port group data */ + struct work_struct activate_mpath; /* Activate path work */ + atomic_t nr_mpath; /* Number of Active mpath */ + +#define SCSI_MPATH_DISK_LIVE 0 +#define SCSI_MPATH_DISK_IO_PENDING 1 +#define SCSI_MPATH_IO_STATS 2 + + unsigned long mpath_flags; /* flag for multipath devices*/ +#endif + struct work_struct requeue_work; struct scsi_device_handler *handler; @@ -294,6 +321,43 @@ struct scsi_device { #define sdev_dbg(sdev, fmt, a...) \ dev_dbg(&(sdev)->sdev_gendev, fmt, ##a) +#ifdef CONFIG_SCSI_MULTIPATH +extern bool scsi_multipath; +extern const struct block_device_operations scsi_mpath_ops; + +static inline bool scsi_sdev_use_alua(struct scsi_device *sdev) +{ + return sdev->handler_data != NULL; +} + +static inline bool scsi_disk_is_multipath(struct gendisk *disk) +{ + return disk->fops == &scsi_mpath_ops; +} + +static inline bool scsi_mpath_enabled(struct scsi_device *sdev) +{ + return IS_ENABLED(CONFIG_SCSI_MULTIPATH); +} +static inline bool scsi_is_sdev_multipath(struct scsi_device *sdev) +{ + return IS_ENABLED(CONFIG_SCSI_MULTIPATH) && sdev->mpath_disk; +} +#else +#define scsi_multipath false; +static inline bool scsi_disk_is_multipath(struct gendisk *disk) +{ + return false; +} +static inline bool scsi_mpath_enabled(struct scsi_device *sdev) +{ + return false; +} +static inline bool scsi_is_sdev_multipath(struct scsi_device *sdev) +{ + return false; +} +#endif /* * like scmd_printk, but the device name is passed in * as a string pointer diff --git a/include/scsi/scsi_host.h b/include/scsi/scsi_host.h index 2b4ab0369ffb..d20def053254 100644 --- a/include/scsi/scsi_host.h +++ b/include/scsi/scsi_host.h @@ -571,6 +571,12 @@ struct Scsi_Host { /* Area to keep a shared tag map */ struct blk_mq_tag_set tag_set; +#ifdef CONFIG_SCSI_MULTIPATH + struct scsi_mpath *mpath_dev; + struct list_head mpath_sdev; + int mpath_alua_grpid; /* Grounp ID for ALUA devices */ +#endif + atomic_t host_blocked; unsigned int host_failed; /* commands that failed. @@ -761,6 +767,7 @@ static inline int scsi_host_in_recovery(struct Scsi_Host *shost) shost->tmf_in_progress; } + extern int scsi_queue_work(struct Scsi_Host *, struct work_struct *); extern void scsi_flush_work(struct Scsi_Host *); diff --git a/include/scsi/scsi_multipath.h b/include/scsi/scsi_multipath.h new file mode 100644 index 000000000000..b441241c8316 --- /dev/null +++ b/include/scsi/scsi_multipath.h @@ -0,0 +1,86 @@ +/* SPDX-License-Identifier: GPL-2.0 */ +#ifndef _SCSI_SCSI_MULTIPATH_H +#define _SCSI_SCSI_MULTIPATH_H + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +struct scsi_device; + +enum scsi_mpath_iopolicy { + SCSI_MPATH_IOPOLICY_NUMA, + SCSI_MPATH_IOPOLICY_RR, +}; + +enum scsi_mpath_access_state { + SCSI_MPATH_OPTIMAL = SCSI_ACCESS_STATE_OPTIMAL, + SCSI_MPATH_ACTIVE = SCSI_ACCESS_STATE_ACTIVE, + SCSI_MPATH_STANDBY = SCSI_ACCESS_STATE_STANDBY, + SCSI_MPATH_UNAVAILABLE = SCSI_ACCESS_STATE_UNAVAILABLE, + SCSI_MPATH_LBA = SCSI_ACCESS_STATE_LBA, + SCSI_MPATH_OFFLINE = SCSI_ACCESS_STATE_OFFLINE, + SCSI_MPATH_TRANSITIONING = SCSI_ACCESS_STATE_TRANSITIONING, + SCSI_MPATH_INVALID = 0xFF +}; + +struct scsi_mpath_dh_data { + const char *hndlr_name; /* device Handler name */ + int group_id; /* Group ID reported from RTPG cmd */ + int tpgs; /* Target Port Groups reported from RTPG cmd */ + int state; /* Target Port Group State */ + char *device_id_str; /* Multipath Device String */ + int device_id_len; /* Device ID Length */ + int valid_states; /* states from RTPG cmd */ + int prefrence; /* Path prefrence for Port Group from RTPG cmd */ + int is_active; /* Current Sdev is active */ +}; + +struct scsi_mpath { + struct srcu_struct srcu; + struct Scsi_Host *shost; /*Scsi_Host where this mpath belong */ + struct list_head mpath_list; /* list of multipath scsi_device */ + struct bio_list mpath_requeue_list; /* list for requeing bio */ + spinlock_t mpath_requeue_lock; + struct work_struct mpath_requeue_work; /* work struct for requeue */ + struct mutex mpath_lock; + unsigned long mpath_start_time; + struct delayed_work activate_mpath; /* Path Activation work */ + struct scsi_device __rcu *current_path[]; /* scsi_device of current path */ +}; + +extern void scsi_mpath_default_iopolicy(struct scsi_device *); +extern void scsi_mpath_unfreeze(struct Scsi_Host *); +extern void scsi_mpath_wait_freeze(struct Scsi_Host *); +extern void scsi_mpath_start_freeze(struct Scsi_Host *); +extern void scsi_mpath_failover_req(struct request *); +extern void scsi_mpath_start_request(struct request *); +extern void scsi_mpath_end_request(struct request *); +extern void scsi_kick_requeue_lists(struct Scsi_Host *); +extern bool scsi_mpath_clear_current_path(struct scsi_device *); +int scsi_multipath_init(struct scsi_device *); +extern int scsi_mpath_failover_disposition(struct scsi_cmnd *); +int scsi_mpath_alloc_disk(struct scsi_device *); +extern void scsi_mpath_remove_disk(struct scsi_device *); +extern void scsi_mpath_shutdown_disk(struct scsi_device *); +void scsi_put_mpath_sdev(struct scsi_device *); +void scsi_mpath_requeue_work(struct work_struct *); +extern void scsi_mpath_dev_release(struct scsi_device *); +void scsi_mpath_kick_requeue_lists(struct Scsi_Host *); +int scsi_mpath_update_state(struct scsi_device *); +extern int scsi_mpath_add_disk(struct scsi_device *); +void scsi_mpath_set_live(struct scsi_device *); +void scsi_activate_path(struct scsi_device *); +void scsi_multipath_iopolicy_update(struct scsi_device *, int); +void scsi_mpath_clear_paths(struct Scsi_Host *); +int scsi_mpath_unique_lun_id(struct scsi_device *); + +extern void scsi_mpath_revalidate_path(struct gendisk *, sector_t); +extern int scsi_mpath_unique_id(struct scsi_device *sdev, u8 id[16], enum blk_unique_id type); +#endif /* _SCSI_SCSI_MULTIPATH_H */ From patchwork Sat Nov 9 04:45:23 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Himanshu Madhani X-Patchwork-Id: 13869235 Received: from mx0b-00069f02.pphosted.com (mx0b-00069f02.pphosted.com [205.220.177.32]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 7C05F12DD95 for ; Sat, 9 Nov 2024 04:45:32 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=205.220.177.32 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1731127534; cv=none; b=C7W3RulvWS/JSz0ZPdb765N8peiJ1LFSg3xysspAraD4HvR4IoFTKWoI54yHoc1J5SdihpJL4zjQ1wDMuhHZbc27RElajK85hHNnHqXZ6qgfJ4c/A0pcPzLxSzvfeLPJJURLQ8r6B+j73B/r7mTn8NXK1eSggo0x33DgaOngPes= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1731127534; c=relaxed/simple; bh=irVvNfjEim6GYSVLhLvKwqHctO8prxPV8Se78OKmg64=; h=From:To:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=oNzOLs3MVWrjjOlwk1bzcqGiyFGJPMio1aRJxctEoXf6pH0l69uB9+4Gjgl6Rd4uzoTKxweOY5XjbBjVfe8pcMRLiArzxwCVeWbiRL2fKxscQUuy+XyBVdkvIe7P8NskWky0smu2+2fD9/tYZQXGtgXn+CSnuoKsI2BbxlqxJNE= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=oracle.com; spf=pass smtp.mailfrom=oracle.com; dkim=pass (2048-bit key) header.d=oracle.com header.i=@oracle.com header.b=D28xjQMN; arc=none smtp.client-ip=205.220.177.32 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=oracle.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=oracle.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=oracle.com header.i=@oracle.com header.b="D28xjQMN" Received: from pps.filterd (m0246632.ppops.net [127.0.0.1]) by mx0b-00069f02.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id 4A94F1Cw022319 for ; Sat, 9 Nov 2024 04:45:31 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=oracle.com; h= content-transfer-encoding:date:from:in-reply-to:message-id :mime-version:references:subject:to; s=corp-2023-11-20; bh=J4Wij hIdXIkIQDbEKfIJhUzOeJo1JOSq3rbJ6cu868g=; b=D28xjQMNzrAlkrKuBDf1R cJXJUjVKdR5pcpqMN/1dEKrKjMffpBu7I0g0rIXBAgYigPFniNWZz46BqDMz7+a5 hgh49Mmu6QtfSy0wQ/5fDATJqeSPTJ2VH/WQ0Q8QkhlKwChlyTT8OL5lXLr6q/ph tbtpLZhsACBavjPkAdgj6vn07WU/meANl8HGMvvdoUaMWfyieab2AfIjPpg6JsCg urhUttZqfQONJmfNEomCCL4jA+dry8XBed2qcm7a7dra5ooMNXp4wf7US20dFCKp rsgZkFHKLCapPB3lvk3F5g/IBBLPwa+vhpZasBUd9BzqXZzkZt+RrpAYfASt7jrZ g== Received: from iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (iadpaimrmta02.appoci.oracle.com [147.154.18.20]) by mx0b-00069f02.pphosted.com (PPS) with ESMTPS id 42t0heg0b9-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK) for ; Sat, 09 Nov 2024 04:45:30 +0000 (GMT) Received: from pps.filterd (iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com [127.0.0.1]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (8.18.1.2/8.18.1.2) with ESMTP id 4A91XjgF034370 for ; Sat, 9 Nov 2024 04:45:30 GMT Received: from pps.reinject (localhost [127.0.0.1]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (PPS) with ESMTPS id 42sx65aj9y-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK) for ; Sat, 09 Nov 2024 04:45:30 +0000 Received: from iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com [127.0.0.1]) by pps.reinject (8.17.1.5/8.17.1.5) with ESMTP id 4A94jTdQ001575 for ; Sat, 9 Nov 2024 04:45:29 GMT Received: from hmadhani-upstream.osdevelopmeniad.oraclevcn.com (hmadhani-upstream.allregionaliads.osdevelopmeniad.oraclevcn.com [100.100.255.48]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (PPS) with ESMTP id 42sx65aj9h-3; Sat, 09 Nov 2024 04:45:29 +0000 From: himanshu.madhani@oracle.com To: martin.petersen@oracle.com, linux-scsi@vger.kernel.org Subject: [RFC v1 2/8] scsi: create multipath capable scsi host Date: Sat, 9 Nov 2024 04:45:23 +0000 Message-ID: <20241109044529.992935-3-himanshu.madhani@oracle.com> X-Mailer: git-send-email 2.41.0.rc2 In-Reply-To: <20241109044529.992935-1-himanshu.madhani@oracle.com> References: <20241109044529.992935-1-himanshu.madhani@oracle.com> Precedence: bulk X-Mailing-List: linux-scsi@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.293,Aquarius:18.0.1057,Hydra:6.0.680,FMLib:17.12.62.30 definitions=2024-11-09_03,2024-11-08_01,2024-09-30_01 X-Proofpoint-Spam-Details: rule=notspam policy=default score=0 mlxlogscore=999 malwarescore=0 adultscore=0 phishscore=0 bulkscore=0 suspectscore=0 spamscore=0 mlxscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.12.0-2409260000 definitions=main-2411090036 X-Proofpoint-ORIG-GUID: mvX4YbmpVAmkb-QV7Q2aaq0Gdg5iRj4E X-Proofpoint-GUID: mvX4YbmpVAmkb-QV7Q2aaq0Gdg5iRj4E From: Himanshu Madhani - Create multipath capable scsi host Signed-off-by: Himanshu Madhani --- drivers/scsi/hosts.c | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/drivers/scsi/hosts.c b/drivers/scsi/hosts.c index e021f1106bea..3cedb2a9af7b 100644 --- a/drivers/scsi/hosts.c +++ b/drivers/scsi/hosts.c @@ -39,6 +39,7 @@ #include #include #include +#include #include "scsi_priv.h" #include "scsi_logging.h" @@ -394,6 +395,14 @@ struct Scsi_Host *scsi_host_alloc(const struct scsi_host_template *sht, int priv struct Scsi_Host *shost; int index; +#ifdef CONFIG_SCSI_MULTIPATH + struct scsi_mpath *mpath_dev; + size_t size = sizeof(*mpath_dev); + + size += num_possible_nodes() * sizeof(struct mpath_dev *); + privsize = privsize + size; +#endif + shost = kzalloc(sizeof(struct Scsi_Host) + privsize, GFP_KERNEL); if (!shost) return NULL; @@ -409,6 +418,9 @@ struct Scsi_Host *scsi_host_alloc(const struct scsi_host_template *sht, int priv init_waitqueue_head(&shost->host_wait); mutex_init(&shost->scan_mutex); +#ifdef CONFIG_SCSI_MULTIPATH + INIT_LIST_HEAD(&shost->mpath_sdev); +#endif index = ida_alloc(&host_index_ida, GFP_KERNEL); if (index < 0) { kfree(shost); From patchwork Sat Nov 9 04:45:24 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Himanshu Madhani X-Patchwork-Id: 13869234 Received: from mx0b-00069f02.pphosted.com (mx0b-00069f02.pphosted.com [205.220.177.32]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 7C0184EB38 for ; Sat, 9 Nov 2024 04:45:32 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=205.220.177.32 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1731127534; cv=none; b=QMYX64hgaYb6uxb91Avj6GLRaWsEvunGtfqR9AJSBgRiXmO3zNw5skzPlgAyIHhV11Uycizs1pbIzTOLgvXmlcRoWZZ7CCysthL+LwefJWlmWbdPz2AhVVZsrd3p18acwSXav7mXs2I5RPdxIT4v8iWRLTl6gx5Hb8t8jpmuHYk= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1731127534; c=relaxed/simple; bh=foNwx9sw09Z3eEUCY7vOW8ppQJBDtfBwDanS8pvUr3A=; h=From:To:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=HZYyEex/CSuH78zRfUpuBV2qI18Mi/6bDtpZR7IEqP7YmF54xdJBPIX0aqIImMdRxof+Td1g4TV0rBBvmuE0Bxpwtf7VGvN/DwUXSVkfTrtgTeaRw+KDvttvQFad54TSHHGQ+NuWjSk/WPra/UoY6J9oH4OHeoHBNcBm0xxPJsM= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=oracle.com; spf=pass smtp.mailfrom=oracle.com; dkim=pass (2048-bit key) header.d=oracle.com header.i=@oracle.com header.b=TfiHileo; arc=none smtp.client-ip=205.220.177.32 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=oracle.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=oracle.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=oracle.com header.i=@oracle.com header.b="TfiHileo" Received: from pps.filterd (m0246632.ppops.net [127.0.0.1]) by mx0b-00069f02.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id 4A94Z2w3017280 for ; Sat, 9 Nov 2024 04:45:31 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=oracle.com; h= content-transfer-encoding:date:from:in-reply-to:message-id :mime-version:references:subject:to; s=corp-2023-11-20; bh=oO6Iu jjQUE9tlwTCeYgufbXUi8gaCUgU56oEnUkT96Q=; b=TfiHileopVYp7XBa3RX7l lbPHAj3ZkHavu18fK+3JTIHRNUmp5sBpFkVqWlxMjCSp/3qP3ZB5FmLpvGnI0k5G ZZYdi+0TmWs9vIfdG8oTiMzQXcpVJdr4fMhhA/urDgf2uUETyDcLdMhdhSXQrKvg ZR0CoL8MOB5XwMi4RTB3I32F2MQzsH31jAp0He0qF94wTHzLmxvezShLkhv0XK8q 4YY+Neoz/iCfhSLVb3x9BAL9ZKlFBefcFWgBt4wC/3kB6C89Nawmax0nQSnVQyDB WRvgwVe1Avh+jIPL3/SHVYI9tlLTJZdK0hC66fd5yqPYP9xxs4NlPU4eF1/3CH1D A== Received: from iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (iadpaimrmta02.appoci.oracle.com [147.154.18.20]) by mx0b-00069f02.pphosted.com (PPS) with ESMTPS id 42t0heg0ba-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK) for ; Sat, 09 Nov 2024 04:45:31 +0000 (GMT) Received: from pps.filterd (iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com [127.0.0.1]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (8.18.1.2/8.18.1.2) with ESMTP id 4A91XthQ034467 for ; Sat, 9 Nov 2024 04:45:30 GMT Received: from pps.reinject (localhost [127.0.0.1]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (PPS) with ESMTPS id 42sx65aja2-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK) for ; Sat, 09 Nov 2024 04:45:30 +0000 Received: from iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com [127.0.0.1]) by pps.reinject (8.17.1.5/8.17.1.5) with ESMTP id 4A94jTdS001575 for ; Sat, 9 Nov 2024 04:45:30 GMT Received: from hmadhani-upstream.osdevelopmeniad.oraclevcn.com (hmadhani-upstream.allregionaliads.osdevelopmeniad.oraclevcn.com [100.100.255.48]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (PPS) with ESMTP id 42sx65aj9h-4; Sat, 09 Nov 2024 04:45:30 +0000 From: himanshu.madhani@oracle.com To: martin.petersen@oracle.com, linux-scsi@vger.kernel.org Subject: [RFC v1 3/8] scsi: Add error handling capability for multipath Date: Sat, 9 Nov 2024 04:45:24 +0000 Message-ID: <20241109044529.992935-4-himanshu.madhani@oracle.com> X-Mailer: git-send-email 2.41.0.rc2 In-Reply-To: <20241109044529.992935-1-himanshu.madhani@oracle.com> References: <20241109044529.992935-1-himanshu.madhani@oracle.com> Precedence: bulk X-Mailing-List: linux-scsi@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.293,Aquarius:18.0.1057,Hydra:6.0.680,FMLib:17.12.62.30 definitions=2024-11-09_03,2024-11-08_01,2024-09-30_01 X-Proofpoint-Spam-Details: rule=notspam policy=default score=0 mlxlogscore=999 malwarescore=0 adultscore=0 phishscore=0 bulkscore=0 suspectscore=0 spamscore=0 mlxscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.12.0-2409260000 definitions=main-2411090036 X-Proofpoint-ORIG-GUID: NYx9pNNNYSU22uCl9lmjvHnaxJud9sMo X-Proofpoint-GUID: NYx9pNNNYSU22uCl9lmjvHnaxJud9sMo From: Himanshu Madhani For multipath capable devices call scsi_mpath_failover_disposition() to kick off failover to another path. This will call path selector algorithm to pick active path for the failover. Signed-off-by: Himanshu Madhani --- drivers/scsi/scsi_error.c | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/drivers/scsi/scsi_error.c b/drivers/scsi/scsi_error.c index 612489afe8d2..d5d1b20928a6 100644 --- a/drivers/scsi/scsi_error.c +++ b/drivers/scsi/scsi_error.c @@ -40,6 +40,7 @@ #include #include #include +#include #include #include "scsi_priv.h" @@ -2047,6 +2048,13 @@ enum scsi_disposition scsi_decide_disposition(struct scsi_cmnd *scmd) maybe_retry: + /* + * For SCSI Multipath check if there are path errors to + * trigger failover to available path + */ + if (scsi_mpath_enabled(scmd->device)) + return scsi_mpath_failover_disposition(scmd); + /* we requeue for retry because the error was retryable, and * the request was not marked fast fail. Note that above, * even if the request is marked fast fail, we still requeue From patchwork Sat Nov 9 04:45:25 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Himanshu Madhani X-Patchwork-Id: 13869239 Received: from mx0b-00069f02.pphosted.com (mx0b-00069f02.pphosted.com [205.220.177.32]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 7BF98139D for ; Sat, 9 Nov 2024 04:45:32 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=205.220.177.32 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1731127535; cv=none; b=B2ku4OnktgGANynSiYazg1uBiHe1spTbV55hexATo0bvQbsK2fb6MOhzZXa0EJ1z27xy5q8+BBuWROcw4YZJyrLYFJqb9UWHdPWVWASu5q5zefqibioGncXo1c2mwksaCowqV3D/Hgu123CTayJAFIMQapmBsE1ENrEd49RXaFg= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1731127535; c=relaxed/simple; bh=Sy3gbEVshRov5R4DMaHvsVO0Rxglh1tmoHhvN8Z//0s=; h=From:To:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=poNF+Rrz5vaOMfYWh7vsgYZ2GYlrNeODcy12x8MMnh4W3ERDAI3MSe7ntHlQxtfLFlNy8K+hvwlGRllFLTGjOc1yTfRUU/lfYgvCI3j2LF3uv0ZMqAxiOc5dz1GFg6yavX7JdvDkDhtlkGV0GOEIsSgmNyd9AchlES0cXmWS5BU= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=oracle.com; spf=pass smtp.mailfrom=oracle.com; dkim=pass (2048-bit key) header.d=oracle.com header.i=@oracle.com header.b=E3mImabQ; arc=none smtp.client-ip=205.220.177.32 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=oracle.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=oracle.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=oracle.com header.i=@oracle.com header.b="E3mImabQ" Received: from pps.filterd (m0333520.ppops.net [127.0.0.1]) by mx0b-00069f02.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id 4A94O1DW006139 for ; Sat, 9 Nov 2024 04:45:31 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=oracle.com; h= content-transfer-encoding:date:from:in-reply-to:message-id :mime-version:references:subject:to; s=corp-2023-11-20; bh=VZSQv Fk+DFUKGYOyaayHV8unSzSwc1BUH+9IG2KXrb8=; b=E3mImabQFU+HQMsbuhnVc MuE/bEEhcwiAAUPqOPh0YoO1SJ1zSFSUyAd4Uhiqy+B+e/JzHpAC5VQHNTtaIpA8 1gbL9Se5g1jUtwl1JuY5eUM2izAUGOmp5Cf+nUtnGHRSPHUNQ7651jJ+ZLLN25Mt EqglN+cy2zpKE40GF65xAbnFiOPlIAjY/W7FLNpKEjCsBMRnvneQkx8XlNBfQIfw A9m2JXT0QzuBbmEuzQGf/ulWndYWBjvbV8PeKQY3ucYyikm9knfsZsmIttD4acxG xasrXHHffGfGp5ADaL5dX6V2VjdRZ9V8ExDnwT9ljrPXYo2Eg4ULnGWeJBnOf4E2 w== Received: from iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (iadpaimrmta02.appoci.oracle.com [147.154.18.20]) by mx0b-00069f02.pphosted.com (PPS) with ESMTPS id 42t0nwg07u-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK) for ; Sat, 09 Nov 2024 04:45:31 +0000 (GMT) Received: from pps.filterd (iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com [127.0.0.1]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (8.18.1.2/8.18.1.2) with ESMTP id 4A91XfqX034355 for ; Sat, 9 Nov 2024 04:45:30 GMT Received: from pps.reinject (localhost [127.0.0.1]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (PPS) with ESMTPS id 42sx65aja5-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK) for ; Sat, 09 Nov 2024 04:45:30 +0000 Received: from iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com [127.0.0.1]) by pps.reinject (8.17.1.5/8.17.1.5) with ESMTP id 4A94jTdU001575 for ; Sat, 9 Nov 2024 04:45:30 GMT Received: from hmadhani-upstream.osdevelopmeniad.oraclevcn.com (hmadhani-upstream.allregionaliads.osdevelopmeniad.oraclevcn.com [100.100.255.48]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (PPS) with ESMTP id 42sx65aj9h-5; Sat, 09 Nov 2024 04:45:30 +0000 From: himanshu.madhani@oracle.com To: martin.petersen@oracle.com, linux-scsi@vger.kernel.org Subject: [RFC v1 4/8] scsi: Complete multipath request Date: Sat, 9 Nov 2024 04:45:25 +0000 Message-ID: <20241109044529.992935-5-himanshu.madhani@oracle.com> X-Mailer: git-send-email 2.41.0.rc2 In-Reply-To: <20241109044529.992935-1-himanshu.madhani@oracle.com> References: <20241109044529.992935-1-himanshu.madhani@oracle.com> Precedence: bulk X-Mailing-List: linux-scsi@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.293,Aquarius:18.0.1057,Hydra:6.0.680,FMLib:17.12.62.30 definitions=2024-11-09_03,2024-11-08_01,2024-09-30_01 X-Proofpoint-Spam-Details: rule=notspam policy=default score=0 mlxlogscore=999 malwarescore=0 adultscore=0 phishscore=0 bulkscore=0 suspectscore=0 spamscore=0 mlxscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.12.0-2409260000 definitions=main-2411090036 X-Proofpoint-GUID: G-VWUbw4loKjpArfHe1tVU-1cLlbqCJx X-Proofpoint-ORIG-GUID: G-VWUbw4loKjpArfHe1tVU-1cLlbqCJx From: Himanshu Madhani Add check for multipath reqeust when scsi_complete is called. For error handling case, call scsi_mpath_failover_req() to complete the multipath IO. Signed-off-by: Himanshu Madhani --- drivers/scsi/scsi_lib.c | 25 +++++++++++++++++++++++++ include/scsi/scsi.h | 1 + 2 files changed, 26 insertions(+) diff --git a/drivers/scsi/scsi_lib.c b/drivers/scsi/scsi_lib.c index 0561b318dade..1c8113abc154 100644 --- a/drivers/scsi/scsi_lib.c +++ b/drivers/scsi/scsi_lib.c @@ -33,6 +33,7 @@ #include #include #include /* scsi_init_limits() */ +#include #include #include @@ -620,6 +621,14 @@ static void scsi_run_queue_async(struct scsi_device *sdev) } } +static inline void __scsi_mpath_end_request(struct request *req, + blk_status_t status) +{ + if (req->cmd_flags & REQ_SCSI_MPATH) + scsi_mpath_end_request(req); + blk_mq_end_request(req, status); +} + /* Returns false when no more bytes to process, true if there are more */ static bool scsi_end_request(struct request *req, blk_status_t error, unsigned int bytes) @@ -661,6 +670,9 @@ static bool scsi_end_request(struct request *req, blk_status_t error, */ percpu_ref_get(&q->q_usage_counter); + if (req->cmd_flags & REQ_SCSI_MPATH) + scsi_mpath_end_request(req); + __blk_mq_end_request(req, error); scsi_run_queue_async(sdev); @@ -1528,6 +1540,9 @@ static void scsi_complete(struct request *rq) case ADD_TO_MLQUEUE: scsi_queue_insert(cmd, SCSI_MLQUEUE_DEVICE_BUSY); break; + case FAILOVER: + scsi_mpath_failover_req(rq); + break; default: scsi_eh_scmd_add(cmd); break; @@ -1840,6 +1855,9 @@ static blk_status_t scsi_queue_rq(struct blk_mq_hw_ctx *hctx, memset(cmd->sense_buffer, 0, SCSI_SENSE_BUFFERSIZE); cmd->submitter = SUBMITTED_BY_BLOCK_LAYER; + if (req->cmd_flags & REQ_SCSI_MPATH) + scsi_mpath_start_request(req); + blk_mq_start_request(req); reason = scsi_dispatch_cmd(cmd); if (reason) { @@ -2811,6 +2829,9 @@ EXPORT_SYMBOL(scsi_target_resume); static int __scsi_internal_device_block_nowait(struct scsi_device *sdev) { + if (scsi_mpath_enabled(sdev)) + scsi_mpath_clear_current_path(sdev); + if (scsi_device_set_state(sdev, SDEV_BLOCK)) return scsi_device_set_state(sdev, SDEV_CREATED_BLOCK); @@ -2927,6 +2948,10 @@ int scsi_internal_device_unblock_nowait(struct scsi_device *sdev, return -EINVAL; } + /* For multipath device set the path live */ + if (scsi_mpath_enabled(sdev)) + scsi_mpath_set_live(sdev); + /* * Try to transition the scsi device to SDEV_RUNNING or one of the * offlined states and goose the device queue if successful. diff --git a/include/scsi/scsi.h b/include/scsi/scsi.h index 96b350366670..544153a01b3f 100644 --- a/include/scsi/scsi.h +++ b/include/scsi/scsi.h @@ -103,6 +103,7 @@ enum scsi_disposition { TIMEOUT_ERROR = 0x2007, SCSI_RETURN_NOT_HANDLED = 0x2008, FAST_IO_FAIL = 0x2009, + FAILOVER = 0x2010, }; /* From patchwork Sat Nov 9 04:45:26 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Himanshu Madhani X-Patchwork-Id: 13869237 Received: from mx0b-00069f02.pphosted.com (mx0b-00069f02.pphosted.com [205.220.177.32]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 09FCE13B280 for ; Sat, 9 Nov 2024 04:45:32 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=205.220.177.32 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1731127534; cv=none; b=BxZooyOd7PrDvJ/W1ug22VF3FsOO71SkCcfJvCUPEn7VQq4WyNM8cX3vJf2YYn0LE1/3nNLekuqs55oqNp12Ilfqh4JnkzMFDONMPFjHJcQon1zPWmsjmDr4AN7E/mIRpo/q6SOMdbrsHDvpETOB76pDYmtQR/OW8tmGPti8SUA= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1731127534; c=relaxed/simple; bh=D5d93k89D+QZyzNGgsaNrH7jQApOu6qGK3BqX6iHGeU=; h=From:To:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=IFuDy4z5vrABu/4qq22B752bvdShB1gBiLgX8Qzm6R8dJpQjErHLBS1IDyhIyj1Xo11L6mr8hHef2QwQDc168QDVlTEnUMwiCnzo1JTQn5Te8o9jK7l7neELCS6yX0EXle6/drIj3YnVjutINAaSpguplJH7JMFSgrDfQpDZmHw= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=oracle.com; spf=pass smtp.mailfrom=oracle.com; dkim=pass (2048-bit key) header.d=oracle.com header.i=@oracle.com header.b=ArRwitL1; arc=none smtp.client-ip=205.220.177.32 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=oracle.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=oracle.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=oracle.com header.i=@oracle.com header.b="ArRwitL1" Received: from pps.filterd (m0246632.ppops.net [127.0.0.1]) by mx0b-00069f02.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id 4A94PdN2005286 for ; Sat, 9 Nov 2024 04:45:32 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=oracle.com; h= content-transfer-encoding:date:from:in-reply-to:message-id :mime-version:references:subject:to; s=corp-2023-11-20; bh=twXep 2c6powMlcxmqDfgQi+ZEuHOdb/wN3zCSA1rAPQ=; b=ArRwitL1V0gaDsuyONCZ6 hyYDth1RLmSmoOpCTEG8OqIcT5icOVBSWdtVDypGjTj7ejqELGmXY4YrYBOdqNf+ LjDhXh+RD85YdfQ5Bnj29OIjTQ1qSpe6BCE0OeUpN/u38w4O3tO7W6YBYQ4JQZwj 05jU8O6LFKDQdfKN8k/zZKudcsB9LbtG3fQF0iHQxzDgE2CQMZz9gYsx4eANei/m /tGHFAREmsIwdSqpLvETVVm+FJcWoGsXArC1DpLOmOBft6mTy4bHW91wQF+bAltH p+2+RQeAgmrT9YcuJ1hc4qQjyXRrjz5Mf70kHt2NPEodMXObtZGdLBYKzpt3nhFu Q== Received: from iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (iadpaimrmta02.appoci.oracle.com [147.154.18.20]) by mx0b-00069f02.pphosted.com (PPS) with ESMTPS id 42t0heg0bb-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK) for ; Sat, 09 Nov 2024 04:45:31 +0000 (GMT) Received: from pps.filterd (iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com [127.0.0.1]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (8.18.1.2/8.18.1.2) with ESMTP id 4A91Xe3Z034332 for ; Sat, 9 Nov 2024 04:45:31 GMT Received: from pps.reinject (localhost [127.0.0.1]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (PPS) with ESMTPS id 42sx65aja8-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK) for ; Sat, 09 Nov 2024 04:45:30 +0000 Received: from iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com [127.0.0.1]) by pps.reinject (8.17.1.5/8.17.1.5) with ESMTP id 4A94jTdW001575 for ; Sat, 9 Nov 2024 04:45:30 GMT Received: from hmadhani-upstream.osdevelopmeniad.oraclevcn.com (hmadhani-upstream.allregionaliads.osdevelopmeniad.oraclevcn.com [100.100.255.48]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (PPS) with ESMTP id 42sx65aj9h-6; Sat, 09 Nov 2024 04:45:30 +0000 From: himanshu.madhani@oracle.com To: martin.petersen@oracle.com, linux-scsi@vger.kernel.org Subject: [RFC v1 5/8] scsi: Add scsi multipath sysfs hooks Date: Sat, 9 Nov 2024 04:45:26 +0000 Message-ID: <20241109044529.992935-6-himanshu.madhani@oracle.com> X-Mailer: git-send-email 2.41.0.rc2 In-Reply-To: <20241109044529.992935-1-himanshu.madhani@oracle.com> References: <20241109044529.992935-1-himanshu.madhani@oracle.com> Precedence: bulk X-Mailing-List: linux-scsi@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.293,Aquarius:18.0.1057,Hydra:6.0.680,FMLib:17.12.62.30 definitions=2024-11-09_03,2024-11-08_01,2024-09-30_01 X-Proofpoint-Spam-Details: rule=notspam policy=default score=0 mlxlogscore=999 malwarescore=0 adultscore=0 phishscore=0 bulkscore=0 suspectscore=0 spamscore=0 mlxscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.12.0-2409260000 definitions=main-2411090036 X-Proofpoint-ORIG-GUID: -IUXNJVmxdj7XlHpNvwlJQOgpR9r6loH X-Proofpoint-GUID: -IUXNJVmxdj7XlHpNvwlJQOgpR9r6loH From: Himanshu Madhani Add Sysfs hook to - Show current multipath state - Show and update multipath iopolicy Signed-off-by: Himanshu Madhani --- drivers/scsi/scsi_sysfs.c | 104 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 104 insertions(+) diff --git a/drivers/scsi/scsi_sysfs.c b/drivers/scsi/scsi_sysfs.c index 32f94db6d6bf..cc7dc5c30d2c 100644 --- a/drivers/scsi/scsi_sysfs.c +++ b/drivers/scsi/scsi_sysfs.c @@ -1198,6 +1198,103 @@ sdev_show_preferred_path(struct device *dev, static DEVICE_ATTR(preferred_path, S_IRUGO, sdev_show_preferred_path, NULL); #endif +#ifdef CONFIG_SCSI_MULTIPATH +static const struct { + unsigned char value; + char *name; +} scsi_multipath_iopolicy[] = { + { SCSI_MPATH_IOPOLICY_NUMA, "NUMA" }, + { SCSI_MPATH_IOPOLICY_RR, "Round-Robin" }, +}; +static const char *scsi_mpath_policy_name(unsigned char policy) +{ + int i; + char *name = NULL; + + for (i = 0; i < ARRAY_SIZE(scsi_multipath_iopolicy); i++) { + if (scsi_multipath_iopolicy[i].value == policy) { + name = scsi_multipath_iopolicy[i].name; + break; + } + } + return name; +} + +static ssize_t +sdev_show_multipath_iopolicy(struct device *dev, + struct device_attribute *attr, + char *buf) +{ + struct scsi_device *sdev = to_scsi_device(dev); + const char *name = scsi_mpath_policy_name(sdev->mpath_iopolicy); + + if (!sdev->mpath_disk) + return -EINVAL; + + return sysfs_emit(buf, "%s\n", name); +} + +static ssize_t sdev_store_multipath_iopolicy(struct device *dev, + struct device_attribute *attr, const char *buf, size_t count) +{ + struct scsi_device *sdev = to_scsi_device(dev); + int i; + + for (i = 0; i < ARRAY_SIZE(scsi_multipath_iopolicy); i++) { + if (sysfs_streq(buf, scsi_mpath_policy_name(i))) { + scsi_multipath_iopolicy_update(sdev, i); + return count; + } + } + + return -EINVAL; +} +static DEVICE_ATTR(multipath_iopolicy, S_IRUGO, sdev_show_multipath_iopolicy, + sdev_store_multipath_iopolicy); + +static const struct { + unsigned char value; + char *name; +} scsi_mpath_states[] = { + { SCSI_MPATH_OPTIMAL, "active/optimized" }, + { SCSI_MPATH_ACTIVE, "active/non-optimized" }, + { SCSI_MPATH_STANDBY, "standby" }, + { SCSI_MPATH_UNAVAILABLE,"unavailable" }, + { SCSI_MPATH_LBA, "lba-dependent" }, + { SCSI_MPATH_OFFLINE, "offline" }, + { SCSI_MPATH_TRANSITIONING,"transitioning" }, +}; + +static const char *scsi_mpath_state_names(unsigned char state) +{ + int i; + char *name = NULL; + + for (i = 0; i < ARRAY_SIZE(scsi_mpath_states); i++) { + if (scsi_mpath_states[i].value == state) { + name = scsi_mpath_states[i].name; + break; + } + } + return name; +} + +static ssize_t +sdev_show_multipath_state(struct device *dev, + struct device_attribute *attr, + char *buf) +{ + struct scsi_device *sdev = to_scsi_device(dev); + const char *name = scsi_mpath_state_names(sdev->mpath_state); + + if (!sdev->mpath_disk) + return -EINVAL; + + return sysfs_emit(buf, "%s\n", name); +} +static DEVICE_ATTR(multipath_state, S_IRUGO, sdev_show_multipath_state, NULL); +#endif + static ssize_t sdev_show_queue_ramp_up_period(struct device *dev, struct device_attribute *attr, @@ -1335,6 +1432,10 @@ static struct attribute *scsi_sdev_attrs[] = { &dev_attr_dh_state.attr, &dev_attr_access_state.attr, &dev_attr_preferred_path.attr, +#endif +#ifdef CONFIG_SCSI_MULTIPATH + &dev_attr_multipath_iopolicy.attr, + &dev_attr_multipath_state.attr, #endif &dev_attr_queue_ramp_up_period.attr, &dev_attr_cdl_supported.attr, @@ -1500,6 +1601,9 @@ void __scsi_remove_device(struct scsi_device *sdev) } else put_device(&sdev->sdev_dev); + if (scsi_is_sdev_multipath(sdev)) + scsi_mpath_dev_release(sdev); + /* * Stop accepting new requests and wait until all queuecommand() and * scsi_run_queue() invocations have finished before tearing down the From patchwork Sat Nov 9 04:45:27 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Himanshu Madhani X-Patchwork-Id: 13869238 Received: from mx0b-00069f02.pphosted.com (mx0b-00069f02.pphosted.com [205.220.177.32]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 5CC2613B297 for ; Sat, 9 Nov 2024 04:45:32 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=205.220.177.32 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1731127535; cv=none; b=TYNPaKxukcvbqeOrlzFSmtpZvWnO33GbNW9wcbuCH4i8RJJmIl41t+tK2Gcnl5q/lPQQJdiE+5+DGzwz9V8yCj1hj89k8Rqr/EqK2xOWJNlT6L3jPUbqrf0JF54+fFlEbTvKsyh516fns2hIgdYW2wfrpwZgubd2HCGe5/jZ2ow= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1731127535; c=relaxed/simple; bh=pbVPF1JeHFk6W+gEpqdB6er2wg+9HdUkxzv7v3aG220=; h=From:To:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=Q1uuM6v/TYrHXN6TsVOH92z57OP5zJrr7B7TY3DGcj7w4I3HXapZTA2NLGOZe/NJITI7zT7whGoDiLvspOXB72f6LDxpOCTPkiLvoVe2+QRGXJ9ew7YXQNJOKBiMxOONCkCUBGdOaYNs7xfD0Gr30G2/E5+Ac2Isz4AAQ/zWe7A= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=oracle.com; spf=pass smtp.mailfrom=oracle.com; dkim=pass (2048-bit key) header.d=oracle.com header.i=@oracle.com header.b=dmFpN9N3; arc=none smtp.client-ip=205.220.177.32 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=oracle.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=oracle.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=oracle.com header.i=@oracle.com header.b="dmFpN9N3" Received: from pps.filterd (m0246631.ppops.net [127.0.0.1]) by mx0b-00069f02.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id 4A94jWRg007697; Sat, 9 Nov 2024 04:45:32 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=oracle.com; h= content-transfer-encoding:date:from:in-reply-to:message-id :mime-version:references:subject:to; s=corp-2023-11-20; bh=YOtXY FXCBL+wEFr5wqDN3+gKTlHYfFzGuZvAl0xwHyE=; b=dmFpN9N3VNQoWZVGFzCwJ wICw5WWz5gDtlGQ6KYt9U7CRz1SgNUalgahfiwGDzjyAggrwvcSz/b0tPkReucgp lajtVV/+u7NkPwxAOPfuGeURfvlhv8fzj5XhFpNuG5D6B6qOYrdoznJwqbTHdCBO dTR7nJE0EUxS7iqFw5XE4W93TUpzNP3nxbqPHBltpViunB2N1Y9C8izu+nbxh0OI 40m4I9EmSk4Euo65SJH6yynpes892kOjtiNBy0/3y8u9DwIK5HO1kRzS9N4/uhUA exfjLtJPbRWQYqNkFVo24UoOfiqXLAX0iK7Oa8sWFruFxA73O6I2c5K0LDr3ssrH g== Received: from iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (iadpaimrmta02.appoci.oracle.com [147.154.18.20]) by mx0b-00069f02.pphosted.com (PPS) with ESMTPS id 42t0k200a3-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK) for ; Sat, 09 Nov 2024 04:45:31 +0000 (GMT) Received: from pps.filterd (iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com [127.0.0.1]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (8.18.1.2/8.18.1.2) with ESMTP id 4A91XfQt034360 for ; Sat, 9 Nov 2024 04:45:31 GMT Received: from pps.reinject (localhost [127.0.0.1]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (PPS) with ESMTPS id 42sx65ajad-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK) for ; Sat, 09 Nov 2024 04:45:31 +0000 Received: from iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com [127.0.0.1]) by pps.reinject (8.17.1.5/8.17.1.5) with ESMTP id 4A94jTdY001575 for ; Sat, 9 Nov 2024 04:45:31 GMT Received: from hmadhani-upstream.osdevelopmeniad.oraclevcn.com (hmadhani-upstream.allregionaliads.osdevelopmeniad.oraclevcn.com [100.100.255.48]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (PPS) with ESMTP id 42sx65aj9h-7; Sat, 09 Nov 2024 04:45:31 +0000 From: himanshu.madhani@oracle.com To: martin.petersen@oracle.com, linux-scsi@vger.kernel.org Subject: [RFC v1 6/8] scsi: Add multipath suppport for device handler Date: Sat, 9 Nov 2024 04:45:27 +0000 Message-ID: <20241109044529.992935-7-himanshu.madhani@oracle.com> X-Mailer: git-send-email 2.41.0.rc2 In-Reply-To: <20241109044529.992935-1-himanshu.madhani@oracle.com> References: <20241109044529.992935-1-himanshu.madhani@oracle.com> Precedence: bulk X-Mailing-List: linux-scsi@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.293,Aquarius:18.0.1057,Hydra:6.0.680,FMLib:17.12.62.30 definitions=2024-11-09_03,2024-11-08_01,2024-09-30_01 X-Proofpoint-Spam-Details: rule=notspam policy=default score=0 mlxlogscore=999 malwarescore=0 adultscore=0 phishscore=0 bulkscore=0 suspectscore=0 spamscore=0 mlxscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.12.0-2409260000 definitions=main-2411090036 X-Proofpoint-ORIG-GUID: 6GMKMaNBb8s55h2OcA2NcB9RQzbQNLm6 X-Proofpoint-GUID: 6GMKMaNBb8s55h2OcA2NcB9RQzbQNLm6 From: Himanshu Madhani Add multipath initialization during handler attachemnet for DH. Also initialize multipath port group data for scsi_device. Signed-off-by: Himanshu Madhani --- drivers/scsi/device_handler/scsi_dh_alua.c | 15 +++++++++++++++ drivers/scsi/scsi_dh.c | 3 +++ 2 files changed, 18 insertions(+) diff --git a/drivers/scsi/device_handler/scsi_dh_alua.c b/drivers/scsi/device_handler/scsi_dh_alua.c index 4eb0837298d4..29bd6517a2e3 100644 --- a/drivers/scsi/device_handler/scsi_dh_alua.c +++ b/drivers/scsi/device_handler/scsi_dh_alua.c @@ -258,6 +258,21 @@ static struct alua_port_group *alua_alloc_pg(struct scsi_device *sdev, return tmp_pg; } + if (scsi_mpath_enabled(sdev)) { + struct scsi_mpath_dh_data *dh_data = sdev->mpath_pg_data; + + dh_data->group_id = pg->group_id; + dh_data->tpgs = pg->tpgs; + dh_data->state = pg->state; + dh_data->valid_states = pg->valid_states; + dh_data->prefrence = pg->pref; + dh_data->is_active = 1; + dh_data->device_id_str = kstrdup(pg->device_id_str, GFP_KERNEL); + dh_data->device_id_len = pg->device_id_len; + + sdev->host->mpath_alua_grpid = pg->group_id; + } + list_add(&pg->node, &port_group_list); spin_unlock(&port_group_lock); diff --git a/drivers/scsi/scsi_dh.c b/drivers/scsi/scsi_dh.c index 7b56e00c7df6..d61eddc3c1f8 100644 --- a/drivers/scsi/scsi_dh.c +++ b/drivers/scsi/scsi_dh.c @@ -129,6 +129,9 @@ static int scsi_dh_handler_attach(struct scsi_device *sdev, if (!try_module_get(scsi_dh->module)) return -EINVAL; + if (scsi_mpath_enabled(sdev)) + scsi_multipath_init(sdev); + error = scsi_dh->attach(sdev); if (error != SCSI_DH_OK) { switch (error) { From patchwork Sat Nov 9 04:45:28 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Himanshu Madhani X-Patchwork-Id: 13869240 Received: from mx0b-00069f02.pphosted.com (mx0b-00069f02.pphosted.com [205.220.177.32]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id A339D286A8 for ; Sat, 9 Nov 2024 04:45:33 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=205.220.177.32 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1731127535; cv=none; b=B+kQ5EibVRxZ97qq+BKLA4mXD98ZoqT8MMDWZ2w/95BdaYCxATIpoWe0RcfjIogqbDoh8fSoWqOkIlPIMnmxf7TL60bn898zsUGNtXMxTIBwAK8bJtdhhRqu5NftgHCCcvpFKrEUgsFZ0A+GB/YS4H/YAixDZ7fzBAD1WoRZ5Pc= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1731127535; c=relaxed/simple; bh=+wQGD7OhU+LITN3CSeh543W8Ng61OzHHq4tpiw8BvmA=; h=From:To:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=TVfp9zoAwMCIKM2uhoAoN/DeoQFMqblQUEz59lrQ5B7+c0nO/d5qAbfZyJvMRjjeYMN9vpc3Rlrc2duF6NEMa966G1Q4FdzDp7TWmTQEAcY8aY4tH+gMi1HuQdfhDDNzPoU2Ut065zfZCOs8QebUP70mx6YZ2Ivs5PMLq14ajug= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=oracle.com; spf=pass smtp.mailfrom=oracle.com; dkim=pass (2048-bit key) header.d=oracle.com header.i=@oracle.com header.b=QSIXPEia; arc=none smtp.client-ip=205.220.177.32 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=oracle.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=oracle.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=oracle.com header.i=@oracle.com header.b="QSIXPEia" Received: from pps.filterd (m0246632.ppops.net [127.0.0.1]) by mx0b-00069f02.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id 4A94PdN3005286 for ; Sat, 9 Nov 2024 04:45:32 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=oracle.com; h= content-transfer-encoding:date:from:in-reply-to:message-id :mime-version:references:subject:to; s=corp-2023-11-20; bh=ETtSE CxwWca1iUuaTGAyoNHvHcywCYSkiw7Y9HP1yj8=; b=QSIXPEia7YWR64EfUJVhL hdguaxoyYHIClmjJoygCex2VeIyBb97b7uvAD6qSsjv6zUx7BDK152yMft0cxHL9 RHMJw1EbJ46NqNsBhlmGe/6yQ3ofHcLM5Nj/j6PIaP0jtYoJch/QDx6nedRpuhrG R/qvyOd/KqtHfc/tAN24FB8s0urPZC/trQlem2r2MqHU4nI5Cv4eloKqIKG+HNbV KSELNXPzd3NYiiY/SDkDX0uR2gbKzBn4UdfGjyvSsoeAjQGGZA4G2ky2rfNrXK+1 uSGOCymUC4fXkXy2xKDuAuNbWNDq1KiD9OJLaRHpat1rSqU5OZbn1wxp/RMvJTgp Q== Received: from iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (iadpaimrmta02.appoci.oracle.com [147.154.18.20]) by mx0b-00069f02.pphosted.com (PPS) with ESMTPS id 42t0heg0bc-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK) for ; Sat, 09 Nov 2024 04:45:32 +0000 (GMT) Received: from pps.filterd (iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com [127.0.0.1]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (8.18.1.2/8.18.1.2) with ESMTP id 4A91Y5d8034515 for ; Sat, 9 Nov 2024 04:45:31 GMT Received: from pps.reinject (localhost [127.0.0.1]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (PPS) with ESMTPS id 42sx65ajaj-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK) for ; Sat, 09 Nov 2024 04:45:31 +0000 Received: from iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com [127.0.0.1]) by pps.reinject (8.17.1.5/8.17.1.5) with ESMTP id 4A94jTda001575 for ; Sat, 9 Nov 2024 04:45:31 GMT Received: from hmadhani-upstream.osdevelopmeniad.oraclevcn.com (hmadhani-upstream.allregionaliads.osdevelopmeniad.oraclevcn.com [100.100.255.48]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (PPS) with ESMTP id 42sx65aj9h-8; Sat, 09 Nov 2024 04:45:31 +0000 From: himanshu.madhani@oracle.com To: martin.petersen@oracle.com, linux-scsi@vger.kernel.org Subject: [RFC v1 7/8] scsi: Add multipath disk init code for sd driver Date: Sat, 9 Nov 2024 04:45:28 +0000 Message-ID: <20241109044529.992935-8-himanshu.madhani@oracle.com> X-Mailer: git-send-email 2.41.0.rc2 In-Reply-To: <20241109044529.992935-1-himanshu.madhani@oracle.com> References: <20241109044529.992935-1-himanshu.madhani@oracle.com> Precedence: bulk X-Mailing-List: linux-scsi@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.293,Aquarius:18.0.1057,Hydra:6.0.680,FMLib:17.12.62.30 definitions=2024-11-09_03,2024-11-08_01,2024-09-30_01 X-Proofpoint-Spam-Details: rule=notspam policy=default score=0 mlxlogscore=999 malwarescore=0 adultscore=0 phishscore=0 bulkscore=0 suspectscore=0 spamscore=0 mlxscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.12.0-2409260000 definitions=main-2411090036 X-Proofpoint-ORIG-GUID: kJaq1VJ95Rt7FTBTZlVIPkRUh9FQ-yaw X-Proofpoint-GUID: kJaq1VJ95Rt7FTBTZlVIPkRUh9FQ-yaw From: Himanshu Madhani This patch adds allocation and initialization code to scsi disk driver. Signed-off-by: Himanshu Madhani --- drivers/scsi/sd.c | 83 +++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 83 insertions(+) diff --git a/drivers/scsi/sd.c b/drivers/scsi/sd.c index 41e2dfa2d67d..b4727b599794 100644 --- a/drivers/scsi/sd.c +++ b/drivers/scsi/sd.c @@ -1483,6 +1483,9 @@ static void sd_uninit_command(struct scsi_cmnd *SCpnt) static bool sd_need_revalidate(struct gendisk *disk, struct scsi_disk *sdkp) { + if (scsi_is_sdev_multipath(sdkp->device)) + return true; + if (sdkp->device->removable || sdkp->write_prot) { if (disk_check_media_change(disk)) return true; @@ -1892,6 +1895,10 @@ static int sd_get_unique_id(struct gendisk *disk, u8 id[16], if (len == 16) break; } + + if (scsi_mpath_enabled(sdev)) + ret = scsi_mpath_unique_id(sdev, id, type); + out_unlock: rcu_read_unlock(); return ret; @@ -3817,6 +3824,33 @@ static int sd_revalidate_disk(struct gendisk *disk) if (sdkp->media_present && scsi_device_supports_vpd(sdp)) sd_read_cpr(sdkp); + /* for multipath device, Adjust queue limits for MPATH disk */ + if (scsi_is_sdev_multipath(sdp)) { + struct queue_limits *mpath_lim = &sdp->mpath_disk->queue->limits; + + blk_mq_freeze_queue(sdp->mpath_disk->queue); + lim = queue_limits_start_update(sdp->mpath_disk->queue); + lim.logical_block_size = mpath_lim->logical_block_size; + lim.physical_block_size = mpath_lim->physical_block_size; + lim.io_min = mpath_lim->io_min; + lim.io_opt = mpath_lim->io_opt; + queue_limits_stack_bdev(&lim, sdp->mpath_disk->part0, 0, + sdp->mpath_disk->disk_name); + + sdp->mpath_disk->flags |= GENHD_FL_HIDDEN; + + set_capacity_and_notify(sdp->mpath_disk, + logical_to_sectors(sdp, sdkp->capacity)); + + err = queue_limits_commit_update(sdp->mpath_disk->queue, &lim); + + scsi_mpath_revalidate_path(sdp->mpath_disk, + logical_to_sectors(sdp, sdkp->capacity)); + + blk_mq_unfreeze_queue(sdp->mpath_disk->queue); + if (err) + return err; + } /* * For a zoned drive, revalidating the zones can be done only once * the gendisk capacity is set. So if this fails, set back the gendisk @@ -3943,6 +3977,9 @@ static int sd_probe(struct device *dev) if (!sdkp) goto out; + if (scsi_mpath_enabled(sdp) && sdp->is_shared) + scsi_mpath_alloc_disk(sdp); + gd = blk_mq_alloc_disk_for_queue(sdp->request_queue, &sd_bio_compl_lkclass); if (!gd) @@ -3960,6 +3997,10 @@ static int sd_probe(struct device *dev) goto out_free_index; } + if (scsi_is_sdev_multipath(sdp)) + snprintf(sdp->mpath_disk->disk_name, DISK_NAME_LEN, "mpath%dsd%d", + sdp->host->host_no, index); + sdkp->device = sdp; sdkp->disk = gd; sdkp->index = index; @@ -4021,6 +4062,21 @@ static int sd_probe(struct device *dev) sdp->host->rpm_autosuspend_delay); } + if (scsi_is_sdev_multipath(sdp)) { + sdp->mpath_disk->major = sd_major((index & 0xf0) >> 4); + sdp->mpath_disk->first_minor = ((index & 0xf) << 4) | (index & 0xfff00); + sdp->mpath_disk->minors = SD_MINORS; + + scsi_mpath_add_disk(sdp); + + if (!test_bit(SCSI_MPATH_DISK_LIVE, &sdp->mpath_flags)) { + device_unregister(&sdkp->disk_dev); + clear_bit(SCSI_MPATH_DISK_LIVE, &sdp->mpath_flags); + put_disk(sdp->mpath_disk); + goto out; + } + } + error = device_add_disk(dev, gd, NULL); if (error) { device_unregister(&sdkp->disk_dev); @@ -4074,12 +4130,20 @@ static int sd_remove(struct device *dev) sd_shutdown(dev); put_disk(sdkp->disk); + + if (scsi_is_sdev_multipath(sdkp->device)) + scsi_mpath_remove_disk(sdkp->device); + return 0; } static void scsi_disk_release(struct device *dev) { struct scsi_disk *sdkp = to_scsi_disk(dev); + struct scsi_device *sdp = to_scsi_device(dev); + + if (scsi_is_sdev_multipath(sdp)) + scsi_mpath_dev_release(sdp); ida_free(&sd_index_ida, sdkp->index); put_device(&sdkp->device->sdev_gendev); @@ -4171,6 +4235,25 @@ static void sd_shutdown(struct device *dev) if (pm_runtime_suspended(dev)) return; + if (scsi_is_sdev_multipath(sdkp->device)) { + struct scsi_device *sdp = sdkp->device; + bool last_path = false; + + if (scsi_mpath_clear_current_path(sdp)) + synchronize_srcu(&sdp->host->mpath_dev->srcu); + + mutex_lock(&sdp->host->mpath_dev->mpath_lock); + list_del_rcu(&sdp->siblings); + if (list_empty(&sdp->host->mpath_sdev)) { + list_del_init(&sdp->mpath_entry); + last_path = true; + } + mutex_unlock(&sdp->host->mpath_dev->mpath_lock); + + if (last_path) + scsi_mpath_shutdown_disk(sdp); + } + if (sdkp->WCE && sdkp->media_present) { sd_printk(KERN_NOTICE, sdkp, "Synchronizing SCSI cache\n"); sd_sync_cache(sdkp); From patchwork Sat Nov 9 04:45:29 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Himanshu Madhani X-Patchwork-Id: 13869241 Received: from mx0b-00069f02.pphosted.com (mx0b-00069f02.pphosted.com [205.220.177.32]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id A5EBD13B5AF for ; Sat, 9 Nov 2024 04:45:33 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=205.220.177.32 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1731127535; cv=none; b=SSabPuuN9dDl+KQoyiGVgjfrezRivQ2Y3QXS74lnQZIFaevXSWWavRuzYzzVbLApwPTbMUPqjG2izPUBALr1+7O2TSsrkgZrsQYonypjUs2EOTtNCuv65IpwmK/0gfUvfrV1GOUFeq/QILHKY3e3EakWylcNOmnJAm0Gr2WtulI= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1731127535; c=relaxed/simple; bh=qOOW9nLFWUmYEQTA8ZNSEXIFIlJYoJPsUasv7zcSurM=; h=From:To:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=YEm/XnPcV4gqsmtJnoHRqNGze0pAF6iQj1YtdEGEEze5H9kfGmdgY6piZCk8S9weVH8+NFQIw3nOh8wnTgWDkCe58H90FD40kYVGWzFt+qGlzDgfKB/4s4CfwTP6cztrEMGAag/L069zCGp9TShMrIDLYQCIUooU1vSauDIrrjM= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=oracle.com; spf=pass smtp.mailfrom=oracle.com; dkim=pass (2048-bit key) header.d=oracle.com header.i=@oracle.com header.b=HHuFh31Z; arc=none smtp.client-ip=205.220.177.32 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=reject dis=none) header.from=oracle.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=oracle.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=oracle.com header.i=@oracle.com header.b="HHuFh31Z" Received: from pps.filterd (m0246630.ppops.net [127.0.0.1]) by mx0b-00069f02.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id 4A94JLP7014056 for ; Sat, 9 Nov 2024 04:45:32 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=oracle.com; h= content-transfer-encoding:date:from:in-reply-to:message-id :mime-version:references:subject:to; s=corp-2023-11-20; bh=n5uA1 6y+/niKduHBsbFinbFKEhvTKbcKZTdT1a52Mrs=; b=HHuFh31ZxXz0STV4JDf/V 4RhPe+ges9aWJjFZfnBpyQ8RWs5qDIFKfFFucu5H46asa1L7qfl+dLmRUhWePSPu RasgSdZbU0IHUofaw1vW9TXwzkzedffaDjYWJJ1JpEg9+GM/zHubsFpVZtbGc2qt ZaggITEwvt0+AcJlW7+GC18jJH5PVkbZgyyCxvHFOgECXf7l/BABPrMwWHHJlIW9 +NCj3dIUI3XgEOI0zTT6web4M/eyt995umh1coGPCu82GfD7MxB9ef8U+NTvnDoC +b6AOSW7vLiyiZeNR8VrrdiZivDYAn3gDQXMF/QVph9pLMMOHUneb/1jCNw3eB37 g== Received: from iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (iadpaimrmta02.appoci.oracle.com [147.154.18.20]) by mx0b-00069f02.pphosted.com (PPS) with ESMTPS id 42t0k580a0-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK) for ; Sat, 09 Nov 2024 04:45:32 +0000 (GMT) Received: from pps.filterd (iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com [127.0.0.1]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (8.18.1.2/8.18.1.2) with ESMTP id 4A91XYb7034280 for ; Sat, 9 Nov 2024 04:45:31 GMT Received: from pps.reinject (localhost [127.0.0.1]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (PPS) with ESMTPS id 42sx65ajam-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK) for ; Sat, 09 Nov 2024 04:45:31 +0000 Received: from iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com [127.0.0.1]) by pps.reinject (8.17.1.5/8.17.1.5) with ESMTP id 4A94jTdc001575 for ; Sat, 9 Nov 2024 04:45:31 GMT Received: from hmadhani-upstream.osdevelopmeniad.oraclevcn.com (hmadhani-upstream.allregionaliads.osdevelopmeniad.oraclevcn.com [100.100.255.48]) by iadpaimrmta02.imrmtpd1.prodappiadaev1.oraclevcn.com (PPS) with ESMTP id 42sx65aj9h-9; Sat, 09 Nov 2024 04:45:31 +0000 From: himanshu.madhani@oracle.com To: martin.petersen@oracle.com, linux-scsi@vger.kernel.org Subject: [RFC v1 8/8] scsi_debug: Add module parameter for ALUA multipath Date: Sat, 9 Nov 2024 04:45:29 +0000 Message-ID: <20241109044529.992935-9-himanshu.madhani@oracle.com> X-Mailer: git-send-email 2.41.0.rc2 In-Reply-To: <20241109044529.992935-1-himanshu.madhani@oracle.com> References: <20241109044529.992935-1-himanshu.madhani@oracle.com> Precedence: bulk X-Mailing-List: linux-scsi@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.293,Aquarius:18.0.1057,Hydra:6.0.680,FMLib:17.12.62.30 definitions=2024-11-09_03,2024-11-08_01,2024-09-30_01 X-Proofpoint-Spam-Details: rule=notspam policy=default score=0 mlxlogscore=999 malwarescore=0 adultscore=0 phishscore=0 bulkscore=0 suspectscore=0 spamscore=0 mlxscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.12.0-2409260000 definitions=main-2411090036 X-Proofpoint-ORIG-GUID: LD_iM0lHVJdmqOOOpIsMOZ7Xc0TMmiN0 X-Proofpoint-GUID: LD_iM0lHVJdmqOOOpIsMOZ7Xc0TMmiN0 From: Himanshu Madhani Signed-off-by: Himanshu Madhani --- drivers/scsi/scsi_debug.c | 16 ++++++++++++++-- 1 file changed, 14 insertions(+), 2 deletions(-) diff --git a/drivers/scsi/scsi_debug.c b/drivers/scsi/scsi_debug.c index 9be2a6a00530..811d3005c0a5 100644 --- a/drivers/scsi/scsi_debug.c +++ b/drivers/scsi/scsi_debug.c @@ -167,6 +167,7 @@ static const char *sdebug_version_date = "20210520"; #define DEF_TUR_MS_TO_READY 0 #define DEF_UUID_CTL 0 #define JDELAY_OVERRIDDEN -9999 +#define DEF_ALUA_MPATH 0 /* Default parameters for ZBC drives */ #define DEF_ZBC_ZONE_SIZE_MB 128 @@ -884,6 +885,8 @@ static bool write_since_sync; static bool sdebug_statistics = DEF_STATISTICS; static bool sdebug_wp; static bool sdebug_allow_restart; +static unsigned int sdebug_alua_mpath = DEF_ALUA_MPATH; + static enum { BLK_ZONED_NONE = 0, BLK_ZONED_HA = 1, @@ -2070,8 +2073,14 @@ static int resp_inquiry(struct scsi_cmnd *scp, struct sdebug_dev_info *devip) arr[3] = 2; /* response_data_format==2 */ arr[4] = SDEBUG_LONG_INQ_SZ - 5; arr[5] = (int)have_dif_prot; /* PROTECT bit */ - if (sdebug_vpd_use_hostno == 0) - arr[5] |= 0x10; /* claim: implicit TPGS */ + if (sdebug_vpd_use_hostno == 0) { + arr[5] |= 0x10; + } else { + if (sdebug_alua_mpath == 1) + arr[5] |= 0x11; + else + arr[5] |= 0x10; + } arr[6] = 0x10; /* claim: MultiP */ /* arr[6] |= 0x40; ... claim: EncServ (enclosure services) */ arr[7] = 0xa; /* claim: LINKED + CMDQUE */ @@ -6643,6 +6652,7 @@ module_param_named(zone_max_open, sdeb_zbc_max_open, int, S_IRUGO); module_param_named(zone_nr_conv, sdeb_zbc_nr_conv, int, S_IRUGO); module_param_named(zone_size_mb, sdeb_zbc_zone_size_mb, int, S_IRUGO); module_param_named(allow_restart, sdebug_allow_restart, bool, S_IRUGO | S_IWUSR); +module_param_named(alua_mpath, sdebug_alua_mpath, int, S_IRUGO | S_IWUSR); MODULE_AUTHOR("Eric Youngdale + Douglas Gilbert"); MODULE_DESCRIPTION("SCSI debug adapter driver"); @@ -6722,6 +6732,8 @@ MODULE_PARM_DESC(zone_max_open, "Maximum number of open zones; [0] for no limit MODULE_PARM_DESC(zone_nr_conv, "Number of conventional zones (def=1)"); MODULE_PARM_DESC(zone_size_mb, "Zone size in MiB (def=auto)"); MODULE_PARM_DESC(allow_restart, "Set scsi_device's allow_restart flag(def=0)"); +MODULE_PARM_DESC(alua_mpath, + "\t 1 = implicit alua \n \t 2 = Explicit & Implicit ALUA, \n \t 0 = No ALUA Support (Default) \n"); #define SDEBUG_INFO_LEN 256 static char sdebug_info[SDEBUG_INFO_LEN];