]> git.ipfire.org Git - thirdparty/snort3.git/commitdiff
Pull request #4945: memory, filters: resolve coverity and TSAN issues
authorMichael Matirko (mmatirko) <mmatirko@cisco.com>
Fri, 31 Oct 2025 21:39:54 +0000 (21:39 +0000)
committerSteven Baigal (sbaigal) <sbaigal@cisco.com>
Fri, 31 Oct 2025 21:39:54 +0000 (21:39 +0000)
Merge in SNORT/snort3 from ~MMATIRKO/snort3:coverity_calamity to master

Squashed commit of the following:

commit 696a51e6dad7ca1c6351831ca2b08899538346b5
Author: Michael Matirko <mmatirko@cisco.com>
Date:   Thu Oct 9 13:52:36 2025 -0400

    memory: resolve race condition on global stats

    filters: resolve lock issues, 2k38 issues in rate_filter and sfthd

    stream: add additional lock/unlock when we do extra_data_log

    perf_monitor: don't decrement index if already zero

    appid: fix printf args

    perf_monitor: fix minor issue with int overflow

    ha: guard against negative shift

    codec: fix byte math, codec coverity issues

    rna: use std::move on RnaTracker to move instead of copying

    snort2lua: use std::move where possible

    stream, loggers: use std::move where possible

    sfthd: fix issues with printf type specifier, cppcheck issues

    detection_engine: use const where possible

53 files changed:
src/detection/detection_engine.cc
src/detection/fp_create.cc
src/filters/rate_filter.cc
src/filters/rate_filter.h
src/filters/sfrf.cc
src/filters/sfrf.h
src/filters/sfthd.cc
src/filters/sfthd.h
src/flow/ha.cc
src/helpers/test/grouped_list_test.cc
src/host_tracker/host_cache_module.cc
src/ips_options/ips_byte_math.cc
src/loggers/alert_talos.cc
src/managers/codec_manager.cc
src/managers/plugin_manager.cc
src/memory/dev_notes.txt
src/memory/memory_module.cc
src/memory/memory_module.h
src/network_inspectors/perf_monitor/perf_monitor.cc
src/network_inspectors/rna/rna_pnd.cc
src/parser/parse_conf.cc
src/parser/var_dependency.cc
src/parser/vars.cc
src/payload_injector/payload_injector.cc
src/service_inspectors/netflow/netflow.cc
src/service_inspectors/netflow/netflow_module.cc
src/stream/base/stream_module.cc
src/stream/stream.cc
src/utils/util_unfold.cc
tools/snort2lua/config_states/config_classification.cc
tools/snort2lua/config_states/config_paf_max.cc
tools/snort2lua/config_states/config_policy_id.cc
tools/snort2lua/config_states/config_ppm.cc
tools/snort2lua/config_states/config_profile.cc
tools/snort2lua/conversion_state.h
tools/snort2lua/data/data_types/dt_option.cc
tools/snort2lua/data/data_types/dt_rule.cc
tools/snort2lua/data/data_types/dt_var.cc
tools/snort2lua/keyword_states/kws_attribute_table.cc
tools/snort2lua/output_states/out_csv.cc
tools/snort2lua/output_states/out_fast.cc
tools/snort2lua/output_states/out_full.cc
tools/snort2lua/output_states/out_tcpdump.cc
tools/snort2lua/preprocessor_states/pps_dcerpc.cc
tools/snort2lua/preprocessor_states/pps_ftp_telnet_protocol.cc
tools/snort2lua/preprocessor_states/pps_http_inspect.cc
tools/snort2lua/preprocessor_states/pps_smtp.cc
tools/snort2lua/preprocessor_states/pps_stream5_global.cc
tools/snort2lua/preprocessor_states/pps_stream5_tcp.cc
tools/snort2lua/rule_states/rule_pcre.cc
tools/snort2lua/rule_states/rule_ttl.cc
tools/u2boat/u2boat.cc
tools/u2spewfoo/u2spewfoo.cc

index b2a0e625c221af6a72d1182b5f86fa7a05d3751b..f8f25f10eaf8e5d8e3f39334997e3136bfb441f4 100644 (file)
@@ -367,7 +367,7 @@ bool DetectionEngine::get_replacement(std::string& s, unsigned& off)
     if ( Analyzer::get_switcher()->get_context()->rpl.empty() )
         return false;
 
-    auto rep = Analyzer::get_switcher()->get_context()->rpl.back();
+    const auto& rep = Analyzer::get_switcher()->get_context()->rpl.back();
 
     s = rep.data;
     off = rep.offset;
