RE: [PATCH] SCSI:STORVSC Use SCSI layer to allocate memory for per-command device request data

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

 




> -----Original Message-----
> From: Christoph Hellwig [mailto:hch@xxxxxx]
> Sent: Monday, December 29, 2014 8:05 PM
> To: KY Srinivasan; Haiyang Zhang; JBottomley@xxxxxxxxxxxxx
> Cc: linux-scsi@xxxxxxxxxxxxxxx; devel@xxxxxxxxxxxxxxxxxxxxxx; linux-
> kernel@xxxxxxxxxxxxxxx; Long Li; Christoph Hellwig
> Subject: [PATCH] SCSI:STORVSC Use SCSI layer to allocate memory for per-
> command device request data
> 
> STORVSC uses its own momory pool to manage device request data.
> However, SCSI layer already has a mechanisim for allocating additional
> memory for each command issued to device driver. This patch removes the
> memory pool in STORVSC and makes it use SCSI layer to allocate memory for
> device request data.
> 
> Reviewed-by: Long Li <longli@xxxxxxxxxxxxx>
> Signed-off-by: Christoph Hellwig <hch@xxxxxx>

Thanks Christoph.
Signed-off-by: K. Y. Srinivasan <kys@xxxxxxxxxxxxx>

> ---
>  drivers/scsi/storvsc_drv.c | 119 +++------------------------------------------
>  1 file changed, 8 insertions(+), 111 deletions(-)
> 
> diff --git a/drivers/scsi/storvsc_drv.c b/drivers/scsi/storvsc_drv.c index
> 4cff0dd..14ee98e 100644
> --- a/drivers/scsi/storvsc_drv.c
> +++ b/drivers/scsi/storvsc_drv.c
> @@ -32,7 +32,6 @@
>  #include <linux/module.h>
>  #include <linux/device.h>
>  #include <linux/hyperv.h>
> -#include <linux/mempool.h>
>  #include <linux/blkdev.h>
>  #include <scsi/scsi.h>
>  #include <scsi/scsi_cmnd.h>
> @@ -309,14 +308,6 @@ enum storvsc_request_type {
>   * This is the end of Protocol specific defines.
>   */
> 
> -
> -/*
> - * We setup a mempool to allocate request structures for this driver
> - * on a per-lun basis. The following define specifies the number of
> - * elements in the pool.
> - */
> -
> -#define STORVSC_MIN_BUF_NR				64
>  static int storvsc_ringbuffer_size = (20 * PAGE_SIZE);
> 
>  module_param(storvsc_ringbuffer_size, int, S_IRUGO); @@ -346,7 +337,6
> @@ static void storvsc_on_channel_callback(void *context);
>  #define STORVSC_IDE_MAX_CHANNELS			1
> 
>  struct storvsc_cmd_request {
> -	struct list_head entry;
>  	struct scsi_cmnd *cmd;
> 
>  	unsigned int bounce_sgl_count;
> @@ -357,7 +347,6 @@ struct storvsc_cmd_request {
>  	/* Synchronize the request/response if needed */
>  	struct completion wait_event;
> 
> -	unsigned char *sense_buffer;
>  	struct hv_multipage_buffer data_buffer;
>  	struct vstor_packet vstor_packet;
>  };
> @@ -389,11 +378,6 @@ struct storvsc_device {
>  	struct storvsc_cmd_request reset_request;  };
> 
> -struct stor_mem_pools {
> -	struct kmem_cache *request_pool;
> -	mempool_t *request_mempool;
> -};
> -
>  struct hv_host_device {
>  	struct hv_device *dev;
>  	unsigned int port;
> @@ -1070,10 +1054,8 @@ static void storvsc_command_completion(struct
> storvsc_cmd_request *cmd_request)  {
>  	struct scsi_cmnd *scmnd = cmd_request->cmd;
>  	struct hv_host_device *host_dev = shost_priv(scmnd->device-
> >host);
> -	void (*scsi_done_fn)(struct scsi_cmnd *);
>  	struct scsi_sense_hdr sense_hdr;
>  	struct vmscsi_request *vm_srb;
> -	struct stor_mem_pools *memp = scmnd->device->hostdata;
>  	struct Scsi_Host *host;
>  	struct storvsc_device *stor_dev;
>  	struct hv_device *dev = host_dev->dev; @@ -1109,14 +1091,7 @@
> static void storvsc_command_completion(struct storvsc_cmd_request
> *cmd_request)
>  		cmd_request->data_buffer.len -
>  		vm_srb->data_transfer_length);
> 
> -	scsi_done_fn = scmnd->scsi_done;
> -
> -	scmnd->host_scribble = NULL;
> -	scmnd->scsi_done = NULL;
> -
> -	scsi_done_fn(scmnd);
> -
> -	mempool_free(cmd_request, memp->request_mempool);
> +	scmnd->scsi_done(scmnd);
>  }
> 
>  static void storvsc_on_io_completion(struct hv_device *device, @@ -1160,7
> +1135,7 @@ static void storvsc_on_io_completion(struct hv_device *device,
>  			SRB_STATUS_AUTOSENSE_VALID) {
>  			/* autosense data available */
> 
> -			memcpy(request->sense_buffer,
> +			memcpy(request->cmd->sense_buffer,
>  			       vstor_packet->vm_srb.sense_data,
>  			       vstor_packet->vm_srb.sense_info_length);
> 
> @@ -1378,55 +1353,6 @@ static int storvsc_do_io(struct hv_device *device,
>  	return ret;
>  }
> 
> -static int storvsc_device_alloc(struct scsi_device *sdevice) -{
> -	struct stor_mem_pools *memp;
> -	int number = STORVSC_MIN_BUF_NR;
> -
> -	memp = kzalloc(sizeof(struct stor_mem_pools), GFP_KERNEL);
> -	if (!memp)
> -		return -ENOMEM;
> -
> -	memp->request_pool =
> -		kmem_cache_create(dev_name(&sdevice->sdev_dev),
> -				sizeof(struct storvsc_cmd_request), 0,
> -				SLAB_HWCACHE_ALIGN, NULL);
> -
> -	if (!memp->request_pool)
> -		goto err0;
> -
> -	memp->request_mempool = mempool_create(number,
> mempool_alloc_slab,
> -						mempool_free_slab,
> -						memp->request_pool);
> -
> -	if (!memp->request_mempool)
> -		goto err1;
> -
> -	sdevice->hostdata = memp;
> -
> -	return 0;
> -
> -err1:
> -	kmem_cache_destroy(memp->request_pool);
> -
> -err0:
> -	kfree(memp);
> -	return -ENOMEM;
> -}
> -
> -static void storvsc_device_destroy(struct scsi_device *sdevice) -{
> -	struct stor_mem_pools *memp = sdevice->hostdata;
> -
> -	if (!memp)
> -		return;
> -
> -	mempool_destroy(memp->request_mempool);
> -	kmem_cache_destroy(memp->request_pool);
> -	kfree(memp);
> -	sdevice->hostdata = NULL;
> -}
> -
>  static int storvsc_device_configure(struct scsi_device *sdevice)  {
>  	scsi_change_queue_depth(sdevice, STORVSC_MAX_IO_REQUESTS);
> @@ -1561,13 +1487,11 @@ static int storvsc_queuecommand(struct
> Scsi_Host *host, struct scsi_cmnd *scmnd)
>  	int ret;
>  	struct hv_host_device *host_dev = shost_priv(host);
>  	struct hv_device *dev = host_dev->dev;
> -	struct storvsc_cmd_request *cmd_request;
> -	unsigned int request_size = 0;
> +	struct storvsc_cmd_request *cmd_request = scsi_cmd_priv(scmnd);
>  	int i;
>  	struct scatterlist *sgl;
>  	unsigned int sg_count = 0;
>  	struct vmscsi_request *vm_srb;
> -	struct stor_mem_pools *memp = scmnd->device->hostdata;
> 
>  	if (vmstor_current_major <= VMSTOR_WIN8_MAJOR) {
>  		/*
> @@ -1584,25 +1508,9 @@ static int storvsc_queuecommand(struct Scsi_Host
> *host, struct scsi_cmnd *scmnd)
>  		}
>  	}
> 
> -	request_size = sizeof(struct storvsc_cmd_request);
> -
> -	cmd_request = mempool_alloc(memp->request_mempool,
> -				       GFP_ATOMIC);
> -
> -	/*
> -	 * We might be invoked in an interrupt context; hence
> -	 * mempool_alloc() can fail.
> -	 */
> -	if (!cmd_request)
> -		return SCSI_MLQUEUE_DEVICE_BUSY;
> -
> -	memset(cmd_request, 0, sizeof(struct storvsc_cmd_request));
> -
>  	/* Setup the cmd request */
>  	cmd_request->cmd = scmnd;
> 
> -	scmnd->host_scribble = (unsigned char *)cmd_request;
> -
>  	vm_srb = &cmd_request->vstor_packet.vm_srb;
>  	vm_srb->win8_extension.time_out_value = 60;
> 
> @@ -1637,9 +1545,6 @@ static int storvsc_queuecommand(struct Scsi_Host
> *host, struct scsi_cmnd *scmnd)
> 
>  	memcpy(vm_srb->cdb, scmnd->cmnd, vm_srb->cdb_length);
> 
> -	cmd_request->sense_buffer = scmnd->sense_buffer;
> -
> -
>  	cmd_request->data_buffer.len = scsi_bufflen(scmnd);
>  	if (scsi_sg_count(scmnd)) {
>  		sgl = (struct scatterlist *)scsi_sglist(scmnd); @@ -1651,10
> +1556,8 @@ static int storvsc_queuecommand(struct Scsi_Host *host, struct
> scsi_cmnd *scmnd)
>  				create_bounce_buffer(sgl,
> scsi_sg_count(scmnd),
>  						     scsi_bufflen(scmnd),
>  						     vm_srb->data_in);
> -			if (!cmd_request->bounce_sgl) {
> -				ret = SCSI_MLQUEUE_HOST_BUSY;
> -				goto queue_error;
> -			}
> +			if (!cmd_request->bounce_sgl)
> +				return SCSI_MLQUEUE_HOST_BUSY;
> 
>  			cmd_request->bounce_sgl_count =
>  				ALIGN(scsi_bufflen(scmnd), PAGE_SIZE) >>
> @@ -1692,27 +1595,21 @@ static int storvsc_queuecommand(struct
> Scsi_Host *host, struct scsi_cmnd *scmnd)
>  			destroy_bounce_buffer(cmd_request->bounce_sgl,
>  					cmd_request->bounce_sgl_count);
> 
> -		ret = SCSI_MLQUEUE_DEVICE_BUSY;
> -		goto queue_error;
> +		return SCSI_MLQUEUE_DEVICE_BUSY;
>  	}
> 
>  	return 0;
> -
> -queue_error:
> -	mempool_free(cmd_request, memp->request_mempool);
> -	scmnd->host_scribble = NULL;
> -	return ret;
>  }
> 
>  static struct scsi_host_template scsi_driver = {
>  	.module	=		THIS_MODULE,
>  	.name =			"storvsc_host_t",
> +	.cmd_size =             sizeof(struct storvsc_cmd_request),
>  	.bios_param =		storvsc_get_chs,
>  	.queuecommand =		storvsc_queuecommand,
>  	.eh_host_reset_handler =	storvsc_host_reset_handler,
> +	.proc_name =		"storvsc_host",
>  	.eh_timed_out =		storvsc_eh_timed_out,
> -	.slave_alloc =		storvsc_device_alloc,
> -	.slave_destroy =	storvsc_device_destroy,
>  	.slave_configure =	storvsc_device_configure,
>  	.cmd_per_lun =		255,
>  	.can_queue =
> 	STORVSC_MAX_IO_REQUESTS*STORVSC_MAX_TARGETS,
> --
> 2.1.0

_______________________________________________
devel mailing list
devel@xxxxxxxxxxxxxxxxxxxxxx
http://driverdev.linuxdriverproject.org/mailman/listinfo/driverdev-devel



[Index of Archives]     [Linux Driver Backports]     [DMA Engine]     [Linux GPIO]     [Linux SPI]     [Video for Linux]     [Linux USB Devel]     [Linux Coverity]     [Linux Audio Users]     [Linux Kernel]     [Linux SCSI]     [Yosemite Backpacking]
  Powered by Linux