|
|
1.1 ! root 1: /* ! 2: * ARP table ! 3: * ! 4: * Copyright (c) 2011 AdaCore ! 5: * ! 6: * Permission is hereby granted, free of charge, to any person obtaining a copy ! 7: * of this software and associated documentation files (the "Software"), to deal ! 8: * in the Software without restriction, including without limitation the rights ! 9: * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell ! 10: * copies of the Software, and to permit persons to whom the Software is ! 11: * furnished to do so, subject to the following conditions: ! 12: * ! 13: * The above copyright notice and this permission notice shall be included in ! 14: * all copies or substantial portions of the Software. ! 15: * ! 16: * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR ! 17: * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, ! 18: * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL ! 19: * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER ! 20: * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, ! 21: * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN ! 22: * THE SOFTWARE. ! 23: */ ! 24: ! 25: #include "slirp.h" ! 26: ! 27: void arp_table_add(Slirp *slirp, uint32_t ip_addr, uint8_t ethaddr[ETH_ALEN]) ! 28: { ! 29: const uint32_t broadcast_addr = ! 30: ~slirp->vnetwork_mask.s_addr | slirp->vnetwork_addr.s_addr; ! 31: ArpTable *arptbl = &slirp->arp_table; ! 32: int i; ! 33: ! 34: DEBUG_CALL("arp_table_add"); ! 35: DEBUG_ARG("ip = 0x%x", ip_addr); ! 36: DEBUG_ARGS((dfd, " hw addr = %02x:%02x:%02x:%02x:%02x:%02x\n", ! 37: ethaddr[0], ethaddr[1], ethaddr[2], ! 38: ethaddr[3], ethaddr[4], ethaddr[5])); ! 39: ! 40: /* Check 0.0.0.0/8 invalid source-only addresses */ ! 41: assert((ip_addr & htonl(~(0xf << 28))) != 0); ! 42: ! 43: if (ip_addr == 0xffffffff || ip_addr == broadcast_addr) { ! 44: /* Do not register broadcast addresses */ ! 45: return; ! 46: } ! 47: ! 48: /* Search for an entry */ ! 49: for (i = 0; i < ARP_TABLE_SIZE; i++) { ! 50: if (arptbl->table[i].ar_sip == ip_addr) { ! 51: /* Update the entry */ ! 52: memcpy(arptbl->table[i].ar_sha, ethaddr, ETH_ALEN); ! 53: return; ! 54: } ! 55: } ! 56: ! 57: /* No entry found, create a new one */ ! 58: arptbl->table[arptbl->next_victim].ar_sip = ip_addr; ! 59: memcpy(arptbl->table[arptbl->next_victim].ar_sha, ethaddr, ETH_ALEN); ! 60: arptbl->next_victim = (arptbl->next_victim + 1) % ARP_TABLE_SIZE; ! 61: } ! 62: ! 63: bool arp_table_search(Slirp *slirp, uint32_t ip_addr, ! 64: uint8_t out_ethaddr[ETH_ALEN]) ! 65: { ! 66: const uint32_t broadcast_addr = ! 67: ~slirp->vnetwork_mask.s_addr | slirp->vnetwork_addr.s_addr; ! 68: ArpTable *arptbl = &slirp->arp_table; ! 69: int i; ! 70: ! 71: DEBUG_CALL("arp_table_search"); ! 72: DEBUG_ARG("ip = 0x%x", ip_addr); ! 73: ! 74: /* Check 0.0.0.0/8 invalid source-only addresses */ ! 75: assert((ip_addr & htonl(~(0xf << 28))) != 0); ! 76: ! 77: /* If broadcast address */ ! 78: if (ip_addr == 0xffffffff || ip_addr == broadcast_addr) { ! 79: /* return Ethernet broadcast address */ ! 80: memset(out_ethaddr, 0xff, ETH_ALEN); ! 81: return 1; ! 82: } ! 83: ! 84: for (i = 0; i < ARP_TABLE_SIZE; i++) { ! 85: if (arptbl->table[i].ar_sip == ip_addr) { ! 86: memcpy(out_ethaddr, arptbl->table[i].ar_sha, ETH_ALEN); ! 87: DEBUG_ARGS((dfd, " found hw addr = %02x:%02x:%02x:%02x:%02x:%02x\n", ! 88: out_ethaddr[0], out_ethaddr[1], out_ethaddr[2], ! 89: out_ethaddr[3], out_ethaddr[4], out_ethaddr[5])); ! 90: return 1; ! 91: } ! 92: } ! 93: ! 94: return 0; ! 95: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.