index 09a69491f8d6d563ba976fa2208577502b90cdf5..c870e032a1fb49aaf8678cdffa2fc0a2fbce0bf3 100644 (file)
@@ -144,7 +144,7 @@ static bool new_sig(int num_children, detection_option_tree_node_t** nodes, OptT
         if ( child->option_type != RULE_OPTION_TYPE_LEAF_NODE )
             continue;
 
-        OptTreeNode* cotn = (OptTreeNode*)child->option_data;
+        const OptTreeNode* cotn = (OptTreeNode*)child->option_data;
         const SigInfo& csi = cotn->sigInfo;
         const SigInfo& osi = otn->sigInfo;
 
@@ -1049,7 +1049,7 @@ static void fpCreatePortObject2RuleGroup(SnortConfig* sc, PortObject2* po, PortO
              node = pox->rule_hash->find_next())
         {
             unsigned sid, gid;
-            int* prindex = (int*)node->data;
+            const int* prindex = (int*)node->data;
 
             /* be safe - no rule index, ignore it */
             if (prindex == nullptr)
@@ -1089,7 +1089,7 @@ static void fpCreatePortObject2RuleGroup(SnortConfig* sc, PortObject2* po, PortO
 static void fpCreatePortTableRuleGroups(SnortConfig* sc, PortTable* p, PortObject2* poaa)
 {
     int cnt = 1;
-    FastPatternConfig* fp = sc->fast_pattern_config;
+    const FastPatternConfig* fp = sc->fast_pattern_config;
     if ( fp->get_debug_print_rule_group_build_details() )
         LogMessage("%d Port Groups in Port Table\n",p->pt_mpo_hash->get_count());
 
@@ -1510,7 +1510,7 @@ static bool fp_print_port_groups(RulePortTables* port_tables)
  */
 static void fpCreateServiceRuleGroups(SnortConfig* sc)
 {
-    FastPatternConfig* fp = sc->fast_pattern_config;
+    const FastPatternConfig* fp = sc->fast_pattern_config;
 
     sc->srmmTable = ServiceMapNew();
 
index eb885a4d389a26e7524ae569963507faa4508b14..f5e58d67fc528bdf339089f8c259e4ea3eba5e1d 100644 (file)
@@ -80,7 +80,7 @@ int RateFilter_Create(
 #ifdef RF_DBG
     printf(
         "THRESHOLD: gid=%u, sid=%u, tracking=%d, count=%u, seconds=%u \n",
-        thdx->gid, thdx->sid, thdx->tracking, thdx->count, thdx->seconds);
+        thdx->gid, thdx->sid, thdx->tracking, unsigned(thdx->count), thdx->seconds);
 #endif
 
     /* Add the object to the table - */
index 55b9585184c6bc5a3f43d306c92fc8d8a03d4154..b905b2726cd8ea09360768cafeafee0d3eab5c98 100644 (file)
@@ -29,7 +29,7 @@ struct Packet;
 struct SnortConfig;
 }
 struct RateFilterConfig;
-struct tSFRFConfigNode;
+class tSFRFConfigNode;
 struct OptTreeNode;
 
 RateFilterConfig* RateFilter_ConfigNew();
index 861c27c4ee3a1f33fc485aac4b562a5fd7a6b2b3..692ee4a1ec6187177c2c09a80d0cbb74eb233230 100644 (file)
@@ -117,15 +117,17 @@ static void SFRF_New(unsigned nbytes)
     nrows = nbytes / (SFRF_BYTES);
 
     /* Create global hash table for all of the IP Nodes */
+    std::lock_guard<std::mutex> lock(sfrf_hash_mutex);
     rf_hash = new XHash(nrows, sizeof(tSFRFTrackingNodeKey), sizeof(tSFRFTrackingNode), nbytes);
 }
 
 void SFRF_Delete()
 {
+    std::lock_guard<std::mutex> lock(sfrf_hash_mutex);
+
     if ( !rf_hash )
         return;
 
-    std::lock_guard<std::mutex> lock(sfrf_hash_mutex);
     delete rf_hash;
     rf_hash = nullptr;
 }
@@ -161,12 +163,21 @@ static void SFRF_SidNodeFree(void* item)
 
 int SFRF_Alloc(unsigned int memcap)
 {
-    if ( rf_hash == nullptr )
+    sfrf_hash_mutex.lock();
+    const XHash* current_rf_hash = rf_hash;
+    sfrf_hash_mutex.unlock();
+
+    if ( current_rf_hash == nullptr )
     {
         SFRF_New(memcap);
 
+        sfrf_hash_mutex.lock();
         if ( rf_hash == nullptr )
+        {
+            sfrf_hash_mutex.unlock();
             return -1;
+        }
+        sfrf_hash_mutex.unlock();
     }
     return 0;
 }
@@ -460,8 +471,8 @@ void SFRF_ShowObjects(RateFilterConfig* config)
             {
                 printf(".........SFRF_ID  =%d\n",cfgNode->tid);
                 printf(".........tracking =%d\n",cfgNode->tracking);
-                printf(".........count    =%u\n",cfgNode->count);
-                printf(".........seconds  =%u\n",cfgNode->seconds);
+                printf(".........count    =%u\n",cfgNode->count.load());
+                printf(".........seconds  =%lu\n",cfgNode->seconds);
             }
         }
     }
@@ -481,13 +492,13 @@ static int checkSamplingPeriod(tSFRFConfigNode* cfgNode, tSFRFTrackingNode* dynN
 {
     if ( cfgNode->seconds )
     {
-        unsigned dt = (unsigned)(curTime - dynNode->tstart);
+        time_t dt = curTime - dynNode->tstart;
 
         if ( dt >= cfgNode->seconds )
         {   // observation period is over, start a new one
             dynNode->tstart = curTime;
 
-            dt = (unsigned)(curTime - dynNode->tlast);
+            dt = curTime - dynNode->tlast;
             if ( dt > cfgNode->seconds )
                 dynNode->overRate = 0;
             else
@@ -534,7 +545,7 @@ static int checkThreshold(tSFRFConfigNode* cfgNode, tSFRFTrackingNode* dynNode,
     if ( dynNode->filterState == FS_ON )
     {
         if ( (cfgNode->timeout != 0 )
-            && ((unsigned)(curTime - dynNode->revertTime) >= cfgNode->timeout))
+            && (curTime - dynNode->revertTime) >= cfgNode->timeout)
         {
             if ( dynNode->count > cfgNode->count || dynNode->overRate )
             {
index c55b156fea3e4296d0f4a63ec757bff676e5067b..7aa2761a12c4673588b8a3d3c82301ba8ca5d16c 100644 (file)
@@ -22,6 +22,7 @@
 #ifndef SFRF_H
 #define SFRF_H
 
+#include <atomic>
 #include <ctime>
 #include <mutex>
 
@@ -64,15 +65,18 @@ typedef enum
     FS_NEW = 0, FS_OFF, FS_ON, FS_MAX
 } FilterState;
 
-struct tSFRFConfigNode
+class tSFRFConfigNode
 {
+public:
     int tid = 0;
     unsigned gid = 0;
     unsigned sid = 0;
     PolicyId policyId = 0;
     SFRF_TRACK tracking = SFRF_TRACK_BY_NONE;
-    unsigned count = 0;
-    unsigned seconds = 0;
+    time_t seconds = 0;
+
+    // The count variable can be updated by multiple threads simultaneously, so it must be atomic
+    std::atomic<unsigned> count{0};
 
     // Action that replaces original rule action on reaching threshold
     snort::IpsAction::Type newAction = 0;
@@ -81,6 +85,54 @@ struct tSFRFConfigNode
     unsigned timeout = 0;
     sfip_var_t* applyTo = nullptr;
 
+    tSFRFConfigNode() = default;
+
+    tSFRFConfigNode(const tSFRFConfigNode& other)
+        : tid(other.tid)
+        , gid(other.gid)
+        , sid(other.sid)
+        , policyId(other.policyId)
+        , tracking(other.tracking)
+        , seconds(other.seconds)
+        , count(other.count.load())
+        , newAction(other.newAction)
+        , timeout(other.timeout)
+        , applyTo(other.applyTo)
+    { }
+
+    tSFRFConfigNode(tSFRFConfigNode&& other) noexcept
+        : tid(other.tid)
+        , gid(other.gid)
+        , sid(other.sid)
+        , policyId(other.policyId)
+        , tracking(other.tracking)
+        , seconds(other.seconds)
+        , count(other.count.load())
+        , newAction(other.newAction)
+        , timeout(other.timeout)
+        , applyTo(other.applyTo)
+    { }
+
+    ~tSFRFConfigNode() = default;
+
+    tSFRFConfigNode& operator=(const tSFRFConfigNode& other)
+    {
+        if (this != &other)
+        {
+            tid = other.tid;
+            gid = other.gid;
+            sid = other.sid;
+            policyId = other.policyId;
+            tracking = other.tracking;
+            seconds = other.seconds;
+            count.store(other.count.load());
+            newAction = other.newAction;
+            timeout = other.timeout;
+            applyTo = other.applyTo;
+        }
+        return *this;
+    }
+
     void init()
     {
         tid = 0;
index 53e2baf5d4badf2a9cbc4c835970ac0c60d6a282..8c5f570755d0b7ff5c0d4b1ed10914aa453c1d70 100644 (file)
@@ -457,16 +457,16 @@ static inline int sfthd_test_non_suppress(
     THD_IP_NODE* sfthd_ip_node,
     time_t curtime)
 {
-    unsigned dt;
+    uint64_t dt;
 
     if ( sfthd_node->type == THD_TYPE_DETECT )
     {
-        dt = (unsigned)(curtime - sfthd_ip_node->tstart);
+        dt = curtime - sfthd_ip_node->tstart;
 
         if ( dt >= sfthd_node->seconds )
         {   /* reset */
             sfthd_ip_node->tstart = curtime;
-            if ( (unsigned)(curtime - sfthd_ip_node->tlast) > sfthd_node->seconds )
+            if ( static_cast<uint64_t>(curtime - sfthd_ip_node->tlast) > sfthd_node->seconds )
                 sfthd_ip_node->prev = 0;
             else
                 sfthd_ip_node->prev = sfthd_ip_node->count - 1;
@@ -486,7 +486,7 @@ static inline int sfthd_test_non_suppress(
     }
     if ( sfthd_node->type == THD_TYPE_LIMIT )
     {
-        dt = (unsigned)(curtime - sfthd_ip_node->tstart);
+        dt = curtime - sfthd_ip_node->tstart;
 
         if ( dt >= sfthd_node->seconds )
         {   /* reset */
@@ -505,7 +505,7 @@ static inline int sfthd_test_non_suppress(
     }
     else if ( sfthd_node->type == THD_TYPE_THRESHOLD )
     {
-        dt = (unsigned)(curtime - sfthd_ip_node->tstart);
+        dt = curtime - sfthd_ip_node->tstart;
         if ( dt >= sfthd_node->seconds )
         {
             sfthd_ip_node->tstart = curtime;
@@ -522,7 +522,7 @@ static inline int sfthd_test_non_suppress(
     }
     else if ( sfthd_node->type == THD_TYPE_BOTH )
     {
-        dt = (unsigned)(curtime - sfthd_ip_node->tstart);
+        dt = curtime - sfthd_ip_node->tstart;
         if ( dt >= sfthd_node->seconds )
         {
             sfthd_ip_node->tstart = curtime;
@@ -875,7 +875,7 @@ int sfthd_show_objects(ThresholdObjects* thd_objs)
                 else
                 {
                     printf(".........count   =%d\n",sfthd_node->count);
-                    printf(".........seconds =%u\n",sfthd_node->seconds);
+                    printf(".........seconds =%lu\n",sfthd_node->seconds);
                 }
             }
         }
index 466d823bd00aa856a2ccf032d9d3729102e67cf5..b5d5ea100e84d1211f8453ef2b9ae63eb74c6b37 100644 (file)
@@ -137,7 +137,7 @@ struct THD_NODE
     int type = 0;
     int priority = 0;
     int count = 0;
-    unsigned seconds = 0;
+    uint64_t seconds = 0;
     sfip_var_t* ip_address = nullptr;
 };
 
index a60faf40be8da154355d419cc8307ed8a1946028..ed72cc7b9b22e685ab3e5e8d8c6f292c768eef14 100644 (file)
@@ -222,6 +222,11 @@ FlowHAClient::FlowHAClient(uint8_t length, bool session_client) : max_length(len
         }
 
         index = ha->handle_counter;
+        
+        // Guard against null index which could cause a shift by a negative amount
+        if (!index)
+            return;
+
         handle = (1 << (index - 1));
         ha->client_map[index] = this;
         ha->handle_counter++;
@@ -247,7 +252,7 @@ static uint8_t write_flow_key(const Flow& flow, HAMessage& msg)
     msg.advance_cursor(sizeof(key->ip_l[3]));
     memcpy(msg.cursor, &key->ip_h[3], sizeof(key->ip_h[3]));
     msg.advance_cursor(sizeof(key->ip_h[3]));
-    memcpy(msg.cursor, ((const uint8_t*) key) + 32, KEY_SIZE_IP4 - 8);
+    memcpy(msg.cursor, (reinterpret_cast<const uint8_t*>(key)) + 32, KEY_SIZE_IP4 - 8);
     msg.advance_cursor(KEY_SIZE_IP4 - 8);
 
     return KEY_TYPE_IP4;
@@ -288,7 +293,7 @@ static uint8_t read_flow_key(HAMessage& msg, const HAMessageHeader* hdr, FlowKey
         key.ip_h[2] = htonl(0xFFFF);
         msg.advance_cursor(sizeof(key.ip_h[3]));
         /* The remainder of the key */
-        memcpy(((uint8_t*) &key) + 32, msg.cursor, KEY_SIZE_IP4 - 8);
+        memcpy((reinterpret_cast<uint8_t*>(&key)) + 32, msg.cursor, KEY_SIZE_IP4 - 8);
         msg.advance_cursor(KEY_SIZE_IP4 - 8);
 
         return KEY_SIZE_IP4;
@@ -334,7 +339,7 @@ static uint16_t calculate_update_msg_content_length(Flow& flow, bool full)
 // at the beginning of the content section.
 static void write_msg_header(const Flow& flow, HAEvent event, uint16_t content_length, HAMessage& msg)
 {
-    HAMessageHeader* hdr = (HAMessageHeader*) msg.cursor;
+    HAMessageHeader* hdr = reinterpret_cast<HAMessageHeader*>(msg.cursor);
     hdr->event = (uint8_t) event;
     hdr->version = HA_MESSAGE_VERSION;
     hdr->total_length = content_length;
@@ -344,7 +349,7 @@ static void write_msg_header(const Flow& flow, HAEvent event, uint16_t content_l
 
 static uint16_t update_msg_header_length(const HAMessage& msg)
 {
-    HAMessageHeader* hdr = (HAMessageHeader*) msg.buffer;
+    HAMessageHeader* hdr = reinterpret_cast<HAMessageHeader*>(msg.buffer);
     hdr->total_length = msg.cursor_position();
     return hdr->total_length;
 }
@@ -359,7 +364,7 @@ static void write_update_msg_client(FlowHAClient* client, Flow& flow, HAMessage&
     // Preemptively insert the client header.  If production fails, roll back the message cursor
     // to its original position.
     uint8_t* original_cursor = msg.cursor;
-    HAClientHeader* header = (HAClientHeader*) original_cursor;
+    HAClientHeader* header = reinterpret_cast<HAClientHeader*>(original_cursor);
     header->client = client->index;
     msg.advance_cursor(sizeof(HAClientHeader));
     if (!client->produce(flow, msg))
@@ -410,7 +415,7 @@ static Flow* consume_ha_update_message(HAMessage& msg, const FlowKey& key, Packe
             break;
         }
 
-        HAClientHeader* header = (HAClientHeader*) msg.cursor;
+        HAClientHeader* header = reinterpret_cast<HAClientHeader*>(msg.cursor);
         if ((header->client >= ha->handle_counter) || (ha->client_map[header->client] == nullptr))
         {
             ErrorMessage("Consuming HA Update message - invalid client index\n");
@@ -479,7 +484,7 @@ static Flow* consume_ha_message(HAMessage& msg,
         return nullptr;
     }
 
-    const HAMessageHeader* hdr = (HAMessageHeader*) msg.cursor;
+    const HAMessageHeader* hdr = reinterpret_cast<HAMessageHeader*>(msg.cursor);
 
     if (hdr->version != HA_MESSAGE_VERSION)
     {
index 51df74944261d87ab2f2de20a67f7804f40bbf06..555158c3822a961731f8b7f5c2d5c79fae96168a 100644 (file)
@@ -72,7 +72,7 @@ TEST_CASE("Basic", "[Double list]")
     SECTION("1 element")
     {
         const Type data = {1, "one"};
-        Elem* el = new Elem(cont, group, data);
+        const Elem* el = new Elem(cont, group, data);
 
         CHECK(el != nullptr);
 
@@ -84,9 +84,9 @@ TEST_CASE("Basic", "[Double list]")
         const Type data1 = {1, "one"};
         const Type data2 = {2, "two"};
         const Type data3 = {3, "three"};
-        Elem* el1 = new Elem(cont, group, data1);
-        Elem* el2 = new Elem(cont, group, data2);
-        Elem* el3 = new Elem(cont, group, data3);
+        const Elem* el1 = new Elem(cont, group, data1);
+        const Elem* el2 = new Elem(cont, group, data2);
+        const Elem* el3 = new Elem(cont, group, data3);
 
         CHECK(el1 != nullptr);
         CHECK(el2 != nullptr);
@@ -107,11 +107,11 @@ TEST_CASE("Groups", "[Double list]")
         const Type data3 = {3, "three"};
         Elem* group_a = nullptr;
 
-        Elem* el1 = new Elem(cont, group_a, data1);
+        const Elem* el1 = new Elem(cont, group_a, data1);
         CHECK(group_a == el1);
-        Elem* el2 = new Elem(cont, group_a, data2);
+        const Elem* el2 = new Elem(cont, group_a, data2);
         CHECK(group_a == el2);
-        Elem* el3 = new Elem(cont, group_a, data3);
+        const Elem* el3 = new Elem(cont, group_a, data3);
         CHECK(group_a == el3);
 
         check_container(cont, data1, data2, data3);
@@ -132,11 +132,11 @@ TEST_CASE("Groups", "[Double list]")
         Elem* group_b = nullptr;
         Elem* group_c = nullptr;
 
-        Elem* el1 = new Elem(cont, group_a, data1);
+        const Elem* el1 = new Elem(cont, group_a, data1);
         CHECK(group_a == el1);
-        Elem* el2 = new Elem(cont, group_b, data2);
+        const Elem* el2 = new Elem(cont, group_b, data2);
         CHECK(group_b == el2);
-        Elem* el3 = new Elem(cont, group_c, data3);
+        const Elem* el3 = new Elem(cont, group_c, data3);
         CHECK(group_c == el3);
 
         check_container(cont, data1, data2, data3);
@@ -207,11 +207,11 @@ TEST_CASE("Groups", "[Double list]")
         const Type data3 = {3, "three"};
         Elem* group_a = nullptr;
 
-        Elem* el1 = new Elem(cont, group_a, data1);
+        const Elem* el1 = new Elem(cont, group_a, data1);
         CHECK(group_a == el1);
         Elem* el2 = new Elem(cont, group_a, data2);
         CHECK(group_a == el2);
-        Elem* el3 = new Elem(cont, group_a, data3);
+        const Elem* el3 = new Elem(cont, group_a, data3);
         CHECK(group_a == el3);
 
         check_container(cont, data1, data2, data3);
@@ -238,9 +238,9 @@ TEST_CASE("Groups", "[Double list]")
 
         Elem* el1 = new Elem(cont, group_a, data1);
         CHECK(group_a == el1);
-        Elem* el2 = new Elem(cont, group_a, data2);
+        const Elem* el2 = new Elem(cont, group_a, data2);
         CHECK(group_a == el2);
-        Elem* el3 = new Elem(cont, group_a, data3);
+        const Elem* el3 = new Elem(cont, group_a, data3);
         CHECK(group_a == el3);
 
         check_container(cont, data1, data2, data3);
@@ -265,9 +265,9 @@ TEST_CASE("Groups", "[Double list]")
         const Type data3 = {3, "three"};
         Elem* group_a = nullptr;
 
-        Elem* el1 = new Elem(cont, group_a, data1);
+        const Elem* el1 = new Elem(cont, group_a, data1);
         CHECK(group_a == el1);
-        Elem* el2 = new Elem(cont, group_a, data2);
+        const Elem* el2 = new Elem(cont, group_a, data2);
         CHECK(group_a == el2);
         Elem* el3 = new Elem(cont, group_a, data3);
         CHECK(group_a == el3);
@@ -381,7 +381,7 @@ TEST_CASE("Memory management (value by copy)", "[Double list]")
     SECTION("delete group")
     {
         const Type data = {1, "one"};
-        Elem* el = new Elem(cont, group_a, data);
+        const Elem* el = new Elem(cont, group_a, data);
 
         CHECK(el != nullptr);
 
@@ -397,8 +397,8 @@ TEST_CASE("Memory management (value by copy)", "[Double list]")
     {
         const Type data1 = {1, "one"};
         const Type data2 = {2, "two"};
-        Elem* el1 = new Elem(cont, group_a, data1);
-        Elem* el2 = new Elem(cont, group_b, data2);
+        const Elem* el1 = new Elem(cont, group_a, data1);
+        const Elem* el2 = new Elem(cont, group_b, data2);
 
         CHECK(el1 != nullptr);
         CHECK(el2 != nullptr);
@@ -418,8 +418,8 @@ TEST_CASE("Memory management (value by copy)", "[Double list]")
     {
         const Type data1 = {1, "one"};
         const Type data2 = {2, "two"};
-        Elem* el1 = new Elem(cont, group_a, data1);
-        Elem* el2 = new Elem(cont, group_b, data2);
+        const Elem* el1 = new Elem(cont, group_a, data1);
+        const Elem* el2 = new Elem(cont, group_b, data2);
 
         CHECK(el1 != nullptr);
         CHECK(el2 != nullptr);
@@ -439,9 +439,9 @@ TEST_CASE("Memory management (value by copy)", "[Double list]")
         const Type data1 = {1, "one"};
         const Type data2 = {2, "two"};
         const Type data3 = {3, "three"};
-        Elem* el1 = new Elem(cont, group_a, data1);
-        Elem* el2 = new Elem(cont, group_b, data2);
-        Elem* el3 = new Elem(cont, group_b, data3);
+        const Elem* el1 = new Elem(cont, group_a, data1);
+        const Elem* el2 = new Elem(cont, group_b, data2);
+        const Elem* el3 = new Elem(cont, group_b, data3);
 
         CHECK(el1 != nullptr);
         CHECK(el2 != nullptr);
@@ -463,9 +463,9 @@ TEST_CASE("Memory management (value by copy)", "[Double list]")
         const Type data1 = {1, "one"};
         const Type data2 = {2, "two"};
         const Type data3 = {3, "three"};
-        Elem* el1 = new Elem(cont, group_a, data1);
-        Elem* el2 = new Elem(cont, group_b, data2);
-        Elem* el3 = new Elem(cont, group_b, data3);
+        const Elem* el1 = new Elem(cont, group_a, data1);
+        const Elem* el2 = new Elem(cont, group_b, data2);
+        const Elem* el3 = new Elem(cont, group_b, data3);
 
         CHECK(el1 != nullptr);
         CHECK(el2 != nullptr);
@@ -503,7 +503,7 @@ TEST_CASE("Memory management (value in-place)", "[Double list]")
 
     SECTION("delete group")
     {
-        Elem* el = new Elem(cont, group_a, 1, "one");
+        const Elem* el = new Elem(cont, group_a, 1, "one");
 
         CHECK(el != nullptr);
 
@@ -517,8 +517,8 @@ TEST_CASE("Memory management (value in-place)", "[Double list]")
 
     SECTION("delete element, then delete group")
     {
-        Elem* el1 = new Elem(cont, group_a, 1, "one");
-        Elem* el2 = new Elem(cont, group_b, 2, "two");
+        const Elem* el1 = new Elem(cont, group_a, 1, "one");
+        const Elem* el2 = new Elem(cont, group_b, 2, "two");
 
         CHECK(el1 != nullptr);
         CHECK(el2 != nullptr);
@@ -536,8 +536,8 @@ TEST_CASE("Memory management (value in-place)", "[Double list]")
 
     SECTION("delete group, then delete element")
     {
-        Elem* el1 = new Elem(cont, group_a, 1, "one");
-        Elem* el2 = new Elem(cont, group_b, 2, "two");
+        const Elem* el1 = new Elem(cont, group_a, 1, "one");
+        const Elem* el2 = new Elem(cont, group_b, 2, "two");
 
         CHECK(el1 != nullptr);
         CHECK(el2 != nullptr);
@@ -554,9 +554,9 @@ TEST_CASE("Memory management (value in-place)", "[Double list]")
 
     SECTION("delete elements (remain), then delete group")
     {
-        Elem* el1 = new Elem(cont, group_a, 1, "one");
-        Elem* el2 = new Elem(cont, group_b, 2, "two");
-        Elem* el3 = new Elem(cont, group_b, 3, "three");
+        const Elem* el1 = new Elem(cont, group_a, 1, "one");
+        const Elem* el2 = new Elem(cont, group_b, 2, "two");
+        const Elem* el3 = new Elem(cont, group_b, 3, "three");
 
         CHECK(el1 != nullptr);
         CHECK(el2 != nullptr);
@@ -575,9 +575,9 @@ TEST_CASE("Memory management (value in-place)", "[Double list]")
 
     SECTION("delete group, then delete elements (remain)")
     {
-        Elem* el1 = new Elem(cont, group_a, 1, "one");
-        Elem* el2 = new Elem(cont, group_b, 2, "two");
-        Elem* el3 = new Elem(cont, group_b, 3, "three");
+        const Elem* el1 = new Elem(cont, group_a, 1, "one");
+        const Elem* el2 = new Elem(cont, group_b, 2, "two");
+        const Elem* el3 = new Elem(cont, group_b, 3, "three");
 
         CHECK(el1 != nullptr);
         CHECK(el2 != nullptr);
index 2d898e3986fbd44685880b499c5701d5a21321c6..2197324f92a0b26690c2d2d0b359c227f736cb05 100644 (file)
@@ -79,7 +79,7 @@ static int host_cache_get_segment_stats(lua_State* L)
 
 static int host_cache_delete_host(lua_State* L)
 {
-    HostCacheModule* mod = (HostCacheModule*) ModuleManager::get_module(HOST_CACHE_NAME);
+    const HostCacheModule* mod = (HostCacheModule*) ModuleManager::get_module(HOST_CACHE_NAME);
     if ( mod )
     {
         const char* ips = luaL_optstring(L, 1, nullptr);
@@ -111,7 +111,7 @@ static int host_cache_delete_host(lua_State* L)
 
 static int host_cache_delete_network_proto(lua_State* L)
 {
-    HostCacheModule* mod = (HostCacheModule*) ModuleManager::get_module(HOST_CACHE_NAME);
+    const HostCacheModule* mod = (HostCacheModule*) ModuleManager::get_module(HOST_CACHE_NAME);
     if ( mod )
     {
         const char* ips = luaL_optstring(L, 1, nullptr);
@@ -151,7 +151,7 @@ static int host_cache_delete_network_proto(lua_State* L)
 
 static int host_cache_delete_transport_proto(lua_State* L)
 {
-    HostCacheModule* mod = (HostCacheModule*) ModuleManager::get_module(HOST_CACHE_NAME);
+    const HostCacheModule* mod = (HostCacheModule*) ModuleManager::get_module(HOST_CACHE_NAME);
     if ( mod )
     {
         const char* ips = luaL_optstring(L, 1, nullptr);
@@ -190,7 +190,7 @@ static int host_cache_delete_transport_proto(lua_State* L)
 
 static int host_cache_delete_service(lua_State* L)
 {
-    HostCacheModule* mod = (HostCacheModule*) ModuleManager::get_module(HOST_CACHE_NAME);
+    const HostCacheModule* mod = (HostCacheModule*) ModuleManager::get_module(HOST_CACHE_NAME);
     if ( mod )
     {
         const char* ips = luaL_optstring(L, 1, nullptr);
@@ -237,7 +237,7 @@ static int host_cache_delete_service(lua_State* L)
 
 static int host_cache_delete_client(lua_State* L)
 {
-    HostCacheModule* mod = (HostCacheModule*) ModuleManager::get_module(HOST_CACHE_NAME);
+    const HostCacheModule* mod = (HostCacheModule*) ModuleManager::get_module(HOST_CACHE_NAME);
     if ( mod )
     {
         const char* ips = luaL_optstring(L, 1, nullptr);
@@ -496,7 +496,7 @@ string HostCacheModule::get_host_cache_segment_stats(int seg_idx)
             + to_string(lru_data.size()) + " trackers, memcap: " + to_string(host_cache.get_max_size())
             + " bytes\n";
 
-        PegCount* counts = (PegCount*) host_cache.get_counts();
+        const PegCount* counts = (PegCount*) host_cache.get_counts();
         for ( int i = 0; pegs[i].type != CountType::END; i++ )
         {
             if ( counts[i] )
@@ -551,7 +551,7 @@ string HostCacheModule::get_host_cache_stats()
         + to_string(lru_data.size()) + " trackers, memcap: " + to_string(host_cache.get_max_size())
         + " bytes\n";
 
-    PegCount* counts = (PegCount*) host_cache.get_counts();
+    const PegCount* counts = (PegCount*) host_cache.get_counts();
     const PegInfo* pegs = host_cache.get_pegs();
 
     for ( int i = 0; pegs[i].type != CountType::END; i++ )
index 9bd18cffb089d7849eecfda0fdac8ec830f275d6..59f0ec94748388a045b2a793e8ad1505ef6d5032 100644 (file)
@@ -245,6 +245,8 @@ int ByteMathOption::calc(uint32_t& value, const uint32_t rvalue)
         }
     case BM_DIVIDE:
         assert(rvalue != 0);
+        if (!rvalue)
+             return NO_MATCH;
         value /= rvalue;
         break;
 
@@ -495,7 +497,7 @@ static void mod_dtor(Module* m)
 
 static IpsOption* byte_math_ctor(Module* p, IpsInfo&)
 {
-    ByteMathModule* m = (ByteMathModule*)p;
+    ByteMathModule* m = reinterpret_cast<ByteMathModule*>(p);
     ByteMathData& data = m->data;
 
     data.result_var = AddVarNameToList(data.result_name);
index 5360c2a448de4681856b82dc8e0da169b1327165..f6a697d08378dcd2345e673a5830dcd76fd3f596 100644 (file)
@@ -127,7 +127,7 @@ void TalosLogger::open()
     if ( sep_pos != string::npos )
         ifname = ifname.substr(sep_pos+1);
 
-    talos_log->name = ifname;
+    talos_log->name = std::move(ifname);
 }
 
 void TalosLogger::close()
@@ -185,14 +185,14 @@ void TalosLogger::alert(Packet*, const char* msg, const Event& event)
     message.pop_back();
 
     rule.key = key.str();
-    rule.msg = message;
+    rule.msg = std::move(message);
     rule.gid = gid;
     rule.sid = sid;
     rule.rev = rev;
     rule.count = 1;
 
     // rule not in map, add it
-    alerts[key.str()] = rule;
+    alerts[key.str()] = std::move(rule);
 }
 
 //-------------------------------------------------------------------------
index 64217bfd0fa3c5dcb61315dc04527b2cb4cd8d42..7e97cc7830a0c6dbedaa61d47fe138d2eb35e1b5 100644 (file)
@@ -142,7 +142,10 @@ void CodecManager::instantiate(CodecApiWrapper& wrap, Module* m)
         static std::size_t codec_id = 1;
 
         if (codec_id >= s_protocols.size())
+        {
             ParseError("A maximum of 256 codecs can be registered");
+            return;
+        }
 
         if (cd_api->pinit)
             cd_api->pinit();
index e87ab9b3dba22b4ad980e332697f2bc4d25456ef..45ca102f5321426c8f92ee078f506463647d5ddd 100644 (file)
@@ -218,7 +218,7 @@ static bool register_plugin(
             return false;  // keep the old one
     }
 
-    p.key = key;
+    p.key = std::move(key);
     p.api = api;
     p.handle = std::move(handle);
     p.source = file;
index 066992fdc7052a9f431cfc2e3666ad38393c709b..514e721b2c3f5696bfc37cec1e40a4d4842f6c9b 100644 (file)
@@ -84,3 +84,14 @@ well enough below the actual hard limit, for example the limit enforced by cgrou
 processing of a single packet will not push us over. It must also allow for additional heap
 overhead.
 
+Note regarding statistics collection in the Memory module:
+
+Locking for statistics collection is minimized as the write operation (update_global_stats)
+is protected by a standard lock to ensure multiple threads don't update the global stats
+simultaneously. We are able to bail out if another thread is currently updating the statistics,
+as they will be approximately equal for either of the simulteneous callers.
+
+Read access (Module::sum_stats) can be protected via a shared lock, since
+all that we require here is that stats are not being updated while we are reading them.
+Thus, we never should block to acquire a writer lock, and the critical section is minimal for
+the Module::sum_stats call.
\ No newline at end of file
index 286eb90c2ead99ef68ab00c2f7540f80bef8a8f0..981292f186b62584cf8fe74c7ecad42ed1b02d4b 100644 (file)
@@ -120,8 +120,15 @@ PegCount* MemoryModule::get_counts() const
 
 void MemoryModule::sum_stats(bool dump_stats)
 {
-    memory::MemoryCap::update_global_stats();
+    if (mem_global_stats_mutex.try_lock())
+    {
+        memory::MemoryCap::update_global_stats();
+        mem_global_stats_mutex.unlock();
+    }
+
+    mem_global_stats_mutex.lock_shared();
     Module::sum_stats(dump_stats);
+    mem_global_stats_mutex.unlock();
 }
 
 void MemoryModule::set_trace(const Trace* trace) const
index 5aa05eaaa5be78b9457485cb0f42f36891b8ac82..66f89a9b28cfb5735100fbc29d47d451d4551a07 100644 (file)
@@ -23,6 +23,8 @@
 
 #include "framework/module.h"
 
+#include <shared_mutex>
+
 class MemoryModule : public snort::Module
 {
 public:
@@ -40,6 +42,8 @@ public:
 
     void set_trace(const snort::Trace*) const override;
     const snort::TraceOption* get_trace_options() const override;
+
+    std::shared_mutex mem_global_stats_mutex;
 };
 
 extern THREAD_LOCAL const snort::Trace* memory_trace;
index 7c2dd891a1e497408245f5154e2832e8c6c5e7d7..612087279d37bbb941684a2ae9e4181311e09df1 100644 (file)
@@ -210,6 +210,8 @@ void PerfMonitor::show(const SnortConfig*) const
 
 void PerfMonitor::disable_tracker(size_t i)
 {
+    assert (i < trackers->size() && i > 0);
+
     WarningMessage("Disabling %s\n", (*trackers)[i]->get_name().c_str());
     auto tracker = trackers->at(i);
 
@@ -253,10 +255,16 @@ void PerfMonitor::tinit()
     if (config->perf_flags & PERF_CPU )
         trackers->emplace_back(new CPUTracker(config));
 
-    for (unsigned i = 0; i < trackers->size(); i++)
+    // Second condition is to prevent overflow, shouldn't happen in practice
+    for (unsigned i = 0; i < trackers->size() && i < std::numeric_limits<unsigned>::max(); i++)
     {
         if (!(*trackers)[i]->open(true))
-            disable_tracker(i--);
+        {
+            disable_tracker(i);
+
+            if (i > 0)
+                i--;
+        }
     }
 
     for (auto& tracker : *trackers)
@@ -265,7 +273,7 @@ void PerfMonitor::tinit()
 
 bool PerfMonReloadTuner::tinit()
 {
-    PerfMonitor* pm = (PerfMonitor*)PigPen::get_inspector(PERF_NAME, true);
+    PerfMonitor* pm = reinterpret_cast<PerfMonitor*>(PigPen::get_inspector(PERF_NAME, true));
     auto* new_constraints = pm->get_constraints();
 
     if (new_constraints->flow_ip_enabled)
@@ -317,9 +325,16 @@ void PerfMonitor::tterm()
 
 void PerfMonitor::rotate()
 {
-    for ( unsigned i = 0; i < trackers->size(); i++ )
-        if ( !(*trackers)[i]->rotate() )
-            disable_tracker(i--);
+    for (auto& tracker : *trackers)
+        {
+            if (!tracker->rotate())
+            {
+                auto found_trk = std::find(trackers->begin(), trackers->end(), tracker);
+                size_t pos = found_trk - trackers->begin();
+                if (found_trk != trackers->end() && pos > 0 && pos < trackers->size())
+                    disable_tracker(pos - 1);
+            }
+        }
 }
 
 void PerfMonitor::swap_constraints(PerfConstraints* constraints)
@@ -452,7 +467,7 @@ static void mod_dtor(Module* m)
 { delete m; }
 
 static Inspector* pm_ctor(Module* m)
-{ return new PerfMonitor(((PerfMonModule*)m)->get_config()); }
+{ return new PerfMonitor((reinterpret_cast<PerfMonModule*>(m))->get_config()); }
 
 static void pm_dtor(Inspector* p)
 { delete p; }
index 8274bbd3ba7af08e4a15a40d2dd517dc89bb9219..9500d63878cf289760b6e9d168fc60b42ea1c1e0 100644 (file)
@@ -715,7 +715,7 @@ void RnaPnd::discover_network_ethernet(const Packet* p)
 
             if ( !etherType or etherType > static_cast<uint16_t>(ProtocolId::ETHERTYPE_MINIMUM) )
             {
-                generate_new_host_mac(p, rt);
+                generate_new_host_mac(p, std::move(rt));
                 return;
             }
 
@@ -723,7 +723,7 @@ void RnaPnd::discover_network_ethernet(const Packet* p)
 
             if ( llc->s.s.DSAP != llc->s.s.SSAP )
             {
-                generate_new_host_mac(p, rt);
+                generate_new_host_mac(p, std::move(rt));
                 return;
             }
 
@@ -745,7 +745,7 @@ void RnaPnd::discover_network_ethernet(const Packet* p)
     }
 
     if ( retval )
-        generate_new_host_mac(p, rt, true);
+        generate_new_host_mac(p, std::move(rt), true);
 
     return;
 }
index 938cf85e35ee685c78482cf54f77759979de961e..10ffc75acba7800ff55222125467aa68f92ea307 100644 (file)
@@ -183,7 +183,7 @@ const char* get_config_file(const char* arg, std::string& file)
     if ( relative_to_include_dir(arg, file) )
         return "I";
 
-    file = hint;
+    file = std::move(hint);
 
     if ( relative_to_parse_dir(arg, file) )
         return "F";
index 222a0fb02d35f146e45f9dab971b0410223611f5..00af5eed45aefd17cdce598ac1955e4b229db2ff 100644 (file)
@@ -62,7 +62,7 @@ static std::list<std::string> extract_variable_names(const char* input)
             ;
 
         std::string variable(input + begin + 1, end - begin - 1);
-        variable_names.push_back(variable);
+        variable_names.push_back(std::move(variable));
         begin = end - 1;
     }
 
index fb598907ad28984c36ff5ed2a0f8620fd61f6083..40d765fd847b9218d497ce6872831bd99f97d588 100644 (file)
@@ -489,7 +489,7 @@ const std::string ExpandVars(const std::string& input_str)
         {
         case '-':
             if (var_contents.empty())
-                var_contents = var_aux;
+                var_contents = std::move(var_aux);
             break;
 
         case '?':
index 4d21af8d11739ee632bdb2f17e07490094058dad..2607eea0202af4426409b37be98342e230af22df 100644 (file)
@@ -163,5 +163,8 @@ const char* PayloadInjector::get_err_string(InjectionReturnStatus status)
 {
     auto iter = InjectionErrorToString.find(status);
     assert (iter != InjectionErrorToString.end());
-    return iter->second;
+    if (iter != InjectionErrorToString.end())
+        return iter->second;
+    else
+        return nullptr;
 }
index 36728296f360927156ce9e399d4b6034f7517872..1e1a3549ff5034b1db33ce9c6fe8c59777b6c91d 100644 (file)
@@ -124,7 +124,10 @@ static void publish_netflow_event(const Packet* p, const NetFlowRule* match, Net
     // LAST_PKT_SECOND - if these aren't set, assume the current wire pkt time
     if (!record.first_pkt_second or !record.last_pkt_second)
     {
+        // Record structures are uint_32 so we must use that here
+        //coverity[y2k38_safety]
         record.first_pkt_second = static_cast<uint32_t>(packet_time());
+        //coverity[y2k38_safety]
         record.last_pkt_second = static_cast<uint32_t>(packet_time());
     }
 
index b3de30bbb52e1a7687e1ad9a73d027d48356c336..0a32ff396ea90cdf9d44fa97fd3c7c30e82b5dea 100644 (file)
@@ -30,6 +30,7 @@
 #include "netflow_cache.h"
 #include "netflow_module.h"
 
+#include "log/messages.h"
 #include "utils/util.h"
 
 using namespace snort;
@@ -242,6 +243,14 @@ void NetFlowModule::parse_service_id_file(const std::string& serv_id_file_path)
             while( std::getline(ss, tmp_str, '\t') )
                 tokens.push_back(tmp_str);
 
+            if ( tokens.size() != 3 )
+            {
+                ParseWarning(WARN_CONF,
+                    "netflow: malformed service id line (expected 3 tab-separated tokens, got %u): %s",
+                    static_cast<unsigned>(tokens.size()), serv_line.c_str());
+                continue;
+            }
+
             // Format is <port> <tcp/udp> <internal ID>
             uint16_t srv_port = std::stoi(tokens[0]);
             std::string proto_str = tokens[1];
@@ -267,7 +276,7 @@ PegCount* NetFlowModule::get_counts() const
         netflow_stats.netflow_cache_bytes_in_use = 0;
         netflow_stats.template_cache_bytes_in_use = 0;
     }
-    return (PegCount*)&netflow_stats;
+    return reinterpret_cast<PegCount*>(&netflow_stats);
 }
 
 const PegInfo* NetFlowModule::get_pegs() const
index f92aa3372e9fc9ebbdc268a948d6d8b3c434c9aa..0dd3156a3078b7f9dcbd59781a3d21dfda4fb9dc 100644 (file)
@@ -234,14 +234,14 @@ uncompleted queue*/
 #endif
     );
     SfIp src_ip,src_subnet;
-    if (!df->set_ip(source_ip, src_ip, src_subnet))
+    if (!df->set_ip(std::move(source_ip), src_ip, src_subnet))
     {
         LogRespond(ctrlcon, "Invalid source ip\n");
         delete df;
         return -1;
     }
     SfIp dst_ip,dst_subnet;
-    if (!df->set_ip(destination_ip, dst_ip, dst_subnet))
+    if (!df->set_ip(std::move(destination_ip), dst_ip, dst_subnet))
     {
         LogRespond(ctrlcon, "Invalid destination ip\n");
         delete df;
@@ -326,14 +326,14 @@ static int dump_flows_summary(lua_State* L)
     DumpFlowsSummary* dfs = new DumpFlowsSummary(ctrlcon);
 
     SfIp src_ip,src_subnet;
-    if (!dfs->set_ip(source_ip, src_ip, src_subnet))
+    if (!dfs->set_ip(std::move(source_ip), src_ip, src_subnet))
     {
         LogRespond(ctrlcon, "Invalid source ip\n");
         delete dfs;
         return -1;
     }
     SfIp dst_ip,dst_subnet;
-    if (!dfs->set_ip(destination_ip, dst_ip, dst_subnet))
+    if (!dfs->set_ip(std::move(destination_ip), dst_ip, dst_subnet))
     {
         LogRespond(ctrlcon, "Invalid destination ip\n");
         delete dfs;
index 3d88004a77b9d34c561d676ef3db304ac5936b95..0611241a72d59a364b358522183dbf6ac80f7311 100644 (file)
@@ -499,8 +499,10 @@ StreamSplitter* Stream::get_splitter(Flow* flow, bool to_server)
 void Stream::log_extra_data(
     Flow* flow, uint32_t mask, const AlertInfo& alert_info)
 {
+    std::lock_guard<std::mutex> xtra_lock(stream_xtra_mutex);
     if ( mask && stream.extra_data_log )
     {
+
         stream.extra_data_log(
             flow, stream.extra_data_context, stream.xtradata_map,
             stream.xtradata_func_count, mask, alert_info);
@@ -777,7 +779,7 @@ uint16_t Stream::get_mss(Flow* flow, bool to_server)
 {
     assert(flow and flow->session and flow->pkt_type == PktType::TCP);
 
-    TcpSession* tcp_session = (TcpSession*)flow->session;
+    TcpSession* tcp_session = reinterpret_cast<TcpSession*>(flow->session);
     return tcp_session->get_mss(to_server);
 }
 
@@ -785,7 +787,7 @@ uint8_t Stream::get_tcp_options_len(Flow* flow, bool to_server)
 {
     assert(flow and flow->session and flow->pkt_type == PktType::TCP);
 
-    TcpSession* tcp_session = (TcpSession*)flow->session;
+    TcpSession* tcp_session = reinterpret_cast<TcpSession*>(flow->session);
     return tcp_session->get_tcp_options_len(to_server);
 }
 
@@ -801,7 +803,7 @@ bool Stream::can_set_no_ack_mode(Flow* flow)
 {
     assert(flow and flow->session and flow->pkt_type == PktType::TCP);
 
-    TcpSession* tcp_session = (TcpSession*)flow->session;
+    TcpSession* tcp_session = reinterpret_cast<TcpSession*>(flow->session);
     return tcp_session->can_set_no_ack();
 }
 
@@ -809,7 +811,7 @@ bool Stream::set_no_ack_mode(Flow* flow, bool on_off)
 {
     assert(flow and flow->session and flow->pkt_type == PktType::TCP);
 
-    TcpSession* tcp_session = (TcpSession*)flow->session;
+    TcpSession* tcp_session = reinterpret_cast<TcpSession*>(flow->session);
     return tcp_session->set_no_ack(on_off);
 }
 
@@ -818,9 +820,9 @@ void Stream::partial_flush(Flow* flow, bool to_server)
     if ( flow->pkt_type == PktType::TCP )
     {
         if ( to_server )
-            ((TcpSession*)flow->session)->server.perform_partial_flush();
+            reinterpret_cast<TcpSession*>(flow->session)->server.perform_partial_flush();
         else
-            ((TcpSession*)flow->session)->client.perform_partial_flush();
+            reinterpret_cast<TcpSession*>(flow->session)->client.perform_partial_flush();
     }
 }
 
@@ -829,7 +831,7 @@ bool Stream::get_held_pkt_seq(Flow* flow, uint32_t& seq)
     if (!flow or !flow->session or !(flow->pkt_type == PktType::TCP))
         return false;
 
-    TcpSession* tcp_session = (TcpSession*)flow->session;
+    TcpSession* tcp_session = reinterpret_cast<TcpSession*>(flow->session);
 
     if (tcp_session->held_packet_dir == SSN_DIR_NONE)
         return false;
index 325de7e743eb33f191c23de47c452b0f5f1f4833..4d5de1c1bf34dcfd63d87aa6987d9b1b542950c2 100644 (file)
@@ -95,7 +95,8 @@ int sf_unfold_header(const uint8_t* inbuf, uint32_t inbuf_size, uint8_t* outbuf,
     if (n < outbuf_size)
         *outbuf_ptr = '\0';
     else
-        outbuf[outbuf_size - 1] = '\0';
+        if (outbuf_size)
+            outbuf[outbuf_size - 1] = '\0';
 
     *output_bytes = outbuf_ptr - outbuf;
     if (folded)
index 3f1d970bb9bdc8a469ac51c1e25add9497e23e56..8b5c0a6355369760ae1cecb260df0bed1700c974 100644 (file)
@@ -62,6 +62,7 @@ bool Classification::convert(std::istringstream& data_stream)
     if (!(data_stream >> priority))
         return false;
 
+    // coverity[tainted_scalar]
     table_api.add_option("priority", priority);
     return true;
 }
index e60ad5f5399011af9ccec908d88f47fd7afb8717..81ab4252c27a72f5f515c4a8c339ec558ed2f29e 100644 (file)
@@ -54,7 +54,7 @@ bool PafMax::convert(std::istringstream& data_stream)
 
         if (!(data_stream >> val))
             return true;
-
+        // coverity[tainted_scalar]
         data_api.failed_conversion(data_stream, std::to_string(val));
     }
     else
index d2636268bb64775c4cd9050c28d1eb6008febabc..81799aa2674df217a21050887b5bf8fc1f71525f 100644 (file)
@@ -42,6 +42,7 @@ bool PolicyId::convert(std::istringstream& data_stream)
     if (data_stream >> policy_id)
     {
         cv.get_table_api().open_table("ips");
+        // coverity[tainted_scalar]
         cv.get_table_api().add_option("id", policy_id);
         cv.get_table_api().close_table();
 
@@ -57,6 +58,7 @@ bool PolicyId::convert(std::istringstream& data_stream)
 
     if (data_stream >> policy_id)
     {
+        // coverity[tainted_scalar]
         data_api.failed_conversion(data_stream, std::to_string(policy_id));
         rc = false;
     }
index 2e24aa58c207dfe42cb324e5a35ca4f0e1dde9af..042961844b17e8bcd6f5b87ce0adcee4aa9864d3 100644 (file)
@@ -114,6 +114,7 @@ bool Ppm::convert(std::istringstream& data_stream)
             {
                 table_api.add_diff_option_comment("suspend-timeout", "max_suspend_time");
                 table_api.add_comment("seconds changed to milliseconds");
+                // coverity[tainted_scalar]
                 tmpval = table_api.add_option("max_suspend_time", opt * 1000);
             }
 
index 90996627c7aaf41b26ae1b423d23b6eda2fee274..a0fd406aad74207f48b70d4832361d2953db108d 100644 (file)
@@ -163,7 +163,7 @@ bool Profilers<table_name>::convert(std::istringstream& data_stream)
                 add_or_append("sort", "no_matches");
             }
             else
-                add_or_append("sort", val);
+                add_or_append("sort", std::move(val));
         }
         else
         {
index b23355ea2d9bed3bac14d8a280c45982082ec365..250320ba5c7cb2041f228cda64378db5d316a58b 100644 (file)
@@ -133,6 +133,7 @@ protected:
             if (append)
                 table_api.append_option(opt_name, val);
             else
+                // coverity[tainted_scalar]
                 table_api.add_option(opt_name, val);
             return true;
         }
@@ -175,6 +176,7 @@ protected:
         if (stream >> val)
         {
             val = !val ? -1 : ( val == -1 ? 0 : val );
+            // coverity[tainted_scalar]
             table_api.add_option(opt_name, val);
             return true;
         }
index 2214e8cfb1e4520129004f23d66f3c377abec0aa..672e9ace693f1bd500e4bc368dcd55dbfbbb9304 100644 (file)
@@ -26,12 +26,12 @@ Option::Option(std::string val, int d)
     if (val.front() == '$')
     {
         val.erase(val.begin());
-        this->value = std::string(val);
+        this->value = std::string(std::move(val));
         this->type = OptionType::VAR;
     }
     else
     {
-        this->value = std::string(val);
+        this->value = std::string(std::move(val));
         this->type = OptionType::STRING;
     }
 }
@@ -39,7 +39,7 @@ Option::Option(std::string val, int d)
 Option::Option(const std::string& n, int val, int d)
 {
     this->name = n;
-    this->value = std::to_string(val);
+    this->value = std::to_string(std::move(val));
     this->depth = d;
     this->type = OptionType::INT;
 }
@@ -60,12 +60,12 @@ Option::Option(const std::string& opt_name, std::string val, int d)
     if (val.front() == '$')
     {
         val.erase(val.begin());
-        this->value = std::string(val);
+        this->value = std::string(std::move(val));
         this->type = OptionType::VAR;
     }
     else
     {
-        this->value = std::string(val);
+        this->value = std::string(std::move(val));
         this->type = OptionType::STRING;
     }
 }
index c764a367bd16ce005ed26f267ee7418b86722c67..908b21dfb364fade964d6bc9ff68e5d98c04016f 100644 (file)
@@ -251,7 +251,7 @@ void Rule::resolve_pcre_buffer_options()
             name == "http_uri" ||
             name == "raw_data")
         {
-            curr_sticky_buffer = name;
+            curr_sticky_buffer = std::move(name);
             ++iter;
         }
         else if (name == "http_header" ||
@@ -266,7 +266,7 @@ void Rule::resolve_pcre_buffer_options()
             }
             else
             {
-                curr_sticky_buffer = name;
+                curr_sticky_buffer = std::move(name);
                 ++iter;
             }
         }
index 4b411b93a292a0b8fc5360e079d44e09bd018d58..d7ea58d3ad6420e3504d4cc121db4bffccda1834 100644 (file)
@@ -73,7 +73,7 @@ bool Variable::add_value(std::string elem)
 
     if (elem.size() <= 1)
     {
-        s = elem;
+        s = std::move(elem);
         end = "";
     }
     else
@@ -81,7 +81,7 @@ bool Variable::add_value(std::string elem)
         const std::size_t pos = elem.find('$', 1);
         if (pos == std::string::npos)
         {
-            s = elem;
+            s = std::move(elem);
             end = "";
         }
         else
@@ -121,7 +121,7 @@ bool Variable::add_value(std::string elem)
 
         VarData* vd = new VarData();
         vd->type = VarType::VARIABLE;
-        vd->data = s;
+        vd->data = std::move(s);
         vars.push_back(vd);
     }
     else if (!vars.empty() && vars.back()->type == VarType::STRING)
@@ -138,12 +138,12 @@ bool Variable::add_value(std::string elem)
         if (!vars.empty() and s != " ")
             s.insert(0, " ");
 
-        vd->data = s;
+        vd->data = std::move(s);
         vars.push_back(vd);
     }
 
     if (!end.empty())
-        return add_value(end);
+        return add_value(std::move(end));
 
     return true;
 }
index f58ab9dd5b7e3bc97dbee7e56822192f6c7663fd..0725bd0390f57aeb3cf26102aa87849533e1f030 100644 (file)
@@ -386,7 +386,7 @@ void AttributeTable::parse_entry()
 
     // add this pair to the map.
     if (!id.empty() && !value.empty())
-        attr_map[id] = value;
+        attr_map[id] = std::move(value);
 }
 
 void AttributeTable::parse_map_entries()
@@ -435,7 +435,7 @@ bool AttributeTable::convert(std::istringstream& data_stream)
             data_api.failed_conversion(data_stream, error_string);
             return false;
         }
-        file = full_file;
+        file = std::move(full_file);
     }
 
     table_api.open_table("hosts");
index 3c41bfab2bbf7489ad3dc97fe503ee824be06902..46daf11dd5a99bb3b87a44b28907697d28feec7d 100644 (file)
@@ -230,6 +230,7 @@ bool AlertCsv::convert(std::istringstream& data_stream)
     else
         limit = (limit + 1024*1024 - 1) / (1024*1024);
 
+    // coverity[tainted_scalar]
     retval = table_api.add_option("limit", limit) && retval;
     retval = table_api.add_comment("limit now in MB, converted") && retval;
     retval = table_api.add_deleted_comment("units") && retval;
index 3116a3e69e95a2e80a8d2b473a5dcee7d511f660..80542a2729228ec85a01a740d059175e1f07f3a4 100644 (file)
@@ -80,6 +80,7 @@ bool AlertFast::convert(std::istringstream& data_stream)
     else
         limit = (limit + 1024*1024 - 1) / (1024*1024);
 
+    // coverity[tainted_scalar]
     retval = table_api.add_option("limit", limit) && retval;
     retval = table_api.add_comment("limit now in MB, converted") && retval;
     retval = table_api.add_deleted_comment("units") && retval;
index b81bc3fb4df5e5b1289a03545c056dbf41425055..bf14f3d1094222e38e13793afc890ff1922d5748 100644 (file)
@@ -65,6 +65,7 @@ bool AlertFull::convert(std::istringstream& data_stream)
     else
         limit = (limit + 1024*1024 - 1) / (1024*1024);
 
+     // coverity[tainted_scalar]
     retval = table_api.add_option("limit", limit) && retval;
     retval = table_api.add_comment("limit now in MB, converted") && retval;
     retval = table_api.add_deleted_comment("units") && retval;
index fbd7efa0f62461ac1566b9ebde374951fd218766..70f11f0d8f75c1200d866466b1a89f765bfecc0e 100644 (file)
@@ -65,6 +65,7 @@ bool LogTcpDump::convert(std::istringstream& data_stream)
     else
         limit = (limit + 1024*1024 - 1) / (1024*1024);
 
+    // coverity[tainted_scalar]
     retval = table_api.add_option("limit", limit) && retval;
     retval = table_api.add_comment("limit now in MB, converted") && retval;
     retval = table_api.add_deleted_comment("units") && retval;
index 8ee36e3e53ebbfb8012a32c14ca6aa6bdae34d9d..479cdab86ee986b03df52eaf0ea81a0c5a416219 100644 (file)
@@ -124,6 +124,7 @@ bool Dcerpc::parse_int_and_add_to_all(const std::string& opt_name, std::istrings
 
     if (stream >> val)
     {
+        // coverity[tainted_scalar]
         return add_option_to_all(opt_name, val, co_only);
     }
 
index 0676e31c5b60f686e2f3f03020e7098179f72a70..a6fcc6576516073b3fef3087bed8706bea4973c5 100644 (file)
@@ -145,7 +145,7 @@ bool FtpServer::parse_alt_max_cmd(std::istringstream& stream)
             Command c;
             c.name = std::string(elem);
             c.length = len;
-            commands.push_back(c);
+            commands.push_back(std::move(c));
             updated = true;
         }
         else
@@ -203,26 +203,26 @@ bool FtpServer::parse_cmd_validity_cmd(std::istringstream& data_stream)
     if (it == commands.end())
     {
         Command c;
-        c.name = std::string(command);
-        c.format = std::string(format);
+        c.name = std::string(std::move(command));
+        c.format = std::string(std::move(format));
         c.length = command_default_len;
-        commands.push_back(c);
+        commands.push_back(std::move(c));
         updated = true;
     }
     // command exists, but format unspecified (length likely specified)
     else if (it->format.empty())
     {
-        it->format = std::string(format);
+        it->format = std::string(std::move(format));
         updated = true;
     }
     // command && format exists, but format is different. create new command
     else if (format != it->format)
     {
         Command c;
-        c.name = std::string(command);
-        c.format = std::string(format);
+        c.name = std::string(std::move(command));
+        c.format = std::string(std::move(format));
         c.length = it->length;
-        commands.push_back(c);
+        commands.push_back(std::move(c));
         updated = true;
     }
     else
@@ -742,7 +742,10 @@ bool Telnet::convert(std::istringstream& data_stream)
             int i_val;
 
             if (data_stream >> i_val)
+            {
+                 // coverity[tainted_scalar]
                 tmpval = table_api.add_option("ayt_attack_thresh", i_val);
+            }
             else
                 tmpval = false;
         }
index d103c1febe0077b30ff56394d7365c05dce04969..568796a0d73be4d8bb90c4cc81fc6728253ee19a 100644 (file)
@@ -106,9 +106,11 @@ bool HttpInspect::convert(std::istringstream& data_stream)
             std::string codemap;
             int code_page;
 
+            // coverity[tainted_scalar]
             if ( (data_stream >> codemap) &&
                 (data_stream >> code_page))
             {
+                // coverity[tainted_scalar]
                 tmpval = table_api.add_option("iis_unicode_map_file", codemap);
                 tmpval = table_api.add_option("iis_unicode_code_page", code_page) && tmpval;
             }
index c91ed2f1b4b46807bcb271e102881fa6b0d222e2..ba0ef8642ce4712ad95c8a1f65eb9dc29ff3c86c 100644 (file)
@@ -86,7 +86,7 @@ bool Smtp::parse_alt_max_cmd(std::istringstream& stream)
             Command c;
             c.name = std::string(elem);
             c.length = len;
-            commands.push_back(c);
+            commands.push_back(std::move(c));
         }
         else
         {
index 915870b9ef7c38d5575aeac56185d87b5a682c0b..dbf56762a22755e60b0176c67dda9d2df70fff2f 100644 (file)
@@ -199,7 +199,10 @@ bool StreamGlobal::convert(std::istringstream& data_stream)
         }
     }
     if ( emit_max_flows )
+    {
+        // coverity[tainted_scalar]
         table_api.add_option("max_flows", tcp_max + udp_max + icmp_max + ip_max);
+    }
 
     if ( emit_pruning_timeout )
         table_api.add_option("pruning_timeout", INT_MAX == pruning_timeout ? 30 : pruning_timeout);
index 1ce62689d7934f64b8f26266bf4089fe60cbd738..7b01fc4e8a730896b1f888234c67b0b6047256ef 100644 (file)
@@ -87,7 +87,9 @@ bool StreamTcp::parse_small_segments(std::istringstream& stream)
         return false;
 
     table_api.open_table("small_segments");
+    // coverity[tainted_scalar]
     table_api.add_option("count", consec_segs);
+    // coverity[tainted_scalar]
     table_api.add_option("maximum_size", min_bytes);
     table_api.close_table();
 
@@ -96,7 +98,10 @@ bool StreamTcp::parse_small_segments(std::istringstream& stream)
         uint16_t port;
 
         while (stream >> port)
+        {
+            // coverity[tainted_scalar]
             ignore_ports += " " + std::to_string(port);
+        }
         table_api.add_deleted_comment(ignore_ports);
     }
 
@@ -346,7 +351,10 @@ bool StreamTcp::convert(std::istringstream& data_stream)
             int val;
 
             if ( arg_stream >> val )
+            {
+                // coverity[tainted_scalar]
                 table_api.add_option("require_3whs", val);
+            }
             else
                 table_api.add_option("require_3whs", 0);
         }
@@ -361,7 +369,7 @@ bool StreamTcp::convert(std::istringstream& data_stream)
                 while (arg_stream >> tmp)
                     addr += " " + tmp;
 
-                add_to_bindings(&Binder::add_when_net, addr);
+                add_to_bindings(&Binder::add_when_net, std::move(addr));
             }
             else
             {
index abf26ead8ba5e8dd053ced08e9d49de93db9f2d4..6af6c7a61068020560896c5761d146ee54291655 100644 (file)
@@ -124,7 +124,7 @@ bool Pcre::convert(std::istringstream& data_stream)
 
         if (!sticky_buffer.empty())
         {
-            buffer = sticky_buffer;
+            buffer = std::move(sticky_buffer);
 
             if (sticky_buffer_set)
                 rule_api.bad_rule(data_stream,
index 4098e822b365716bcc87f68bc7b9fd0e7f79d246..edc16e9ecf59eca68e51a4ec1762df88116e038c 100644 (file)
@@ -49,7 +49,7 @@ bool Ttl::convert(std::istringstream& stream)
         std::string new_val;
 
         if ( arg.find('-') == std::string::npos )
-            new_val = arg;
+            new_val = std::move(arg);
         else
         {
             if ( arg.find('-') != arg.rfind('-') )
@@ -79,6 +79,7 @@ bool Ttl::convert(std::istringstream& stream)
                     arg_stream >> low;
                     arg_stream.ignore(1);
                     arg_stream >> high;
+                    // coverity[tainted_scalar]
                     new_val = std::to_string(low) + "<=>" + std::to_string(high);
                 }
             }
index 880ce79ad00a1a9748f3424c23091c020fb7b8b2..8ccb84c986d544254df9762440217ea0a52f54d3 100644 (file)
@@ -205,6 +205,8 @@ static int GetRecord(FILE* input, u2record* rec)
     /* Read in the data portion of the record */
     if (rec->length > buffer_size)
     {
+        // If we fail to allocate here, we simply error out
+        // coverity[tainted_scalar]
         tmp = (uint8_t*)malloc(rec->length * sizeof(uint8_t));
         if (tmp == nullptr)
         {
@@ -221,6 +223,7 @@ static int GetRecord(FILE* input, u2record* rec)
             buffer_size = rec->length;
         }
     }
+    // coverity[tainted_scalar]
     items_read = fread(rec->data, sizeof(uint8_t), rec->length, input);
     if (items_read != rec->length)
     {
index ab89e30ad5028027b864e4dde9f657050a4831ef..36cf531440db31e1f84f302f750aa28b0e367b8c 100644 (file)
@@ -129,6 +129,7 @@ static bool get_record(u2iterator* it, u2record* record)
 
     s_pos = ftell(it->file);
 
+    // coverity[tainted_scalar]
     tmp = (uint8_t*)realloc(record->data, record->length);
 
     if (!tmp)
@@ -556,14 +557,19 @@ static int u2dump(char* file)
     while ( get_record(it, &record) )
     {
         if ( record.type == UNIFIED2_EVENT3 and record.length == sizeof(Unified2Event) )
+        {
             event3_dump(&record);
-
+        }
         else if ( (record.type == UNIFIED2_PACKET) or (record.type == UNIFIED2_BUFFER) )
+        {
+            // coverity[tainted_scalar]
             packet_dump(&record);
-
+        }
         else if (record.type == UNIFIED2_EXTRA_DATA)
+        {
+            // coverity[tainted_scalar]
             extradata_dump(&record);
-
+        }
         // deprecated
         else if ( record.type == UNIFIED2_IDS_EVENT_VLAN and
             record.length == sizeof(Unified2IDSEvent) )