]> git.ipfire.org Git - thirdparty/snort3.git/commitdiff
Pull request #4145: filters: make rate_filter multithreaded + cleanup
authorMichael Matirko (mmatirko) <mmatirko@cisco.com>
Wed, 17 Jan 2024 21:43:12 +0000 (21:43 +0000)
committerSteven Baigal (sbaigal) <sbaigal@cisco.com>
Wed, 17 Jan 2024 21:43:12 +0000 (21:43 +0000)
Merge in SNORT/snort3 from ~MMATIRKO/snort3:multithread_sfrf to master

Squashed commit of the following:

commit e5d9ad1293230a926f6acc3720042a858bf35998
Author: Michael Matirko <mmatirko@cisco.com>
Date:   Tue Oct 31 16:06:07 2023 -0400

    filters: make rate_filter multithreaded + some cleanup

src/filters/sfrf.cc
src/filters/sfrf.h
src/filters/sfrf_test.cc
src/main/analyzer.cc
src/main/modules.cc

index 62bb87a4921b8e6c2ec0e35aa14b7201a2877c5a..d169cf1b09f81ab51868c0099e896cb5b21db32a 100644 (file)
@@ -42,26 +42,22 @@ using namespace snort;
 
 // Number of hash rows for gid 1 (rules)
 #define SFRF_GEN_ID_1_ROWS 4096
+
 // Number of hash rows for non-zero gid
 #define SFRF_GEN_ID_ROWS   512
 
 // maximum number of norevert rate_filter configuration allowed.
 #define SFRF_NO_REVERT_LIMIT 1000
 
-// private data ...
-
 THREAD_LOCAL RateFilterStats rate_filter_stats;
 
-/* Key to find tracking nodes in trackingHash.
- */
 PADDING_GUARD_BEGIN
 typedef struct
 {
-    ///policy identifier.
+    ///policy identifier
     PolicyId policyId;
 
-    /* Internally generated threshold identity for a configured threshold.
-    */
+    // threshold identity
     int tid;
 
     /* Stores either source or destination IP address on a matching packet, depending on
@@ -83,10 +79,8 @@ typedef struct
     // automatically initialized to FS_NEW when allocated
     FilterState filterState;
 
-#ifdef SFRF_OVER_RATE
     int overRate;    // 0 = count not exceeded in prior seconds
     time_t tlast;    // time of most recent event
-#endif
 
     /* number of packets counted against a specific IP address or threshold.
      */
@@ -101,45 +95,16 @@ typedef struct
     time_t revertTime;
 } tSFRFTrackingNode;
 
-static THREAD_LOCAL XHash* rf_hash = nullptr;
-
-// private methods ...
-static int _checkThreshold(
-    tSFRFConfigNode*,
-    tSFRFTrackingNode*,
-    time_t curTime
-    );
-
-static int _checkSamplingPeriod(
-    tSFRFConfigNode*,
-    tSFRFTrackingNode*,
-    time_t curTime
-    );
-
-static tSFRFTrackingNode* _getSFRFTrackingNode(
-    const SfIp*,
-    unsigned tid,
-    time_t curTime
-    );
-
-static void _updateDependentThresholds(
-    RateFilterConfig* config,
-    unsigned gid,
-    unsigned sid,
-    const SfIp* sip,
-    const SfIp* dip,
-    time_t curTime
-    );
-
-// public methods ...
-/* Create a new threshold global context
- *
- * Create a threshold table, initialize the threshold system, and optionally
- * limit it's memory usage.
- *
- * @param nbytes maximum memory to use for thresholding objects, in bytes.
- * @return  pointer to newly created tSFRFContext
-*/
+static XHash* rf_hash = nullptr;
+
+static int checkThreshold(tSFRFConfigNode*, tSFRFTrackingNode*, time_t curTime);
+static int checkSamplingPeriod(tSFRFConfigNode*, tSFRFTrackingNode*, time_t curTime);
+
+static tSFRFTrackingNode* getSFRFTrackingNode(const SfIp*, unsigned tid, time_t curTime);
+
+static void updateDependentThresholds(RateFilterConfig* config, unsigned gid, unsigned sid,
+    const SfIp* sip, const SfIp* dip, time_t curTime);
+
 #define SFRF_BYTES (sizeof(tSFRFTrackingNodeKey) + sizeof(tSFRFTrackingNode))
 
 static void SFRF_New(unsigned nbytes)
@@ -161,12 +126,14 @@ void SFRF_Delete()
     if ( !rf_hash )
         return;
 
+    std::lock_guard<std::mutex> lock(sfrf_hash_mutex);
     delete rf_hash;
     rf_hash = nullptr;
 }
 
 void SFRF_Flush()
 {
+    std::lock_guard<std::mutex> lock(sfrf_hash_mutex);
     if ( rf_hash )
         rf_hash->clear_hash();
 }
@@ -186,11 +153,6 @@ static void SFRF_ConfigNodeFree(void* item)
     snort_free(node);
 }
 
-/* free tSFRFSidNode and related buffers.
- *
- * @param item - pointer to tSFRFSidNode to be freed.
- * @returns void
- */
 static void SFRF_SidNodeFree(void* item)
 {
     tSFRFSidNode* pSidnode = (tSFRFSidNode*)item;
@@ -210,21 +172,6 @@ int SFRF_Alloc(unsigned int memcap)
     return 0;
 }
 
-
-/*  Add a permanent threshold object to the threshold table. Multiple
- * objects may be defined for each gid and sid pair. Internally
- * a unique threshold id is generated for each pair.
- *
- * Threshold objects track the number of events seen during the time
- * interval specified by seconds. Depending on the type of threshold
- * object and the count value, the thresholding object determines if
- * the current event should be logged or dropped.
- *
- * @param pContext Threshold object from SFRF_ContextNew()
- * @param cfgNode Permanent Thresholding Object
- *
- * @return @retval  0 successfully added the thresholding object, !0 otherwise
-*/
 int SFRF_ConfigAdd(SnortConfig*, RateFilterConfig* rf_config, tSFRFConfigNode* cfgNode)
 {
     GHash* genHash;
@@ -254,8 +201,6 @@ int SFRF_ConfigAdd(SnortConfig*, RateFilterConfig* rf_config, tSFRFConfigNode* c
         rf_config->noRevertCount++;
     }
 
-    /* Check for an existing 'gid' entry, if none found then create one.
-       Get the hash table for this gid */
     genHash = rf_config->genHash[cfgNode->gid];
 
     if ( !genHash )
@@ -305,7 +250,6 @@ int SFRF_ConfigAdd(SnortConfig*, RateFilterConfig* rf_config, tSFRFConfigNode* c
         }
     }
 
-    /* Create a tSFRFConfigNode for this tSFRFSidNode (Object) */
     pNewConfigNode = (tSFRFConfigNode*)snort_calloc(sizeof(tSFRFConfigNode));
     *pNewConfigNode = *cfgNode;
 
@@ -322,55 +266,23 @@ int SFRF_ConfigAdd(SnortConfig*, RateFilterConfig* rf_config, tSFRFConfigNode* c
         return -6;
     }
 
-#ifdef SFRF_DEBUG
-    printf("--%d-%u-%u: Threshold node added to tail of list\n",
-        pNewConfigNode->tid,
-        pNewConfigNode->gid,
-        pNewConfigNode->sid);
-    fflush(stdout);
-#endif
     sflist_add_tail(pSidNode->configNodeList,pNewConfigNode);
 
     return 0;
 }
 
