1/* $FreeBSD$ */ 2 3/* 4 * Based upon 4.4BSD's /usr/sbin/arp 5 */ 6#include <sys/param.h> 7#include <sys/file.h> 8#include <sys/socket.h> 9#include <sys/sysctl.h> 10#include <net/if.h> 11#if __FreeBSD_version >= 300000 12# include <net/if_var.h> 13#endif 14#include <net/if_dl.h> 15#include <net/if_types.h> 16#if defined(__FreeBSD__) 17# include "radix_ipf.h" 18#endif 19#ifndef __osf__ 20# include <net/route.h> 21#endif 22#include <netinet/in.h> 23#include <netinet/if_ether.h> 24#include <arpa/inet.h> 25#include <netinet/in.h> 26#include <netinet/in_systm.h> 27#include <netinet/ip.h> 28#include <netinet/ip_var.h> 29#include <netinet/tcp.h> 30#include <unistd.h> 31#include <string.h> 32#include <stdlib.h> 33#include <netdb.h> 34#include <errno.h> 35#include <nlist.h> 36#include <stdio.h> 37#include "ipsend.h" 38#include "iplang/iplang.h" 39 40 41/* 42 * lookup host and return 43 * its IP address in address 44 * (4 bytes) 45 */ 46int resolve(host, address) 47char *host, *address; 48{ 49 struct hostent *hp; 50 u_long add; 51 52 add = inet_addr(host); 53 if (add == -1) 54 { 55 if (!(hp = gethostbyname(host))) 56 { 57 fprintf(stderr, "unknown host: %s\n", host); 58 return -1; 59 } 60 bcopy((char *)hp->h_addr, (char *)address, 4); 61 return 0; 62 } 63 bcopy((char*)&add, address, 4); 64 return 0; 65} 66 67 68int arp(addr, eaddr) 69char *addr, *eaddr; 70{ 71 int mib[6]; 72 size_t needed; 73 char *lim, *buf, *next; 74 struct rt_msghdr *rtm; 75 struct sockaddr_inarp *sin; 76 struct sockaddr_dl *sdl; 77 78#ifdef IPSEND 79 if (arp_getipv4(addr, ether) == 0) 80 return 0; 81#endif 82 83 if (!addr) 84 return -1; 85 86 mib[0] = CTL_NET; 87 mib[1] = PF_ROUTE; 88 mib[2] = 0; 89 mib[3] = AF_INET; 90 mib[4] = NET_RT_FLAGS; 91#ifdef RTF_LLINFO 92 mib[5] = RTF_LLINFO; 93#else 94 mib[5] = 0; 95#endif 96 97 if (sysctl(mib, 6, NULL, &needed, NULL, 0) == -1) 98 { 99 perror("route-sysctl-estimate"); 100 exit(-1); 101 } 102 if ((buf = malloc(needed)) == NULL) 103 { 104 perror("malloc"); 105 exit(-1); 106 } 107 if (sysctl(mib, 6, buf, &needed, NULL, 0) == -1) 108 { 109 perror("actual retrieval of routing table"); 110 exit(-1); 111 } 112 lim = buf + needed; 113 for (next = buf; next < lim; next += rtm->rtm_msglen) 114 { 115 rtm = (struct rt_msghdr *)next; 116 sin = (struct sockaddr_inarp *)(rtm + 1); 117 sdl = (struct sockaddr_dl *)(sin + 1); 118 if (!bcmp(addr, (char *)&sin->sin_addr, 119 sizeof(struct in_addr))) 120 { 121 bcopy(LLADDR(sdl), eaddr, sdl->sdl_alen); 122 return 0; 123 } 124 } 125 return -1; 126} 127