diff options
author | Jens Axboe <axboe@kernel.dk> | 2021-12-04 15:55:31 -0700 |
---|---|---|
committer | Jens Axboe <axboe@kernel.dk> | 2021-12-04 15:57:30 -0700 |
commit | d84c29b19ed0b130000619cff40141bb1fc3615b (patch) | |
tree | bf06ba54eda6552068899225d790d18678a39289 | |
parent | a49427fbbe0a2b25cefd77d9a78df2b7d96d661f (diff) | |
download | liburing-d84c29b19ed0b130000619cff40141bb1fc3615b.tar.gz liburing-d84c29b19ed0b130000619cff40141bb1fc3615b.tar.bz2 |
Don't truncate addr fields to 32-bit on 32-bit
For the commands where we use it as a lookup key, then we don't want to
rob 32-bit applications from the potential of using the full 64-bit
type. This includes commands like:
poll_remove, poll_update, prep_cancel
Also provide 64-bit u64 types of the sqe set data and the cqe get data
helpers, along with a define that allows applications to check for the
presence of it.
NOTE: this may trigger compile warnings in applications that
currently use these helpers, which is also why a few test cases had
to get adapted. The fixup is trivial, and the above define can help
applications check if one or the other is the current one.
Link: https://github.com/axboe/liburing/issues/490
Reported-by: Rémi Bernon <rbernon@codeweavers.com>
Signed-off-by: Jens Axboe <axboe@kernel.dk>
-rw-r--r-- | src/include/liburing.h | 47 | ||||
-rw-r--r-- | test/accept.c | 2 | ||||
-rw-r--r-- | test/io-cancel.c | 6 | ||||
-rw-r--r-- | test/multicqes_drain.c | 2 | ||||
-rw-r--r-- | test/poll-cancel-ton.c | 2 | ||||
-rw-r--r-- | test/poll-cancel.c | 2 | ||||
-rw-r--r-- | test/poll-mshot-update.c | 6 |
7 files changed, 48 insertions, 19 deletions
diff --git a/src/include/liburing.h b/src/include/liburing.h index 230cd61..3705c5b 100644 --- a/src/include/liburing.h +++ b/src/include/liburing.h @@ -219,6 +219,11 @@ static inline void io_uring_cqe_seen(struct io_uring *ring, /* * Command prep helpers */ + +/* + * Associate pointer @data with the sqe, for later retrieval from the cqe + * at command completion time with io_uring_cqe_get_data(). + */ static inline void io_uring_sqe_set_data(struct io_uring_sqe *sqe, void *data) { sqe->user_data = (unsigned long) data; @@ -229,6 +234,27 @@ static inline void *io_uring_cqe_get_data(const struct io_uring_cqe *cqe) return (void *) (uintptr_t) cqe->user_data; } +/* + * Assign a 64-bit value to this sqe, which can get retrieved at completion + * time with io_uring_cqe_get_data64. Just like the non-64 variants, except + * these store a 64-bit type rather than a data pointer. + */ +static inline void io_uring_sqe_set_data64(struct io_uring_sqe *sqe, + __u64 data) +{ + sqe->user_data = data; +} + +static inline __u64 io_uring_cqe_get_data64(const struct io_uring_cqe *cqe) +{ + return cqe->user_data; +} + +/* + * Tell the app the have the 64-bit variants of the get/set userdata + */ +#define LIBURING_HAVE_DATA64 + static inline void io_uring_sqe_set_flags(struct io_uring_sqe *sqe, unsigned flags) { @@ -387,18 +413,20 @@ static inline void io_uring_prep_poll_multishot(struct io_uring_sqe *sqe, } static inline void io_uring_prep_poll_remove(struct io_uring_sqe *sqe, - void *user_data) + __u64 user_data) { - io_uring_prep_rw(IORING_OP_POLL_REMOVE, sqe, -1, user_data, 0, 0); + io_uring_prep_rw(IORING_OP_POLL_REMOVE, sqe, -1, NULL, 0, 0); + sqe->addr = user_data; } static inline void io_uring_prep_poll_update(struct io_uring_sqe *sqe, - void *old_user_data, - void *new_user_data, + __u64 old_user_data, + __u64 new_user_data, unsigned poll_mask, unsigned flags) { - io_uring_prep_rw(IORING_OP_POLL_REMOVE, sqe, -1, old_user_data, flags, - (__u64)(uintptr_t)new_user_data); + io_uring_prep_rw(IORING_OP_POLL_REMOVE, sqe, -1, NULL, flags, + new_user_data); + sqe->addr = old_user_data; sqe->poll32_events = __io_uring_prep_poll_mask(poll_mask); } @@ -459,10 +487,11 @@ static inline void io_uring_prep_accept_direct(struct io_uring_sqe *sqe, int fd, __io_uring_set_target_fixed_file(sqe, file_index); } -static inline void io_uring_prep_cancel(struct io_uring_sqe *sqe, void *user_data, - int flags) +static inline void io_uring_prep_cancel(struct io_uring_sqe *sqe, + __u64 user_data, int flags) { - io_uring_prep_rw(IORING_OP_ASYNC_CANCEL, sqe, -1, user_data, 0, 0); + io_uring_prep_rw(IORING_OP_ASYNC_CANCEL, sqe, -1, NULL, 0, 0); + sqe->addr = user_data; sqe->cancel_flags = (__u32) flags; } diff --git a/test/accept.c b/test/accept.c index a4fc677..af2997f 100644 --- a/test/accept.c +++ b/test/accept.c @@ -329,7 +329,7 @@ static int test_accept_cancel(unsigned usecs) usleep(usecs); sqe = io_uring_get_sqe(&m_io_uring); - io_uring_prep_cancel(sqe, (void *) 1, 0); + io_uring_prep_cancel(sqe, 1, 0); sqe->user_data = 2; ret = io_uring_submit(&m_io_uring); assert(ret == 1); diff --git a/test/io-cancel.c b/test/io-cancel.c index 703ffa7..c1df0df 100644 --- a/test/io-cancel.c +++ b/test/io-cancel.c @@ -128,7 +128,7 @@ static int start_cancel(struct io_uring *ring, int do_partial, int async_cancel) fprintf(stderr, "sqe get failed\n"); goto err; } - io_uring_prep_cancel(sqe, (void *) (unsigned long) i + 1, 0); + io_uring_prep_cancel(sqe, i + 1, 0); if (async_cancel) sqe->flags |= IOSQE_ASYNC; sqe->user_data = 0; @@ -246,7 +246,7 @@ static int test_dont_cancel_another_ring(void) fprintf(stderr, "%s: failed to get sqe\n", __FUNCTION__); return 1; } - io_uring_prep_cancel(sqe, (void *) (unsigned long)1, 0); + io_uring_prep_cancel(sqe, 1, 0); sqe->user_data = 2; ret = io_uring_submit(&ring2); @@ -326,7 +326,7 @@ static int test_cancel_req_across_fork(void) fprintf(stderr, "%s: failed to get sqe\n", __FUNCTION__); return 1; } - io_uring_prep_cancel(sqe, (void *) (unsigned long)1, 0); + io_uring_prep_cancel(sqe, 1, 0); sqe->user_data = 2; ret = io_uring_submit(&ring); diff --git a/test/multicqes_drain.c b/test/multicqes_drain.c index b107a48..148cdd7 100644 --- a/test/multicqes_drain.c +++ b/test/multicqes_drain.c @@ -91,7 +91,7 @@ void io_uring_sqe_prep(int op, struct io_uring_sqe *sqe, unsigned sqe_flags, int io_uring_prep_nop(sqe); break; case cancel: - io_uring_prep_poll_remove(sqe, (void *)(long)arg); + io_uring_prep_poll_remove(sqe, arg); break; } sqe->flags = sqe_flags; diff --git a/test/poll-cancel-ton.c b/test/poll-cancel-ton.c index f0875cd..05bf565 100644 --- a/test/poll-cancel-ton.c +++ b/test/poll-cancel-ton.c @@ -55,7 +55,7 @@ static int del_polls(struct io_uring *ring, int fd, int nr) sqe = io_uring_get_sqe(ring); data = sqe_index[lrand48() % nr]; - io_uring_prep_poll_remove(sqe, data); + io_uring_prep_poll_remove(sqe, (__u64)(uintptr_t)data); } ret = io_uring_submit(ring); diff --git a/test/poll-cancel.c b/test/poll-cancel.c index 408159d..6bddc6c 100644 --- a/test/poll-cancel.c +++ b/test/poll-cancel.c @@ -79,7 +79,7 @@ static int test_poll_cancel(void) pds[1].is_poll = 0; pds[1].is_cancel = 1; - io_uring_prep_poll_remove(sqe, &pds[0]); + io_uring_prep_poll_remove(sqe, (__u64)(uintptr_t)&pds[0]); io_uring_sqe_set_data(sqe, &pds[1]); ret = io_uring_submit(&ring); diff --git a/test/poll-mshot-update.c b/test/poll-mshot-update.c index 75ee52f..d06699a 100644 --- a/test/poll-mshot-update.c +++ b/test/poll-mshot-update.c @@ -42,7 +42,7 @@ static int has_poll_update(void) return -1; sqe = io_uring_get_sqe(&ring); - io_uring_prep_poll_update(sqe, NULL, NULL, POLLIN, IORING_TIMEOUT_UPDATE); + io_uring_prep_poll_update(sqe, 0, 0, POLLIN, IORING_TIMEOUT_UPDATE); ret = io_uring_submit(&ring); if (ret != 1) @@ -86,8 +86,8 @@ static int reap_polls(struct io_uring *ring) sqe = io_uring_get_sqe(ring); /* update event */ - io_uring_prep_poll_update(sqe, (void *)(unsigned long)i, NULL, - POLLIN, IORING_POLL_UPDATE_EVENTS); + io_uring_prep_poll_update(sqe, i, 0, POLLIN, + IORING_POLL_UPDATE_EVENTS); sqe->user_data = 0x12345678; } |