Hello community, here is the log from the commit of package vhba-kmp for openSUSE:Factory checked in at 2019-07-04 15:43:32 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Comparing /work/SRC/openSUSE:Factory/vhba-kmp (Old) and /work/SRC/openSUSE:Factory/.vhba-kmp.new.4615 (New) ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "vhba-kmp" Thu Jul 4 15:43:32 2019 rev:16 rq:713218 version:20190410 Changes: -------- --- /work/SRC/openSUSE:Factory/vhba-kmp/vhba-kmp.changes 2019-06-01 09:51:06.315291399 +0200 +++ /work/SRC/openSUSE:Factory/.vhba-kmp.new.4615/vhba-kmp.changes 2019-07-04 15:43:32.754134936 +0200 @@ -1,0 +2,8 @@ +Mon Jul 1 13:45:02 UTC 2019 - Aaron Stern <ukbeas...@ptotonmail.com> + +-Update to new upstream release 20190410 + * Fixes crash when mounting disk image on linux 5.1 + * Remove vhba-scsiapi.diff, as upstream builds with linux 5.1 + + +------------------------------------------------------------------- Old: ---- vhba-module-20170610.tar.bz2 vhba-scsiapi.diff New: ---- vhba-module-20190410.tar.bz2 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Other differences: ------------------ ++++++ vhba-kmp.spec ++++++ --- /var/tmp/diff_new_pack.WTjluk/_old 2019-07-04 15:43:33.526136141 +0200 +++ /var/tmp/diff_new_pack.WTjluk/_new 2019-07-04 15:43:33.530136147 +0200 @@ -17,7 +17,7 @@ Name: vhba-kmp -Version: 20170610 +Version: 20190410 Release: 0 Summary: Virtual SCSI Host Bus Adapter License: GPL-2.0-or-later @@ -29,7 +29,6 @@ Source2: %name-preamble Patch1: vhba-no-werror.diff Patch2: vhba-devname.diff -Patch3: vhba-scsiapi.diff BuildRequires: kernel-syms >= 2.6.20 BuildRequires: modutils BuildRoot: %{_tmppath}/%{name}-%{version}-build ++++++ vhba-module-20170610.tar.bz2 -> vhba-module-20190410.tar.bz2 ++++++ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/vhba-module-20170610/Makefile new/vhba-module-20190410/Makefile --- old/vhba-module-20170610/Makefile 2017-06-10 23:29:17.000000000 +0200 +++ new/vhba-module-20190410/Makefile 2019-04-11 13:30:43.000000000 +0200 @@ -1,4 +1,4 @@ -VHBA_VERSION := 20170610 +VHBA_VERSION := 20190302 KERNELRELEASE ?= $(shell uname -r) KDIR ?= /lib/modules/$(KERNELRELEASE)/build diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/vhba-module-20170610/debian/changelog new/vhba-module-20190410/debian/changelog --- old/vhba-module-20170610/debian/changelog 2017-06-10 23:29:17.000000000 +0200 +++ new/vhba-module-20190410/debian/changelog 2019-04-11 13:30:43.000000000 +0200 @@ -1,3 +1,3 @@ -vhba-module (20170610-1) debian; urgency=low +vhba-module (20190302-1) debian; urgency=low * Initial Release. Closes: #705409 -- Henrik Stokseth <hstok...@users.sourceforge.net> Sat, 05 Apr 2014 12:00:00 +0100 diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/vhba-module-20170610/vhba.c new/vhba-module-20190410/vhba.c --- old/vhba-module-20170610/vhba.c 2017-06-10 23:29:17.000000000 +0200 +++ new/vhba-module-20190410/vhba.c 2019-04-11 13:30:43.000000000 +0200 @@ -74,6 +74,7 @@ #define VHBA_MAX_ID 32 #define VHBA_CAN_QUEUE 32 #define VHBA_INVALID_ID VHBA_MAX_ID +#define VHBA_KBUF_SIZE PAGE_SIZE #define DATA_TO_DEVICE(dir) ((dir) == DMA_TO_DEVICE || (dir) == DMA_BIDIRECTIONAL) #define DATA_FROM_DEVICE(dir) ((dir) == DMA_FROM_DEVICE || (dir) == DMA_BIDIRECTIONAL) @@ -108,6 +109,7 @@ struct vhba_command { struct scsi_cmnd *cmd; + unsigned long serial_number; int status; struct list_head entry; }; @@ -118,6 +120,11 @@ struct list_head cmd_list; wait_queue_head_t cmd_wq; atomic_t refcnt; + + unsigned char *kbuf; + size_t kbuf_size; + + unsigned long cmd_count; }; struct vhba_host { @@ -169,6 +176,11 @@ init_waitqueue_head(&vdev->cmd_wq); atomic_set(&vdev->refcnt, 1); + vdev->kbuf = NULL; + vdev->kbuf_size = 0; + + vdev->cmd_count = 0; + return vdev; } @@ -199,6 +211,7 @@ vcmd->cmd = cmd; spin_lock_irqsave(&vdev->cmd_lock, flags); + vcmd->serial_number = vdev->cmd_count++; list_add_tail(&vcmd->entry, &vdev->cmd_list); spin_unlock_irqrestore(&vdev->cmd_lock, flags); @@ -445,7 +458,7 @@ struct vhba_device *vdev; int retval; - scmd_dbg(cmd, "queue %lu\n", cmd->serial_number); + scmd_dbg(cmd, "queue %p\n", cmd); vdev = vhba_lookup_device(cmd->device->id); if (!vdev) { @@ -476,7 +489,7 @@ struct vhba_device *vdev; int retval = SUCCESS; - scmd_warn(cmd, "abort %lu\n", cmd->serial_number); + scmd_warn(cmd, "abort %p\n", cmd); vdev = vhba_lookup_device(cmd->device->id); if (vdev) { @@ -500,15 +513,18 @@ .cmd_per_lun = 1, .max_sectors = VHBA_MAX_SECTORS_PER_IO, .sg_tablesize = 256, +#if LINUX_VERSION_CODE >= KERNEL_VERSION(5, 0, 0) + .max_segment_size = VHBA_KBUF_SIZE, +#endif }; -static ssize_t do_request (struct scsi_cmnd *cmd, char __user *buf, size_t buf_len) +static ssize_t do_request (struct vhba_device *vdev, unsigned long cmd_serial_number, struct scsi_cmnd *cmd, char __user *buf, size_t buf_len) { struct vhba_request vreq; ssize_t ret; - scmd_dbg(cmd, "request %lu, cdb 0x%x, bufflen %d, use_sg %d\n", - cmd->serial_number, cmd->cmnd[0], scsi_bufflen(cmd), scsi_sg_count(cmd)); + scmd_dbg(cmd, "request %lu (%p), cdb 0x%x, bufflen %d, use_sg %d\n", + cmd_serial_number, cmd, cmd->cmnd[0], scsi_bufflen(cmd), scsi_sg_count(cmd)); ret = sizeof(vreq); if (DATA_TO_DEVICE(cmd->sc_data_direction)) { @@ -520,7 +536,7 @@ return -EIO; } - vreq.tag = cmd->serial_number; + vreq.tag = cmd_serial_number; vreq.lun = cmd->device->lun; memcpy(vreq.cdb, cmd->cmnd, MAX_COMMAND_SIZE); vreq.cdb_len = cmd->cmd_len; @@ -534,42 +550,33 @@ buf += sizeof(vreq); if (scsi_sg_count(cmd)) { - unsigned char buf_stack[64]; - unsigned char *kaddr, *uaddr, *kbuf; + unsigned char *kaddr, *uaddr; struct scatterlist *sg = scsi_sglist(cmd); int i; uaddr = (unsigned char *) buf; - if (vreq.data_len > 64) { - kbuf = kmalloc(PAGE_SIZE, GFP_KERNEL); - } else { - kbuf = buf_stack; - } - for (i = 0; i < scsi_sg_count(cmd); i++) { size_t len = sg[i].length; + if (len > vdev->kbuf_size) { + scmd_warn(cmd, "segment size (%zu) exceeds kbuf size (%zu)!", len, vdev->kbuf_size); + len = vdev->kbuf_size; + } + #ifdef USE_SG_PAGE kaddr = vhba_kmap_atomic(sg_page(&sg[i])); #else kaddr = vhba_kmap_atomic(sg[i].page); #endif - memcpy(kbuf, kaddr + sg[i].offset, len); + memcpy(vdev->kbuf, kaddr + sg[i].offset, len); vhba_kunmap_atomic(kaddr); - if (copy_to_user(uaddr, kbuf, len)) { - if (kbuf != buf_stack) { - kfree(kbuf); - } + if (copy_to_user(uaddr, vdev->kbuf, len)) { return -EFAULT; } uaddr += len; } - - if (kbuf != buf_stack) { - kfree(kbuf); - } } else { if (copy_to_user(buf, scsi_sglist(cmd), vreq.data_len)) { return -EFAULT; @@ -580,12 +587,12 @@ return ret; } -static ssize_t do_response (struct scsi_cmnd *cmd, const char __user *buf, size_t buf_len, struct vhba_response *res) +static ssize_t do_response (struct vhba_device *vdev, unsigned long cmd_serial_number, struct scsi_cmnd *cmd, const char __user *buf, size_t buf_len, struct vhba_response *res) { ssize_t ret = 0; - scmd_dbg(cmd, "response %lu, status %x, data len %d, use_sg %d\n", - cmd->serial_number, res->status, res->data_len, scsi_sg_count(cmd)); + scmd_dbg(cmd, "response %lu (%p), status %x, data len %d, use_sg %d\n", + cmd_serial_number, cmd, res->status, res->data_len, scsi_sg_count(cmd)); if (res->status) { unsigned char sense_stack[SCSI_SENSE_BUFFERSIZE]; @@ -616,26 +623,21 @@ to_read = res->data_len; if (scsi_sg_count(cmd)) { - unsigned char buf_stack[64]; - unsigned char *kaddr, *uaddr, *kbuf; + unsigned char *kaddr, *uaddr; struct scatterlist *sg = scsi_sglist(cmd); int i; uaddr = (unsigned char *)buf; - if (res->data_len > 64) { - kbuf = kmalloc(PAGE_SIZE, GFP_KERNEL); - } else { - kbuf = buf_stack; - } - for (i = 0; i < scsi_sg_count(cmd); i++) { size_t len = (sg[i].length < to_read) ? sg[i].length : to_read; - if (copy_from_user(kbuf, uaddr, len)) { - if (kbuf != buf_stack) { - kfree(kbuf); - } + if (len > vdev->kbuf_size) { + scmd_warn(cmd, "segment size (%zu) exceeds kbuf size (%zu)!", len, vdev->kbuf_size); + len = vdev->kbuf_size; + } + + if (copy_from_user(vdev->kbuf, uaddr, len)) { return -EFAULT; } uaddr += len; @@ -645,7 +647,7 @@ #else kaddr = vhba_kmap_atomic(sg[i].page); #endif - memcpy(kaddr + sg[i].offset, kbuf, len); + memcpy(kaddr + sg[i].offset, vdev->kbuf, len); vhba_kunmap_atomic(kaddr); to_read -= len; @@ -653,10 +655,6 @@ break; } } - - if (kbuf != buf_stack) { - kfree(kbuf); - } } else { if (copy_from_user(scsi_sglist(cmd), buf, res->data_len)) { return -EFAULT; @@ -695,7 +693,7 @@ struct vhba_command *vcmd; list_for_each_entry(vcmd, &vdev->cmd_list, entry) { - if (vcmd->cmd->serial_number == tag) { + if (vcmd->serial_number == tag) { break; } } @@ -764,7 +762,7 @@ } } - ret = do_request(vcmd->cmd, buf, buf_len); + ret = do_request(vdev, vcmd->serial_number, vcmd->cmd, buf, buf_len); spin_lock_irqsave(&vdev->cmd_lock, flags); if (ret >= 0) { @@ -807,7 +805,7 @@ vcmd->status = VHBA_REQ_WRITING; spin_unlock_irqrestore(&vdev->cmd_lock, flags); - ret = do_response(vcmd->cmd, buf + sizeof(res), buf_len - sizeof(res), &res); + ret = do_response(vdev, vcmd->serial_number, vcmd->cmd, buf + sizeof(res), buf_len - sizeof(res), &res); spin_lock_irqsave(&vdev->cmd_lock, flags); if (ret >= 0) { @@ -905,6 +903,12 @@ return -ENOMEM; } + vdev->kbuf_size = VHBA_KBUF_SIZE; + vdev->kbuf = kmalloc(vdev->kbuf_size, GFP_KERNEL); + if (!vdev->kbuf) { + return -ENOMEM; + } + if (!(retval = vhba_add_device(vdev))) { file->private_data = vdev; } @@ -931,7 +935,7 @@ list_for_each_entry(vcmd, &vdev->cmd_list, entry) { WARN_ON(vcmd->status == VHBA_REQ_READING || vcmd->status == VHBA_REQ_WRITING); - scmd_warn(vcmd->cmd, "device released with command %lu\n", vcmd->cmd->serial_number); + scmd_warn(vcmd->cmd, "device released with command %lu (%p)\n", vcmd->serial_number, vcmd->cmd); vcmd->cmd->result = DID_NO_CONNECT << 16; vcmd->cmd->scsi_done(vcmd->cmd); @@ -940,6 +944,9 @@ INIT_LIST_HEAD(&vdev->cmd_list); spin_unlock_irqrestore(&vdev->cmd_lock, flags); + kfree(vdev->kbuf); + vdev->kbuf = NULL; + vhba_device_put(vdev); return 0;