components/dnsmasq/patches/01_use_siocsxarp.patch
author majid.valiollahzadeh@oracle.com <majid.valiollahzadeh@oracle.com>
Wed, 16 Sep 2015 09:08:20 -0700
changeset 4868 86ad1ef86709
parent 1750 cae903cb1692
permissions -rw-r--r--
21762187 problem in UTILITY/RSYNC

If there are multiple datalinks configured with IP addresses from the same
subnet, then the datalink to which an on-link device's ARP entry will be
associated depends on the order in which these datalinks were plumbed with
IP addresses. In that, the datalink that was plumbed for IP last will have
the ARP entry associated against it. To avoid, this we need to use
SIOCSXARP ioctl to specify the exact datalink.

This patch was developed in-house. Since it is Solaris-specific it is not
suitable for upstream.

--- dnsmasq-2.68/src/dhcp.c	2013-12-08 07:58:29.000000000 -0800
+++ ORIGINAL/src/dhcp.c	2014-03-07 10:14:16.639192664 -0800
@@ -418,17 +418,24 @@
   else
     {
       /* unicast to unconfigured client. Inject mac address direct into ARP cache. 
-	 Note that this only works for ethernet on solaris, because we use SIOCSARP
-	 and not SIOCSXARP, which would be perfect, except that it returns ENXIO 
-	 mysteriously. Bah. Fall back to broadcast for other net types. */
-      struct arpreq req;
+	 Fall back to broadcast for other net types. */
+      struct xarpreq xreq;
+      int ifnamsz = strlen(ifr.ifr_name);
+
+      dest.sin_family = AF_INET;
       dest.sin_addr = mess->yiaddr;
       dest.sin_port = htons(daemon->dhcp_client_port);
-      *((struct sockaddr_in *)&req.arp_pa) = dest;
-      req.arp_ha.sa_family = AF_UNSPEC;
-      memcpy(req.arp_ha.sa_data, mess->chaddr, mess->hlen);
-      req.arp_flags = ATF_COM;
-      ioctl(daemon->dhcpfd, SIOCSARP, &req);
+      *((struct sockaddr_in *)&xreq.xarp_pa) = dest;
+      xreq.xarp_ha.sdl_nlen = ifnamsz;
+      memcpy(xreq.xarp_ha.sdl_data, ifr.ifr_name, ifnamsz);
+      xreq.xarp_ha.sdl_family = AF_LINK;
+      xreq.xarp_ha.sdl_index = iface_index;
+      /* 6 corresponds to IFT_ETHER */
+      xreq.xarp_ha.sdl_type = 6;
+      xreq.xarp_ha.sdl_alen = ETHER_ADDR_LEN;
+      memcpy(xreq.xarp_ha.sdl_data + ifnamsz, mess->chaddr, mess->hlen);
+      xreq.xarp_flags = ATF_COM;
+      ioctl(daemon->dhcpfd, SIOCSXARP, &xreq);
     }
 #elif defined(HAVE_BSD_NETWORK)
   else