-/*
- *
- *  Find/Test/Add an event against a single threshold object.
- *  Events without thresholding objects are automatically loggable.
- *
- *  @param pContext     Threshold table pointer
- *  @param cfgNode Permanent Thresholding Object
- *  @param ip     Event/Packet Src IP address- should be host ordered for comparison
- *  @param curTime Current Event/Packet time in seconds
- *  @param op operation of type SFRF_COUNT_OPERATION
- *
- *  @return  integer
- *  @retval   !0 : rate limit is reached. Return value contains new action.
- *  @retval   0 : Otherwise
- */
-static int SFRF_TestObject(
-    tSFRFConfigNode* cfgNode,
-    const SfIp* ip,
-    time_t curTime,
-    SFRF_COUNT_OPERATION op
-    )
+static int SFRF_TestObject(tSFRFConfigNode* cfgNode, const SfIp* ip, time_t curTime,
+    SFRF_COUNT_OPERATION op)
 {
     tSFRFTrackingNode* dynNode;
     int retValue = -1;
 
-    dynNode = _getSFRFTrackingNode(ip, cfgNode->tid, curTime);
+    dynNode = getSFRFTrackingNode(ip, cfgNode->tid, curTime);
 
     if ( dynNode == nullptr )
         return retValue;
 
-    if ( _checkSamplingPeriod(cfgNode, dynNode, curTime) != 0 )
-    {
-#ifdef SFRF_DEBUG
-        printf("...Sampling period reset\n");
-        fflush(stdout);
-#endif
-    }
+    checkSamplingPeriod(cfgNode, dynNode, curTime);
 
     switch (op)
     {
@@ -398,7 +310,7 @@ static int SFRF_TestObject(
         break;
     }
 
-    retValue = _checkThreshold(cfgNode, dynNode, curTime);
+    retValue = checkThreshold(cfgNode, dynNode, curTime);
 
     // we drop after the session count has been incremented
     // but the decrement will never come so we "fix" it here
@@ -411,14 +323,6 @@ static int SFRF_TestObject(
         if ( act->drops_traffic() )
             dynNode->count--;
     }
-
-#ifdef SFRF_DEBUG
-    printf("--SFRF_DEBUG: %d-%u-%u: %u Packet IP %s, op: %d, count %u, action %d\n",
-        cfgNode->tid, cfgNode->gid,
-        cfgNode->sid, (unsigned)curTime, ip->ntoa(), op,
-        dynNode->count, retValue);
-    fflush(stdout);
-#endif
     return retValue;
 }
 
@@ -427,31 +331,8 @@ static inline int SFRF_AppliesTo(tSFRFConfigNode* pCfg, const SfIp* ip)
     return ( !pCfg->applyTo || sfvar_ip_in(pCfg->applyTo, ip) );
 }
 
