pcap-nit.c 10 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417
  1. /*
  2. * Copyright (c) 1990, 1991, 1992, 1993, 1994, 1995, 1996
  3. * The Regents of the University of California. All rights reserved.
  4. *
  5. * Redistribution and use in source and binary forms, with or without
  6. * modification, are permitted provided that: (1) source code distributions
  7. * retain the above copyright notice and this paragraph in its entirety, (2)
  8. * distributions including binary code include the above copyright notice and
  9. * this paragraph in its entirety in the documentation or other materials
  10. * provided with the distribution, and (3) all advertising materials mentioning
  11. * features or use of this software display the following acknowledgement:
  12. * ``This product includes software developed by the University of California,
  13. * Lawrence Berkeley Laboratory and its contributors.'' Neither the name of
  14. * the University nor the names of its contributors may be used to endorse
  15. * or promote products derived from this software without specific prior
  16. * written permission.
  17. * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
  18. * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
  19. * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
  20. */
  21. #ifdef HAVE_CONFIG_H
  22. #include <config.h>
  23. #endif
  24. #include <sys/types.h>
  25. #include <sys/time.h>
  26. #include <sys/timeb.h>
  27. #include <sys/file.h>
  28. #include <sys/ioctl.h>
  29. #include <sys/socket.h>
  30. #include <net/if.h>
  31. #include <net/nit.h>
  32. #include <netinet/in.h>
  33. #include <netinet/in_systm.h>
  34. #include <netinet/ip.h>
  35. #include <netinet/if_ether.h>
  36. #include <netinet/ip_var.h>
  37. #include <netinet/udp.h>
  38. #include <netinet/udp_var.h>
  39. #include <netinet/tcp.h>
  40. #include <netinet/tcpip.h>
  41. #include <ctype.h>
  42. #include <errno.h>
  43. #include <stdio.h>
  44. #include "pcap-int.h"
  45. #ifdef HAVE_OS_PROTO_H
  46. #include "os-proto.h"
  47. #endif
  48. /*
  49. * The chunk size for NIT. This is the amount of buffering
  50. * done for read calls.
  51. */
  52. #define CHUNKSIZE (2*1024)
  53. /*
  54. * The total buffer space used by NIT.
  55. */
  56. #define BUFSPACE (4*CHUNKSIZE)
  57. /* Forwards */
  58. static int nit_setflags(int, int, int, char *);
  59. /*
  60. * Private data for capturing on NIT devices.
  61. */
  62. struct pcap_nit {
  63. struct pcap_stat stat;
  64. };
  65. static int
  66. pcap_stats_nit(pcap_t *p, struct pcap_stat *ps)
  67. {
  68. struct pcap_nit *pn = p->priv;
  69. /*
  70. * "ps_recv" counts packets handed to the filter, not packets
  71. * that passed the filter. As filtering is done in userland,
  72. * this does not include packets dropped because we ran out
  73. * of buffer space.
  74. *
  75. * "ps_drop" presumably counts packets dropped by the socket
  76. * because of flow control requirements or resource exhaustion;
  77. * it doesn't count packets dropped by the interface driver.
  78. * As filtering is done in userland, it counts packets regardless
  79. * of whether they would've passed the filter.
  80. *
  81. * These statistics don't include packets not yet read from the
  82. * kernel by libpcap or packets not yet read from libpcap by the
  83. * application.
  84. */
  85. *ps = pn->stat;
  86. return (0);
  87. }
  88. static int
  89. pcap_read_nit(pcap_t *p, int cnt, pcap_handler callback, u_char *user)
  90. {
  91. struct pcap_nit *pn = p->priv;
  92. register int cc, n;
  93. register u_char *bp, *cp, *ep;
  94. register struct nit_hdr *nh;
  95. register int caplen;
  96. cc = p->cc;
  97. if (cc == 0) {
  98. cc = read(p->fd, (char *)p->buffer, p->bufsize);
  99. if (cc < 0) {
  100. if (errno == EWOULDBLOCK)
  101. return (0);
  102. pcap_fmt_errmsg_for_errno(p->errbuf, sizeof(p->errbuf),
  103. errno, "pcap_read");
  104. return (-1);
  105. }
  106. bp = (u_char *)p->buffer;
  107. } else
  108. bp = p->bp;
  109. /*
  110. * Loop through each packet. The increment expression
  111. * rounds up to the next int boundary past the end of
  112. * the previous packet.
  113. */
  114. n = 0;
  115. ep = bp + cc;
  116. while (bp < ep) {
  117. /*
  118. * Has "pcap_breakloop()" been called?
  119. * If so, return immediately - if we haven't read any
  120. * packets, clear the flag and return -2 to indicate
  121. * that we were told to break out of the loop, otherwise
  122. * leave the flag set, so that the *next* call will break
  123. * out of the loop without having read any packets, and
  124. * return the number of packets we've processed so far.
  125. */
  126. if (p->break_loop) {
  127. if (n == 0) {
  128. p->break_loop = 0;
  129. return (-2);
  130. } else {
  131. p->cc = ep - bp;
  132. p->bp = bp;
  133. return (n);
  134. }
  135. }
  136. nh = (struct nit_hdr *)bp;
  137. cp = bp + sizeof(*nh);
  138. switch (nh->nh_state) {
  139. case NIT_CATCH:
  140. break;
  141. case NIT_NOMBUF:
  142. case NIT_NOCLUSTER:
  143. case NIT_NOSPACE:
  144. pn->stat.ps_drop = nh->nh_dropped;
  145. continue;
  146. case NIT_SEQNO:
  147. continue;
  148. default:
  149. pcap_snprintf(p->errbuf, sizeof(p->errbuf),
  150. "bad nit state %d", nh->nh_state);
  151. return (-1);
  152. }
  153. ++pn->stat.ps_recv;
  154. bp += ((sizeof(struct nit_hdr) + nh->nh_datalen +
  155. sizeof(int) - 1) & ~(sizeof(int) - 1));
  156. caplen = nh->nh_wirelen;
  157. if (caplen > p->snapshot)
  158. caplen = p->snapshot;
  159. if (bpf_filter(p->fcode.bf_insns, cp, nh->nh_wirelen, caplen)) {
  160. struct pcap_pkthdr h;
  161. h.ts = nh->nh_timestamp;
  162. h.len = nh->nh_wirelen;
  163. h.caplen = caplen;
  164. (*callback)(user, &h, cp);
  165. if (++n >= cnt && !PACKET_COUNT_IS_UNLIMITED(cnt)) {
  166. p->cc = ep - bp;
  167. p->bp = bp;
  168. return (n);
  169. }
  170. }
  171. }
  172. p->cc = 0;
  173. return (n);
  174. }
  175. static int
  176. pcap_inject_nit(pcap_t *p, const void *buf, size_t size)
  177. {
  178. struct sockaddr sa;
  179. int ret;
  180. memset(&sa, 0, sizeof(sa));
  181. strncpy(sa.sa_data, device, sizeof(sa.sa_data));
  182. ret = sendto(p->fd, buf, size, 0, &sa, sizeof(sa));
  183. if (ret == -1) {
  184. pcap_fmt_errmsg_for_errno(p->errbuf, PCAP_ERRBUF_SIZE,
  185. errno, "send");
  186. return (-1);
  187. }
  188. return (ret);
  189. }
  190. static int
  191. nit_setflags(pcap_t *p)
  192. {
  193. struct nit_ioc nioc;
  194. memset(&nioc, 0, sizeof(nioc));
  195. nioc.nioc_typetomatch = NT_ALLTYPES;
  196. nioc.nioc_snaplen = p->snapshot;
  197. nioc.nioc_bufalign = sizeof(int);
  198. nioc.nioc_bufoffset = 0;
  199. if (p->opt.buffer_size != 0)
  200. nioc.nioc_bufspace = p->opt.buffer_size;
  201. else {
  202. /* Default buffer size */
  203. nioc.nioc_bufspace = BUFSPACE;
  204. }
  205. if (p->opt.immediate) {
  206. /*
  207. * XXX - will this cause packets to be delivered immediately?
  208. * XXX - given that this is for SunOS prior to 4.0, do
  209. * we care?
  210. */
  211. nioc.nioc_chunksize = 0;
  212. } else
  213. nioc.nioc_chunksize = CHUNKSIZE;
  214. if (p->opt.timeout != 0) {
  215. nioc.nioc_flags |= NF_TIMEOUT;
  216. nioc.nioc_timeout.tv_sec = p->opt.timeout / 1000;
  217. nioc.nioc_timeout.tv_usec = (p->opt.timeout * 1000) % 1000000;
  218. }
  219. if (p->opt.promisc)
  220. nioc.nioc_flags |= NF_PROMISC;
  221. if (ioctl(p->fd, SIOCSNIT, &nioc) < 0) {
  222. pcap_fmt_errmsg_for_errno(p->errbuf, PCAP_ERRBUF_SIZE,
  223. errno, "SIOCSNIT");
  224. return (-1);
  225. }
  226. return (0);
  227. }
  228. static int
  229. pcap_activate_nit(pcap_t *p)
  230. {
  231. int fd;
  232. struct sockaddr_nit snit;
  233. if (p->opt.rfmon) {
  234. /*
  235. * No monitor mode on SunOS 3.x or earlier (no
  236. * Wi-Fi *devices* for the hardware that supported
  237. * them!).
  238. */
  239. return (PCAP_ERROR_RFMON_NOTSUP);
  240. }
  241. /*
  242. * Turn a negative snapshot value (invalid), a snapshot value of
  243. * 0 (unspecified), or a value bigger than the normal maximum
  244. * value, into the maximum allowed value.
  245. *
  246. * If some application really *needs* a bigger snapshot
  247. * length, we should just increase MAXIMUM_SNAPLEN.
  248. */
  249. if (p->snapshot <= 0 || p->snapshot > MAXIMUM_SNAPLEN)
  250. p->snapshot = MAXIMUM_SNAPLEN;
  251. if (p->snapshot < 96)
  252. /*
  253. * NIT requires a snapshot length of at least 96.
  254. */
  255. p->snapshot = 96;
  256. memset(p, 0, sizeof(*p));
  257. p->fd = fd = socket(AF_NIT, SOCK_RAW, NITPROTO_RAW);
  258. if (fd < 0) {
  259. pcap_fmt_errmsg_for_errno(p->errbuf, PCAP_ERRBUF_SIZE,
  260. errno, "socket");
  261. goto bad;
  262. }
  263. snit.snit_family = AF_NIT;
  264. (void)strncpy(snit.snit_ifname, p->opt.device, NITIFSIZ);
  265. if (bind(fd, (struct sockaddr *)&snit, sizeof(snit))) {
  266. /*
  267. * XXX - there's probably a particular bind error that
  268. * means "there's no such device" and a particular bind
  269. * error that means "that device doesn't support NIT";
  270. * they might be the same error, if they both end up
  271. * meaning "NIT doesn't know about that device".
  272. */
  273. pcap_fmt_errmsg_for_errno(p->errbuf, PCAP_ERRBUF_SIZE,
  274. errno, "bind: %s", snit.snit_ifname);
  275. goto bad;
  276. }
  277. if (nit_setflags(p) < 0)
  278. goto bad;
  279. /*
  280. * NIT supports only ethernets.
  281. */
  282. p->linktype = DLT_EN10MB;
  283. p->bufsize = BUFSPACE;
  284. p->buffer = malloc(p->bufsize);
  285. if (p->buffer == NULL) {
  286. pcap_fmt_errmsg_for_errno(p->errbuf, PCAP_ERRBUF_SIZE,
  287. errno, "malloc");
  288. goto bad;
  289. }
  290. /*
  291. * "p->fd" is a socket, so "select()" should work on it.
  292. */
  293. p->selectable_fd = p->fd;
  294. /*
  295. * This is (presumably) a real Ethernet capture; give it a
  296. * link-layer-type list with DLT_EN10MB and DLT_DOCSIS, so
  297. * that an application can let you choose it, in case you're
  298. * capturing DOCSIS traffic that a Cisco Cable Modem
  299. * Termination System is putting out onto an Ethernet (it
  300. * doesn't put an Ethernet header onto the wire, it puts raw
  301. * DOCSIS frames out on the wire inside the low-level
  302. * Ethernet framing).
  303. */
  304. p->dlt_list = (u_int *) malloc(sizeof(u_int) * 2);
  305. /*
  306. * If that fails, just leave the list empty.
  307. */
  308. if (p->dlt_list != NULL) {
  309. p->dlt_list[0] = DLT_EN10MB;
  310. p->dlt_list[1] = DLT_DOCSIS;
  311. p->dlt_count = 2;
  312. }
  313. p->read_op = pcap_read_nit;
  314. p->inject_op = pcap_inject_nit;
  315. p->setfilter_op = install_bpf_program; /* no kernel filtering */
  316. p->setdirection_op = NULL; /* Not implemented. */
  317. p->set_datalink_op = NULL; /* can't change data link type */
  318. p->getnonblock_op = pcap_getnonblock_fd;
  319. p->setnonblock_op = pcap_setnonblock_fd;
  320. p->stats_op = pcap_stats_nit;
  321. return (0);
  322. bad:
  323. pcap_cleanup_live_common(p);
  324. return (PCAP_ERROR);
  325. }
  326. pcap_t *
  327. pcap_create_interface(const char *device _U_, char *ebuf)
  328. {
  329. pcap_t *p;
  330. p = pcap_create_common(ebuf, sizeof (struct pcap_nit));
  331. if (p == NULL)
  332. return (NULL);
  333. p->activate_op = pcap_activate_nit;
  334. return (p);
  335. }
  336. /*
  337. * XXX - there's probably a particular bind error that means "that device
  338. * doesn't support NIT"; if so, we should try a bind and use that.
  339. */
  340. static int
  341. can_be_bound(const char *name _U_)
  342. {
  343. return (1);
  344. }
  345. static int
  346. get_if_flags(const char *name _U_, bpf_u_int32 *flags _U_, char *errbuf _U_)
  347. {
  348. /*
  349. * Nothing we can do.
  350. * XXX - is there a way to find out whether an adapter has
  351. * something plugged into it?
  352. */
  353. return (0);
  354. }
  355. int
  356. pcap_platform_finddevs(pcap_if_list_t *devlistp, char *errbuf)
  357. {
  358. return (pcap_findalldevs_interfaces(devlistp, errbuf, can_be_bound,
  359. get_if_flags));
  360. }
  361. /*
  362. * Libpcap version string.
  363. */
  364. const char *
  365. pcap_lib_version(void)
  366. {
  367. return (PCAP_VERSION_STRING);
  368. }