ruby/ext/socket
Misaki Shioi 4c270200db
[Feature #120782] Introduction of Happy Eyeballs Version 2 (RFC8305) in TCPSocket.new (#11653)
* Introduction of Happy Eyeballs Version 2 (RFC8305) in TCPSocket.new

This is an implementation of Happy Eyeballs version 2 (RFC 8305) in `TCPSocket.new`.
See https://github.com/ruby/ruby/pull/11653

1. Background
Prior to this implementation, I implemented Happy Eyeballs Version 2 (HEv2) for `Socket.tcp` in https://github.com/ruby/ruby/pull/9374.
HEv2 is an algorithm defined in [RFC 8305](https://datatracker.ietf.org/doc/html/rfc8305), aimed at improving network connectivity.
For more details on the specific cases that HEv2 helps, please refer to https://bugs.ruby-lang.org/issues/20108.

2. Proposal & Outcome
This proposal implements the same HEv2 algorithm in `TCPSocket.new`.
Since `TCPSocket.new` is used more widely than `Socket.tcp`, this change is expected to broaden the impact of HEv2's benefits.
Like `Socket.tcp`, I have also added `fast_fallback` keyword argument to `TCPSocket.new`.
This option is set to true by default, enabling the HEv2 functionality.
However, users can explicitly set it to false to disable HEv2 and use the previous behavior of `TCPSocket.new`.

It should be noted that HEv2 is enabled only in environments where pthreads are available.
This specification follows the approach taken in https://bugs.ruby-lang.org/issues/19965 , where name resolution can be interrupted.
(In environments where pthreads are not available, the `fast_fallback` option is ignored.)

3. Performance
Below is the benchmark of 100 requests to `www.ruby-lang.org` with the fast_fallback option set to true and false, respectively.
While there is a slight performance degradation when HEv2 is enabled, the degradation is smaller compared to that seen in `Socket.tcp`.

```
~/s/build ❯❯❯ ../install/bin/ruby ../ruby/test.rb
Rehearsal --------------------------------------------------------
fast_fallback: true    0.017588   0.097045   0.114633 (  1.460664)
fast_fallback: false   0.014033   0.078984   0.093017 (  1.413951)
----------------------------------------------- total: 0.207650sec

                           user     system      total        real
fast_fallback: true    0.020891   0.124054   0.144945 (  1.473816)
fast_fallback: false   0.018392   0.110852   0.129244 (  1.466014)
```

* Update debug prints

Co-authored-by: Nobuyoshi Nakada <nobu.nakada@gmail.com>

* Remove debug prints

* misc

* Disable HEv2 in Win

* Raise resolution error with hostname resolution

* Fix to handle errors

* Remove warnings

* Errors that do not need to be handled

* misc

* Improve doc

* Fix bug on cancellation

* Avoid EAI_ADDRFAMILY for resolving IPv6

* Follow upstream

* misc

* Refactor connection_attempt_fds management

- Introduced allocate_connection_attempt_fds and reallocate_connection_attempt_fds for improved memory allocation of connection_attempt_fds
- Added remove_connection_attempt_fd to resize connection_attempt_fds dynamically.
- Simplified the in_progress_fds function to only check the size of connection_attempt_fds.

* Rename do_pthread_create to raddrinfo_pthread_create to avoid conflicting

---------

Co-authored-by: Nobuyoshi Nakada <nobu.nakada@gmail.com>
2024-11-12 10:06:48 +09:00
..
lib [DOC] Improve `Socket::tcp` with Happy Eyeballs Version 2 2024-10-20 19:26:01 +09:00
.document * ext/socket/.document: Add ifaddr.c. 2013-05-14 14:48:00 +00:00
addrinfo.h Expand tabs [ci skip] 2022-07-21 09:42:04 -07:00
ancdata.c Move directives outside `rb_ary_new3` call 2024-10-10 11:30:37 +09:00
basicsocket.c Update `BasicSocket` to use `rb_io_blocking_region`. 2024-10-09 21:05:01 +13:00
constants.c Expand tabs [ci skip] 2022-07-21 09:42:04 -07:00
depend ruby tool/update-deps --fix 2024-04-27 21:55:28 +09:00
extconf.rb Revert "Set AI_ADDRCONFIG when making getaddrinfo(3) calls for outgoing conns" 2024-02-01 11:09:54 +11:00
getaddrinfo.c Don't check for null pointer in calls to free 2023-06-30 09:13:31 -04:00
getnameinfo.c Expand tabs [ci skip] 2022-07-21 09:42:04 -07:00
ifaddr.c Expand tabs [ci skip] 2022-07-21 09:42:04 -07:00
init.c Support `IO#timeout` for `rsock_connect`. (#11880) 2024-10-12 10:08:34 +13:00
ipsocket.c [Feature #120782] Introduction of Happy Eyeballs Version 2 (RFC8305) in TCPSocket.new (#11653) 2024-11-12 10:06:48 +09:00
mkconstants.rb Drop support for old ERB 2024-03-03 00:55:45 +09:00
option.c Add support for `sockaddr_un` on Windows. (#6513) 2022-11-17 14:50:25 -08:00
raddrinfo.c [Feature #120782] Introduction of Happy Eyeballs Version 2 (RFC8305) in TCPSocket.new (#11653) 2024-11-12 10:06:48 +09:00
rubysocket.h [Feature #120782] Introduction of Happy Eyeballs Version 2 (RFC8305) in TCPSocket.new (#11653) 2024-11-12 10:06:48 +09:00
socket.c Support `IO#timeout` for `rsock_connect`. (#11880) 2024-10-12 10:08:34 +13:00
sockport.h * ext/socket: Bypass getaddrinfo() if node and serv are numeric. 2014-02-19 10:37:43 +00:00
sockssocket.c [Feature #120782] Introduction of Happy Eyeballs Version 2 (RFC8305) in TCPSocket.new (#11653) 2024-11-12 10:06:48 +09:00
tcpserver.c [Feature #120782] Introduction of Happy Eyeballs Version 2 (RFC8305) in TCPSocket.new (#11653) 2024-11-12 10:06:48 +09:00
tcpsocket.c [Feature #120782] Introduction of Happy Eyeballs Version 2 (RFC8305) in TCPSocket.new (#11653) 2024-11-12 10:06:48 +09:00
udpsocket.c Support `IO#timeout` for `rsock_connect`. (#11880) 2024-10-12 10:08:34 +13:00
unixserver.c Add support for `sockaddr_un` on Windows. (#6513) 2022-11-17 14:50:25 -08:00
unixsocket.c Support `IO#timeout` for `rsock_connect`. (#11880) 2024-10-12 10:08:34 +13:00