]> git.ipfire.org Git - thirdparty/FORT-validator.git/commitdiff
Remove > 65535 validation from --server.port
authorAlberto Leiva Popper <ydahhrk@gmail.com>
Wed, 7 Feb 2024 19:08:09 +0000 (13:08 -0600)
committerAlberto Leiva Popper <ydahhrk@gmail.com>
Thu, 8 Feb 2024 20:24:17 +0000 (14:24 -0600)
While trying to implement the upcoming patch, I found myself trying to
refactor this validation. The implementation was awkward; instead of
ntohs'ing sockaddr_in.sin_port, it extracted the bytes manually:

port = (unsigned char)((*result)->ai_addr->sa_data[0]) << 8;
port += (unsigned char)((*result)->ai_addr->sa_data[1]);

But on second thought, I'm not seeing this validation eye to eye.
It's intended to prevent `getaddrinfo()` from parsing
`--server.port=120000` like `--server.port=54464` (120000 % 65536) on
Linux, but... thing is, this "port out of bounds" quirk looks like an
everyday Linux idiosyncrasy.

Linux being Linux:

$ nc -lv 127.0.0.1 120000
Listening on localhost 54464

It's weird but seems inoffensive, and some beardos might even expect it.

`getaddrinfo()` returns proper errors in the BSDs, so the validation is
redundant there.

src/rtr/rtr.c

index 172e7ab7c7467050d09a5c5d8bda73b9fa30e6c3..135d40402ae6313188b3036e5267d6d683473ba7 100644 (file)
@@ -105,9 +105,7 @@ static int
 init_addrinfo(char const *hostname, char const *service,
     struct addrinfo **result)
 {
-       char *tmp;
        struct addrinfo hints;
-       unsigned long parsed, port;
        int error;
 
        memset(&hints, 0 , sizeof(hints));
@@ -126,26 +124,6 @@ init_addrinfo(char const *hostname, char const *service,
                return error;
        }
 
-       errno = 0;
-       parsed = strtoul(service, &tmp, 10);
-       if (errno || *tmp != '\0')
-               return 0; /* Ok, not a number */
-
-       /*
-        * 'getaddrinfo' isn't very strict validating the service when a port
-        * number is indicated. If a port larger than the max (65535) is
-        * received, the 16 rightmost bits are utilized as the port and set at
-        * the addrinfo returned.
-        *
-        * So, a manual validation is implemented. Port is actually a uint16_t,
-        * so read what's necessary and compare using the same data type.
-        */
-       port = (unsigned char)((*result)->ai_addr->sa_data[0]) << 8;
-       port += (unsigned char)((*result)->ai_addr->sa_data[1]);
-       if (parsed != port)
-               return pr_op_err("Service port %s is out of range (max value is %d)",
-                   service, USHRT_MAX);
-
        return 0;
 }