aboutsummaryrefslogtreecommitdiff
path: root/networking/udhcp/arpping.c
diff options
context:
space:
mode:
authorDenys Vlasenko <vda.linux@googlemail.com>2009-06-16 10:20:27 +0200
committerDenys Vlasenko <vda.linux@googlemail.com>2009-06-16 10:20:27 +0200
commit47f2d7ef7d4dbeea19a55f9d73ef826f9d06650f (patch)
treea84db8f0215526b9728f2f2b94214100e853a98c /networking/udhcp/arpping.c
parent1f363a086779152ab04067e81484b8bb69e4af72 (diff)
downloadbusybox-w32-47f2d7ef7d4dbeea19a55f9d73ef826f9d06650f.tar.gz
busybox-w32-47f2d7ef7d4dbeea19a55f9d73ef826f9d06650f.tar.bz2
busybox-w32-47f2d7ef7d4dbeea19a55f9d73ef826f9d06650f.zip
udhcpd: don't fail ARP check if returned MAC matches client's one
Also, do not unicast replies to yiaddr. Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
Diffstat (limited to 'networking/udhcp/arpping.c')
-rw-r--r--networking/udhcp/arpping.c21
1 files changed, 18 insertions, 3 deletions
diff --git a/networking/udhcp/arpping.c b/networking/udhcp/arpping.c
index b10bff651..fa0989d0f 100644
--- a/networking/udhcp/arpping.c
+++ b/networking/udhcp/arpping.c
@@ -41,7 +41,11 @@ enum {
41 41
42/* Returns 1 if no reply received */ 42/* Returns 1 if no reply received */
43 43
44int FAST_FUNC arpping(uint32_t test_ip, uint32_t from_ip, uint8_t *from_mac, const char *interface) 44int FAST_FUNC arpping(uint32_t test_ip,
45 const uint8_t *safe_mac,
46 uint32_t from_ip,
47 uint8_t *from_mac,
48 const char *interface)
45{ 49{
46 int timeout_ms; 50 int timeout_ms;
47 struct pollfd pfd[1]; 51 struct pollfd pfd[1];
@@ -73,7 +77,7 @@ int FAST_FUNC arpping(uint32_t test_ip, uint32_t from_ip, uint8_t *from_mac, con
73 arp.operation = htons(ARPOP_REQUEST); /* ARP op code */ 77 arp.operation = htons(ARPOP_REQUEST); /* ARP op code */
74 memcpy(arp.sHaddr, from_mac, 6); /* source hardware address */ 78 memcpy(arp.sHaddr, from_mac, 6); /* source hardware address */
75 memcpy(arp.sInaddr, &from_ip, sizeof(from_ip)); /* source IP address */ 79 memcpy(arp.sInaddr, &from_ip, sizeof(from_ip)); /* source IP address */
76 /* tHaddr is zero-fiiled */ /* target hardware address */ 80 /* tHaddr is zero-filled */ /* target hardware address */
77 memcpy(arp.tInaddr, &test_ip, sizeof(test_ip)); /* target IP address */ 81 memcpy(arp.tInaddr, &test_ip, sizeof(test_ip)); /* target IP address */
78 82
79 memset(&addr, 0, sizeof(addr)); 83 memset(&addr, 0, sizeof(addr));
@@ -98,13 +102,24 @@ int FAST_FUNC arpping(uint32_t test_ip, uint32_t from_ip, uint8_t *from_mac, con
98 r = read(s, &arp, sizeof(arp)); 102 r = read(s, &arp, sizeof(arp));
99 if (r < 0) 103 if (r < 0)
100 break; 104 break;
105
106 //bb_error_msg("sHaddr %02x:%02x:%02x:%02x:%02x:%02x",
107 // arp.sHaddr[0], arp.sHaddr[1], arp.sHaddr[2],
108 // arp.sHaddr[3], arp.sHaddr[4], arp.sHaddr[5]);
109
101 if (r >= ARP_MSG_SIZE 110 if (r >= ARP_MSG_SIZE
102 && arp.operation == htons(ARPOP_REPLY) 111 && arp.operation == htons(ARPOP_REPLY)
103 /* don't check it: Linux doesn't return proper tHaddr (fixed in 2.6.24?) */ 112 /* don't check it: Linux doesn't return proper tHaddr (fixed in 2.6.24?) */
104 /* && memcmp(arp.tHaddr, from_mac, 6) == 0 */ 113 /* && memcmp(arp.tHaddr, from_mac, 6) == 0 */
105 && *((uint32_t *) arp.sInaddr) == test_ip 114 && *((uint32_t *) arp.sInaddr) == test_ip
106 ) { 115 ) {
107 rv = 0; 116 /* if ARP source MAC matches safe_mac
117 * (which is client's MAC), then it's not a conflict
118 * (client simply already has this IP and replies to ARPs!)
119 */
120 if (!safe_mac || memcmp(safe_mac, arp.sHaddr, 6) != 0)
121 rv = 0;
122 //else bb_error_msg("sHaddr == safe_mac");
108 break; 123 break;
109 } 124 }
110 } 125 }