Skip to content

Commit 90611bb

Browse files
committed
Merge branch 'for-6.15/io_uring' into for-6.15/io_uring-epoll-wait
* for-6.15/io_uring: (30 commits) io_uring: use lockless_cq flag in io_req_complete_post() io_uring: pass struct io_tw_state by value io_uring: introduce type alias for io_tw_state io_uring/rsrc: avoid NULL check in io_put_rsrc_node() io_uring: pass ctx instead of req to io_init_req_drain() io_uring: use IO_REQ_LINK_FLAGS more io_uring/net: improve recv bundles io_uring/waitid: use generic io_cancel_remove() helper io_uring/futex: use generic io_cancel_remove() helper io_uring/cancel: add generic cancel helper io_uring/waitid: convert to io_cancel_remove_all() io_uring/futex: convert to io_cancel_remove_all() io_uring/cancel: add generic remove_all helper io_uring/kbuf: uninline __io_put_kbufs io_uring/kbuf: introduce io_kbuf_drop_legacy() io_uring/kbuf: open code __io_put_kbuf() io_uring/kbuf: remove legacy kbuf caching io_uring/kbuf: simplify __io_put_kbuf io_uring/kbuf: move locking into io_kbuf_drop() io_uring/kbuf: remove legacy kbuf kmem cache ...
2 parents 87a132e + 62aa980 commit 90611bb

File tree

22 files changed

+440
-493
lines changed

22 files changed

+440
-493
lines changed

