* Problem about sq->khead update and ring full judgement
@ 2023-11-02 18:43 Ferry Meng
2023-11-02 19:13 ` Gabriel Krisman Bertazi
0 siblings, 1 reply; 2+ messages in thread
From: Ferry Meng @ 2023-11-02 18:43 UTC (permalink / raw)
To: io-uring, axboe; +Cc: joseph.qi
Hi all:
I'm using io_uring in a program, with SQPOLL feature enabled. The
userspace program will actively count the queue status of urings, the
programming model is similar to:
{
sqe = io_uring_get_sqe();
if(sqe){
/* prepare next request */
queue_count++;
}
{
cqe = io_uring_peek_cqe();
if(cqe){
queue_count--;
}
}
In this way, maybe we can assume that " sq_ring_size - queue_count
= sqe_left_we_can_alloc "?
Userspace program will compare queue_count with io_uring's sq_size
: if queue is not full ( queue_count < sq_size), it will try getting new
sqe(means Initiating a new IO request).
Now I'm currently coming into a situation where I/O is very high
—— Userspace program submit lots of sqes (around 2000) at the same time,
meanwhile sq_ring_size is 4096. In kernel,
__io_sq_thread->io_submit_sqes(), I see that nr(to_submit) is also over
2000. At a point, a strange point comes out: Userspace program find
sq_ring is not full, but Kernel(in fact liburing::io_uring_get_sqe)
think sq_ring is full.
After analyzing, I find the reason is: kernel update "sq->khead"
after submitting "all" sqes. The running of my program is : Before
kernel update khead, userspace program has received many cqes, causing
queue_count-- . After decreasing queue_count, user-program thinks
sq_ring is not full, and try to start new IO requeust. As sq->head is
not updated, io_uring_get_sqe() returns NULL.
My questions are:
1. Is userspace 'queue_count' judgement reasonable? From
'traditional' point of view, if we want to find sq_ring full or not, we
can just use io_uring_get_sqe() to check. Maybe this discussion is
similar to this issue in a way: https://github.com/axboe/liburing/issues/88
2. I must confess that it's very strange that cqe's average
receiving latency is shorter than the consumption time of sqe(Now it
really happens and I'm trying to find why this happened, or it's a just
some bug). Assuming this scenario is reasonable, it seems that we can
update sq->khead more often to get higher throughput. When userspace
gets more 'sensetive', it can send out more IO requests. And it won't
cause much more overhead if kernel atomically update 'khead'
a-little-bit more.
^ permalink raw reply [flat|nested] 2+ messages in thread
* Re: Problem about sq->khead update and ring full judgement
2023-11-02 18:43 Problem about sq->khead update and ring full judgement Ferry Meng
@ 2023-11-02 19:13 ` Gabriel Krisman Bertazi
0 siblings, 0 replies; 2+ messages in thread
From: Gabriel Krisman Bertazi @ 2023-11-02 19:13 UTC (permalink / raw)
To: Ferry Meng; +Cc: io-uring, axboe, joseph.qi
Ferry Meng <[email protected]> writes:
> Hi all:
> I'm using io_uring in a program, with SQPOLL feature enabled. The
> userspace program will actively count the queue status of urings, the
> programming model is similar to:
> {
> sqe = io_uring_get_sqe();
> if(sqe){
> /* prepare next request */
> queue_count++;
> }
>
>
> {
> cqe = io_uring_peek_cqe();
> if(cqe){
> queue_count--;
> }
> }
>
> In this way, maybe we can assume that " sq_ring_size - queue_count =
> sqe_left_we_can_alloc "?
> Now I'm currently coming into a situation where I/O is very high ——
> Userspace program submit lots of sqes (around 2000) at the same time,
> meanwhile sq_ring_size is 4096. In kernel,
> __io_sq_thread->io_submit_sqes(), I see that nr(to_submit) is also over
> 2000. At a point, a strange point comes out: Userspace program find
> sq_ring is not full, but Kernel(in fact liburing::io_uring_get_sqe)
> think sq_ring is full.
>
> After analyzing, I find the reason is: kernel update "sq->khead"
> after submitting "all" sqes. The running of my program is : Before
> kernel update khead, userspace program has received many cqes, causing
> queue_count-- . After decreasing queue_count, user-program thinks
> sq_ring is not full, and try to start new IO requeust. As sq->head is
> not updated, io_uring_get_sqe() returns NULL.
>
> My questions are:
>
> 1. Is userspace 'queue_count' judgement reasonable? From
> 'traditional' point of view, if we want to find sq_ring full or not, we
> can just use io_uring_get_sqe() to check
Not really. IIUC, you cannot rely on the number of CQEs to account for
submission queue space. The SQE is consumed and the SQ pointer advanced
before the request is completed, so you can have more inflight than SQ
entry space. Maybe what you want is io_uring_sq_space_left(3)?
--
Gabriel Krisman Bertazi
^ permalink raw reply [flat|nested] 2+ messages in thread
end of thread, other threads:[~2023-11-02 19:14 UTC | newest]
Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2023-11-02 18:43 Problem about sq->khead update and ring full judgement Ferry Meng
2023-11-02 19:13 ` Gabriel Krisman Bertazi
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox