diff --git a/README.md b/README.md index 2f7c644..f64ac1e 100644 --- a/README.md +++ b/README.md @@ -26,7 +26,6 @@ Supported packet capture engines - PCAP - AF_PACKET - Netmap -- SnabbSwitch (experimental) - PF_RING / PF_RING ZC (available only for CentOS 6 for compatibiliy, otherwise use AF_PACKET) You can check out the [comparison table](https://fastnetmon.com/docs/capture_backends/) for all available packet capture engines. diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 01b7fc4..4eebb78 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -210,15 +210,6 @@ add_library(ipfix_rfc STATIC ipfix_rfc.cpp) # Our packet parser add_library(fastnetmon_packet_parser STATIC fastnetmon_packet_parser.c) -# -DENABLE_SNABBSWITCH_SUPPORT=ON .. -if (ENABLE_SNABBSWITCH_SUPPORT) - add_definitions(-DSNABB_SWITCH) - add_library(snabbswitch_plugin STATIC snabbswitch_plugin/snabbswitch_collector.cpp) - - link_directories(/usr/src/snabbswitch/src) - target_link_libraries(snabbswitch_plugin snabb) -endif() - CHECK_CXX_SOURCE_COMPILES(" #include int main() { @@ -580,10 +571,6 @@ if (ENABLE_GOBGP_SUPPORT) target_link_libraries(fastnetmon gobgp_action) endif() -if (ENABLE_SNABBSWITCH_SUPPORT) - target_link_libraries(fastnetmon snabbswitch_plugin) -endif() - if (ENABLE_AFPACKET_SUPPORT) target_link_libraries(fastnetmon afpacket_plugin) endif() @@ -598,10 +585,6 @@ endif() if (BUILD_PLUGIN_RUNNER) add_executable(fastnetmon_plugin_runner plugin_runner.cpp) - if (ENABLE_SNABBSWITCH_SUPPORT) - target_link_libraries(fastnetmon_plugin_runner snabbswitch_plugin) - endif() - if (ENABLE_AFPACKET_SUPPORT) target_link_libraries(fastnetmon_plugin_runner afpacket_plugin) endif() diff --git a/src/fast_platform.h b/src/fast_platform.h deleted file mode 100644 index ac9b436..0000000 --- a/src/fast_platform.h +++ /dev/null @@ -1,27 +0,0 @@ -#ifndef FAST_PLATFORM_H -#define FAST_PLATFORM_H - -// This file automatically generated for your platform (Linux, FreeBSD and others) with cmake - -/* Platform specific paths */ - -std::string fastnetmon_version = "1.1.8 master git-23efd99d277a4e3161c3e6c510ad010e6e436842"; - -std::string pid_path = "/var/run/fastnetmon.pid"; -std::string global_config_path = "/etc/fastnetmon.conf"; - -std::string log_file_path = "/var/log/fastnetmon.log"; -std::string attack_details_folder = "/var/log/fastnetmon_attacks"; - -// Default path to notify script -std::string notify_script_path = "/usr/local/bin/notify_about_attack.sh"; - -// Default path to file with networks for whitelising -std::string white_list_path = "/etc/networks_whitelist"; - -// Default path to file with all networks listing -std::string networks_list_path = "/etc/networks_list"; - -/* Platform specific paths end */ - -#endif diff --git a/src/fastnetmon.conf b/src/fastnetmon.conf index ca9a353..a48f31c 100644 --- a/src/fastnetmon.conf +++ b/src/fastnetmon.conf @@ -92,9 +92,6 @@ pfring_sampling_ratio = 1 # Netmap traffic capture (very fast but needs patched drivers) mirror_netmap = off -# SnabbSwitch traffic capture -mirror_snabbswitch = off - # AF_PACKET capture engine # Please use it only with modern Linux kernels (3.6 and more) # And please install birq for irq ditribution over cores @@ -108,9 +105,6 @@ mirror_af_packet_custom_sampling_rate = 1 # Available modes: cpu, lb, hash, random, rollover, queue_mapping mirror_af_packet_fanout_mode = cpu -# use PCI-e addresses here instead of OS device names. You can find them in "lspci" output -interfaces_snabbswitch = 0000:04:00.0,0000:04:00.1,0000:03:00.0,0000:03:00.1 - # Port mirroring sampling ratio netmap_sampling_ratio = 1 diff --git a/src/fastnetmon.cpp b/src/fastnetmon.cpp index 1a6423f..049b001 100644 --- a/src/fastnetmon.cpp +++ b/src/fastnetmon.cpp @@ -66,10 +66,6 @@ #include "pfring_plugin/pfring_collector.h" #endif -#ifdef SNABB_SWITCH -#include "snabbswitch_plugin/snabbswitch_collector.h" -#endif - #ifdef FASTNETMON_ENABLE_AFPACKET #include "afpacket_plugin/afpacket_collector.h" #endif @@ -263,7 +259,6 @@ void init_global_ban_settings() { bool enable_conection_tracking = true; -bool enable_snabbswitch_collection = false; bool enable_afpacket_collection = false; bool enable_data_collection_from_mirror = true; bool enable_netmap_collection = false; @@ -1316,10 +1311,6 @@ bool load_configuration_file() { } } - if (configuration_map.count("mirror_snabbswitch") != 0) { - enable_snabbswitch_collection = configuration_map["mirror_snabbswitch"] == "on"; - } - if (configuration_map.count("mirror_afpacket") != 0) { enable_afpacket_collection = configuration_map["mirror_afpacket"] == "on"; } @@ -3085,12 +3076,6 @@ int main(int argc, char** argv) { } #endif -#ifdef SNABB_SWITCH - if (enable_snabbswitch_collection) { - packet_capture_plugin_thread_group.add_thread(new boost::thread(start_snabbswitch_collection, process_packet)); - } -#endif - #ifdef FASTNETMON_ENABLE_AFPACKET if (enable_afpacket_collection) { packet_capture_plugin_thread_group.add_thread(new boost::thread(start_afpacket_collection, process_packet)); diff --git a/src/grep.sh b/src/grep.sh new file mode 100755 index 0000000..8ff2c29 --- /dev/null +++ b/src/grep.sh @@ -0,0 +1,10 @@ +#!/bin/bash + +script_dir=`dirname "$0"` + +find $script_dir/.. -type f | egrep -v 'fastnetmon.pb.cc|.git|build'> /tmp/file_list + +for i in `cat /tmp/file_list` ; do + grep -Hi "$1" $i +done + diff --git a/src/plugin_runner.cpp b/src/plugin_runner.cpp index c4bede8..dc3e3c7 100644 --- a/src/plugin_runner.cpp +++ b/src/plugin_runner.cpp @@ -25,10 +25,6 @@ #include "afpacket_plugin/afpacket_collector.h" #endif -#ifdef SNABB_SWITCH -#include "snabbswitch_plugin/snabbswitch_collector.h" -#endif - #ifdef NETMAP_PLUGIN #include "netmap_plugin/netmap_collector.h" #endif @@ -108,7 +104,7 @@ int main(int argc, char* argv[]) { init_logging(); if (argc < 2) { - std::cout << "Please specify sflow, netflow, raw, dpi, snabbswitch, afpacket as param" << std::endl; + std::cout << "Please specify sflow, netflow, raw, dpi, afpacket as param" << std::endl; return 1; } @@ -138,14 +134,6 @@ int main(int argc, char* argv[]) { } else if (strstr(argv[1], "pcap") != NULL) { std::cout << "Starting pcap" << std::endl; start_pcap_collection(process_packet); - } else if (strstr(argv[1], "snabbswitch") != NULL) { - std::cout << "Starting snabbswitch" << std::endl; - -#ifdef SNABB_SWITCH - start_snabbswitch_collection(process_packet); -#else - printf("SnabbSwitch support is not compiled here\n"); -#endif } else if (strstr(argv[1], "pfring") != NULL) { #ifdef PF_RING std::cout << "Starting pf_ring" << std::endl; diff --git a/src/snabbswitch_plugin/snabbswitch_collector.cpp b/src/snabbswitch_plugin/snabbswitch_collector.cpp deleted file mode 100644 index 2824941..0000000 --- a/src/snabbswitch_plugin/snabbswitch_collector.cpp +++ /dev/null @@ -1,155 +0,0 @@ -// log4cpp logging facility -#include "log4cpp/Appender.hh" -#include "log4cpp/BasicLayout.hh" -#include "log4cpp/Category.hh" -#include "log4cpp/FileAppender.hh" -#include "log4cpp/Layout.hh" -#include "log4cpp/OstreamAppender.hh" -#include "log4cpp/PatternLayout.hh" -#include "log4cpp/Priority.hh" - -#include -#include - -#include "../fast_library.h" - -// For support uint32_t, uint16_t -#include - -// For config map operations -#include -#include - -#include -#include -#include - -#include "../fastnetmon_packet_parser.h" - -// For support: IPPROTO_TCP, IPPROTO_ICMP, IPPROTO_UDP -#include -#include -#include - -#include "snabbswitch_collector.h" - -#include "unified_parser.hpp" - -#ifdef __cplusplus -extern "C" { -#endif - -// This code defined in SnabbSwitch -int start_snabb_switch(int snabb_argc, const char** snabb_argv); - -#ifdef __cplusplus -} -#endif - -// Get log4cpp logger from main program -extern log4cpp::Category& logger; - -// Pass unparsed packets number to main program -extern uint64_t total_unparsed_packets; - -// Global configuration map -extern std::map configuration_map; - -// This variable name should be uniq for every plugin! -process_packet_pointer snabbswitch_process_func_ptr = NULL; - -inline void firehose_packet(const char* pciaddr, char* data, int length); - -/* Intel 82599 "Legacy" receive descriptor format. - * See Intel 82599 data sheet section 7.1.5. - * http://www.intel.com/content/dam/www/public/us/en/documents/datasheets/82599-10-gbe-controller-datasheet.pdf - */ -struct firehose_rdesc { - uint64_t address; - uint16_t length; - uint16_t cksum; - uint8_t status; - uint8_t errors; - uint16_t vlan; -} __attribute__((packed)); - -void firehose_packet(const char* pciaddr, char* data, int length) { - simple_packet_t packet; - - if (!parse_raw_packet_to_simple_packet((u_char*)data, length, packet, false)) { - total_unparsed_packets++; - - return; - } - - snabbswitch_process_func_ptr(packet); -} - -#ifdef __cplusplus -extern "C" { -#endif - -int firehose_callback_v1(const char* pciaddr, char** packets, struct firehose_rdesc* rxring, int ring_size, int index); - -#ifdef __cplusplus -} -#endif - -int firehose_callback_v1(const char* pciaddr, char** packets, struct firehose_rdesc* rxring, int ring_size, int index) { - while (rxring[index].status & 1) { - int next_index = (index + 1) & (ring_size - 1); - __builtin_prefetch(packets[next_index]); - firehose_packet(pciaddr, packets[index], rxring[index].length); - rxring[index].status = 0; /* reset descriptor for reuse */ - index = next_index; - } - - return index; -} - -void start_snabbswitch_collection(process_packet_pointer func_ptr) { - logger << log4cpp::Priority::INFO << "SnabbSwitch plugin started"; - snabbswitch_process_func_ptr = func_ptr; - - std::string interfaces_list = ""; - - if (configuration_map.count("interfaces_snabbswitch") != 0) { - interfaces_list = configuration_map["interfaces_snabbswitch"]; - } - - std::vector interfaces_for_capture; - boost::split(interfaces_for_capture, interfaces_list, boost::is_any_of(","), boost::token_compress_on); - - if (interfaces_for_capture.size() == 0) { - logger << log4cpp::Priority::ERROR << "Please specify list of PCI-e addresses for SnabbSwitch capture"; - } - - logger << log4cpp::Priority::INFO << "SnabbSwitch will listen on " - << interfaces_for_capture.size() << " interfaces"; - - boost::thread_group snabbswitch_main_threads; - - for (std::vector::iterator interface = interfaces_for_capture.begin(); - interface != interfaces_for_capture.end(); ++interface) { - - // We could specify multiple NIC's for single thread with multiple --input - const char* cli_arguments[5]; - - cli_arguments[0] = "snabb"; // emulate call of standard application - cli_arguments[1] = "firehose"; - cli_arguments[2] = "--input"; - cli_arguments[3] = interface->c_str(); - cli_arguments[4] = "weird_data"; - - int cli_number_of_arguments = sizeof(cli_arguments) / sizeof(char*); - - logger << log4cpp::Priority::INFO - << "We are starting SnabbSwitch instance for PCIe interface " << *interface; - snabbswitch_main_threads.add_thread( - new boost::thread(start_snabb_switch, cli_number_of_arguments, cli_arguments)); - // We should sleep here because init code of SnabbSwitch is not thread safe - sleep(10); - } - - snabbswitch_main_threads.join_all(); -} diff --git a/src/snabbswitch_plugin/snabbswitch_collector.h b/src/snabbswitch_plugin/snabbswitch_collector.h deleted file mode 100644 index 4ddf3e5..0000000 --- a/src/snabbswitch_plugin/snabbswitch_collector.h +++ /dev/null @@ -1,8 +0,0 @@ -#ifndef SNABBSWITCH_PLUGIN_H -#define SNABBSWITCH_PLUGIN_H - -#include "../fastnetmon_types.h" - -void start_snabbswitch_collection(process_packet_pointer func_ptr); - -#endif diff --git a/src/tests/snabb/README.md b/src/tests/snabb/README.md deleted file mode 100644 index 16be055..0000000 --- a/src/tests/snabb/README.md +++ /dev/null @@ -1,73 +0,0 @@ -### Here we store all code related with Snabb switch intergration :) We like it because it's awesome! - -First of all, please compile Snabb Switch from next branch: -```bash -cd /usr/src/ -git clone https://github.com/SnabbCo/snabbswitch.git -b next -cd snabbswitch -make -``` - -Then compile our .so library: -``` -g++ -O3 ../../fastnetmon_packet_parser.c -c -o fastnetmon_packet_parser.o -fPIC -g++ -O3 -shared -o capturecallback.so -fPIC capturecallback.cpp fastnetmon_packet_parser.o -``` - -Polly enabled clang compilation (offer significant speedup): -```bash -alias pollycc="/usr/src/polly/llvm_build/bin/clang -Xclang -load -Xclang /usr/src/polly/llvm_build/lib/LLVMPolly.so" - -pollycc -O3 ../../fastnetmon_packet_parser.c -c -o fastnetmon_packet_parser.o -fPIC -pollycc -O3 -shared -o capturecallback.so -fPIC capturecallback.c fastnetmon_packet_parser.o -``` - -Get NIC's PCI address: -```bash -lspci -m|grep 82599 -00:05.0 "Ethernet controller" "Intel Corporation" "82599ES 10-Gigabit SFI/SFP+ Network Connection" -r01 "Intel Corporation" "Ethernet Server Adapter X520-2" -00:06.0 "Ethernet controller" "Intel Corporation" "82599ES 10-Gigabit SFI/SFP+ Network Connection" -r01 "Intel Corporation" "Ethernet Server Adapter X520-2" -``` - -For example, we will use 00:06.0, we need convert this value to Snabb's format with adding 4 leading zeroes: 0000:00:06.0 - -Run capture: -```bash -/usr/src/snabbswitch/src/snabb firehose --input 0000:03:00.0 --input 0000:03:00.1 /usr/src/fastnetmon/src/tests/snabb/capturecallback.so -``` - -I have got really amazing results: -```bash -Loading shared object: ./capturecallback.so -Initializing NIC: 0000:00:06.0 -Run speed printer from C code -Processing traffic... - -We process: 14566196 pps -We process: 14820487 pps -We process: 14856881 pps -We process: 14863727 pps -``` - -We achieved this with only single logical core of i7 3820 CPU: -```bash -1 [ 0.0%] -5 [ 0.0%] -2 [ 0.0%] -6 [ 0.0%] -3 [ 0.0%] -7 [|||||||||||||||||||||||||||||||||||||||||||||||||||||||||||100.0%] -4 [ 0.0%] -8 [ 0.0%] -``` - -Really awesome! Huge thanks to Luke Gorrie for great help with it! - -Once the testing is done we can rebind the NIC to the kernel `ixgbe` -driver. This can be done either be reloading `ixgbe` or, less -disruptively, like this: - -```bash -echo 0000:00:06.0 | sudo tee /sys/bus/pci/drivers/ixgbe/bind -``` - diff --git a/src/tests/snabb/capturetodisk.cpp b/src/tests/snabb/capturetodisk.cpp deleted file mode 100644 index 51b98db..0000000 --- a/src/tests/snabb/capturetodisk.cpp +++ /dev/null @@ -1,266 +0,0 @@ -// Author: Pavel.Odintsov@gmail.com -// License GPLv2 - -#include -#include -#include -#include -#include -#include - -#include -#include -#include - -#include -#include -#include - -#include "../../fastnetmon_pcap_format.h" - -/* - -Compile it: -g++ -O3 -fPIC -std=c++11 ../../fastnetmon_pcap_format.cpp -c -o fastnetmon_pcap_format.o -g++ -O3 -shared -o capturetodisk.so -fPIC capturetodisk.cpp fastnetmon_pcap_format.o -std=c++11 -lboost_system - -Run it: -/usr/src/snabbswitch/src/snabb firehose --input 0000:02:00.0 --input 0000:02:00.1 /usr/src/fastnetmon/src/tests/snabb/capturetodisk.so - -Please use ext4 with writeback feature: -mount -odata=writeback /dev/sdb /mnt - -*/ - -class packet_buffer_t { - public: - unsigned char buffer[1600]; - unsigned int length; -}; - -typedef std::shared_ptr packet_buffer_shared_pointer_t; -constexpr auto size_spsc_queue = 1048576; - -// We use persistent preallocation for ext4 and allocate 20 GB for storing data before any operations -uint64_t preallocate_packet_dump_file_size = 1073741824ul * 20ul; - -typedef boost::lockfree::spsc_queue > my_spsc_queue_t; - -int pcap_file = 0; -my_spsc_queue_t my_spsc_queue; - -#ifdef __cplusplus -extern "C" { -#endif - -/* Called once before processing packets. */ -void firehose_start(); /* optional */ - -#ifdef __cplusplus -} -#endif - -/* Called once after processing packets. */ -void firehose_stop(); /* optional */ - -void firehose_stop() { - // Close file and flush data - close(pcap_file); -} - -/* - * Process a packet received from a NIC. - * - * pciaddr: name of PCI device packet is received from - * data: packet payload (ethernet frame) - * length: payload length in bytes - */ - -inline void firehose_packet(const char* pciaddr, char* data, int length); - -/* Intel 82599 "Legacy" receive descriptor format. - * See Intel 82599 data sheet section 7.1.5. - * http://www.intel.com/content/dam/www/public/us/en/documents/datasheets/82599-10-gbe-controller-datasheet.pdf - */ -struct firehose_rdesc { - uint64_t address; - uint16_t length; - uint16_t cksum; - uint8_t status; - uint8_t errors; - uint16_t vlan; -} __attribute__((packed)); - -/* Traverse the hardware receive descriptor ring. - * Process each packet that is ready. - * Return the updated ring index. - */ - -#ifdef __cplusplus -extern "C" { -#endif - -int firehose_callback_v1(const char* pciaddr, char** packets, struct firehose_rdesc* rxring, int ring_size, int index) { - while (rxring[index].status & 1) { - int next_index = (index + 1) & (ring_size - 1); - __builtin_prefetch(packets[next_index]); - firehose_packet(pciaddr, packets[index], rxring[index].length); - rxring[index].status = 0; /* reset descriptor for reuse */ - index = next_index; - } - return index; -} - -#ifdef __cplusplus -} -#endif - -uint64_t received_packets = 0; -uint64_t received_bytes = 0; - -void* speed_printer(void* ptr) { - while (1) { - uint64_t packets_before = received_packets; - uint64_t bytes_before = received_bytes; - - sleep(1); - - uint64_t packets_after = received_packets; - uint64_t bytes_after = received_bytes; - - uint64_t pps = packets_after - packets_before; - uint64_t bps = bytes_after - bytes_before; - - float gbps_speed = (float)bps / 1024 / 1024 / 1024 * 8; - float gb_total = (float)received_bytes / 1024 / 1024 / 1024; - - printf("We process: %llu pps %.2f Gbps. We will store %.2f megabytes per second. We have " - "stored %.2f GB of data\n", - (long long)pps, gbps_speed, gbps_speed / 8 * 1024, gb_total); - } -} - -void write_packet_to_file(packet_buffer_shared_pointer_t packet) { - struct timeval current_time; - - current_time.tv_sec = 0; - current_time.tv_usec = 0; - - // It's performance killer! - bool we_do_timestamps = false; - - if (we_do_timestamps) { - gettimeofday(¤t_time, NULL); - } - - struct fastnetmon_pcap_pkthdr pcap_packet_header; - - pcap_packet_header.ts_sec = current_time.tv_sec; - pcap_packet_header.ts_usec = current_time.tv_usec; - - pcap_packet_header.incl_len = packet->length; - pcap_packet_header.orig_len = packet->length; - - unsigned int packet_header_written_bytes = - write(pcap_file, &pcap_packet_header, sizeof(pcap_packet_header)); - - if (packet_header_written_bytes != sizeof(pcap_packet_header)) { - printf("Can't write pcap pcaket header\n"); - } - - unsigned int packet_written_bytes = write(pcap_file, packet->buffer, packet->length); - - if (packet_written_bytes != packet->length) { - printf("Can't write data to file\n"); - } -} - -void* packets_consumer(void* ptr) { - printf("Start consumer thread\n"); - packet_buffer_shared_pointer_t packet; - - while (true) { - while (my_spsc_queue.pop(packet)) { - write_packet_to_file(packet); - - __sync_fetch_and_add(&received_packets, 1); - __sync_fetch_and_add(&received_bytes, packet->length); - } - } -} - -void sigproc(int sig) { - firehose_stop(); - - printf("We caught SINGINT and will finish application\n"); - exit(0); -} - -#ifdef __cplusplus -extern "C" { -#endif - -// We will start speed printer -void firehose_start() { - signal(SIGINT, sigproc); - - pcap_file = open("/mnt/traffic_capture.pcap", O_TRUNC | O_WRONLY | O_CREAT); - - if (pcap_file < 0) { - printf("Can't open file for capture\n"); - exit(-1); - } - - printf("Preaallocate %llu bytes on file system for storing traffic\n", preallocate_packet_dump_file_size); - int fallocate_result = posix_fallocate(pcap_file, 0, preallocate_packet_dump_file_size); - - if (fallocate_result != 0) { - printf("fallocate failed! Please check disk space and Linux Kernel Code\n"); - } - - /* Caching is useless for our case because we have average linear traffic in most cases - // We enable full buffering: _IOFBF - int setvbuf_result = setvbuf(pcap_file, NULL, _IONBF, 1024 * 1024 * 4); - - if (setvbuf_result != 0) { - printf("Can't set buffer for file operation\n"); - } - */ - - struct fastnetmon_pcap_file_header pcap_header; - fill_pcap_header(&pcap_header, 1600); - - unsigned int written_bytes = write(pcap_file, &pcap_header, sizeof(pcap_header)); - - if (written_bytes != sizeof(pcap_header)) { - printf("Can't write pcap header\n"); - } - - pthread_t thread; - pthread_create(&thread, NULL, speed_printer, NULL); - - pthread_t consumer_thread; - pthread_create(&consumer_thread, NULL, packets_consumer, NULL); - - pthread_detach(thread); - pthread_detach(consumer_thread); -} - -#ifdef __cplusplus -} -#endif - -void firehose_packet(const char* pciaddr, char* data, int length) { - std::shared_ptr packet_pointer(new packet_buffer_t); - packet_pointer->length = length; - - if (length < 1600) { - memcpy(packet_pointer->buffer, data, length); - } else { - printf("So big packet: %d\n", length); - } - - // Put pointer to the tube! - while (!my_spsc_queue.push(packet_pointer)) - ; -}