]> git.ipfire.org Git - thirdparty/suricata.git/commitdiff
af-packet: improve mmaped running mode.
authorEric Leblond <eric@regit.org>
Thu, 5 Jul 2012 05:41:16 +0000 (07:41 +0200)
committerVictor Julien <victor@inliniac.net>
Mon, 3 Sep 2012 13:27:38 +0000 (15:27 +0200)
The mmaped mode was using a too small ring buffer size which was
not able to handle burst of packets coming from the network. This
may explain the important packet loss rate observed by Edward
Fjellskål.
This patch increases the default value and adds a ring-size
variable which can be used to manually tune the value.

src/runmode-af-packet.c
src/source-af-packet.c
src/source-af-packet.h
suricata.yaml.in

index 18f1b9b3059e5430e5aa9cdb576818de30b01a2a..d9309a4ec468e7cc860f2498c09092b00738c9fc 100644 (file)
@@ -50,6 +50,8 @@
 
 #include "source-af-packet.h"
 
+extern int max_pending_packets;
+
 static const char *default_mode_auto = NULL;
 static const char *default_mode_autofp = NULL;
 
@@ -222,6 +224,21 @@ void *ParseAFPConfig(const char *iface)
     } else {
         aconf->buffer_size = 0;
     }
+    if ((ConfGetChildValueInt(if_root, "ring-size", &value)) == 1) {
+        aconf->ring_size = value;
+        if (value * aconf->threads < max_pending_packets) {
+            aconf->ring_size = max_pending_packets / aconf->threads + 1;
+            SCLogWarning(SC_ERR_AFP_CREATE, "Inefficient setup: ring-size < max_pending_packets. "
+                         "Resetting to decent value %d.", aconf->ring_size);
+            /* We want at least that max_pending_packets packets can be handled by the
+             * interface. This is generous if we have multiple interfaces listening. */
+        }
+    } else {
+        /* We want that max_pending_packets packets can be handled by suricata
+         * for this interface. To take burst into account we multiply the obtained
+         * size by 2. */
+        aconf->ring_size = max_pending_packets * 2 / aconf->threads;
+    }
 
     (void)ConfGetChildValueBool(if_root, "disable-promisc", (int *)&boolval);
     if (boolval) {
index 0ed71e1376c2f309bcc841a375d9e4ec065e8070..82e5c345eeb12b94698aa6e42b2cc657998254df 100644 (file)
@@ -181,6 +181,7 @@ typedef struct AFPThreadVars_
     char *ring_buf;
     char *frame_buf;
     unsigned int frame_offset;
+    int ring_size;
 } AFPThreadVars;
 
 TmEcode ReceiveAFP(ThreadVars *, Packet *, void *, PacketQueue *, PacketQueue *);
@@ -668,7 +669,7 @@ frame size: TPACKET_ALIGN(snaplen + TPACKET_ALIGN(TPACKET_ALIGN(tp_hdrlen) + siz
         SCLogInfo("frame size to big");
         return -1;
     }
-    ptv->req.tp_frame_nr = max_pending_packets; /* Warrior mode */
+    ptv->req.tp_frame_nr = ptv->ring_size;
     ptv->req.tp_block_nr = ptv->req.tp_frame_nr / frames_per_block + 1;
     /* exact division */
     ptv->req.tp_frame_nr = ptv->req.tp_block_nr * frames_per_block;
@@ -971,6 +972,7 @@ TmEcode ReceiveAFPThreadInit(ThreadVars *tv, void *initdata, void **data) {
     }
 
     ptv->buffer_size = afpconfig->buffer_size;
+    ptv->ring_size = afpconfig->ring_size;
 
     ptv->promisc = afpconfig->promisc;
     ptv->checksum_mode = afpconfig->checksum_mode;
index 40c1d92c1b6ee8121dae81821e3ad224b227954f..02b1d63a2f3f6e6f4737af96385c7d71364f88e2 100644 (file)
@@ -52,6 +52,8 @@ typedef struct AFPIfaceConfig_
     int threads;
     /* socket buffer size */
     int buffer_size;
+    /* ring size in number of packets */
+    int ring_size;
     /* cluster param */
     int cluster_id;
     int cluster_type;
index 7ffb3ae9c91a27082f9c6ac985bc2f1b7b81b1b8..4fc9ef6dc384976cf7e93de09d978e72a9ff0596 100644 (file)
@@ -230,6 +230,12 @@ af-packet:
     defrag: yes
     # To use the ring feature of AF_PACKET, set 'use-mmap' to yes
     use-mmap: yes
+    # Ring size will be computed with respect to max_pending_packets and number
+    # of threads. You can set manually the ring size in number of packets by setting
+    # the following value. If you are using flow cluster-type and have really network
+    # intensive single-flow you could want to set the ring-size independantly of the number
+    # of threads:
+    #ring-size: 2048
     # recv buffer size, increase value could improve performance
     # buffer-size: 32768
     # Set to yes to disable promiscuous mode