lkml.org 
[lkml]   [2018]   [Mar]   [3]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    From
    Subject[PATCH AUTOSEL for 4.4 078/115] scsi: sg: check for valid direction before starting the request
    Date
    From: Johannes Thumshirn <jthumshirn@suse.de>

    [ Upstream commit 28676d869bbb5257b5f14c0c95ad3af3a7019dd5 ]

    Check for a valid direction before starting the request, otherwise we
    risk running into an assertion in the scsi midlayer checking for valid
    requests.

    [mkp: fixed typo]

    Signed-off-by: Johannes Thumshirn <jthumshirn@suse.de>
    Link: http://www.spinics.net/lists/linux-scsi/msg104400.html
    Reported-by: Dmitry Vyukov <dvyukov@google.com>
    Signed-off-by: Hannes Reinecke <hare@suse.com>
    Tested-by: Johannes Thumshirn <jthumshirn@suse.de>
    Reviewed-by: Christoph Hellwig <hch@lst.de>
    Signed-off-by: Martin K. Petersen <martin.petersen@oracle.com>
    Signed-off-by: Sasha Levin <alexander.levin@microsoft.com>
    ---
    drivers/scsi/sg.c | 46 ++++++++++++++++++++++++++++++++++------------
    1 file changed, 34 insertions(+), 12 deletions(-)

    diff --git a/drivers/scsi/sg.c b/drivers/scsi/sg.c
    index 0f0ff75755e0..27f92f4ea6bc 100644
    --- a/drivers/scsi/sg.c
    +++ b/drivers/scsi/sg.c
    @@ -674,18 +674,14 @@ sg_write(struct file *filp, const char __user *buf, size_t count, loff_t * ppos)
    * is a non-zero input_size, so emit a warning.
    */
    if (hp->dxfer_direction == SG_DXFER_TO_FROM_DEV) {
    - static char cmd[TASK_COMM_LEN];
    - if (strcmp(current->comm, cmd)) {
    - printk_ratelimited(KERN_WARNING
    - "sg_write: data in/out %d/%d bytes "
    - "for SCSI command 0x%x-- guessing "
    - "data in;\n program %s not setting "
    - "count and/or reply_len properly\n",
    - old_hdr.reply_len - (int)SZ_SG_HEADER,
    - input_size, (unsigned int) cmnd[0],
    - current->comm);
    - strcpy(cmd, current->comm);
    - }
    + printk_ratelimited(KERN_WARNING
    + "sg_write: data in/out %d/%d bytes "
    + "for SCSI command 0x%x-- guessing "
    + "data in;\n program %s not setting "
    + "count and/or reply_len properly\n",
    + old_hdr.reply_len - (int)SZ_SG_HEADER,
    + input_size, (unsigned int) cmnd[0],
    + current->comm);
    }
    k = sg_common_write(sfp, srp, cmnd, sfp->timeout, blocking);
    return (k < 0) ? k : count;
    @@ -764,6 +760,29 @@ sg_new_write(Sg_fd *sfp, struct file *file, const char __user *buf,
    return count;
    }

    +static bool sg_is_valid_dxfer(sg_io_hdr_t *hp)
    +{
    + switch (hp->dxfer_direction) {
    + case SG_DXFER_NONE:
    + if (hp->dxferp || hp->dxfer_len > 0)
    + return false;
    + return true;
    + case SG_DXFER_TO_DEV:
    + case SG_DXFER_FROM_DEV:
    + case SG_DXFER_TO_FROM_DEV:
    + if (!hp->dxferp || hp->dxfer_len == 0)
    + return false;
    + return true;
    + case SG_DXFER_UNKNOWN:
    + if ((!hp->dxferp && hp->dxfer_len) ||
    + (hp->dxferp && hp->dxfer_len == 0))
    + return false;
    + return true;
    + default:
    + return false;
    + }
    +}
    +
    static int
    sg_common_write(Sg_fd * sfp, Sg_request * srp,
    unsigned char *cmnd, int timeout, int blocking)
    @@ -784,6 +803,9 @@ sg_common_write(Sg_fd * sfp, Sg_request * srp,
    "sg_common_write: scsi opcode=0x%02x, cmd_size=%d\n",
    (int) cmnd[0], (int) hp->cmd_len));

    + if (!sg_is_valid_dxfer(hp))
    + return -EINVAL;
    +
    k = sg_start_req(srp, cmnd);
    if (k) {
    SCSI_LOG_TIMEOUT(1, sg_printk(KERN_INFO, sfp->parentdp,
    --
    2.14.1
    \
     
     \ /
      Last update: 2018-03-04 00:03    [W:2.981 / U:0.024 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site