Skip to content

Commit c1dd91d

Browse files
committed
io_uring: add comments on how the async buffered read retry works
The retry based logic here isn't easy to follow unless you're already familiar with how io_uring does task_work based retries. Add some comments explaining the flow a little better. Suggested-by: Linus Torvalds <[email protected]> Signed-off-by: Jens Axboe <[email protected]>
1 parent cbd287c commit c1dd91d

File tree

1 file changed

+22
-1
lines changed

1 file changed

+22
-1
lines changed

fs/io_uring.c

Lines changed: 22 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2952,6 +2952,16 @@ static int io_read_prep(struct io_kiocb *req, const struct io_uring_sqe *sqe,
29522952
return io_rw_prep_async(req, READ, force_nonblock);
29532953
}
29542954

2955+
/*
2956+
* This is our waitqueue callback handler, registered through lock_page_async()
2957+
* when we initially tried to do the IO with the iocb armed our waitqueue.
2958+
* This gets called when the page is unlocked, and we generally expect that to
2959+
* happen when the page IO is completed and the page is now uptodate. This will
2960+
* queue a task_work based retry of the operation, attempting to copy the data
2961+
* again. If the latter fails because the page was NOT uptodate, then we will
2962+
* do a thread based blocking retry of the operation. That's the unexpected
2963+
* slow path.
2964+
*/
29552965
static int io_async_buf_func(struct wait_queue_entry *wait, unsigned mode,
29562966
int sync, void *arg)
29572967
{
@@ -3004,7 +3014,18 @@ static inline int kiocb_wait_page_queue_init(struct kiocb *kiocb,
30043014
return -EOPNOTSUPP;
30053015
}
30063016

3007-
3017+
/*
3018+
* This controls whether a given IO request should be armed for async page
3019+
* based retry. If we return false here, the request is handed to the async
3020+
* worker threads for retry. If we're doing buffered reads on a regular file,
3021+
* we prepare a private wait_page_queue entry and retry the operation. This
3022+
* will either succeed because the page is now uptodate and unlocked, or it
3023+
* will register a callback when the page is unlocked at IO completion. Through
3024+
* that callback, io_uring uses task_work to setup a retry of the operation.
3025+
* That retry will attempt the buffered read again. The retry will generally
3026+
* succeed, or in rare cases where it fails, we then fall back to using the
3027+
* async worker threads for a blocking retry.
3028+
*/
30083029
static bool io_rw_should_retry(struct io_kiocb *req)
30093030
{
30103031
struct kiocb *kiocb = &req->rw.kiocb;

0 commit comments

Comments
 (0)