As a precedent, nc has a conversational, specific style of error reporting when a socketopt fails. With the IPv4/6-specific options, we refactored the code to the point that the error messages are less specific and maybe misleading (e.g. setting ToS on an IPv6 socket).
This patch makes the per-address-family options instead have specific error reporting, and IMO simplifies things a bit as well. I'll admit it I have an ulterior motive here too. Structuring code like this also makes it easier to add #ifdefs for non-existent sockopts for the portable version packaged with LibreSSL. diff --git a/src/usr.bin/nc/netcat.c b/src/usr.bin/nc/netcat.c index c9c5ebe..f5dfe18 100644 --- a/src/usr.bin/nc/netcat.c +++ b/src/usr.bin/nc/netcat.c @@ -1412,18 +1412,13 @@ set_common_sockopts(int s, int af) err(1, NULL); } if (Tflag != -1) { - int proto, option; - - if (af == AF_INET6) { - proto = IPPROTO_IPV6; - option = IPV6_TCLASS; - } else { - proto = IPPROTO_IP; - option = IP_TOS; - } - - if (setsockopt(s, proto, option, &Tflag, sizeof(Tflag)) == -1) + if (af == AF_INET && setsockopt(s, IPPROTO_IP, + IP_TOS, &Tflag, sizeof(Tflag)) == -1) err(1, "set IP ToS"); + + else if (af == AF_INET6 && setsockopt(s, IPPROTO_IPV6, + IPV6_TCLASS, &Tflag, sizeof(Tflag)) == -1) + err(1, "set IPv6 traffic class"); } if (Iflag) { if (setsockopt(s, SOL_SOCKET, SO_RCVBUF, @@ -1435,28 +1430,25 @@ set_common_sockopts(int s, int af) &Oflag, sizeof(Oflag)) == -1) err(1, "set TCP send buffer size"); } - if (ttl != -1 || minttl != -1) { - int proto, in_ttl_opt, out_ttl_opt; - switch (af) { - case AF_INET: - proto = IPPROTO_IP; - in_ttl_opt = IP_MINTTL; - out_ttl_opt = IP_TTL; - break; - case AF_INET6: - proto = IPPROTO_IPV6; - in_ttl_opt = IPV6_MINHOPCOUNT; - out_ttl_opt = IPV6_UNICAST_HOPS; - break; - default: - errx(1, "unknown address family: %d", af); - } - if (minttl != -1 && setsockopt(s, proto, in_ttl_opt, - &minttl, sizeof(minttl))) - err(1, "setsockopt minttl"); - if (ttl != -1 && setsockopt(s, proto, out_ttl_opt, - &ttl, sizeof(ttl))) - err(1, "setsockopt ttl"); + + if (ttl != -1) { + if (af == AF_INET && setsockopt(s, IPPROTO_IP, + IP_TTL, &ttl, sizeof(ttl))) + err(1, "set IP TTL"); + + else if (af == AF_INET6 && setsockopt(s, IPPROTO_IPV6, + IPV6_UNICAST_HOPS, &ttl, sizeof(ttl))) + err(1, "set IPv6 unicast hops"); + } + + if (minttl != -1) { + if (af == AF_INET && setsockopt(s, IPPROTO_IP, + IP_MINTTL, &minttl, sizeof(minttl))) + err(1, "set IP min TTL"); + + else if (af == AF_INET6 && setsockopt(s, IPPROTO_IPV6, + IPV6_MINHOPCOUNT, &minttl, sizeof(minttl))) + err(1, "set IPv6 min hop count"); } }