diff options
author | Tomas Winkler <tomas.winkler@intel.com> | 2015-02-10 11:39:36 +0300 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@linuxfoundation.org> | 2015-03-02 06:36:59 +0300 |
commit | 3d33ff2457355a9dd3c3178b04ab6669882b306c (patch) | |
tree | 692168d2c6df72783349246c879995212d3f7dd3 /drivers/misc/mei/main.c | |
parent | 3908be6f9aa5517bc717f8ffdaaafd89a1b78471 (diff) | |
download | linux-3d33ff2457355a9dd3c3178b04ab6669882b306c.tar.xz |
mei: fix device reset on mei_cl_irq_read_msg allocation failure
On memory allocation failure mei_cl_irq_read_msg will
return with error that will cause device reset.
Instead we should propagate error to caller and
just clean the read queues.
Signed-off-by: Tomas Winkler <tomas.winkler@intel.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
Diffstat (limited to 'drivers/misc/mei/main.c')
-rw-r--r-- | drivers/misc/mei/main.c | 17 |
1 files changed, 13 insertions, 4 deletions
diff --git a/drivers/misc/mei/main.c b/drivers/misc/mei/main.c index 3c019c0e60eb..cbdbf4af2bf7 100644 --- a/drivers/misc/mei/main.c +++ b/drivers/misc/mei/main.c @@ -192,8 +192,8 @@ static ssize_t mei_read(struct file *file, char __user *ubuf, goto out; } - if (cl->read_cb) { - cb = cl->read_cb; + cb = cl->read_cb; + if (cb) { /* read what left */ if (cb->buf_idx > *offset) goto copy_buffer; @@ -218,7 +218,8 @@ static ssize_t mei_read(struct file *file, char __user *ubuf, } if (MEI_READ_COMPLETE != cl->reading_state && - !waitqueue_active(&cl->rx_wait)) { + !waitqueue_active(&cl->rx_wait)) { + if (file->f_flags & O_NONBLOCK) { rets = -EAGAIN; goto out; @@ -248,12 +249,20 @@ static ssize_t mei_read(struct file *file, char __user *ubuf, rets = -ENODEV; goto out; } + if (cl->reading_state != MEI_READ_COMPLETE) { rets = 0; goto out; } - /* now copy the data to user space */ + copy_buffer: + /* now copy the data to user space */ + if (cb->status) { + rets = cb->status; + dev_dbg(dev->dev, "read operation failed %d\n", rets); + goto free; + } + dev_dbg(dev->dev, "buf.size = %d buf.idx= %ld\n", cb->response_buffer.size, cb->buf_idx); if (length == 0 || ubuf == NULL || *offset > cb->buf_idx) { |