crossbeam icon indicating copy to clipboard operation
crossbeam copied to clipboard

Support faster send/recv by not notifying the other side

Open ryoqun opened this issue 2 years ago • 4 comments

(this is a draft)

Introduce a new send variant called (send_buffered()), which doesn't notify receivers to avoid syscalls/context switches at the cost of increased latency.

sometimes, it's not desirable to incur the potential futex wake syscall cost for each and every message send.

as far as i can tell, there is no way to do like this in the current api:

// sender thread
// some tight looping
loop {
    ...
    let task = ...;
    if !needs_flush {
        sender.send_buffered(Frame::Payload(task)).unwrap();
    } else {
        sender.send(Frame::Flush).unwrap();
    }
}

// receiver thread
loop {
    // receiver.try_recv() and std::thread::sleep() can't be used
    // because we want Flush to be handled immediately.
    while let Ok(msg) = receier.recv_timeout(Duration::from_millis(20)) {
      ...
    }
}

naming

I haven't decided yet.. considering .recv(), {try_,}send_{timeout_,}unnotified()/{try_,}recv_{timeout_,}unnotified() might be better.

ryoqun avatar Nov 25 '23 07:11 ryoqun

Thanks for the PR! I think it's actually less-syscall, not syscall-free, but this could be more efficient when sending multiple messages continuously. However, we would need a clear caveat in the documentation about the footgun: misuse of this will block the receiver forever.

As for the name, I think unnotified is clearer.

taiki-e avatar Nov 29 '23 02:11 taiki-e

@taiki-e really thanks for the initial feedback!

Thanks for the PR! I think it's actually less-syscall, not syscall-free, but this could be more efficient when sending multiple messages continuously.

thanks for understanding of the use case.

However, we would need a clear caveat in the documentation about the footgun: misuse of this will block the receiver forever.

agreed. added doc comments what that in mind.

As for the name, I think unnotified is clearer.

agreed with this too.

so, I've refreshed this pr with full coverage of all send methods for the unnotified variant and finished writing doc comments, also ci should be passing.

i have a few questions:

  • is it okay to add these bunch of _unnotified methods naively? i mean, as you can see, the diff is already daunting... ;) Or, some other api is desired instead like builder api or a generic one like send_with_options().
  • recv methods should be added for the unnotified variant as well before this pr can be merged for the sake of completeness?
  • also what about select!?

lastly, I'm planning to write some unit tests once the direction of this pr is good.

last and not least, really thanks for reviewing this pr. I'll try to be very responsive in coming days. my work is blocked on this and other open prs at crossbeam.. so, I'd like them to be shipped asap... :)

ryoqun avatar Nov 30 '23 07:11 ryoqun

send_silent might be a good name for this.

ibraheemdev avatar Feb 29 '24 06:02 ibraheemdev