include/linux/io_uring_types.h

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -360,7 +360,6 @@ struct io_ring_ctx {
360360

361361
spinlock_t completion_lock;
362362

363-
struct list_head io_buffers_comp;
364363
struct list_head cq_overflow_list;
365364

366365
struct hlist_head waitid_list;
@@ -379,8 +378,6 @@ struct io_ring_ctx {
379378
unsigned int file_alloc_start;
380379
unsigned int file_alloc_end;
381380

382-
struct list_head io_buffers_cache;
383-
384381
/* Keep this last, we don't need it for the fast path */
385382
struct wait_queue_head poll_wq;
386383
struct io_restriction restrictions;
@@ -439,8 +436,15 @@ struct io_ring_ctx {
439436
struct io_mapped_region param_region;
440437
};
441438

439+
/*
440+
* Token indicating function is called in task work context:
441+
* ctx->uring_lock is held and any completions generated will be flushed.
442+
* ONLY core io_uring.c should instantiate this struct.
443+
*/
442444
struct io_tw_state {
443445
};
446+
/* Alias to use in code that doesn't instantiate struct io_tw_state */
447+
typedef struct io_tw_state io_tw_token_t;
444448

445449
enum {
446450
REQ_F_FIXED_FILE_BIT = IOSQE_FIXED_FILE_BIT,
@@ -566,7 +570,7 @@ enum {
566570
REQ_F_HAS_METADATA = IO_REQ_FLAG(REQ_F_HAS_METADATA_BIT),
567571
};
568572

569-
typedef void (*io_req_tw_func_t)(struct io_kiocb *req, struct io_tw_state *ts);
573+
typedef void (*io_req_tw_func_t)(struct io_kiocb *req, io_tw_token_t tw);
570574

571575
struct io_task_work {
572576
struct llist_node node;

io_uring/cancel.c

Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -341,3 +341,45 @@ int io_sync_cancel(struct io_ring_ctx *ctx, void __user *arg)
341341
fput(file);
342342
return ret;
343343
}
344+
345+
bool io_cancel_remove_all(struct io_ring_ctx *ctx, struct io_uring_task *tctx,
346+
struct hlist_head *list, bool cancel_all,
347+
bool (*cancel)(struct io_kiocb *))
348+
{
349+
struct hlist_node *tmp;
350+
struct io_kiocb *req;
351+
bool found = false;
352+
353+
lockdep_assert_held(&ctx->uring_lock);
354+
355+
hlist_for_each_entry_safe(req, tmp, list, hash_node) {
356+
if (!io_match_task_safe(req, tctx, cancel_all))
357+
continue;
358+
hlist_del_init(&req->hash_node);
359+
if (cancel(req))
360+
found = true;
361+
}
362+
363+
return found;
364+
}
365+
366+
int io_cancel_remove(struct io_ring_ctx *ctx, struct io_cancel_data *cd,
367+
unsigned int issue_flags, struct hlist_head *list,
368+
bool (*cancel)(struct io_kiocb *))
369+
{
370+
struct hlist_node *tmp;
371+
struct io_kiocb *req;
372+
int nr = 0;
373+
374+
io_ring_submit_lock(ctx, issue_flags);
375+
hlist_for_each_entry_safe(req, tmp, list, hash_node) {
376+
if (!io_cancel_req_match(req, cd))
377+
continue;
378+
if (cancel(req))
379+
nr++;
380+
if (!(cd->flags & IORING_ASYNC_CANCEL_ALL))
381+
break;
382+
}
383+
io_ring_submit_unlock(ctx, issue_flags);
384+
return nr ?: -ENOENT;
385+
}

io_uring/cancel.h

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,14 @@ int io_try_cancel(struct io_uring_task *tctx, struct io_cancel_data *cd,
2424
int io_sync_cancel(struct io_ring_ctx *ctx, void __user *arg);
2525
bool io_cancel_req_match(struct io_kiocb *req, struct io_cancel_data *cd);
2626

27+
bool io_cancel_remove_all(struct io_ring_ctx *ctx, struct io_uring_task *tctx,
28+
struct hlist_head *list, bool cancel_all,
29+
bool (*cancel)(struct io_kiocb *));
30+
31+
int io_cancel_remove(struct io_ring_ctx *ctx, struct io_cancel_data *cd,
32+
unsigned int issue_flags, struct hlist_head *list,
33+
bool (*cancel)(struct io_kiocb *));
34+
2735
static inline bool io_cancel_match_sequence(struct io_kiocb *req, int sequence)
2836
{
2937
if (req->cancel_seq_set && sequence == req->work.cancel_seq)

io_uring/futex.c

Lines changed: 11 additions & 47 deletions
Original file line numberDiff line numberDiff line change
@@ -44,30 +44,30 @@ void io_futex_cache_free(struct io_ring_ctx *ctx)
4444
io_alloc_cache_free(&ctx->futex_cache, kfree);
4545
}
4646

47-
static void __io_futex_complete(struct io_kiocb *req, struct io_tw_state *ts)
47+
static void __io_futex_complete(struct io_kiocb *req, io_tw_token_t tw)
4848
{
4949
req->async_data = NULL;
5050
hlist_del_init(&req->hash_node);
51-
io_req_task_complete(req, ts);
51+
io_req_task_complete(req, tw);
5252
}
5353

54-
static void io_futex_complete(struct io_kiocb *req, struct io_tw_state *ts)
54+
static void io_futex_complete(struct io_kiocb *req, io_tw_token_t tw)
5555
{
5656
struct io_futex_data *ifd = req->async_data;
5757
struct io_ring_ctx *ctx = req->ctx;
5858

59-
io_tw_lock(ctx, ts);
59+
io_tw_lock(ctx, tw);
6060
if (!io_alloc_cache_put(&ctx->futex_cache, ifd))
6161
kfree(ifd);
62-
__io_futex_complete(req, ts);
62+
__io_futex_complete(req, tw);
6363
}
6464

65-
static void io_futexv_complete(struct io_kiocb *req, struct io_tw_state *ts)
65+
static void io_futexv_complete(struct io_kiocb *req, io_tw_token_t tw)
6666
{
6767
struct io_futex *iof = io_kiocb_to_cmd(req, struct io_futex);
6868
struct futex_vector *futexv = req->async_data;
6969

70-
io_tw_lock(req->ctx, ts);
70+
io_tw_lock(req->ctx, tw);
7171

7272
if (!iof->futexv_unqueued) {
7373
int res;
@@ -79,7 +79,7 @@ static void io_futexv_complete(struct io_kiocb *req, struct io_tw_state *ts)
7979

8080
kfree(req->async_data);
8181
req->flags &= ~REQ_F_ASYNC_DATA;
82-
__io_futex_complete(req, ts);
82+
__io_futex_complete(req, tw);
8383
}
8484

8585
static bool io_futexv_claim(struct io_futex *iof)
@@ -90,7 +90,7 @@ static bool io_futexv_claim(struct io_futex *iof)
9090
return true;
9191
}
9292

93-
static bool __io_futex_cancel(struct io_ring_ctx *ctx, struct io_kiocb *req)
93+
static bool __io_futex_cancel(struct io_kiocb *req)
9494
{
9595
/* futex wake already done or in progress */
9696
if (req->opcode == IORING_OP_FUTEX_WAIT) {
@@ -116,49 +116,13 @@ static bool __io_futex_cancel(struct io_ring_ctx *ctx, struct io_kiocb *req)
116116
int io_futex_cancel(struct io_ring_ctx *ctx, struct io_cancel_data *cd,
117117
unsigned int issue_flags)
118118
{
119-
struct hlist_node *tmp;
120-
struct io_kiocb *req;
121-
int nr = 0;
122-
123-
if (cd->flags & (IORING_ASYNC_CANCEL_FD|IORING_ASYNC_CANCEL_FD_FIXED))
124-
return -ENOENT;
125-
126-
io_ring_submit_lock(ctx, issue_flags);
127-
hlist_for_each_entry_safe(req, tmp, &ctx->futex_list, hash_node) {
128-
if (req->cqe.user_data != cd->data &&
129-
!(cd->flags & IORING_ASYNC_CANCEL_ANY))
130-
continue;
131-
if (__io_futex_cancel(ctx, req))
132-
nr++;
133-
if (!(cd->flags & IORING_ASYNC_CANCEL_ALL))
134-
break;
135-
}
136-
io_ring_submit_unlock(ctx, issue_flags);
137-
138-
if (nr)
139-
return nr;
140-
141-
return -ENOENT;
119+
return io_cancel_remove(ctx, cd, issue_flags, &ctx->futex_list, __io_futex_cancel);
142120
}
143121

144122
bool io_futex_remove_all(struct io_ring_ctx *ctx, struct io_uring_task *tctx,
145123
bool cancel_all)
146124
{
147-
struct hlist_node *tmp;
148-
struct io_kiocb *req;
149-
bool found = false;
150-
151-
lockdep_assert_held(&ctx->uring_lock);
152-
153-
hlist_for_each_entry_safe(req, tmp, &ctx->futex_list, hash_node) {
154-
if (!io_match_task_safe(req, tctx, cancel_all))
155-
continue;
156-
hlist_del_init(&req->hash_node);
157-
__io_futex_cancel(ctx, req);
158-
found = true;
159-
}
160-
161-
return found;
125+
return io_cancel_remove_all(ctx, tctx, &ctx->futex_list, cancel_all, __io_futex_cancel);
162126
}
163127

164128
int io_futex_prep(struct io_kiocb *req, const struct io_uring_sqe *sqe)

0 commit comments

Comments
 (0)