]> git.ipfire.org Git - thirdparty/suricata.git/commitdiff
af-packet: force suricata in IPS mode when needed
authorEric Leblond <eric@regit.org>
Fri, 19 Sep 2014 14:54:00 +0000 (16:54 +0200)
committerVictor Julien <victor@inliniac.net>
Mon, 22 Sep 2014 15:27:21 +0000 (17:27 +0200)
AF_PACKET is not setting the engine mode to IPS when some
interfaces are peered and use IPS mode. This is due to the
fact, it is possible to peer 2 interfaces and run an IPS on
them and have a third one that is running in normal IDS mode.

In fact this choice is the bad one as unwanted side effect is
that there is no drop log and that stream inline is not used.

To fix that, this patch puts suricata in IPS mode as soon as
there is two interfaces in IPS mode. And it displays a error
message to warn user that the accuracy of detection on IDS only
interfaces will be low.

src/runmode-af-packet.c
src/runmode-af-packet.h
src/suricata.c

index 51d6ea43034969e85b2d3a1c4bc7f28000517f6b..0388aafab6b3db25e3fb7cccd44190a0e2b217de 100644 (file)
@@ -333,6 +333,76 @@ int AFPConfigGeThreadsCount(void *conf)
     return afp->threads;
 }
 
+int AFPRunModeIsIPS()
+{
+    int nlive = LiveGetDeviceCount();
+    int ldev;
+    ConfNode *if_root;
+    ConfNode *if_default = NULL;
+    ConfNode *af_packet_node;
+    int has_ips = 0;
+    int has_ids = 0;
+
+    /* Find initial node */
+    af_packet_node = ConfGetNode("af-packet");
+    if (af_packet_node == NULL) {
+        return 0;
+    }
+
+    if_default = ConfNodeLookupKeyValue(af_packet_node, "interface", "default");
+
+    for (ldev = 0; ldev < nlive; ldev++) {
+        char *live_dev = LiveGetDeviceName(ldev);
+        char *copymodestr = NULL;
+        if_root = ConfNodeLookupKeyValue(af_packet_node, "interface", live_dev);
+
+        if (if_root == NULL) {
+            if (if_default == NULL) {
+                SCLogError(SC_ERR_INVALID_VALUE, "Problem with config file");
+                return 0;
+            }
+            if_root = if_default;
+        }
+
+        if (ConfGetChildValueWithDefault(if_root, if_default, "copy-mode", &copymodestr) == 1) {
+            if (strcmp(copymodestr, "ips") == 0) {
+                has_ips = 1;
+            } else {
+                has_ids = 1;
+            }
+        } else {
+            has_ids = 1;
+        }
+    }
+
+    if (has_ids && has_ips) {
+        SCLogInfo("AF_PACKET mode using IPS and IDS mode");
+        for (ldev = 0; ldev < nlive; ldev++) {
+            char *live_dev = LiveGetDeviceName(ldev);
+            if_root = ConfNodeLookupKeyValue(af_packet_node, "interface", live_dev);
+            char *copymodestr = NULL;
+
+            if (if_root == NULL) {
+                if (if_default == NULL) {
+                    SCLogError(SC_ERR_INVALID_VALUE, "Problem with config file");
+                    return 0;
+                }
+                if_root = if_default;
+            }
+
+            if (! ((ConfGetChildValueWithDefault(if_root, if_default, "copy-mode", &copymodestr) == 1) &&
+                        (strcmp(copymodestr, "ips") == 0))) {
+                SCLogError(SC_ERR_INVALID_ARGUMENT,
+                        "AF_PACKET IPS mode used and interface '%s' is in IDS or TAP mode. "
+                        "Sniffing '%s' but expect bad result as stream-inline is activated.",
+                        live_dev, live_dev);
+            }
+        }
+    }
+
+    return has_ips;
+}
+
 /**
  * \brief RunModeIdsAFPAuto set up the following thread packet handlers:
  *        - Receive thread (from live iface)
index b6637861ac5a34e6441108c7f36d95848c73dea7..0e1c764dd764664a0c232f41f2eae1ef8cb84e0c 100644 (file)
@@ -29,5 +29,6 @@ int RunModeIdsAFPAutoFp(DetectEngineCtx *);
 int RunModeIdsAFPWorkers(DetectEngineCtx *);
 void RunModeIdsAFPRegister(void);
 const char *RunModeAFPGetDefaultMode(void);
+int AFPRunModeIsIPS();
 
 #endif /* __RUNMODE_AF_PACKET_H__ */
index a42e597ed5b8e5f6250ec672cd69fe1cfd3985d7..9549827939560b4501e07c45ccf7efc677ce2c25 100644 (file)
@@ -993,6 +993,10 @@ static TmEcode ParseInterfacesList(int run_mode, char *pcap_dev)
                 SCLogError(SC_ERR_INITIALIZATION, "No interface found in config for af-packet");
                 SCReturnInt(TM_ECODE_FAILED);
             }
+            if (AFPRunModeIsIPS()) {
+                SCLogInfo("AF_PACKET: Setting IPS mode");
+                EngineModeSetIPS();
+            }
         }
 #ifdef HAVE_NFLOG
     } else if (run_mode == RUNMODE_NFLOG) {