[WebSocket] Ensure TCP_NODELAY is always set

Almost all WebSocket implementations (including all major browsers)
disable Nagle's algorithm to favor low latency over packet overhead.

This was also the case in Godot 3.x, while in Godot 4.0 this was only
being done for clients and wasn't even always working due to a bug.

This commit fixes the aforementioned bug, and forces TCP_NODELAY when
accepting a stream as a server.
This commit is contained in:
Fabio Alessandrelli 2024-07-22 14:02:05 +02:00
parent e25f3c0d38
commit d65e7aab76
2 changed files with 3 additions and 2 deletions

View file

@ -139,7 +139,7 @@
<return type="void" /> <return type="void" />
<param index="0" name="enabled" type="bool" /> <param index="0" name="enabled" type="bool" />
<description> <description>
Disable Nagle's algorithm on the underling TCP socket (default). See [method StreamPeerTCP.set_no_delay] for more information. Disable Nagle's algorithm on the underlying TCP socket (default). See [method StreamPeerTCP.set_no_delay] for more information.
[b]Note:[/b] Not available in the Web export. [b]Note:[/b] Not available in the Web export.
</description> </description>
</method> </method>

View file

@ -99,7 +99,6 @@ void WSLPeer::Resolver::try_next_candidate(Ref<StreamPeerTCP> &p_tcp) {
p_tcp->poll(); p_tcp->poll();
StreamPeerTCP::Status status = p_tcp->get_status(); StreamPeerTCP::Status status = p_tcp->get_status();
if (status == StreamPeerTCP::STATUS_CONNECTED) { if (status == StreamPeerTCP::STATUS_CONNECTED) {
p_tcp->set_no_delay(true);
ip_candidates.clear(); ip_candidates.clear();
return; return;
} else if (status == StreamPeerTCP::STATUS_CONNECTING) { } else if (status == StreamPeerTCP::STATUS_CONNECTING) {
@ -113,6 +112,7 @@ void WSLPeer::Resolver::try_next_candidate(Ref<StreamPeerTCP> &p_tcp) {
while (ip_candidates.size()) { while (ip_candidates.size()) {
Error err = p_tcp->connect_to_host(ip_candidates.pop_front(), port); Error err = p_tcp->connect_to_host(ip_candidates.pop_front(), port);
if (err == OK) { if (err == OK) {
p_tcp->set_no_delay(true);
return; return;
} else { } else {
p_tcp->disconnect_from_host(); p_tcp->disconnect_from_host();
@ -142,6 +142,7 @@ Error WSLPeer::accept_stream(Ref<StreamPeer> p_stream) {
} }
ERR_FAIL_COND_V(connection.is_null() || tcp.is_null(), ERR_INVALID_PARAMETER); ERR_FAIL_COND_V(connection.is_null() || tcp.is_null(), ERR_INVALID_PARAMETER);
is_server = true; is_server = true;
tcp->set_no_delay(true);
ready_state = STATE_CONNECTING; ready_state = STATE_CONNECTING;
handshake_buffer->resize(WSL_MAX_HEADER_SIZE); handshake_buffer->resize(WSL_MAX_HEADER_SIZE);
handshake_buffer->seek(0); handshake_buffer->seek(0);