-/* Test a an event against the threshold database. Events without thresholding
- * objects are automatically loggable.
- *
- * @param pContext     Threshold table pointer
- * @param gid  Generator Id from the event
- * @param sid  Signature Id from the event
- * @param sip     Event/Packet Src IP address
- * @param dip     Event/Packet Dst IP address
- * @param curTime Current Event/Packet time
- * @param op operation of type SFRF_COUNT_OPERATION
- *
- * @return  -1 if packet is within dos_threshold and therefore action is allowed.
- *         >=0 if packet violates a dos_threshold and therefore new_action should
- *             replace rule action. new_action value is returned.
- */
-int SFRF_TestThreshold(
-    RateFilterConfig* config,
-    unsigned gid,
-    unsigned sid,
-    PolicyId policy_id,
-    const SfIp* sip,
-    const SfIp* dip,
-    time_t curTime,
-    SFRF_COUNT_OPERATION op
-    )
+int SFRF_TestThreshold(RateFilterConfig* config, unsigned gid, unsigned sid, PolicyId policy_id,
+    const SfIp* sip, const SfIp* dip, time_t curTime, SFRF_COUNT_OPERATION op)
 {
     GHash* genHash;
     tSFRFSidNode* pSidNode;
@@ -460,18 +341,13 @@ int SFRF_TestThreshold(
     int status = -1;
     tSFRFGenHashKey key;
 
-#ifdef SFRF_DEBUG
-    printf("--%d-%u-%u: %s() entering\n", 0, gid, sid, __func__);
-    fflush(stdout);
-#endif
-
     if ( gid >= SFRF_MAX_GENID )
         return status; /* bogus gid */
 
     // Some events (like 'TCP connection closed' raised by inspector may
     // not have any configured threshold but may impact thresholds for other
     // events (like 'TCP connection opened'
-    _updateDependentThresholds(config, gid, sid, sip, dip, curTime);
+    updateDependentThresholds(config, gid, sid, sip, dip, curTime);
 
     /*
      *  Get the hash table for this gid
@@ -479,10 +355,6 @@ int SFRF_TestThreshold(
     genHash = config->genHash [ gid ];
     if ( !genHash )
     {
-#ifdef SFRF_DEBUG
-        printf("--SFRF_DEBUG: %d-%u-%u: no hash table entry for gid\n", 0, gid, sid);
-        fflush(stdout);
-#endif
         return status;
     }
 
@@ -495,21 +367,12 @@ int SFRF_TestThreshold(
     pSidNode = (tSFRFSidNode*)genHash->find((void*)&key);
     if ( !pSidNode )
     {
-#ifdef SFRF_DEBUG
-        printf("--SFRF_DEBUG: %d-%u-%u: no DOS THD object\n", 0, gid, sid);
-        fflush(stdout);
-#endif
         return status;
     }
 
     /* No List of Threshold objects - bail and log it */
     if ( !pSidNode->configNodeList )
     {
-#ifdef SFRF_DEBUG
-        printf("--SFRF_DEBUG: %d-%u-%u: No user configuration\n",
-            0, gid, sid);
-        fflush(stdout);
-#endif
         return status;
     }
 
@@ -547,16 +410,9 @@ int SFRF_TestThreshold(
         break;
 
         default:
-            // error case
             break;
         }
 
-#ifdef SFRF_DEBUG
-        printf("--SFRF_DEBUG: %d-%u-%u: Time %u, rate limit blocked: %d\n",
-            cfgNode->tid, gid, sid, (unsigned)curTime, newStatus);
-        fflush(stdout);
-#endif
-
         // rate limit is reached
         if ( newStatus >= 0 && (status == -1) )
         {
@@ -568,11 +424,6 @@ int SFRF_TestThreshold(
     return status;
 }
 
-/* A function to print the thresholding objects to stdout.
- *
- * @param pContext pointer to global threshold context
- * @return
- */
 void SFRF_ShowObjects(RateFilterConfig* config)
 {
     tSFRFSidNode* pSidnode;
@@ -617,6 +468,7 @@ void SFRF_ShowObjects(RateFilterConfig* config)
     }
 }
 
+
 /* Set sampling period rate limit
  *
  * @param cfgNode threshold configuration node
@@ -626,10 +478,7 @@ void SFRF_ShowObjects(RateFilterConfig* config)
  * @returns 0 if continuing with old sampling period.
  *          1 if new sampling period is started.
  */
-static int _checkSamplingPeriod(
-    tSFRFConfigNode* cfgNode,
-    tSFRFTrackingNode* dynNode,
-    time_t curTime)
+static int checkSamplingPeriod(tSFRFConfigNode* cfgNode, tSFRFTrackingNode* dynNode, time_t curTime)
 {
     if ( cfgNode->seconds )
     {
@@ -639,25 +488,22 @@ static int _checkSamplingPeriod(
         {   // observation period is over, start a new one
             dynNode->tstart = curTime;
 
-#ifdef SFRF_OVER_RATE
             dt = (unsigned)(curTime - dynNode->tlast);
             if ( dt > cfgNode->seconds )
                 dynNode->overRate = 0;
             else
                 dynNode->overRate = (dynNode->count > cfgNode->count);
+
             dynNode->tlast = curTime;
-#endif
             dynNode->count = 0;
             return 1;
         }
     }
-#ifdef SFRF_OVER_RATE
     else
     {
         dynNode->overRate = (dynNode->count > cfgNode->count);
     }
     dynNode->tlast = curTime;
-#endif
     return 0;
 }
 
@@ -679,11 +525,7 @@ static int _checkSamplingPeriod(
  * @returns 0 if threshold is not reached
  *          1 otherwise
  */
-static int _checkThreshold(
-    tSFRFConfigNode* cfgNode,
-    tSFRFTrackingNode* dynNode,
-    time_t curTime
-    )
+static int checkThreshold(tSFRFConfigNode* cfgNode, tSFRFTrackingNode* dynNode, time_t curTime)
 {
     /* Once newAction is activated, it stays active for the revert timeout, unless ANR
      * causes the node itself to disappear.
@@ -695,78 +537,44 @@ static int _checkThreshold(
         if ( (cfgNode->timeout != 0 )
             && ((unsigned)(curTime - dynNode->revertTime) >= cfgNode->timeout))
         {
-#ifdef SFRF_OVER_RATE
             if ( dynNode->count > cfgNode->count || dynNode->overRate )
             {
-#ifdef SFRF_DEBUG
-                printf("...dos action continued, count %u\n", dynnode->count);
-                fflush(stdout);
-#endif
                 dynNode->revertTime = curTime;
                 return cfgNode->newAction;
             }
-#endif
-#ifdef SFRF_DEBUG
-            printf("...dos action stopped, count %u\n", dynnode->count);
-            fflush(stdout);
-#endif
             dynNode->filterState = FS_OFF;
         }
         else
         {
-#ifdef SFRF_DEBUG
-            printf("...DOS action continued, count %u\n", dynNode->count);
-            fflush(stdout);
-#endif
             return cfgNode->newAction;
         }
     }
 
-#ifdef SFRF_OVER_RATE
     if ( dynNode->count <= cfgNode->count && !dynNode->overRate )
-#else
-    if ( dynNode->count <= cfgNode->count )
-#endif
     {
         // rate limit not reached.
-#ifdef SFRF_DEBUG
-        printf("...DOS action nop, count %u\n", dynNode->count);
-        fflush(stdout);
-#endif
         return -1;
     }
 
     // rate limit reached.
     dynNode->revertTime = curTime;
     dynNode->filterState = FS_ON;
-#ifdef SFRF_OVER_RATE
     dynNode->overRate = 1;
-#endif
-#ifdef SFRF_DEBUG
-    printf("...DOS action started, count %u\n", dynNode->count);
-    fflush(stdout);
-#endif
 
     return Actions::get_max_types() + cfgNode->newAction;
 }
 
-static void _updateDependentThresholds(
-    RateFilterConfig* config,
-    unsigned gid,
-    unsigned sid,
-    const SfIp* sip,
-    const SfIp* dip,
-    time_t curTime
-    )
+static void updateDependentThresholds(RateFilterConfig* config, unsigned gid,
+    unsigned sid, const SfIp* sip, const SfIp* dip, time_t curTime)
 {
     if ( gid == GID_SESSION &&
         sid == SESSION_EVENT_CLEAR )
     {
         // decrementing counters - this results in the following sequence:
         // 1. sfdos_thd_test_threshold(gid internal, sid DEL)
-        // 2.    _updateDependentThresholds(gid internal, sid DEL)
+        // 2.    updateDependentThresholds(gid internal, sid DEL)
         // 3.    |   sfdos_thd_test_threshold(gid internal, sid ADD)
-        // 4.    |       _updateDependentThresholds(gid internal, sid ADD)
+        // 4.    |       updateDependentThresholds(gid internal, sid ADD)
         // 5.    continue with regularly scheduled programming (ie step 1)
 
         SFRF_TestThreshold(config, gid, SESSION_EVENT_SETUP, get_network_policy()->policy_id,
@@ -775,7 +583,7 @@ static void _updateDependentThresholds(
     }
 }
 
-static tSFRFTrackingNode* _getSFRFTrackingNode(const SfIp* ip, unsigned tid, time_t curTime)
+static tSFRFTrackingNode* getSFRFTrackingNode(const SfIp* ip, unsigned tid, time_t curTime)
 {
     tSFRFTrackingNode* dynNode = nullptr;
     tSFRFTrackingNodeKey key;
@@ -786,6 +594,7 @@ static tSFRFTrackingNode* _getSFRFTrackingNode(const SfIp* ip, unsigned tid, tim
     key.policyId = get_inspection_policy()->policy_id;
     key.padding = 0;
 
+    std::lock_guard<std::mutex> lock(sfrf_hash_mutex);
     // Check for any Permanent sid objects for this gid or add this one ...
     if ( rf_hash->insert(&key, nullptr) == HASH_NOMEM )
     {
@@ -799,9 +608,7 @@ static tSFRFTrackingNode* _getSFRFTrackingNode(const SfIp* ip, unsigned tid, tim
     {
         // first time initialization
         dynNode->tstart = curTime;
-#ifdef SFRF_OVER_RATE
         dynNode->tlast = curTime;
-#endif
         dynNode->filterState = FS_OFF;
     }
 
index b72bfc1655ce369430ab7d9122985bdc971176ac..46ac8da539bbe65bf221590932451b33ee84b785 100644 (file)
 #ifndef SFRF_H
 #define SFRF_H
 
-// Implements rate_filter feature for snort
-
 #include <ctime>
+#include <mutex>
 
 #include "actions/actions.h"
 #include "framework/counts.h"
 #include "main/policy.h"
+#include "sfip/sf_ip.h"
+#include "sfip/sf_ipvar.h"
 
 namespace snort
 {
@@ -37,13 +38,8 @@ struct SfIp;
 struct SnortConfig;
 }
 
-// define to use over rate threshold
-#define SFRF_OVER_RATE
-
-// used for the dimensions of the gid lookup array.
 #define SFRF_MAX_GENID 8129
 
-// rate_filter tracking by src, by dst, or by rule
 typedef enum
 {
     SFRF_TRACK_BY_SRC = 1,
@@ -52,8 +48,7 @@ typedef enum
     SFRF_TRACK_BY_MAX
 } SFRF_TRACK;
 
-/* Type of operation for threshold tracking nodes.
- */
+
 typedef enum
 {
     SFRF_COUNT_NOP,
@@ -68,72 +63,34 @@ typedef enum
     FS_NEW = 0, FS_OFF, FS_ON, FS_MAX
 } FilterState;
 
-/* A threshold configuration object, created for each configured rate_filter.
- * These are created at initialization, and remain static.
- */
 struct tSFRFConfigNode
 {
-    // Internally generated unique threshold identity
     int tid;
-
-    // Generator id from configured threshold
     unsigned gid;
-
-    // Signature id from configured threshold
     unsigned sid;
-
-    // Signature id from configured threshold
     PolicyId policyId;
-
-    // Threshold tracking by src, dst or rule
     SFRF_TRACK tracking;
-
-    // Number of rule matching before rate limit is reached.
     unsigned count;
-
-    // Duration in seconds for determining rate of rule matching
     unsigned seconds;
-
-    // Action that replaces original rule action on reaching threshold
     Actions::Type newAction;
-
-    // Threshold action duration in seconds before reverting to original rule action
     unsigned timeout;
-
-    // ip set to restrict rate_filter
     sfip_var_t* applyTo;
 };
 
-/* tSFRFSidNode acts as a container of gid+sid based threshold objects,
- * this allows multiple threshold objects to be applied to a single
- * gid+sid pair. This is static data elements, built at initialization.
- */
 struct tSFRFSidNode
 {
-    // List of threshold configuration nodes of type tSFRFConfigNode
     PolicyId policyId;
-
-    // Generator id from configured threshold
     unsigned gid;
-
-    // Signature id from configured threshold
     unsigned sid;
-
-    // List of threshold configuration nodes of type tSFRFConfigNode
     struct sf_list* configNodeList;
 };
 
 struct tSFRFGenHashKey
 {
-    ///policy identifier
     PolicyId policyId;
-
-    // Signature id from configured threshold
     unsigned sid;
 };
 
-/* Single global context containing rate_filter configuration nodes.
- */
 struct RateFilterConfig
 {
     /* Array of hash, indexed by gid. Each array element is a hash, which
@@ -152,25 +109,18 @@ struct RateFilterStats
     PegCount xhash_nomem_peg = 0;
 };
 
-/*
- * Prototypes
- */
 void SFRF_Delete();
 void SFRF_Flush();
 int SFRF_ConfigAdd(snort::SnortConfig*, RateFilterConfig*, tSFRFConfigNode*);
 
-int SFRF_TestThreshold(
-    RateFilterConfig *config,
-    unsigned gid,
-    unsigned sid,
-    PolicyId policyid,
-    const snort::SfIp *sip,
-    const snort::SfIp *dip,
-    time_t curTime,
-    SFRF_COUNT_OPERATION);
+int SFRF_TestThreshold(RateFilterConfig *config, unsigned gid, unsigned sid,
+    PolicyId policyid, const snort::SfIp *sip, const snort::SfIp *dip,
+    time_t curTime, SFRF_COUNT_OPERATION);
 
 void SFRF_ShowObjects(RateFilterConfig*);
 
+int SFRF_Alloc(unsigned int memcap);
+
 inline void enable_internal_event(RateFilterConfig* config, uint32_t sid)
 {
     if (config == nullptr)
@@ -187,6 +137,6 @@ inline bool is_internal_event_enabled(RateFilterConfig* config, uint32_t sid)
     return (config->internal_event_mask & (1 << sid));
 }
 
-int SFRF_Alloc(unsigned int memcap);
+static std::mutex sfrf_hash_mutex;
 
 #endif
index 4abc280189192932effb91617b277644f0a1772b..8112d9053057b1318ca742b7bf7b55243ff40718 100644 (file)
@@ -149,358 +149,6 @@ static RateData rfData[] =
 
 static EventData evData[] =
 {
-#ifndef SFRF_OVER_RATE
-    { 0, 200, 1110, IP4_SRC, IP4_DST, 0.0, RULE_ORIG }
-    ,{ 1, 200, 1110, IP4_SRC, IP4_DST, 0.1, RULE_NEW }
-    ,{ 2, 200, 1110, IP4_SRC, IP4_DST, 0.2, RULE_NEW }
-    ,{ 3, 200, 1110, IP4_SRC, IP4_DST, 1.0, RULE_NEW }
-    ,{ 4, 200, 1110, IP4_SRC, IP4_DST, 9.9, RULE_NEW }
-
-    ,{ 0, 200, 1111, IP4_SRC, IP4_DST, 0.0, RULE_ORIG }
-    ,{ 1, 200, 1111, IP4_EXT, IP4_DST, 0.1, RULE_ORIG }
-    ,{ 2, 200, 1111, IP4_SRC, IP4_DST, 0.2, RULE_NEW }
-    ,{ 3, 200, 1111, IP4_SRC, IP4_DST, 1.0, RULE_ORIG }
-    ,{ 4, 200, 1111, IP4_SRC, IP4_DST, 1.1, RULE_NEW }
-    ,{ 5, 200, 1111, IP4_SRC, IP4_DST, 1.2, RULE_NEW }
-    ,{ 6, 200, 1111, IP4_SRC, IP4_DST, 2.0, RULE_ORIG }
-    ,{ 7, 200, 1111, IP4_SRC, IP4_DST, 3.0, RULE_ORIG }
-
-    ,{ 0, 200, 1121, IP4_SRC, IP4_DST, 0.0, RULE_ORIG }
-    ,{ 1, 200, 1121, IP4_SRC, IP4_DST, 0.1, RULE_NEW }
-    ,{ 2, 200, 1121, IP4_SRC, IP4_DST, 0.2, RULE_NEW }
-    ,{ 3, 200, 1121, IP4_SRC, IP4_DST, 0.3, RULE_NEW }
-    ,{ 4, 200, 1121, IP4_SRC, IP4_DST, 0.4, RULE_NEW }
-    ,{ 5, 200, 1121, IP4_SRC, IP4_DST, 1.0, RULE_NEW }
-    ,{ 6, 200, 1121, IP4_SRC, IP4_DST, 1.1, RULE_NEW }
-    ,{ 7, 200, 1121, IP4_SRC, IP4_DST, 1.2, RULE_NEW }
-    ,{ 8, 200, 1121, IP4_SRC, IP4_DST, 1.3, RULE_NEW }
-    ,{ 9, 200, 1121, IP4_SRC, IP4_DST, 1.4, RULE_NEW }
-    ,{ 10, 200, 1121, IP4_SRC, IP4_DST, 2.0, RULE_ORIG }
-    ,{ 11, 200, 1121, IP4_SRC, IP4_DST, 2.1, RULE_NEW }
-    ,{ 12, 200, 1121, IP4_SRC, IP4_DST, 3.0, RULE_NEW }
-    ,{ 13, 200, 1121, IP4_SRC, IP4_DST, 4.0, RULE_ORIG }
-    ,{ 14, 200, 1121, IP4_SRC, IP4_DST, 5.0, RULE_NEW }
-    ,{ 15, 200, 1121, IP4_SRC, IP4_DST, 5.1, RULE_NEW }
-    ,{ 16, 200, 1121, IP4_SRC, IP4_DST, 6.0, RULE_ORIG }
-    ,{ 17, 200, 1121, IP4_SRC, IP4_DST, 8.0, RULE_ORIG }
-    ,{ 18, 200, 1121, IP4_SRC, IP4_DST,10.0, RULE_ORIG }
-
-    ,{ 0, 200, 1311, IP4_SRC, IP4_DST, 0.0, RULE_ORIG }
-    ,{ 1, 200, 1311, IP4_SRC, IP4_DST, 0.1, RULE_ORIG }
-    ,{ 2, 200, 1311, IP4_SRC, IP4_DST, 0.2, RULE_ORIG }
-    ,{ 3, 200, 1311, IP4_SRC, IP4_DST, 0.3, RULE_NEW }
-    ,{ 4, 200, 1311, IP4_SRC, IP4_DST, 0.4, RULE_NEW }
-    ,{ 5, 200, 1311, IP4_SRC, IP4_DST, 1.0, RULE_ORIG }
-    ,{ 6, 200, 1311, IP4_SRC, IP4_DST, 1.1, RULE_ORIG }
-    ,{ 7, 200, 1311, IP4_SRC, IP4_DST, 1.2, RULE_ORIG }
-    ,{ 8, 200, 1311, IP4_SRC, IP4_DST, 1.3, RULE_NEW }
-    ,{ 9, 200, 1311, IP4_SRC, IP4_DST, 1.4, RULE_NEW }
-    ,{ 10, 200, 1311, IP4_SRC, IP4_DST, 2.0, RULE_ORIG }
-    ,{ 11, 200, 1311, IP4_SRC, IP4_DST, 2.1, RULE_ORIG }
-    ,{ 12, 200, 1311, IP4_SRC, IP4_DST, 3.0, RULE_ORIG }
-
-    ,{ 0, 200, 1321, IP4_SRC, IP4_DST, 0.0, RULE_ORIG }
-    ,{ 1, 200, 1321, IP4_SRC, IP4_DST, 0.1, RULE_ORIG }
-    ,{ 2, 200, 1321, IP4_SRC, IP4_DST, 0.2, RULE_ORIG }
-    ,{ 3, 200, 1321, IP4_SRC, IP4_DST, 0.3, RULE_NEW }
-    ,{ 4, 200, 1321, IP4_SRC, IP4_DST, 0.4, RULE_NEW }
-    ,{ 5, 200, 1321, IP4_SRC, IP4_DST, 1.0, RULE_NEW }
-    ,{ 6, 200, 1321, IP4_SRC, IP4_DST, 1.1, RULE_NEW }
-    ,{ 7, 200, 1321, IP4_SRC, IP4_DST, 1.2, RULE_NEW }
-    ,{ 8, 200, 1321, IP4_SRC, IP4_DST, 1.3, RULE_NEW }
-    ,{ 9, 200, 1321, IP4_SRC, IP4_DST, 1.4, RULE_NEW }
-    ,{ 10, 200, 1321, IP4_SRC, IP4_DST, 2.0, RULE_ORIG }
-    ,{ 11, 200, 1321, IP4_SRC, IP4_DST, 2.1, RULE_ORIG }
-    ,{ 12, 200, 1321, IP4_SRC, IP4_DST, 3.0, RULE_ORIG }
-    ,{ 13, 200, 1321, IP4_SRC, IP4_DST, 4.0, RULE_ORIG }
-    ,{ 14, 200, 1321, IP4_SRC, IP4_DST, 5.0, RULE_ORIG }
-
-    ,{ 0, 200, 1312, IP4_SRC, IP4_DST, 0.0, RULE_ORIG }
-    ,{ 1, 200, 1312, IP4_SRC, IP4_DST, 0.1, RULE_ORIG }
-    ,{ 2, 200, 1312, IP4_SRC, IP4_DST, 0.2, RULE_ORIG }
-    ,{ 3, 200, 1312, IP4_SRC, IP4_DST, 0.3, RULE_NEW }
-    ,{ 4, 200, 1312, IP4_SRC, IP4_DST, 0.4, RULE_NEW }
-    ,{ 5, 200, 1312, IP4_SRC, IP4_DST, 1.0, RULE_NEW }
-    ,{ 6, 200, 1312, IP4_SRC, IP4_DST, 1.1, RULE_NEW }
-    ,{ 7, 200, 1312, IP4_SRC, IP4_DST, 1.2, RULE_NEW }
-    ,{ 8, 200, 1312, IP4_SRC, IP4_DST, 1.3, RULE_NEW }
-    ,{ 9, 200, 1312, IP4_SRC, IP4_DST, 1.4, RULE_NEW }
-    ,{ 10, 200, 1312, IP4_SRC, IP4_DST, 2.0, RULE_ORIG }
-    ,{ 11, 200, 1312, IP4_SRC, IP4_DST, 2.1, RULE_ORIG }
-    ,{ 12, 200, 1312, IP4_SRC, IP4_DST, 3.0, RULE_ORIG }
-    ,{ 13, 200, 1312, IP4_SRC, IP4_DST, 4.0, RULE_ORIG }
-    ,{ 14, 200, 1312, IP4_SRC, IP4_DST, 5.0, RULE_ORIG }
-
-    ,{ 0, 200, 2111, IP4_SRC, IP4_DST, 0.0, RULE_ORIG }
-    ,{ 1, 200, 2111, IP4_SRC, IP4_EXT, 0.1, RULE_ORIG }
-    ,{ 2, 200, 2111, IP4_SRC, IP4_DST, 0.2, RULE_NEW }
-    ,{ 3, 200, 2111, IP4_SRC, IP4_DST, 1.0, RULE_ORIG }
-    ,{ 4, 200, 2111, IP4_SRC, IP4_EXT, 1.1, RULE_ORIG }
-    ,{ 5, 200, 2111, IP4_SRC, IP4_DST, 1.2, RULE_NEW }
-    ,{ 6, 200, 2111, IP4_SRC, IP4_DST, 2.0, RULE_ORIG }
-    ,{ 7, 200, 2111, IP4_SRC, IP4_DST, 3.0, RULE_ORIG }
-
-    ,{ 0, 200, 3111, IP4_EXT, IP4_DST, 0.0, RULE_ORIG }
-    ,{ 1, 200, 3111, IP4_SRC, IP4_EXT, 0.1, RULE_NEW }
-    ,{ 2, 200, 3111, IP4_SRC, IP4_DST, 0.2, RULE_NEW }
-    ,{ 3, 200, 3111, IP4_EXT, IP4_DST, 1.0, RULE_ORIG }
-    ,{ 4, 200, 3111, IP4_EXT, IP4_DST, 1.1, RULE_NEW }
-    ,{ 5, 200, 3111, IP4_SRC, IP4_EXT, 1.2, RULE_NEW }
-    ,{ 6, 200, 3111, IP4_SRC, IP4_EXT, 2.0, RULE_ORIG }
-    ,{ 7, 200, 3111, IP4_SRC, IP4_DST, 3.0, RULE_ORIG }
-
-    ,{ 0, 210, 3311, IP4_SRC, IP4_DST,  0.0, RULE_ORIG }
-    ,{ 1, 210, 3311, IP4_SRC, IP4_DST,  0.1, RULE_ORIG }
-    ,{ 2, 210, 3311, IP4_SRC, IP4_DST,  0.2, RULE_ORIG }
-    ,{ 3, 210, 3311, IP4_SRC, IP4_DST,  0.3, RULE_NEW }
-    ,{ 4, 210, 3311, IP4_SRC, IP4_DST,  0.4, RULE_NEW }
-    ,{ 5, 210, 3311, IP4_SRC, IP4_DST,  1.0, RULE_ORIG }
-    ,{ 6, 210, 3311, IP4_SRC, IP4_DST,  1.1, RULE_ORIG }
-    ,{ 7, 210, 3311, IP4_SRC, IP4_DST,  1.2, RULE_ORIG }
-    ,{ 8, 210, 3311, IP4_SRC, IP4_DST,  1.3, RULE_NEW }
-    ,{ 9, 210, 3311, IP4_SRC, IP4_DST,  1.4, RULE_NEW }
-    ,{ 10, 210, 3311, IP4_SRC, IP4_DST,  2.0, RULE_ORIG }
-    ,{ 11, 210, 3311, IP4_SRC, IP4_DST,  2.1, RULE_ORIG }
-    ,{ 12, 210, 3311, IP4_SRC, IP4_DST,  3.0, RULE_ORIG }
-    ,{ 13, 210, 3311, IP4_SRC, IP4_DST,  5.0, RULE_ORIG }
-    ,{ 14, 210, 3311, IP4_SRC, IP4_DST,  5.1, RULE_ORIG }
-    ,{ 15, 210, 3311, IP4_SRC, IP4_DST,  5.2, RULE_ORIG }
-    ,{ 16, 210, 3311, IP4_SRC, IP4_DST,  5.3, RULE_NEW }
-    ,{ 17, 210, 3311, IP4_SRC, IP4_DST,  9.8, RULE_ORIG }
-    ,{ 18, 210, 3311, IP4_SRC, IP4_DST,  9.9, RULE_ORIG }
-    ,{ 19, 210, 3311, IP4_SRC, IP4_DST, 10.0, RULE_ORIG }
-    ,{ 20, 210, 3311, IP4_SRC, IP4_DST, 11.0, RULE_ORIG }
-
-    ,{ 0, 210, 3315, IP4_SRC, IP4_DST,  0.0, RULE_ORIG }
-    ,{ 1, 210, 3315, IP4_SRC, IP4_DST,  0.1, RULE_ORIG }
-    ,{ 2, 210, 3315, IP4_SRC, IP4_DST,  0.2, RULE_ORIG }
-    ,{ 3, 210, 3315, IP4_SRC, IP4_DST,  0.3, RULE_NEW }
-    ,{ 4, 210, 3315, IP4_SRC, IP4_DST,  0.4, RULE_NEW }
-    ,{ 5, 210, 3315, IP4_SRC, IP4_DST,  1.0, RULE_NEW }
-    ,{ 6, 210, 3315, IP4_SRC, IP4_DST,  1.1, RULE_NEW }
-    ,{ 7, 210, 3315, IP4_SRC, IP4_DST,  1.2, RULE_NEW }
-    ,{ 8, 210, 3315, IP4_SRC, IP4_DST,  1.3, RULE_NEW }
-    ,{ 9, 210, 3315, IP4_SRC, IP4_DST,  1.4, RULE_NEW }
-    ,{ 10, 210, 3315, IP4_SRC, IP4_DST,  2.0, RULE_NEW }
-    ,{ 11, 210, 3315, IP4_SRC, IP4_DST,  2.1, RULE_NEW }
-    ,{ 12, 210, 3315, IP4_SRC, IP4_DST,  3.0, RULE_NEW }
-    ,{ 13, 210, 3315, IP4_SRC, IP4_DST,  5.0, RULE_ORIG }
-    ,{ 14, 210, 3315, IP4_SRC, IP4_DST,  5.1, RULE_ORIG }
-    ,{ 15, 210, 3315, IP4_SRC, IP4_DST,  5.2, RULE_ORIG }
-    ,{ 16, 210, 3315, IP4_SRC, IP4_DST,  5.3, RULE_NEW }
-    ,{ 17, 210, 3315, IP4_SRC, IP4_DST,  9.8, RULE_NEW }
-    ,{ 18, 210, 3315, IP4_SRC, IP4_DST,  9.9, RULE_NEW }
-    ,{ 19, 210, 3315, IP4_SRC, IP4_DST, 10.0, RULE_ORIG }
-    ,{ 20, 210, 3315, IP4_SRC, IP4_DST, 11.0, RULE_ORIG }
-
-    ,{ 0, 210, 3319, IP4_SRC, IP4_DST,  0.0, RULE_ORIG }
-    ,{ 1, 210, 3319, IP4_SRC, IP4_DST,  0.1, RULE_ORIG }
-    ,{ 2, 210, 3319, IP4_SRC, IP4_DST,  0.2, RULE_ORIG }
-    ,{ 3, 210, 3319, IP4_SRC, IP4_DST,  0.3, RULE_NEW }
-    ,{ 4, 210, 3319, IP4_SRC, IP4_DST,  0.4, RULE_NEW }
-    ,{ 5, 210, 3319, IP4_SRC, IP4_DST,  1.0, RULE_NEW }
-    ,{ 6, 210, 3319, IP4_SRC, IP4_DST,  1.1, RULE_NEW }
-    ,{ 7, 210, 3319, IP4_SRC, IP4_DST,  1.2, RULE_NEW }
-    ,{ 8, 210, 3319, IP4_SRC, IP4_DST,  1.3, RULE_NEW }
-    ,{ 9, 210, 3319, IP4_SRC, IP4_DST,  1.4, RULE_NEW }
-    ,{ 10, 210, 3319, IP4_SRC, IP4_DST,  2.0, RULE_NEW }
-    ,{ 11, 210, 3319, IP4_SRC, IP4_DST,  2.1, RULE_NEW }
-    ,{ 12, 210, 3319, IP4_SRC, IP4_DST,  3.0, RULE_NEW }
-    ,{ 13, 210, 3319, IP4_SRC, IP4_DST,  5.0, RULE_NEW }
-    ,{ 14, 210, 3319, IP4_SRC, IP4_DST,  5.1, RULE_NEW }
-    ,{ 15, 210, 3319, IP4_SRC, IP4_DST,  5.2, RULE_NEW }
-    ,{ 16, 210, 3319, IP4_SRC, IP4_DST,  5.3, RULE_NEW }
-    ,{ 17, 210, 3319, IP4_SRC, IP4_DST,  9.8, RULE_ORIG }
-    ,{ 18, 210, 3319, IP4_SRC, IP4_DST,  9.9, RULE_ORIG }
-    ,{ 19, 210, 3319, IP4_SRC, IP4_DST, 10.0, RULE_ORIG }
-    ,{ 20, 210, 3319, IP4_SRC, IP4_DST, 11.0, RULE_ORIG }
-
-    ,{ 0, 210, 3351, IP4_SRC, IP4_DST,  0.0, RULE_ORIG }
-    ,{ 1, 210, 3351, IP4_SRC, IP4_DST,  0.1, RULE_ORIG }
-    ,{ 2, 210, 3351, IP4_SRC, IP4_DST,  0.2, RULE_ORIG }
-    ,{ 3, 210, 3351, IP4_SRC, IP4_DST,  0.3, RULE_NEW }
-    ,{ 4, 210, 3351, IP4_SRC, IP4_DST,  0.4, RULE_NEW }
-    ,{ 5, 210, 3351, IP4_SRC, IP4_DST,  5.0, RULE_ORIG }
-    ,{ 6, 210, 3351, IP4_SRC, IP4_DST,  5.1, RULE_ORIG }
-    ,{ 7, 210, 3351, IP4_SRC, IP4_DST,  5.2, RULE_ORIG }
-    ,{ 8, 210, 3351, IP4_SRC, IP4_DST,  5.3, RULE_NEW }
-    ,{ 9, 210, 3351, IP4_SRC, IP4_DST,  5.4, RULE_NEW }
-    ,{ 10, 210, 3351, IP4_SRC, IP4_DST, 10.0, RULE_ORIG }
-    ,{ 11, 210, 3351, IP4_SRC, IP4_DST, 10.1, RULE_ORIG }
-    ,{ 12, 210, 3351, IP4_SRC, IP4_DST, 15.0, RULE_ORIG }
-    ,{ 13, 210, 3351, IP4_SRC, IP4_DST, 19.0, RULE_ORIG }
-    ,{ 14, 210, 3351, IP4_SRC, IP4_DST, 25.0, RULE_ORIG }
-    ,{ 15, 210, 3351, IP4_SRC, IP4_DST, 25.1, RULE_ORIG }
-    ,{ 16, 210, 3351, IP4_SRC, IP4_DST, 25.2, RULE_ORIG }
-    ,{ 17, 210, 3351, IP4_SRC, IP4_DST, 25.3, RULE_NEW }
-    ,{ 18, 210, 3351, IP4_SRC, IP4_DST, 45.8, RULE_ORIG }
-    ,{ 19, 210, 3351, IP4_SRC, IP4_DST, 45.9, RULE_ORIG }
-    ,{ 20, 210, 3351, IP4_SRC, IP4_DST, 50.0, RULE_ORIG }
-    ,{ 21, 210, 3351, IP4_SRC, IP4_DST, 55.0, RULE_ORIG }
-
-    ,{ 0, 210, 3355, IP4_SRC, IP4_DST,  0.0, RULE_ORIG }
-    ,{ 1, 210, 3355, IP4_SRC, IP4_DST,  0.1, RULE_ORIG }
-    ,{ 2, 210, 3355, IP4_SRC, IP4_DST,  0.2, RULE_ORIG }
-    ,{ 3, 210, 3355, IP4_SRC, IP4_DST,  0.3, RULE_NEW }
-    ,{ 4, 210, 3355, IP4_SRC, IP4_DST,  0.4, RULE_NEW }
-    ,{ 5, 210, 3355, IP4_SRC, IP4_DST,  5.0, RULE_ORIG }
-    ,{ 6, 210, 3355, IP4_SRC, IP4_DST,  5.1, RULE_ORIG }
-    ,{ 7, 210, 3355, IP4_SRC, IP4_DST,  5.2, RULE_ORIG }
-    ,{ 8, 210, 3355, IP4_SRC, IP4_DST,  5.3, RULE_NEW }
-    ,{ 9, 210, 3355, IP4_SRC, IP4_DST,  5.4, RULE_NEW }
-    ,{ 10, 210, 3355, IP4_SRC, IP4_DST, 10.0, RULE_ORIG }
-    ,{ 11, 210, 3355, IP4_SRC, IP4_DST, 10.1, RULE_ORIG }
-    ,{ 12, 210, 3355, IP4_SRC, IP4_DST, 15.0, RULE_ORIG }
-    ,{ 13, 210, 3355, IP4_SRC, IP4_DST, 19.0, RULE_ORIG }
-    ,{ 14, 210, 3355, IP4_SRC, IP4_DST, 25.0, RULE_ORIG }
-    ,{ 15, 210, 3355, IP4_SRC, IP4_DST, 25.1, RULE_ORIG }
-    ,{ 16, 210, 3355, IP4_SRC, IP4_DST, 25.2, RULE_ORIG }
-    ,{ 17, 210, 3355, IP4_SRC, IP4_DST, 25.3, RULE_NEW }
-    ,{ 18, 210, 3355, IP4_SRC, IP4_DST, 45.8, RULE_ORIG }
-    ,{ 19, 210, 3355, IP4_SRC, IP4_DST, 45.9, RULE_ORIG }
-    ,{ 20, 210, 3355, IP4_SRC, IP4_DST, 50.0, RULE_ORIG }
-    ,{ 21, 210, 3355, IP4_SRC, IP4_DST, 55.0, RULE_ORIG }
-
-    ,{ 0, 210, 3359, IP4_SRC, IP4_DST,  0.0, RULE_ORIG }
-    ,{ 1, 210, 3359, IP4_SRC, IP4_DST,  0.1, RULE_ORIG }
-    ,{ 2, 210, 3359, IP4_SRC, IP4_DST,  0.2, RULE_ORIG }
-    ,{ 3, 210, 3359, IP4_SRC, IP4_DST,  0.3, RULE_NEW }
-    ,{ 4, 210, 3359, IP4_SRC, IP4_DST,  0.4, RULE_NEW }
-    ,{ 5, 210, 3359, IP4_SRC, IP4_DST,  5.0, RULE_NEW }
-    ,{ 6, 210, 3359, IP4_SRC, IP4_DST,  5.1, RULE_NEW }
-    ,{ 7, 210, 3359, IP4_SRC, IP4_DST,  5.2, RULE_NEW }
-    ,{ 8, 210, 3359, IP4_SRC, IP4_DST,  5.3, RULE_NEW }
-    ,{ 9, 210, 3359, IP4_SRC, IP4_DST,  5.4, RULE_NEW }
-    ,{ 10, 210, 3359, IP4_SRC, IP4_DST, 10.0, RULE_ORIG }
-    ,{ 11, 210, 3359, IP4_SRC, IP4_DST, 10.1, RULE_ORIG }
-    ,{ 12, 210, 3359, IP4_SRC, IP4_DST, 15.0, RULE_ORIG }
-    ,{ 13, 210, 3359, IP4_SRC, IP4_DST, 19.0, RULE_ORIG }
-    ,{ 14, 210, 3359, IP4_SRC, IP4_DST, 25.0, RULE_ORIG }
-    ,{ 15, 210, 3359, IP4_SRC, IP4_DST, 25.1, RULE_ORIG }
-    ,{ 16, 210, 3359, IP4_SRC, IP4_DST, 25.2, RULE_ORIG }
-    ,{ 17, 210, 3359, IP4_SRC, IP4_DST, 25.3, RULE_NEW }
-    ,{ 18, 210, 3359, IP4_SRC, IP4_DST, 45.8, RULE_ORIG }
-    ,{ 19, 210, 3359, IP4_SRC, IP4_DST, 45.9, RULE_ORIG }
-    ,{ 20, 210, 3359, IP4_SRC, IP4_DST, 50.0, RULE_ORIG }
-    ,{ 21, 210, 3359, IP4_SRC, IP4_DST, 55.0, RULE_ORIG }
-
-    ,{ 0, 210, 3391, IP4_SRC, IP4_DST,  0.0, RULE_ORIG }
-    ,{ 1, 210, 3391, IP4_SRC, IP4_DST,  0.1, RULE_ORIG }
-    ,{ 2, 210, 3391, IP4_SRC, IP4_DST,  0.2, RULE_ORIG }
-    ,{ 3, 210, 3391, IP4_SRC, IP4_DST,  0.3, RULE_NEW }
-    ,{ 4, 210, 3391, IP4_SRC, IP4_DST,  0.4, RULE_NEW }
-    ,{ 5, 210, 3391, IP4_SRC, IP4_DST,  9.0, RULE_ORIG }
-    ,{ 6, 210, 3391, IP4_SRC, IP4_DST,  9.1, RULE_ORIG }
-    ,{ 7, 210, 3391, IP4_SRC, IP4_DST,  9.2, RULE_ORIG }
-    ,{ 8, 210, 3391, IP4_SRC, IP4_DST,  9.3, RULE_NEW }
-    ,{ 9, 210, 3391, IP4_SRC, IP4_DST,  9.4, RULE_NEW }
-    ,{ 10, 210, 3391, IP4_SRC, IP4_DST, 18.0, RULE_ORIG }
-    ,{ 11, 210, 3391, IP4_SRC, IP4_DST, 18.1, RULE_ORIG }
-    ,{ 12, 210, 3391, IP4_SRC, IP4_DST, 27.0, RULE_ORIG }
-    ,{ 13, 210, 3391, IP4_SRC, IP4_DST, 35.0, RULE_ORIG }
-    ,{ 14, 210, 3391, IP4_SRC, IP4_DST, 45.0, RULE_ORIG }
-    ,{ 15, 210, 3391, IP4_SRC, IP4_DST, 45.1, RULE_ORIG }
-    ,{ 16, 210, 3391, IP4_SRC, IP4_DST, 45.2, RULE_ORIG }
-    ,{ 17, 210, 3391, IP4_SRC, IP4_DST, 45.3, RULE_NEW }
-    ,{ 18, 210, 3391, IP4_SRC, IP4_DST, 81.8, RULE_ORIG }
-    ,{ 19, 210, 3391, IP4_SRC, IP4_DST, 81.9, RULE_ORIG }
-    ,{ 20, 210, 3391, IP4_SRC, IP4_DST, 90.0, RULE_ORIG }
-    ,{ 21, 210, 3391, IP4_SRC, IP4_DST, 99.0, RULE_ORIG }
-
-    ,{ 0, 210, 3395, IP4_SRC, IP4_DST,  0.0, RULE_ORIG }
-    ,{ 1, 210, 3395, IP4_SRC, IP4_DST,  0.1, RULE_ORIG }
-    ,{ 2, 210, 3395, IP4_SRC, IP4_DST,  0.2, RULE_ORIG }
-    ,{ 3, 210, 3395, IP4_SRC, IP4_DST,  0.3, RULE_NEW }
-    ,{ 4, 210, 3395, IP4_SRC, IP4_DST,  0.4, RULE_NEW }
-    ,{ 5, 210, 3395, IP4_SRC, IP4_DST,  9.0, RULE_ORIG }
-    ,{ 6, 210, 3395, IP4_SRC, IP4_DST,  9.1, RULE_ORIG }
-    ,{ 7, 210, 3395, IP4_SRC, IP4_DST,  9.2, RULE_ORIG }
-    ,{ 8, 210, 3395, IP4_SRC, IP4_DST,  9.3, RULE_NEW }
-    ,{ 9, 210, 3395, IP4_SRC, IP4_DST,  9.4, RULE_NEW }
-    ,{ 10, 210, 3395, IP4_SRC, IP4_DST, 18.0, RULE_ORIG }
-    ,{ 11, 210, 3395, IP4_SRC, IP4_DST, 18.1, RULE_ORIG }
-    ,{ 12, 210, 3395, IP4_SRC, IP4_DST, 27.0, RULE_ORIG }
-    ,{ 13, 210, 3395, IP4_SRC, IP4_DST, 35.0, RULE_ORIG }
-    ,{ 14, 210, 3395, IP4_SRC, IP4_DST, 45.0, RULE_ORIG }
-    ,{ 15, 210, 3395, IP4_SRC, IP4_DST, 45.1, RULE_ORIG }
-    ,{ 16, 210, 3395, IP4_SRC, IP4_DST, 45.2, RULE_ORIG }
-    ,{ 17, 210, 3395, IP4_SRC, IP4_DST, 45.3, RULE_NEW }
-    ,{ 18, 210, 3395, IP4_SRC, IP4_DST, 81.8, RULE_ORIG }
-    ,{ 19, 210, 3395, IP4_SRC, IP4_DST, 81.9, RULE_ORIG }
-    ,{ 20, 210, 3395, IP4_SRC, IP4_DST, 90.0, RULE_ORIG }
-    ,{ 21, 210, 3395, IP4_SRC, IP4_DST, 99.0, RULE_ORIG }
-
-    ,{ 0, 210, 3399, IP4_SRC, IP4_DST,  0.0, RULE_ORIG }
-    ,{ 1, 210, 3399, IP4_SRC, IP4_DST,  0.1, RULE_ORIG }
-    ,{ 2, 210, 3399, IP4_SRC, IP4_DST,  0.2, RULE_ORIG }
-    ,{ 3, 210, 3399, IP4_SRC, IP4_DST,  0.3, RULE_NEW }
-    ,{ 4, 210, 3399, IP4_SRC, IP4_DST,  0.4, RULE_NEW }
-    ,{ 5, 210, 3399, IP4_SRC, IP4_DST,  9.0, RULE_ORIG }
-    ,{ 6, 210, 3399, IP4_SRC, IP4_DST,  9.1, RULE_ORIG }
-    ,{ 7, 210, 3399, IP4_SRC, IP4_DST,  9.2, RULE_ORIG }
-    ,{ 8, 210, 3399, IP4_SRC, IP4_DST,  9.3, RULE_NEW }
-    ,{ 9, 210, 3399, IP4_SRC, IP4_DST,  9.4, RULE_NEW }
-    ,{ 10, 210, 3399, IP4_SRC, IP4_DST, 18.0, RULE_ORIG }
-    ,{ 11, 210, 3399, IP4_SRC, IP4_DST, 18.1, RULE_ORIG }
-    ,{ 12, 210, 3399, IP4_SRC, IP4_DST, 27.0, RULE_ORIG }
-    ,{ 13, 210, 3399, IP4_SRC, IP4_DST, 35.0, RULE_ORIG }
-    ,{ 14, 210, 3399, IP4_SRC, IP4_DST, 45.0, RULE_ORIG }
-    ,{ 15, 210, 3399, IP4_SRC, IP4_DST, 45.1, RULE_ORIG }
-    ,{ 16, 210, 3399, IP4_SRC, IP4_DST, 45.2, RULE_ORIG }
-    ,{ 17, 210, 3399, IP4_SRC, IP4_DST, 45.3, RULE_NEW }
-    ,{ 18, 210, 3399, IP4_SRC, IP4_DST, 81.8, RULE_ORIG }
-    ,{ 19, 210, 3399, IP4_SRC, IP4_DST, 81.9, RULE_ORIG }
-    ,{ 20, 210, 3399, IP4_SRC, IP4_DST, 90.0, RULE_ORIG }
-    ,{ 21, 210, 3399, IP4_SRC, IP4_DST, 99.0, RULE_ORIG }
-
-    ,{ 0, 300, 1110, IP4_SRC, IP4_DST, 0.0, RULE_ORIG }
-    ,{ 1, 300, 1110, IP4_EXT, IP4_DST, 0.1, RULE_ORIG }
-    ,{ 2, 300, 1110, IP4_EXT, IP4_DST, 0.2, RULE_ORIG }
-    ,{ 3, 300, 1110, IP4_SRC, IP4_DST, 1.0, RULE_ORIG }
-    ,{ 4, 300, 1110, IP4_SRC, IP4_DST, 1.9, RULE_NEW }
-    ,{ 5, 300, 1110, IP4_SRC, IP4_DST, 2.0, RULE_NEW }
-    ,{ 6, 300, 1110, IP4_SRC, IP4_DST, 9.9, RULE_NEW }
-
-    ,{ 0, 300, 2110, IP4_SRC, IP4_DST, 0.0, RULE_ORIG }
-    ,{ 1, 300, 2110, IP4_SRC, IP4_EXT, 0.1, RULE_ORIG }
-    ,{ 2, 300, 2110, IP4_SRC, IP4_EXT, 0.2, RULE_ORIG }
-    ,{ 3, 300, 2110, IP4_SRC, IP4_DST, 1.0, RULE_ORIG }
-    ,{ 4, 300, 2110, IP4_SRC, IP4_DST, 1.9, RULE_NEW }
-    ,{ 5, 300, 2110, IP4_SRC, IP4_DST, 2.0, RULE_NEW }
-    ,{ 6, 300, 2110, IP4_SRC, IP4_DST, 9.9, RULE_NEW }
-
-    ,{ 0, 310, 1110, IP4_EXT, IP4_DST, 0.0, RULE_ORIG }
-    ,{ 1, 310, 1110, IP4_SRC, IP4_DST, 0.1, RULE_ORIG }
-    ,{ 2, 310, 1110, IP4_SRC, IP4_DST, 0.2, RULE_ORIG }
-    ,{ 3, 310, 1110, IP4_EXT, IP4_DST, 1.0, RULE_ORIG }
-    ,{ 4, 310, 1110, IP4_EXT, IP4_DST, 1.9, RULE_NEW }
-    ,{ 5, 310, 1110, IP4_EXT, IP4_DST, 2.0, RULE_NEW }
-    ,{ 6, 310, 1110, IP4_EXT, IP4_DST, 9.9, RULE_NEW }
-
-    ,{ 0, 310, 2110, IP4_SRC, IP4_EXT, 0.0, RULE_ORIG }
-    ,{ 1, 310, 2110, IP4_SRC, IP4_DST, 0.1, RULE_ORIG }
-    ,{ 2, 310, 2110, IP4_SRC, IP4_DST, 0.2, RULE_ORIG }
-    ,{ 3, 310, 2110, IP4_SRC, IP4_EXT, 1.0, RULE_ORIG }
-    ,{ 4, 310, 2110, IP4_SRC, IP4_EXT, 1.9, RULE_NEW }
-    ,{ 5, 310, 2110, IP4_SRC, IP4_EXT, 2.0, RULE_NEW }
-    ,{ 6, 310, 2110, IP4_SRC, IP4_EXT, 9.9, RULE_NEW }
-
-    ,{ 0, 410, 1110, IP6_EXT, IP6_DST, 0.0, RULE_ORIG }
-    ,{ 1, 410, 1110, IP6_SRC, IP6_DST, 0.1, RULE_ORIG }
-    ,{ 2, 410, 1110, IP6_SRC, IP6_DST, 0.2, RULE_ORIG }
-    ,{ 3, 410, 1110, IP6_EXT, IP6_DST, 1.0, RULE_ORIG }
-    ,{ 4, 410, 1110, IP6_EXT, IP6_DST, 1.9, RULE_NEW }
-    ,{ 5, 410, 1110, IP6_EXT, IP6_DST, 2.0, RULE_NEW }
-    ,{ 6, 410, 1110, IP6_EXT, IP6_DST, 9.9, RULE_NEW }
-
-    ,{ 0, 410, 2110, IP6_SRC, IP6_EXT, 0.0, RULE_ORIG }
-    ,{ 1, 410, 2110, IP6_SRC, IP6_DST, 0.1, RULE_ORIG }
-    ,{ 2, 410, 2110, IP6_SRC, IP6_DST, 0.2, RULE_ORIG }
-    ,{ 3, 410, 2110, IP6_SRC, IP6_EXT, 1.0, RULE_ORIG }
-    ,{ 4, 410, 2110, IP6_SRC, IP6_EXT, 1.9, RULE_NEW }
-    ,{ 5, 410, 2110, IP6_SRC, IP6_EXT, 2.0, RULE_NEW }
-    ,{ 6, 410, 2110, IP6_SRC, IP6_EXT, 9.9, RULE_NEW }
-#else
     { 0, 200, 1110, IP4_SRC, IP4_DST, 0.0, RULE_ORIG }
     ,{ 1, 200, 1110, IP4_SRC, IP4_DST, 0.1, RULE_NEW }
     ,{ 2, 200, 1110, IP4_SRC, IP4_DST, 0.2, RULE_NEW }
@@ -851,7 +499,6 @@ static EventData evData[] =
     ,{ 4, 410, 2110, IP6_SRC, IP6_EXT, 1.9, RULE_NEW }
     ,{ 5, 410, 2110, IP6_SRC, IP6_EXT, 2.0, RULE_NEW }
     ,{ 6, 410, 2110, IP6_SRC, IP6_EXT, 9.9, RULE_NEW }
-#endif
 };
 
 #define NUM_EVENTS (sizeof(evData)/sizeof(evData[0]))
index e487b9682bc00f0a45ed7c60775d389f09eadb69..061933477fc8743c07edf716f395986ff4747cac 100644 (file)
@@ -659,7 +659,6 @@ void Analyzer::init_unprivileged()
 
     // init filters hash tables that depend on alerts
     sfthreshold_alloc(sc->threshold_config->memcap, sc->threshold_config->memcap);
-    SFRF_Alloc(sc->rate_filter_config->memcap);
 }
 
 void Analyzer::reinit(const SnortConfig* sc)
@@ -727,8 +726,6 @@ void Analyzer::term()
     delete switcher;
 
     sfthreshold_free();
-    RateFilter_Cleanup();
-
     TraceApi::thread_term();
 }
 
index 53ac50f1449c1ee50c183caa95da3a0c07223bf3..59ee55975f153638b83843360310deaa35d97448 100644 (file)
@@ -1593,6 +1593,7 @@ class RateFilterModule : public Module
 public:
     RateFilterModule() : Module("rate_filter", rate_filter_help, rate_filter_params, true)
     { thdx.applyTo = nullptr; }
+
     ~RateFilterModule() override;
     bool set(const char*, Value&, SnortConfig*) override;
     bool begin(const char*, int, SnortConfig*) override;
@@ -1617,6 +1618,7 @@ private:
 
 RateFilterModule::~RateFilterModule()
 {
+    RateFilter_Cleanup();
     if ( thdx.applyTo )
         sfvar_free(thdx.applyTo);
 }
@@ -1656,8 +1658,9 @@ bool RateFilterModule::set(const char*, Value& v, SnortConfig*)
     return true;
 }
 
-bool RateFilterModule::begin(const char*, int, SnortConfig*)
+bool RateFilterModule::begin(const char*, int, SnortConfig* sc)
 {
+    SFRF_Alloc(sc->rate_filter_config->memcap);
     memset(&thdx, 0, sizeof(thdx));
     return true;
 }