static pcap_t* open_pcap_dev(const char* ifname, int frameSize, char* errbuf) { pcap_t* handle = pcap_create(ifname, errbuf); if (handle) { int err; err = pcap_set_snaplen(handle, frameSize); if (err) AVB_LOGF_WARNING("Cannot set snap len %d", err); err = pcap_set_promisc(handle, 1); if (err) AVB_LOGF_WARNING("Cannot set promisc %d", err); err = pcap_set_immediate_mode(handle, 1); if (err) AVB_LOGF_WARNING("Cannot set immediate mode %d", err); // we need timeout (here 100ms) otherwise we could block for ever err = pcap_set_timeout(handle, 100); if (err) AVB_LOGF_WARNING("Cannot set timeout %d", err); err = pcap_set_tstamp_precision(handle, PCAP_TSTAMP_PRECISION_NANO); if (err) AVB_LOGF_WARNING("Cannot set tstamp nano precision %d", err); err = pcap_set_tstamp_type(handle, PCAP_TSTAMP_ADAPTER_UNSYNCED); if (err) AVB_LOGF_WARNING("Cannot set tstamp adapter unsynced %d", err); err = pcap_activate(handle); if (err) AVB_LOGF_WARNING("Cannot activate pcap %d", err); } return handle; }
void Sniffer::set_immediate_mode(bool enabled) { // As of libpcap version 1.5.0 this function exists. Before, it was // technically always immediate mode since capture used TPACKET_V1/2 // which doesn't do packet buffering. #ifdef HAVE_PCAP_IMMEDIATE_MODE if (pcap_set_immediate_mode(get_pcap_handle(), enabled)) { throw pcap_error(pcap_geterr(get_pcap_handle())); } #endif // HAVE_PCAP_IMMEDIATE_MODE }
//------------------------------------------------------------------------------ static pcap_t* startPcap(void) { pcap_t* pPcapInst = NULL; char errorMessage[PCAP_ERRBUF_SIZE]; // Create a pcap live capture handle pPcapInst = pcap_create(edrvInstance_l.initParam.pDevName, errorMessage); if (pPcapInst == NULL) { DEBUG_LVL_ERROR_TRACE("%s() Error!! Can't open pcap: %s\n", __func__, errorMessage); } // Set snapshot length for a not-yet-activated capture handle if (pcap_set_snaplen(pPcapInst, 65535) < 0) { DEBUG_LVL_ERROR_TRACE("%s() couldn't set PCAP snap length\n", __func__); } // Set promiscuous mode for a not-yet-activated capture handle if (pcap_set_promisc(pPcapInst, 1) < 0) { DEBUG_LVL_ERROR_TRACE("%s() couldn't set PCAP promiscuous mode\n", __func__); } // Pcap immediate mode only supported by libpcap >=1.5.0 #ifdef PCAP_ERROR_TSTAMP_PRECISION_NOTSUP // Set immediate mode for a not-yet-activated capture handle if (pcap_set_immediate_mode(pPcapInst, 1) < 0) { DEBUG_LVL_ERROR_TRACE("%s() couldn't set PCAP immediate mode\n", __func__); } #endif // Activate the pcap capture handle with the previous parameters if (pcap_activate(pPcapInst) < 0) { DEBUG_LVL_ERROR_TRACE("%s() couldn't activate PCAP\n", __func__); } return pPcapInst; }
int main(int argc, char **argv) { register int op; register char *cp, *cmdbuf, *device; long longarg; char *p; int timeout = 1000; int immediate = 0; int nonblock = 0; bpf_u_int32 localnet, netmask; struct bpf_program fcode; char ebuf[PCAP_ERRBUF_SIZE]; int status; int packet_count; device = NULL; if ((cp = strrchr(argv[0], '/')) != NULL) program_name = cp + 1; else program_name = argv[0]; opterr = 0; while ((op = getopt(argc, argv, "i:mnt:")) != -1) { switch (op) { case 'i': device = optarg; break; case 'm': immediate = 1; break; case 'n': nonblock = 1; break; case 't': longarg = strtol(optarg, &p, 10); if (p == optarg || *p != '\0') { error("Timeout value \"%s\" is not a number", optarg); /* NOTREACHED */ } if (longarg < 0) { error("Timeout value %ld is negative", longarg); /* NOTREACHED */ } if (longarg > INT_MAX) { error("Timeout value %ld is too large (> %d)", longarg, INT_MAX); /* NOTREACHED */ } timeout = (int)longarg; break; default: usage(); /* NOTREACHED */ } } if (device == NULL) { device = pcap_lookupdev(ebuf); if (device == NULL) error("%s", ebuf); } *ebuf = '\0'; pd = pcap_create(device, ebuf); if (pd == NULL) error("%s", ebuf); status = pcap_set_snaplen(pd, 65535); if (status != 0) error("%s: pcap_set_snaplen failed: %s", device, pcap_statustostr(status)); if (immediate) { status = pcap_set_immediate_mode(pd, 1); if (status != 0) error("%s: pcap_set_immediate_mode failed: %s", device, pcap_statustostr(status)); } status = pcap_set_timeout(pd, timeout); if (status != 0) error("%s: pcap_set_timeout failed: %s", device, pcap_statustostr(status)); status = pcap_activate(pd); if (status < 0) { /* * pcap_activate() failed. */ error("%s: %s\n(%s)", device, pcap_statustostr(status), pcap_geterr(pd)); } else if (status > 0) { /* * pcap_activate() succeeded, but it's warning us * of a problem it had. */ warning("%s: %s\n(%s)", device, pcap_statustostr(status), pcap_geterr(pd)); } if (pcap_lookupnet(device, &localnet, &netmask, ebuf) < 0) { localnet = 0; netmask = 0; warning("%s", ebuf); } cmdbuf = copy_argv(&argv[optind]); if (pcap_compile(pd, &fcode, cmdbuf, 1, netmask) < 0) error("%s", pcap_geterr(pd)); if (pcap_setfilter(pd, &fcode) < 0) error("%s", pcap_geterr(pd)); if (pcap_setnonblock(pd, nonblock, ebuf) == -1) error("pcap_setnonblock failed: %s", ebuf); printf("Listening on %s\n", device); for (;;) { packet_count = 0; status = pcap_dispatch(pd, -1, countme, (u_char *)&packet_count); if (status < 0) break; if (status != 0) { printf("%d packets seen, %d packets counted after pcap_dispatch returns\n", status, packet_count); } } if (status == -2) { /* * We got interrupted, so perhaps we didn't * manage to finish a line we were printing. * Print an extra newline, just in case. */ putchar('\n'); } (void)fflush(stdout); if (status == -1) { /* * Error. Report it. */ (void)fprintf(stderr, "%s: pcap_loop: %s\n", program_name, pcap_geterr(pd)); } pcap_close(pd); exit(status == -1 ? 1 : 0); }
static int tc_pcap_open(pcap_t **pd, char *device, int snap_len, int buf_size) { int status; char ebuf[PCAP_ERRBUF_SIZE]; *ebuf = '\0'; *pd = pcap_create(device, ebuf); if (*pd == NULL) { tc_log_info(LOG_ERR, 0, "pcap create error:%s", ebuf); fprintf(stderr, "pcap create error:%s\n", ebuf); return TC_ERR; } status = pcap_set_snaplen(*pd, snap_len); if (status != 0) { tc_log_info(LOG_ERR, 0, "pcap_set_snaplen error:%s", pcap_statustostr(status)); return TC_ERR; } status = pcap_set_promisc(*pd, 1); if (status != 0) { tc_log_info(LOG_ERR, 0, "pcap_set_promisc error:%s", pcap_statustostr(status)); } status = pcap_set_timeout(*pd, 10); if (status != 0) { tc_log_info(LOG_ERR, 0, "pcap_set_timeout error:%s", pcap_statustostr(status)); return TC_ERR; } status = pcap_set_buffer_size(*pd, buf_size); if (status != 0) { tc_log_info(LOG_ERR, 0, "pcap_set_buffer_size error:%s", pcap_statustostr(status)); return TC_ERR; } tc_log_info(LOG_NOTICE, 0, "pcap_set_buffer_size:%d", buf_size); #if (HAVE_SET_IMMEDIATE_MODE) status = pcap_set_immediate_mode(*pd, 1); if (status != 0) { tc_log_info(LOG_ERR, 0, "pcap_set_immediate_mode error:%s", pcap_statustostr(status)); return TC_ERR; } #endif status = pcap_activate(*pd); if (status < 0) { tc_log_info(LOG_ERR, 0, "pcap_activate error:%s", pcap_statustostr(status)); return TC_ERR; } else if (status > 0) { tc_log_info(LOG_WARN, 0, "pcap activate warn:%s", pcap_statustostr(status)); } return TC_OK; }
pcap_t *pcap_open(const char *source, int snaplen, int flags, int read_timeout, struct pcap_rmtauth *auth, char *errbuf) { char name[PCAP_BUF_SIZE]; int type; pcap_t *fp; int status; /* * A null device name is equivalent to the "any" device - * which might not be supported on this platform, but * this means that you'll get a "not supported" error * rather than, say, a crash when we try to dereference * the null pointer. */ if (source == NULL) source = "any"; if (strlen(source) > PCAP_BUF_SIZE) { pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "The source string is too long. Cannot handle it correctly."); return NULL; } /* * Determine the type of the source (file, local, remote) and, * if it's file or local, the name of the file or capture device. */ if (pcap_parsesrcstr(source, &type, NULL, NULL, name, errbuf) == -1) return NULL; switch (type) { case PCAP_SRC_FILE: return pcap_open_offline(name, errbuf); case PCAP_SRC_IFLOCAL: fp = pcap_create(name, errbuf); break; case PCAP_SRC_IFREMOTE: /* * Although we already have host, port and iface, we prefer * to pass only 'source' to pcap_open_rpcap(), so that it * has to call pcap_parsesrcstr() again. * This is less optimized, but much clearer. */ return pcap_open_rpcap(source, snaplen, flags, read_timeout, auth, errbuf); default: pcap_strlcpy(errbuf, "Source type not supported", PCAP_ERRBUF_SIZE); return NULL; } if (fp == NULL) return (NULL); status = pcap_set_snaplen(fp, snaplen); if (status < 0) goto fail; if (flags & PCAP_OPENFLAG_PROMISCUOUS) { status = pcap_set_promisc(fp, 1); if (status < 0) goto fail; } if (flags & PCAP_OPENFLAG_MAX_RESPONSIVENESS) { status = pcap_set_immediate_mode(fp, 1); if (status < 0) goto fail; } #ifdef _WIN32 /* * This flag is supported on Windows only. * XXX - is there a way to support it with * the capture mechanisms on UN*X? It's not * exactly a "set direction" operation; I * think it means "do not capture packets * injected with pcap_sendpacket() or * pcap_inject()". */ /* disable loopback capture if requested */ if (flags & PCAP_OPENFLAG_NOCAPTURE_LOCAL) fp->opt.nocapture_local = 1; #endif /* _WIN32 */ status = pcap_set_timeout(fp, read_timeout); if (status < 0) goto fail; status = pcap_activate(fp); if (status < 0) goto fail; return fp; fail: if (status == PCAP_ERROR) pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "%s: %s", name, fp->errbuf); else if (status == PCAP_ERROR_NO_SUCH_DEVICE || status == PCAP_ERROR_PERM_DENIED || status == PCAP_ERROR_PROMISC_PERM_DENIED) pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "%s: %s (%s)", name, pcap_statustostr(status), fp->errbuf); else pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "%s: %s", name, pcap_statustostr(status)); pcap_close(fp); return NULL; }
int main(int argc, char *argv[]) { signal (SIGINT, signal_handler); //printf("\033[?1049h\033[H"); clear_log(); my_log("Software switch starting..."); my_log(pcap_lib_version()); int option = 0, ret; char c; pthread_t config_thread; char errbuf[PCAP_ERRBUF_SIZE]; p1 = create_port_struct(1); p2 = create_port_struct(2); while ((option = getopt(argc, argv,"h l 1:2: m")) != -1) { switch (option) { case '1' : strcpy(p1->name, optarg); break; case '2' : strcpy(p2->name, optarg); break; case 'l': list_interfaces(); exit(0); case 'm': mock_rule(); break; case 'h': default: print_usage(); exit(EXIT_FAILURE); } } p1->handle = pcap_create(p1->name, errbuf); if ( (ret = pcap_setdirection(p1->handle, PCAP_D_IN)) != 0){ printf("pcap_setdirection returned %i\n", ret); my_log("pcap_setdirection failed"); pcap_perror(p1->handle, 0); //exit(-1); } if ( pcap_set_promisc(p1->handle, 1) != 0){ printf("pcap_set_promisc returned \n%s\n", pcap_geterr(p1->handle)); my_log("pcap_set_promisc failed"); pcap_perror(p1->handle, 0); exit(-1); } if ( pcap_set_immediate_mode(p1->handle, 1) != 0){ printf("pcap_set_immediate_mode returned \n%s\n", pcap_geterr(p1->handle)); my_log("pcap_set_immediate_mode failed"); pcap_perror(p1->handle, 0); exit(-1); } if ( pcap_activate(p1->handle)){ printf("Failed to open interface %s\n", pcap_geterr(p1->handle)); exit(-1); } else { sprintf(log_b, "Handle activated for %s", p1->name); my_log(log_b); } p2->handle = pcap_create(p2->name, errbuf); if ( pcap_setdirection(p2->handle, PCAP_D_OUT) != 0){ my_log("pcap_setdirection failed"); pcap_perror(p2->handle, 0); //exit(-1); } if ( pcap_set_promisc(p2->handle, 1) != 0){ my_log("pcap_set_promisc failed"); pcap_perror(p2->handle, 0); exit(-1); } if ( pcap_set_immediate_mode(p2->handle, 1) != 0){ my_log("pcap_set_immediate_mode failed"); pcap_perror(p2->handle, 0); exit(-1); } if ( pcap_activate(p2->handle)){ printf("Failed to open interface %s\n", pcap_geterr(p2->handle)); exit(-1); } else { sprintf(log_b, "Handle activated for %s", p2->name); my_log(log_b); } //exit(0); my_log("Deleting mac table.."); clear_mac(); sprintf(log_b, "Default action is %s", (DEFAULT_ACTION == R_ALLOW)? "R_ALLOW" : "R_DENY"); my_log(log_b); my_log("Creating threads..."); pthread_mutex_init(&mutex, NULL); if ( pthread_create(&(p1->thread), 0, port_listener, (void *)p1) ){ my_log("Error creating p1 thread"); exit(-1); } if ( pthread_create(&(p2->thread), 0, port_listener, (void *)p2) ){ my_log("Error creating p2 thread"); exit(-1); } pthread_create(&config_thread, 0, config, 0); while (1) { mac_delete_old_entries(5); if(pause_rendering == 1) continue; // render here system("clear"); print_mac(); print_rules(); print_stats_header(); print_stats(p1->in, "1 IN"); print_stats(p1->out, "1 OUT"); print_stats(p2->in, "2 IN"); print_stats(p2->out, "2 OUT"); printf("p1in: %i\tp1out: %i\tp2in: %i\tp2out: %i\n", p1in, p1out, p2in, p2out); sleep(1); } pthread_join(config_thread, 0); pthread_join(p1->thread, 0); pthread_join(p2->thread, 0); //printf("\033[?1049l"); // go back return 0; }