]> git.ipfire.org Git - thirdparty/freeradius-server.git/commitdiff
use IPV6_BOUND_IF, too.
authorAlan T. DeKok <aland@freeradius.org>
Thu, 8 Jun 2023 07:37:36 +0000 (09:37 +0200)
committerAlan T. DeKok <aland@freeradius.org>
Thu, 8 Jun 2023 07:38:22 +0000 (09:38 +0200)
And minor cleanups and consistency changes

src/lib/util/socket.c

index 7c9aea7b158a0dcc18c0c16ef979759b3eaedc8a..1fa9b94e156479b5d73b1cc89a3afb6a6049e109 100644 (file)
@@ -267,7 +267,7 @@ int fr_socket_bind(int sockfd, char const *ifname, fr_ipaddr_t *src_ipaddr, uint
         */
        if (ifname) {
 #ifdef HAVE_NET_IF_H
-               uint32_t scope_id;
+               unsigned int scope_id;
 
                scope_id = if_nametoindex(ifname);
                if (!scope_id) {
@@ -309,7 +309,7 @@ int fr_socket_bind(int sockfd, char const *ifname, fr_ipaddr_t *src_ipaddr, uint
 #endif
                        ret = setsockopt(sockfd, SOL_SOCKET, SO_BINDTODEVICE, ifname, strlen(ifname));
                        if (ret < 0) {
-                               fr_strerror_printf_push("Bind failed on interface %s: %s",
+                               fr_strerror_printf_push("Failed binding socket to interface %s: %s",
                                                        ifname, fr_syserror(errno));
                                return -1;
                        } /* else it worked. */
@@ -319,21 +319,35 @@ int fr_socket_bind(int sockfd, char const *ifname, fr_ipaddr_t *src_ipaddr, uint
                         */
                        my_ipaddr.scope_id = scope_id;
                }
+
                /*
                 *      SO_BINDTODEVICE succeeded, so we're always
                 *      bound to the socket.
                 */
 
-#elif defined(IP_BOUND_IF)
+#elif defined(IP_BOUND_IF) || defined(IPV6_BOUND_IF)
                {
-                       int idx = if_nametoindex(ifname);
-                       if (idx == 0) {
-                       error:
-                               fr_strerror_printf("Failed binding socket to %s: %s", ifname, fr_syserror(errno));
+                       int idx = scope_id;
+
+                       if (my_ipaddr.af == AF_INET) {
+                               if (unlikely(setsockopt(sockfd, IPPROTO_IP, IP_BOUND_IF, &idx, sizeof(idx)) < 0)) {
+                               error:
+                                       fr_strerror_printf_push("Failed binding socket to interface %s: %s",
+                                                               ifname, fr_syserror(errno));
+                                       return -1;
+                               }
+
+                       } else if (my_ipaddr.af == AF_INET6) {
+                               if (unlikely(setsockopt(sockfd, IPPROTO_IPV6, IPV6_BOUND_IF, &idx, sizeof(idx)) < 0)) goto error;
+
+                       } else {
+                               fr_strerror_printf("Invalid address family for 'interface = ...'");
                                return -1;
                        }
-                       if (unlikely(setsockopt(sockfd, IPPROTO_IP, IP_BOUND_IF, &idx, sizeof(idx)) < 0)) goto error;
+
+                       my_ipaddr.scope_id = scope_id;
                }
+
 #else
                {
                        struct ifaddrs *list = NULL;