Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

io_uring/waitid: use io_waitid_remove_wq() consistently

Use it everywhere that the wait_queue_entry is removed from the head,
and be a bit more cautious in zeroing out iw->head whenever the entry is
removed from the list.

Signed-off-by: Jens Axboe <axboe@kernel.dk>

+11 -4
+11 -4
io_uring/waitid.c
··· 179 179 static inline bool io_waitid_drop_issue_ref(struct io_kiocb *req) 180 180 { 181 181 struct io_waitid *iw = io_kiocb_to_cmd(req, struct io_waitid); 182 - struct io_waitid_async *iwa = req->async_data; 183 182 184 183 if (!atomic_sub_return(1, &iw->refs)) 185 184 return false; 185 + 186 + io_waitid_remove_wq(req); 186 187 187 188 /* 188 189 * Wakeup triggered, racing with us. It was prevented from ··· 191 190 */ 192 191 req->io_task_work.func = io_waitid_cb; 193 192 io_req_task_work_add(req); 194 - remove_wait_queue(iw->head, &iwa->wo.child_wait); 195 193 return true; 196 194 } 197 195 ··· 245 245 return 0; 246 246 247 247 list_del_init(&wait->entry); 248 + iw->head = NULL; 248 249 249 250 /* cancel is in progress */ 250 251 if (atomic_fetch_inc(&iw->refs) & IO_WAITID_REF_MASK) ··· 272 271 iw->which = READ_ONCE(sqe->len); 273 272 iw->upid = READ_ONCE(sqe->fd); 274 273 iw->options = READ_ONCE(sqe->file_index); 274 + iw->head = NULL; 275 275 iw->infop = u64_to_user_ptr(READ_ONCE(sqe->addr2)); 276 276 return 0; 277 277 } ··· 303 301 * callback. 304 302 */ 305 303 io_ring_submit_lock(ctx, issue_flags); 304 + 305 + /* 306 + * iw->head is valid under the ring lock, and as long as the request 307 + * is on the waitid_list where cancelations may find it. 308 + */ 309 + iw->head = &current->signal->wait_chldexit; 306 310 hlist_add_head(&req->hash_node, &ctx->waitid_list); 307 311 308 312 init_waitqueue_func_entry(&iwa->wo.child_wait, io_waitid_wait); 309 313 iwa->wo.child_wait.private = req->tctx->task; 310 - iw->head = &current->signal->wait_chldexit; 311 314 add_wait_queue(iw->head, &iwa->wo.child_wait); 312 315 313 316 ret = __do_wait(&iwa->wo); ··· 335 328 } 336 329 337 330 hlist_del_init(&req->hash_node); 338 - remove_wait_queue(iw->head, &iwa->wo.child_wait); 331 + io_waitid_remove_wq(req); 339 332 ret = io_waitid_finish(req, ret); 340 333 341 334 io_ring_submit_unlock(ctx, issue_flags);