Re: [PATCH 05/15] megaraid_sas: Update device Queue depth based on interface type

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On 18.12.2015 14:26, Sumit Saxena wrote:
> This patch will update device Queue depth based on interface type(SAS, SATA..) for sysPDs.
> For Virtual disks(VDs), there will be no change in queue depth(will remain 256).
> To fetch interface type(SAS or SATA or FC..) of syspD, driver will send DCMD MR_DCMD_PD_GET_INFO per sysPD.
>
> Signed-off-by: Sumit Saxena <sumit.saxena@xxxxxxxxxxxxx>
> Signed-off-by: Kashyap Desai <kashyap.desai@xxxxxxxxxxxxx>
>
> ---
>  drivers/scsi/megaraid/megaraid_sas.h      |  270 ++++++++++++++++++++++++++++-
>  drivers/scsi/megaraid/megaraid_sas_base.c |  127 ++++++++++++++
>  2 files changed, 396 insertions(+), 1 deletions(-)
>
> diff --git a/drivers/scsi/megaraid/megaraid_sas.h b/drivers/scsi/megaraid/megaraid_sas.h
> index 0fcb156..773fc54 100644
> --- a/drivers/scsi/megaraid/megaraid_sas.h
> +++ b/drivers/scsi/megaraid/megaraid_sas.h
> @@ -215,6 +215,7 @@
>  
>  #define MR_DCMD_CTRL_SET_CRASH_DUMP_PARAMS	0x01190100
>  #define MR_DRIVER_SET_APP_CRASHDUMP_MODE	(0xF0010000 | 0x0600)
> +#define MR_DCMD_PD_GET_INFO			0x02020000
>  
>  /*
>   * Global functions
> @@ -435,6 +436,257 @@ enum MR_PD_STATE {
>  	MR_PD_STATE_SYSTEM              = 0x40,
>   };
>  
> +union MR_PD_REF {
> +	struct {
> +		u16	 deviceId;
> +		u16	 seqNum;
> +	} mrPdRef;
> +	u32	 ref;
> +};
> +
> +/*
> + * define the DDF Type bit structure
> + */
> +union MR_PD_DDF_TYPE {
> +	 struct {
> +		union {
> +			struct {
> +#ifndef __BIG_ENDIAN_BITFIELD
> +				 u16	 forcedPDGUID:1;
> +				 u16	 inVD:1;
> +				 u16	 isGlobalSpare:1;
> +				 u16	 isSpare:1;
> +				 u16	 isForeign:1;
> +				 u16	 reserved:7;
> +				 u16	 intf:4;
> +#else
> +				 u16	 intf:4;
> +				 u16	 reserved:7;
> +				 u16	 isForeign:1;
> +				 u16	 isSpare:1;
> +				 u16	 isGlobalSpare:1;
> +				 u16	 inVD:1;
> +				 u16	 forcedPDGUID:1;
> +#endif
> +			 } pdType;
> +			 u16	 type;
> +		 };
> +		 u16	 reserved;
> +	 } ddf;
> +	 struct {
> +		 u32	reserved;
> +	 } nonDisk;
> +	 u32	 type;
> +} __packed;
> +
> +/*
> + * defines the progress structure
> + */
> +union MR_PROGRESS {
> +	struct  {
> +		u16 progress;
> +		union {
> +			u16 elapsedSecs;
> +			u16 elapsedSecsForLastPercent;
> +		};
> +	} mrProgress;
> +	u32 w;
> +} __packed;
> +
> +/*
> + * defines the physical drive progress structure
> + */
> +struct MR_PD_PROGRESS {
> +	struct {
> +#ifndef MFI_BIG_ENDIAN
> +		u32     rbld:1;
> +		u32     patrol:1;
> +		u32     clear:1;
> +		u32     copyBack:1;
> +		u32     erase:1;
> +		u32     locate:1;
> +		u32     reserved:26;
> +#else
> +		u32     reserved:26;
> +		u32     locate:1;
> +		u32     erase:1;
> +		u32     copyBack:1;
> +		u32     clear:1;
> +		u32     patrol:1;
> +		u32     rbld:1;
> +#endif
> +	} active;
> +	union MR_PROGRESS     rbld;
> +	union MR_PROGRESS     patrol;
> +	union {
> +		union MR_PROGRESS     clear;
> +		union MR_PROGRESS     erase;
> +	};
> +
> +	struct {
> +#ifndef MFI_BIG_ENDIAN
> +		u32     rbld:1;
> +		u32     patrol:1;
> +		u32     clear:1;
> +		u32     copyBack:1;
> +		u32     erase:1;
> +		u32     reserved:27;
> +#else
> +		u32     reserved:27;
> +		u32     erase:1;
> +		u32     copyBack:1;
> +		u32     clear:1;
> +		u32     patrol:1;
> +		u32     rbld:1;
> +#endif
> +	} pause;
> +
> +	union MR_PROGRESS     reserved[3];
> +} __packed;
> +
> +struct  MR_PD_INFO {
> +	union MR_PD_REF	ref;
> +	u8 inquiryData[96];
> +	u8 vpdPage83[64];
> +	u8 notSupported;
> +	u8 scsiDevType;
> +
> +	union {
> +		u8 connectedPortBitmap;
> +		u8 connectedPortNumbers;
> +	};
> +
> +	u8 deviceSpeed;
> +	u32 mediaErrCount;
> +	u32 otherErrCount;
> +	u32 predFailCount;
> +	u32 lastPredFailEventSeqNum;
> +
> +	u16 fwState;
> +	u8 disabledForRemoval;
> +	u8 linkSpeed;
> +	union MR_PD_DDF_TYPE state;
> +
> +	struct {
> +		u8 count;
> +#ifndef __BIG_ENDIAN_BITFIELD
> +		u8 isPathBroken:4;
> +		u8 reserved3:3;
> +		u8 widePortCapable:1;
> +#else
> +		u8 widePortCapable:1;
> +		u8 reserved3:3;
> +		u8 isPathBroken:4;
> +#endif
> +
> +		u8 connectorIndex[2];
> +		u8 reserved[4];
> +		u64 sasAddr[2];
> +		u8 reserved2[16];
> +	} pathInfo;
> +
> +	u64 rawSize;
> +	u64 nonCoercedSize;
> +	u64 coercedSize;
> +	u16 enclDeviceId;
> +	u8 enclIndex;
> +
> +	union {
> +		u8 slotNumber;
> +		u8 enclConnectorIndex;
> +	};
> +
> +	struct MR_PD_PROGRESS progInfo;
> +	u8 badBlockTableFull;
> +	u8 unusableInCurrentConfig;
> +	u8 vpdPage83Ext[64];
> +	u8 powerState;
> +	u8 enclPosition;
> +	u32 allowedOps;
> +	u16 copyBackPartnerId;
> +	u16 enclPartnerDeviceId;
> +	struct {
> +#ifndef __BIG_ENDIAN_BITFIELD
> +		u16 fdeCapable:1;
> +		u16 fdeEnabled:1;
> +		u16 secured:1;
> +		u16 locked:1;
> +		u16 foreign:1;
> +		u16 needsEKM:1;
> +		u16 reserved:10;
> +#else
> +		u16 reserved:10;
> +		u16 needsEKM:1;
> +		u16 foreign:1;
> +		u16 locked:1;
> +		u16 secured:1;
> +		u16 fdeEnabled:1;
> +		u16 fdeCapable:1;
> +#endif
> +	} security;
> +	u8 mediaType;
> +	u8 notCertified;
> +	u8 bridgeVendor[8];
> +	u8 bridgeProductIdentification[16];
> +	u8 bridgeProductRevisionLevel[4];
> +	u8 satBridgeExists;
> +
> +	u8 interfaceType;
> +	u8 temperature;
> +	u8 emulatedBlockSize;
> +	u16 userDataBlockSize;
> +	u16 reserved2;
> +
> +	struct {
> +#ifndef __BIG_ENDIAN_BITFIELD
> +		u32 piType:3;
> +		u32 piFormatted:1;
> +		u32 piEligible:1;
> +		u32 NCQ:1;
> +		u32 WCE:1;
> +		u32 commissionedSpare:1;
> +		u32 emergencySpare:1;
> +		u32 ineligibleForSSCD:1;
> +		u32 ineligibleForLd:1;
> +		u32 useSSEraseType:1;
> +		u32 wceUnchanged:1;
> +		u32 supportScsiUnmap:1;
> +		u32 reserved:18;
> +#else
> +		u32 reserved:18;
> +		u32 supportScsiUnmap:1;
> +		u32 wceUnchanged:1;
> +		u32 useSSEraseType:1;
> +		u32 ineligibleForLd:1;
> +		u32 ineligibleForSSCD:1;
> +		u32 emergencySpare:1;
> +		u32 commissionedSpare:1;
> +		u32 WCE:1;
> +		u32 NCQ:1;
> +		u32 piEligible:1;
> +		u32 piFormatted:1;
> +		u32 piType:3;
> +#endif
> +	} properties;
> +
> +	u64 shieldDiagCompletionTime;
> +	u8 shieldCounter;
> +
> +	u8 linkSpeedOther;
> +	u8 reserved4[2];
> +
> +	struct {
> +#ifndef __BIG_ENDIAN_BITFIELD
> +		u32 bbmErrCountSupported:1;
> +		u32 bbmErrCount:31;
> +#else
> +		u32 bbmErrCount:31;
> +		u32 bbmErrCountSupported:1;
> +#endif
> +	} bbmErr;
> +
> +	u8 reserved1[512-428];
> +} __packed;
>  
>   /*
>   * defines the physical drive address structure
> @@ -474,6 +726,7 @@ struct megasas_pd_list {
>  	u16             tid;
>  	u8             driveType;
>  	u8             driveState;
> +	u8             interface;
>  } __packed;
>  
>   /*
> @@ -1718,6 +1971,19 @@ struct MR_DRV_SYSTEM_INFO {
>  	u8	reserved[1980];
>  };
>  
> +enum MR_PD_TYPE {
> +		 UNKNOWN_DRIVE = 0,
> +		 PARALLEL_SCSI = 1,
> +		 SAS_PD = 2,
> +		 SATA_PD = 3,
> +		 FC_PD = 4,
> +};
> +
> +/* JBOD Queue depth definitions */
> +#define MEGASAS_SATA_QD	32
> +#define MEGASAS_SAS_QD	64
> +#define MEGASAS_DEFAULT_PD_QD	64
> +
>  struct megasas_instance {
>  
>  	__le32 *producer;
> @@ -1732,6 +1998,8 @@ struct megasas_instance {
>  	dma_addr_t vf_affiliation_111_h;
>  	struct MR_CTRL_HB_HOST_MEM *hb_host_mem;
>  	dma_addr_t hb_host_mem_h;
> +	struct MR_PD_INFO *pd_info;
> +	dma_addr_t pd_info_h;
>  
>  	__le32 *reply_queue;
>  	dma_addr_t reply_queue_h;
> @@ -1780,7 +2048,7 @@ struct megasas_instance {
>  	struct megasas_evt_detail *evt_detail;
>  	dma_addr_t evt_detail_h;
>  	struct megasas_cmd *aen_cmd;
> -	struct mutex aen_mutex;
> +	struct mutex hba_mutex;
>  	struct semaphore ioctl_sem;
>  
>  	struct Scsi_Host *host;
> diff --git a/drivers/scsi/megaraid/megaraid_sas_base.c b/drivers/scsi/megaraid/megaraid_sas_base.c
> index c1dc23c..df93fa1 100644
> --- a/drivers/scsi/megaraid/megaraid_sas_base.c
> +++ b/drivers/scsi/megaraid/megaraid_sas_base.c
> @@ -104,6 +104,8 @@ static int megasas_ld_list_query(struct megasas_instance *instance,
>  static int megasas_issue_init_mfi(struct megasas_instance *instance);
>  static int megasas_register_aen(struct megasas_instance *instance,
>  				u32 seq_num, u32 class_locale_word);
> +static int
> +megasas_get_pd_info(struct megasas_instance *instance, u16 device_id);
>  /*
>   * PCI ID table for all supported controllers
>   */
> @@ -1796,6 +1798,44 @@ void megasas_update_sdev_properties(struct scsi_device *sdev)
>  	}
>  }
>  
> +static void megasas_set_device_queue_depth(struct scsi_device *sdev)
> +{
> +	u16				pd_index = 0;
> +	int		ret = DCMD_FAILED;
> +	struct megasas_instance *instance;
> +
> +	instance = megasas_lookup_instance(sdev->host->host_no);
> +
> +	if (sdev->channel < MEGASAS_MAX_PD_CHANNELS) {
> +		pd_index = (sdev->channel * MEGASAS_MAX_DEV_PER_CHANNEL) + sdev->id;
> +
> +		if (instance->pd_info) {
> +			mutex_lock(&instance->hba_mutex);
> +			ret = megasas_get_pd_info(instance, pd_index);
> +			mutex_unlock(&instance->hba_mutex);
> +		}
> +
> +		if (ret != DCMD_SUCCESS)
> +			return;
> +
> +		if (instance->pd_list[pd_index].driveState == MR_PD_STATE_SYSTEM) {
> +
> +			switch (instance->pd_list[pd_index].interface) {
> +			case SAS_PD:
> +				scsi_change_queue_depth(sdev, MEGASAS_SAS_QD);
> +				break;
> +
> +			case SATA_PD:
> +				scsi_change_queue_depth(sdev, MEGASAS_SATA_QD);
> +				break;
> +
> +			default:
> +				scsi_change_queue_depth(sdev, MEGASAS_DEFAULT_PD_QD);
> +			}
> +		}
> +	}
> +}
> +
>  
>  static int megasas_slave_configure(struct scsi_device *sdev)
>  {
> @@ -1813,6 +1853,7 @@ static int megasas_slave_configure(struct scsi_device *sdev)
>  				return -ENXIO;
>  		}
>  	}
> +	megasas_set_device_queue_depth(sdev);
>  	megasas_update_sdev_properties(sdev);
>  
>  	/*
> @@ -3922,6 +3963,73 @@ dcmd_timeout_ocr_possible(struct megasas_instance *instance) {
>  		return INITIATE_OCR;
>  }
>  
> +static int
> +megasas_get_pd_info(struct megasas_instance *instance, u16 device_id)
> +{
> +	int ret;
> +	struct megasas_cmd *cmd;
> +	struct megasas_dcmd_frame *dcmd;
> +
> +	cmd = megasas_get_cmd(instance);
> +
> +	if (!cmd) {
> +		dev_err(&instance->pdev->dev, "Failed to get cmd %s\n", __func__);
> +		return -ENOMEM;
> +	}
> +
> +	dcmd = &cmd->frame->dcmd;
> +
> +	memset(instance->pd_info, 0, sizeof(*instance->pd_info));
> +	memset(dcmd->mbox.b, 0, MFI_MBOX_SIZE);
> +
> +	dcmd->mbox.s[0] = cpu_to_le16(device_id);
> +	dcmd->cmd = MFI_CMD_DCMD;
> +	dcmd->cmd_status = 0xFF;
> +	dcmd->sge_count = 1;
> +	dcmd->flags = cpu_to_le16(MFI_FRAME_DIR_READ);
> +	dcmd->timeout = 0;
> +	dcmd->pad_0 = 0;
> +	dcmd->data_xfer_len = cpu_to_le32(sizeof(struct MR_PD_INFO));
> +	dcmd->opcode = cpu_to_le32(MR_DCMD_PD_GET_INFO);
> +	dcmd->sgl.sge32[0].phys_addr = cpu_to_le32(instance->pd_info_h);
> +	dcmd->sgl.sge32[0].length = cpu_to_le32(sizeof(struct MR_PD_INFO));
> +
> +	if (instance->ctrl_context && !instance->mask_interrupts)
> +		ret = megasas_issue_blocked_cmd(instance, cmd, MFI_IO_TIMEOUT_SECS);
> +	else
> +		ret = megasas_issue_polled(instance, cmd);
> +
> +	switch (ret) {
> +	case DCMD_SUCCESS:
> +		instance->pd_list[device_id].interface =
> +				instance->pd_info->state.ddf.pdType.intf;
> +		break;
> +
> +	case DCMD_TIMEOUT:
> +
> +		switch (dcmd_timeout_ocr_possible(instance)) {
> +		case INITIATE_OCR:
> +			cmd->flags |= DRV_DCMD_SKIP_REFIRE;
> +			megasas_reset_fusion(instance->host,
> +				MFI_IO_TIMEOUT_OCR);
> +			break;
> +		case KILL_ADAPTER:
> +			megaraid_sas_kill_hba(instance);
> +			break;
> +		case IGNORE_TIMEOUT:
> +			dev_info(&instance->pdev->dev, "Ignore DCMD timeout: %s %d\n",
> +				__func__, __LINE__);
> +			break;
> +		}
> +
> +		break;
> +	}
> +
> +	if (ret != DCMD_TIMEOUT)
> +		megasas_return_cmd(instance, cmd);
> +
> +	return ret;
> +}
>  /*
>   * megasas_get_pd_list_info -	Returns FW's pd_list structure
>   * @instance:				Adapter soft state
> @@ -5680,6 +5788,12 @@ static int megasas_probe_one(struct pci_dev *pdev,
>  		goto fail_alloc_dma_buf;
>  	}
>  
> +	instance->pd_info = pci_alloc_consistent(pdev,
> +		sizeof(struct MR_PD_INFO), &instance->pd_info_h);

Hi,
is it possible to use here 'dma_alloc_coherent + GFP_KERNEL' 
instead of pci_alloc_consistent with GFP_ATOMIC ?
--tm

> +
> +	if (!instance->pd_info)
> +		dev_err(&instance->pdev->dev, "Failed to alloc mem for pd_info\n");
> +
>  	/*
>  	 * Initialize locks and queues
>  	 */
> @@ -5696,6 +5810,7 @@ static int megasas_probe_one(struct pci_dev *pdev,
>  	spin_lock_init(&instance->completion_lock);
>  
>  	mutex_init(&instance->reset_mutex);
> +	mutex_init(&instance->hba_mutex);
>  
>  	/*
>  	 * Initialize PCI related and misc parameters
> @@ -5810,6 +5925,10 @@ fail_alloc_dma_buf:
>  				    instance->evt_detail,
>  				    instance->evt_detail_h);
>  
> +	if (instance->pd_info)
> +		pci_free_consistent(pdev, sizeof(struct MR_PD_INFO),
> +					instance->pd_info,
> +					instance->pd_info_h);
>  	if (instance->producer)
>  		pci_free_consistent(pdev, sizeof(u32), instance->producer,
>  				    instance->producer_h);
> @@ -6071,6 +6190,10 @@ fail_init_mfi:
>  				instance->evt_detail,
>  				instance->evt_detail_h);
>  
> +	if (instance->pd_info)
> +		pci_free_consistent(pdev, sizeof(struct MR_PD_INFO),
> +					instance->pd_info,
> +					instance->pd_info_h);
>  	if (instance->producer)
>  		pci_free_consistent(pdev, sizeof(u32), instance->producer,
>  				instance->producer_h);
> @@ -6189,6 +6312,10 @@ static void megasas_detach_one(struct pci_dev *pdev)
>  		pci_free_consistent(pdev, sizeof(struct megasas_evt_detail),
>  				instance->evt_detail, instance->evt_detail_h);
>  
> +	if (instance->pd_info)
> +		pci_free_consistent(pdev, sizeof(struct MR_PD_INFO),
> +					instance->pd_info,
> +					instance->pd_info_h);
>  	if (instance->vf_affiliation)
>  		pci_free_consistent(pdev, (MAX_LOGICAL_DRIVES + 1) *
>  				    sizeof(struct MR_LD_VF_AFFILIATION),

--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html



[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Index of Archives]     [SCSI Target Devel]     [Linux SCSI Target Infrastructure]     [Kernel Newbies]     [IDE]     [Security]     [Git]     [Netfilter]     [Bugtraq]     [Yosemite News]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Linux RAID]     [Linux ATA RAID]     [Linux IIO]     [Samba]     [Device Mapper]
  Powered by Linux