aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJens Axboe <axboe@kernel.dk>2020-09-02 09:30:31 -0600
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>2020-09-09 19:14:32 +0200
commitbf8fe7b755c2ccdf8fd739ad71dd0d035588511a (patch)
tree9a60235e263297a6f86caacd52c96eb79b4e084e
parenta8bf40a7538fbc9652457506fc3e5ca5c3228732 (diff)
downloadlinux-yocto-bf8fe7b755c2ccdf8fd739ad71dd0d035588511a.tar.gz
linux-yocto-bf8fe7b755c2ccdf8fd739ad71dd0d035588511a.tar.bz2
linux-yocto-bf8fe7b755c2ccdf8fd739ad71dd0d035588511a.zip
io_uring: no read/write-retry on -EAGAIN error and O_NONBLOCK marked file
commit 355afaeb578abac907217c256a844cfafb0337b2 upstream. Actually two things that need fixing up here: - The io_rw_reissue() -EAGAIN retry is explicit to block devices and regular files, so don't ever attempt to do that on other types of files. - If we hit -EAGAIN on a nonblock marked file, don't arm poll handler for it. It should just complete with -EAGAIN. Cc: stable@vger.kernel.org Reported-by: Norman Maurer <norman.maurer@googlemail.com> Signed-off-by: Jens Axboe <axboe@kernel.dk> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
-rw-r--r--fs/io_uring.c13
1 files changed, 13 insertions, 0 deletions
diff --git a/fs/io_uring.c b/fs/io_uring.c
index 467c4f3dca1d..38f3ec15ba3b 100644
--- a/fs/io_uring.c
+++ b/fs/io_uring.c
@@ -2697,8 +2697,15 @@ static int io_read(struct io_kiocb *req, bool force_nonblock)
else
ret2 = -EINVAL;
+ /* no retry on NONBLOCK marked file */
+ if (ret2 == -EAGAIN && (req->file->f_flags & O_NONBLOCK)) {
+ ret = 0;
+ goto done;
+ }
+
/* Catch -EAGAIN return for forced non-blocking submission */
if (!force_nonblock || ret2 != -EAGAIN) {
+ done:
kiocb_done(kiocb, ret2);
} else {
copy_iov:
@@ -2823,7 +2830,13 @@ static int io_write(struct io_kiocb *req, bool force_nonblock)
*/
if (ret2 == -EOPNOTSUPP && (kiocb->ki_flags & IOCB_NOWAIT))
ret2 = -EAGAIN;
+ /* no retry on NONBLOCK marked file */
+ if (ret2 == -EAGAIN && (req->file->f_flags & O_NONBLOCK)) {
+ ret = 0;
+ goto done;
+ }
if (!force_nonblock || ret2 != -EAGAIN) {
+done:
kiocb_done(kiocb, ret2);
} else {
copy_iov: