mirror of
https://github.com/storytold/effectcraft.git
synced 2026-10-30 04:57:54 -06:00
Scripts: socket tests wait for the buffers to stay full on macOS
`backpressure` stopped writing at the first WouldBlock. On macOS the accepted stream does not keep the listener's 4 KiB receive buffer (it gets about 114 KiB), so that WouldBlock only meant the 4 KiB send buffer was full; it drained into the peer, and the 64 KiB write in a_write_to_a_peer_that_stops_reading_fails_after_the_timeout and a_blocked_socket_doesnt_hold_up_the_others_and_close_interrupts_it then succeeded instead of blocking. Both tests failed on every run. The helper now stops only after writes have stayed blocked for 200 ms, still within its 16 MiB and 5 s limits. The socket code is unchanged.
This commit is contained in:
@@ -394,19 +394,33 @@ mod tests {
|
||||
|
||||
/// Fill bounded socket buffers nonblocking, rather than assuming a 64 MiB write stalls.
|
||||
/// In particular, Windows may accept that entire write with its default send buffering.
|
||||
/// Writes must stay blocked for [`SETTLED`] before the buffers count as full: on macOS the
|
||||
/// accepted stream does not keep the listener's 4 KiB receive buffer (it gets about 114 KiB),
|
||||
/// so the first `WouldBlock` only means the 4 KiB send buffer is full, and the send buffer then
|
||||
/// drains into the peer's larger receive buffer.
|
||||
fn backpressure(id: u32) {
|
||||
const SETTLED: Duration = Duration::from_millis(200);
|
||||
let mut stream = super::imp::test_stream(id);
|
||||
socket2::SockRef::from(&stream).set_send_buffer_size(4096).unwrap();
|
||||
stream.set_nonblocking(true).unwrap();
|
||||
let start = Instant::now();
|
||||
let chunk = [b'x'; 4096];
|
||||
let mut sent = 0;
|
||||
let mut blocked_since = None;
|
||||
loop {
|
||||
assert!(sent < 16 * 1024 * 1024 && start.elapsed() < Duration::from_secs(5), "could not establish backpressure");
|
||||
match stream.write(&chunk) {
|
||||
Ok(0) => panic!("peer closed while establishing backpressure"),
|
||||
Ok(n) => sent += n,
|
||||
Err(e) if e.kind() == ErrorKind::WouldBlock => break,
|
||||
Ok(n) => {
|
||||
sent += n;
|
||||
blocked_since = None;
|
||||
}
|
||||
Err(e) if e.kind() == ErrorKind::WouldBlock => {
|
||||
if blocked_since.get_or_insert_with(Instant::now).elapsed() >= SETTLED {
|
||||
break;
|
||||
}
|
||||
std::thread::sleep(Duration::from_millis(5));
|
||||
}
|
||||
Err(e) if e.kind() == ErrorKind::Interrupted => continue,
|
||||
Err(e) => panic!("establishing backpressure: {e}"),
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user