1/* $NetBSD: sbpf.c,v 1.4 2018/02/04 08:19:42 mrg Exp $ */ 2 3/* 4 * (C)opyright 1995-1998 Darren Reed. (from tcplog) 5 * 6 * See the IPFILTER.LICENCE file for details on licencing. 7 * 8 */ 9#include <sys/param.h> 10#include <sys/types.h> 11#include <sys/mbuf.h> 12#include <sys/time.h> 13#include <sys/timeb.h> 14#include <sys/socket.h> 15#include <sys/file.h> 16#include <sys/ioctl.h> 17#if BSD < 199103 18#include <sys/fcntlcom.h> 19#endif 20#if (__FreeBSD_version >= 300000) 21# include <sys/dirent.h> 22#else 23# include <sys/dir.h> 24#endif 25#include <net/bpf.h> 26 27#include <net/if.h> 28#include <netinet/in.h> 29#include <netinet/in_systm.h> 30#include <netinet/ip.h> 31#include <netinet/ip_icmp.h> 32#include <netinet/ip_var.h> 33#include <netinet/udp.h> 34#include <netinet/tcp.h> 35 36#include <stdio.h> 37#include <netdb.h> 38#include <string.h> 39#include <unistd.h> 40#include <stdlib.h> 41#ifdef __NetBSD__ 42# include <paths.h> 43#endif 44#include <ctype.h> 45#include <signal.h> 46#include <errno.h> 47 48#include "ip_compat.h" 49#include "ipsend.h" 50 51#if !defined(lint) 52static __attribute__((__used__)) const char sccsid[] = "@(#)sbpf.c 1.3 8/25/95 (C)1995 Darren Reed"; 53static __attribute__((__used__)) const char rcsid[] = "@(#)Id: sbpf.c,v 1.1.1.2 2012/07/22 13:44:37 darrenr Exp $"; 54#endif 55 56/* 57 * the code herein is dervied from libpcap. 58 */ 59static u_char *buf = NULL; 60static int bufsize = 0, timeout = 1; 61 62 63int initdevice(device, tout) 64 char *device; 65 int tout; 66{ 67 struct bpf_version bv; 68 struct timeval to; 69 struct ifreq ifr; 70#ifdef _PATH_BPF 71 char *bpfname = _PATH_BPF; 72 int fd; 73 74 if ((fd = open(bpfname, O_RDWR)) < 0) 75 { 76 fprintf(stderr, "no bpf devices available as /dev/bpfxx\n"); 77 return -1; 78 } 79#else 80 char bpfname[16]; 81 int fd = 0, i; 82 83 for (i = 0; i < 16; i++) 84 { 85 (void) sprintf(bpfname, "/dev/bpf%d", i); 86 if ((fd = open(bpfname, O_RDWR)) >= 0) 87 break; 88 } 89 if (i == 16) 90 { 91 fprintf(stderr, "no bpf devices available as /dev/bpfxx\n"); 92 return -1; 93 } 94#endif 95 96 if (ioctl(fd, BIOCVERSION, (caddr_t)&bv) < 0) 97 { 98 perror("BIOCVERSION"); 99 return -1; 100 } 101 if (bv.bv_major != BPF_MAJOR_VERSION || 102 bv.bv_minor < BPF_MINOR_VERSION) 103 { 104 fprintf(stderr, "kernel bpf (v%d.%d) filter out of date:\n", 105 bv.bv_major, bv.bv_minor); 106 fprintf(stderr, "current version: %d.%d\n", 107 BPF_MAJOR_VERSION, BPF_MINOR_VERSION); 108 return -1; 109 } 110 111 (void) strncpy(ifr.ifr_name, device, sizeof(ifr.ifr_name)); 112 if (ioctl(fd, BIOCSETIF, &ifr) == -1) 113 { 114 fprintf(stderr, "%s(%d):", ifr.ifr_name, fd); 115 perror("BIOCSETIF"); 116 exit(1); 117 } 118 /* 119 * get kernel buffer size 120 */ 121 if (ioctl(fd, BIOCGBLEN, &bufsize) == -1) 122 { 123 perror("BIOCSBLEN"); 124 exit(-1); 125 } 126 buf = (u_char*)malloc(bufsize); 127 /* 128 * set the timeout 129 */ 130 timeout = tout; 131 to.tv_sec = 1; 132 to.tv_usec = 0; 133 if (ioctl(fd, BIOCSRTIMEOUT, (caddr_t)&to) == -1) 134 { 135 perror("BIOCSRTIMEOUT"); 136 exit(-1); 137 } 138 139 (void) ioctl(fd, BIOCFLUSH, 0); 140 return fd; 141} 142 143 144/* 145 * output an IP packet onto a fd opened for /dev/bpf 146 */ 147int sendip(fd, pkt, len) 148 int fd, len; 149 char *pkt; 150{ 151 if (write(fd, pkt, len) == -1) 152 { 153 perror("send"); 154 return -1; 155 } 156 157 return len; 158} 159