96 |
static const struct eth_addr ethbroadcast = {{0xff,0xff,0xff,0xff,0xff,0xff}}; |
static const struct eth_addr ethbroadcast = {{0xff,0xff,0xff,0xff,0xff,0xff}}; |
97 |
static struct etharp_entry arp_table[ARP_TABLE_SIZE]; |
static struct etharp_entry arp_table[ARP_TABLE_SIZE]; |
98 |
|
|
99 |
/** ask update_arp_entry() to create new entry instead of merely update existing */ |
/** |
100 |
/** ask find_entry() to create new entry instead of merely finding existing */ |
* Try hard to create a new entry - we want the IP address to appear in |
101 |
#define ETHARP_CREATE 1 |
* the cache (even if this means removing an active entry or so). */ |
102 |
|
#define ETHARP_TRY_HARD 1 |
103 |
|
|
104 |
static s8_t find_entry(struct ip_addr *ipaddr, u8_t flags); |
static s8_t find_entry(struct ip_addr *ipaddr, u8_t flags); |
105 |
static err_t update_arp_entry(struct netif *netif, struct ip_addr *ipaddr, struct eth_addr *ethaddr, u8_t flags); |
static err_t update_arp_entry(struct netif *netif, struct ip_addr *ipaddr, struct eth_addr *ethaddr, u8_t flags); |
106 |
/** |
/** |
181 |
* If ipaddr is NULL, return a initialized new entry in state ETHARP_EMPTY. |
* If ipaddr is NULL, return a initialized new entry in state ETHARP_EMPTY. |
182 |
* |
* |
183 |
* In all cases, attempt to create new entries from an empty entry. If no |
* In all cases, attempt to create new entries from an empty entry. If no |
184 |
* empty entries are available and ETHARP_CREATE flag is set, recycle |
* empty entries are available and ETHARP_TRY_HARD flag is set, recycle |
185 |
* old entries. Heuristic choose the least important entry for recycling. |
* old entries. Heuristic choose the least important entry for recycling. |
186 |
* |
* |
187 |
* @param ipaddr IP address to find in ARP cache, or to add if not found. |
* @param ipaddr IP address to find in ARP cache, or to add if not found. |
188 |
* @param flags |
* @param flags |
189 |
* - ETHARP_CREATE: Try hard to create a entry by allowing recycling. |
* - ETHARP_TRY_HARD: Try hard to create a entry by allowing recycling. |
190 |
* |
* |
191 |
* @return The ARP entry index that matched or is created, ERR_MEM if no |
* @return The ARP entry index that matched or is created, ERR_MEM if no |
192 |
* entry is found or could be recycled. |
* entry is found or could be recycled. |
306 |
LWIP_ASSERT("i < ARP_TABLE_SIZE", i < ARP_TABLE_SIZE); |
LWIP_ASSERT("i < ARP_TABLE_SIZE", i < ARP_TABLE_SIZE); |
307 |
|
|
308 |
/* allowed to recycle a entry? */ |
/* allowed to recycle a entry? */ |
309 |
if (flags & ETHARP_CREATE) { |
if (flags & ETHARP_TRY_HARD) { |
310 |
/* recycle (no-op for an already empty entry) */ |
/* recycle (no-op for an already empty entry) */ |
311 |
arp_table[i].state = ETHARP_STATE_EMPTY; |
arp_table[i].state = ETHARP_STATE_EMPTY; |
312 |
} |
} |
342 |
* @param ipaddr IP address of the inserted ARP entry. |
* @param ipaddr IP address of the inserted ARP entry. |
343 |
* @param ethaddr Ethernet address of the inserted ARP entry. |
* @param ethaddr Ethernet address of the inserted ARP entry. |
344 |
* @param flags Defines behaviour: |
* @param flags Defines behaviour: |
345 |
* - ETHARP_CREATE Allows ARP to insert this as a new item. If not specified, |
* - ETHARP_TRY_HARD Allows ARP to insert this as a new item. If not specified, |
346 |
* only existing ARP entries will be updated. |
* only existing ARP entries will be updated. |
347 |
* |
* |
348 |
* @return |
* @return |
349 |
* - ERR_OK Succesfully updated ARP cache. |
* - ERR_OK Succesfully updated ARP cache. |
350 |
* - ERR_MEM If we could not add a new ARP entry when ETHARP_CREATE was set. |
* - ERR_MEM If we could not add a new ARP entry when ETHARP_TRY_HARD was set. |
351 |
* - ERR_ARG Non-unicast address given, those will not appear in ARP cache. |
* - ERR_ARG Non-unicast address given, those will not appear in ARP cache. |
352 |
* |
* |
353 |
* @see pbuf_free() |
* @see pbuf_free() |
434 |
incoming IP packet comes from a host on the local network. */ |
incoming IP packet comes from a host on the local network. */ |
435 |
hdr = p->payload; |
hdr = p->payload; |
436 |
/* source is on local network? */ |
/* source is on local network? */ |
437 |
if (!ip_addr_maskcmp(&(hdr->ip.src), &(netif->ip_addr), &(netif->netmask))) { |
if (!ip_addr_netcmp(&(hdr->ip.src), &(netif->ip_addr), &(netif->netmask))) { |
438 |
/* do nothing */ |
/* do nothing */ |
439 |
return; |
return; |
440 |
} |
} |
441 |
|
|
442 |
LWIP_DEBUGF(ETHARP_DEBUG | DBG_TRACE, ("etharp_ip_input: updating ETHARP table.\n")); |
LWIP_DEBUGF(ETHARP_DEBUG | DBG_TRACE, ("etharp_ip_input: updating ETHARP table.\n")); |
443 |
/* update ARP table, ask to insert entry */ |
/* update ARP table */ |
444 |
update_arp_entry(netif, &(hdr->ip.src), &(hdr->eth.src), ETHARP_CREATE); |
/* @todo We could use ETHARP_TRY_HARD if we think we are going to talk |
445 |
|
* back soon (for example, if the destination IP address is ours. */ |
446 |
|
update_arp_entry(netif, &(hdr->ip.src), &(hdr->eth.src), 0); |
447 |
} |
} |
448 |
|
|
449 |
|
|
496 |
if (for_us) { |
if (for_us) { |
497 |
/* add IP address in ARP cache; assume requester wants to talk to us. |
/* add IP address in ARP cache; assume requester wants to talk to us. |
498 |
* can result in directly sending the queued packets for this host. */ |
* can result in directly sending the queued packets for this host. */ |
499 |
update_arp_entry(netif, &sipaddr, &(hdr->shwaddr), ETHARP_CREATE); |
update_arp_entry(netif, &sipaddr, &(hdr->shwaddr), ETHARP_TRY_HARD); |
500 |
/* ARP message not directed to us? */ |
/* ARP message not directed to us? */ |
501 |
} else { |
} else { |
502 |
/* update the source IP address in the cache, if present */ |
/* update the source IP address in the cache, if present */ |
629 |
/* destination IP address is an IP unicast address */ |
/* destination IP address is an IP unicast address */ |
630 |
} else { |
} else { |
631 |
/* outside local network? */ |
/* outside local network? */ |
632 |
if (!ip_addr_maskcmp(ipaddr, &(netif->ip_addr), &(netif->netmask))) { |
if (!ip_addr_netcmp(ipaddr, &(netif->ip_addr), &(netif->netmask))) { |
633 |
/* interface has default gateway? */ |
/* interface has default gateway? */ |
634 |
if (netif->gw.addr != 0) { |
if (netif->gw.addr != 0) { |
635 |
/* send to hardware address of default gateway IP address */ |
/* send to hardware address of default gateway IP address */ |
711 |
} |
} |
712 |
|
|
713 |
/* find entry in ARP cache, ask to create entry if queueing packet */ |
/* find entry in ARP cache, ask to create entry if queueing packet */ |
714 |
i = find_entry(ipaddr, (q != NULL) ? ETHARP_CREATE : 0); |
i = find_entry(ipaddr, ETHARP_TRY_HARD); |
715 |
|
|
716 |
/* could not find or create entry? */ |
/* could not find or create entry? */ |
717 |
if (i < 0) return (err_t)i; |
if (i < 0) return (err_t)i; |