]> git.ipfire.org Git - thirdparty/snort3.git/commitdiff
Merge pull request #1436 in SNORT/snort3 from ~CWAXMAN/snort3:_offload_context_active...
authorMichael Altizer (mialtize) <mialtize@cisco.com>
Mon, 19 Nov 2018 22:16:33 +0000 (17:16 -0500)
committerMichael Altizer (mialtize) <mialtize@cisco.com>
Mon, 19 Nov 2018 22:16:33 +0000 (17:16 -0500)
Squashed commit of the following:

commit e8de483008ea240e3bc7095c11d552aee1fcd467
Author: Carter Waxman <cwaxman@cisco.com>
Date:   Mon Nov 12 11:01:38 2018 -0500

    active: added peg count for injects

commit 489561ea2fa79a178ea26cf696377741bf7895b0
Author: Carter Waxman <cwaxman@cisco.com>
Date:   Fri Oct 26 09:02:16 2018 -0400

    active, detection: active state is tied to specific packet, not thread

64 files changed:
src/actions/act_react.cc
src/actions/act_reject.cc
src/actions/actions.cc
src/codecs/ip/cd_gre.cc
src/codecs/ip/cd_ipv4.cc
src/codecs/ip/cd_ipv6.cc
src/codecs/link/cd_mpls.cc
src/codecs/misc/cd_gtp.cc
src/codecs/misc/cd_teredo.cc
src/detection/context_switcher.cc
src/detection/detection_engine.cc
src/detection/ips_context.h
src/file_api/file_api.h
src/file_api/file_cache.cc
src/file_api/file_cache.h
src/file_api/file_flows.cc
src/file_api/file_flows.h
src/file_api/file_lib.cc
src/file_api/file_lib.h
src/file_api/file_policy.cc
src/file_api/file_policy.h
src/file_api/file_segment.cc
src/file_api/file_segment.h
src/flow/flow_cache.cc
src/flow/flow_control.cc
src/framework/codec.h
src/loggers/alert_csv.cc
src/loggers/alert_fast.cc
src/loggers/alert_json.cc
src/loggers/unified2.cc
src/main/modules.cc
src/main/snort.cc
src/mime/file_mime_process.cc
src/mime/file_mime_process.h
src/network_inspectors/appid/test/log_message_mock.h
src/network_inspectors/normalize/normalize.cc
src/network_inspectors/reputation/reputation_inspect.cc
src/packet_io/active.cc
src/packet_io/active.h
src/protocols/packet.cc
src/protocols/packet.h
src/protocols/packet_manager.cc
src/service_inspectors/dce_rpc/dce_smb2.cc
src/service_inspectors/dce_rpc/dce_smb_utils.cc
src/service_inspectors/dce_rpc/smb_message.cc
src/service_inspectors/ftp_telnet/ftp_data.cc
src/service_inspectors/ftp_telnet/ftpdata_splitter.cc
src/service_inspectors/http_inspect/http_msg_body.cc
src/service_inspectors/http_inspect/http_msg_header.cc
src/service_inspectors/http_inspect/http_stream_splitter_finish.cc
src/service_inspectors/imap/imap.cc
src/service_inspectors/pop/pop.cc
src/service_inspectors/smtp/smtp.cc
src/service_inspectors/smtp/smtp_xlink2state.cc
src/stream/file/file_session.cc
src/stream/ip/ip_defrag.cc
src/stream/ip/ip_session.cc
src/stream/stream.cc
src/stream/stream.h
src/stream/tcp/tcp_normalizer.cc
src/stream/tcp/tcp_session.cc
src/stream/tcp/test/tcp_normalizer_test.cc
src/stream/udp/udp_session.cc
src/stream/user/user_session.cc

index 392c31116cf9a8f19d35cd7ebd5ce392a009722d..23b9cb01cd4e56d55c26c40f7ab306742b9d2f81 100644 (file)
@@ -133,7 +133,7 @@ void ReactAction::exec(Packet* p)
 {
     Profile profile(reactPerfStats);
 
-    if ( Active::is_reset_candidate(p) )
+    if ( p->active->is_reset_candidate(p) )
         send(p);
 }
 
@@ -142,16 +142,18 @@ void ReactAction::send(Packet* p)
     EncodeFlags df = (p->is_from_server()) ? ENC_FLAG_FWD : 0;
     EncodeFlags sent = config->buf_len;
 
+    Active* act = p->active;
+
     if ( p->packet_flags & PKT_STREAM_EST )
     {
-        Active::send_data(p, df, (uint8_t*)config->resp_buf, config->buf_len);
-        // Active::send_data() sends a FIN, so need to bump seq by 1.
+        act->send_data(p, df, (uint8_t*)config->resp_buf, config->buf_len);
+        // act->send_data() sends a FIN, so need to bump seq by 1.
         sent++;
     }
 
     EncodeFlags rf = ENC_FLAG_SEQ | (ENC_FLAG_VAL & sent);
-    Active::send_reset(p, rf);
-    Active::send_reset(p, ENC_FLAG_FWD);
+    act->send_reset(p, rf);
+    act->send_reset(p, ENC_FLAG_FWD);
 }
 
 //-------------------------------------------------------------------------
index 1ea4ef958edefca4e83c06f5c074339c5ea43728..5e58437c83af188f039146b62fd65b91ff671400 100644 (file)
@@ -98,17 +98,19 @@ void RejectAction::exec(Packet* p)
     if ( !p->ptrs.ip_api.is_ip() )
         return;
 
+    Active* act = p->active;
+
     switch ( p->type() )
     {
     case PktType::TCP:
-        if ( !Active::is_reset_candidate(p) )
+        if ( !act->is_reset_candidate(p) )
             return;
         break;
 
     case PktType::UDP:
     case PktType::ICMP:
     case PktType::IP:
-        if ( !Active::is_unreachable_candidate(p) )
+        if ( !act->is_unreachable_candidate(p) )
             return;
         break;
 
@@ -121,31 +123,32 @@ void RejectAction::exec(Packet* p)
 
 void RejectAction::send(Packet* p)
 {
+    Active* act = p->active;
     uint32_t flags = 0;
 
-    if ( Active::is_reset_candidate(p) )
+    if ( act->is_reset_candidate(p) )
         flags |= (mask & REJ_RST_BOTH);
 
-    if ( Active::is_unreachable_candidate(p) )
+    if ( act->is_unreachable_candidate(p) )
         flags |= (mask & REJ_UNR_ALL);
 
     if ( flags & REJ_RST_SRC )
-        Active::send_reset(p, 0);
+        act->send_reset(p, 0);
 
     if ( flags & REJ_RST_DST )
-        Active::send_reset(p, ENC_FLAG_FWD);
+        act->send_reset(p, ENC_FLAG_FWD);
 
     if ( flags & REJ_UNR_FWD )
         Active::send_unreach(p, snort::UnreachResponse::FWD);
 
     if ( flags & REJ_UNR_NET )
-        Active::send_unreach(p, snort::UnreachResponse::NET);
+        act->send_unreach(p, snort::UnreachResponse::NET);
 
     if ( flags & REJ_UNR_HOST )
-        Active::send_unreach(p, snort::UnreachResponse::HOST);
+        act->send_unreach(p, snort::UnreachResponse::HOST);
 
     if ( flags & REJ_UNR_PORT )
-        Active::send_unreach(p, snort::UnreachResponse::PORT);
+        act->send_unreach(p, snort::UnreachResponse::PORT);
 }
 
 //-------------------------------------------------------------------------
index 96fb7e78688771637cb727cdd3f3ac0968c331ee..b00fabdcf0cd3d14186163fc8881a4dc77bb9de0 100644 (file)
@@ -119,19 +119,19 @@ void Actions::execute(Actions::Type action, Packet* p, const OptTreeNode* otn,
         break;
 
     case Actions::DROP:
-        Active::drop_packet(p);
+        p->active->drop_packet(p);
         alert(p, otn);
         SetTags(p, otn, event_id);
         break;
 
     case Actions::BLOCK:
-        Active::block_session(p);
+        p->active->block_session(p);
         alert(p, otn);
         SetTags(p, otn, event_id);
         break;
 
     case Actions::RESET:
-        Active::reset_session(p);
+        p->active->reset_session(p);
         alert(p, otn);
         SetTags(p, otn, event_id);
         break;
@@ -146,15 +146,15 @@ void Actions::apply(Actions::Type action, Packet* p)
     switch ( action )
     {
     case Actions::DROP:
-        Active::drop_packet(p);
+        p->active->drop_packet(p);
         break;
 
     case Actions::BLOCK:
-        Active::block_session(p);
+        p->active->block_session(p);
         break;
 
     case Actions::RESET:
-        Active::reset_session(p);
+        p->active->reset_session(p);
         break;
 
     default:
index c7d04b039ca5f7d9bed4c240fb8fbc71eb70217a..c072212f029cc8448d334c538c66de22eae98ba1 100644 (file)
@@ -26,7 +26,6 @@
 #include "framework/codec.h"
 #include "log/text_log.h"
 #include "main/snort_config.h"
-#include "packet_io/active.h"
 #include "protocols/gre.h"
 
 using namespace snort;
@@ -206,7 +205,7 @@ bool GreCodec::decode(const RawData& raw, CodecData& codec, DecodeData&)
     }
 
     if (SnortConfig::tunnel_bypass_enabled(TUNNEL_GRE))
-        Active::set_tunnel_bypass();
+        codec.tunnel_bypass = true;
 
     codec.lyr_len = len;
     codec.next_prot_id = greh->proto();
index 3817fd6246c103bfed89b998b9a58190c3de8564..22ddf8bf3ffaaaf334fa4de3af33340a148a3c41 100644 (file)
 #include <random>
 
 #include "codecs/codec_module.h"
+#include "framework/codec.h"
 #include "log/log_text.h"
 #include "log/messages.h"
 #include "main/snort_config.h"
-#include "packet_io/active.h"
 #include "parser/parse_ip.h"
 #include "protocols/ip.h"
 #include "protocols/ipv4.h"
@@ -206,7 +206,7 @@ bool Ipv4Codec::decode(const RawData& raw, CodecData& codec, DecodeData& snort)
         if ( codec.codec_flags & CODEC_NON_IP_TUNNEL )
             codec.codec_flags &= ~CODEC_NON_IP_TUNNEL;
         else if ( snort::SnortConfig::tunnel_bypass_enabled(TUNNEL_4IN6) )
-            Active::set_tunnel_bypass();
+            codec.tunnel_bypass = true;
     }
     else if (snort.ip_api.is_ip4())
     {
@@ -214,7 +214,7 @@ bool Ipv4Codec::decode(const RawData& raw, CodecData& codec, DecodeData& snort)
         if ( codec.codec_flags & CODEC_NON_IP_TUNNEL )
             codec.codec_flags &= ~CODEC_NON_IP_TUNNEL;
         else if (snort::SnortConfig::tunnel_bypass_enabled(TUNNEL_4IN4))
-            Active::set_tunnel_bypass();
+            codec.tunnel_bypass = true;
     }
 
     // set the api now since this layer has been verified as valid
index d05cd5557450c31ebedba917c51cc9b0d0d533d6..785e943ddba49449bb912dd5a9cc6fa640ef2ba0 100644 (file)
@@ -28,7 +28,6 @@
 #include "framework/codec.h"
 #include "log/text_log.h"
 #include "main/snort_config.h"
-#include "packet_io/active.h"
 
 using namespace snort;
 
@@ -188,7 +187,7 @@ bool Ipv6Codec::decode(const RawData& raw, CodecData& codec, DecodeData& snort)
         if ( codec.codec_flags & CODEC_NON_IP_TUNNEL )
             codec.codec_flags &= ~CODEC_NON_IP_TUNNEL;
         else if ( SnortConfig::tunnel_bypass_enabled(TUNNEL_6IN4) )
-            Active::set_tunnel_bypass();
+            codec.tunnel_bypass = true;
     }
     else if (snort.ip_api.is_ip6())
     {
@@ -196,7 +195,7 @@ bool Ipv6Codec::decode(const RawData& raw, CodecData& codec, DecodeData& snort)
         if ( codec.codec_flags & CODEC_NON_IP_TUNNEL )
             codec.codec_flags &= ~CODEC_NON_IP_TUNNEL;
         else if (SnortConfig::tunnel_bypass_enabled(TUNNEL_6IN6))
-            Active::set_tunnel_bypass();
+            codec.tunnel_bypass = true;
     }
 
     IPV6CheckIsatap(ip6h, snort, codec); // check for isatap before overwriting the ip_api.
index 13ae1ca21b12e01cf5354b292893dcb1f4389e09..3e04f6692836880c6255b06cf08559a8488211fe 100644 (file)
@@ -26,7 +26,6 @@
 #include "flow/flow.h"
 #include "framework/codec.h"
 #include "main/snort_config.h"
-#include "packet_io/active.h"
 #include "utils/safec.h"
 
 using namespace snort;
@@ -209,7 +208,7 @@ bool MplsCodec::decode(const RawData& raw, CodecData& codec, DecodeData& snort)
     }   /* while bos not 1, peel off more labels */
 
     if (SnortConfig::tunnel_bypass_enabled(TUNNEL_MPLS))
-        Active::set_tunnel_bypass();
+        codec.tunnel_bypass = true;
 
     codec.lyr_len = (const uint8_t*)tmpMplsHdr - raw.data;
 
index 5bf7100e5cc83ea3ec0481e7d2a90aca0df66ea9..eddd1273a711c64f6c701b4badca833cfae8c952 100644 (file)
@@ -25,7 +25,6 @@
 #include "codecs/codec_module.h"
 #include "framework/codec.h"
 #include "main/snort_config.h"
-#include "packet_io/active.h"
 
 using namespace snort;
 
@@ -176,7 +175,7 @@ bool GtpCodec::decode(const RawData& raw, CodecData& codec, DecodeData& dd)
     }
 
     if ( SnortConfig::tunnel_bypass_enabled(TUNNEL_GTP) )
-        Active::set_tunnel_bypass();
+        codec.tunnel_bypass = true;
 
     codec.lyr_len = len;
     codec.proto_bits |= PROTO_BIT__GTP;
index d1d9a5820378e433dbe169247dd6409544ba6c41..ac7bc215c426af2360eb7944b291fa5d00fa491f 100644 (file)
@@ -24,7 +24,6 @@
 
 #include "framework/codec.h"
 #include "main/snort_config.h"
-#include "packet_io/active.h"
 #include "protocols/teredo.h"
 
 using namespace snort;
@@ -89,7 +88,7 @@ bool TeredoCodec::decode(const RawData& raw, CodecData& codec, DecodeData& snort
         codec.codec_flags |= CODEC_TEREDO_SEEN;  // for ipv6 codec
 
         if ( SnortConfig::tunnel_bypass_enabled(TUNNEL_TEREDO) )
-            Active::set_tunnel_bypass();
+            codec.tunnel_bypass = true;
 
         if ( (!teredo::is_teredo_port(snort.sp)) && (!teredo::is_teredo_port(snort.dp)) )
             codec.codec_flags |= CODEC_ENCAP_LAYER;
index 6c2bf9f65f4fce99f73cbef0ce4c7eaadccd7faa..756e2a3eb372361e839a309ea70923ada5fcdd60 100644 (file)
@@ -28,6 +28,7 @@
 
 #include "main/modules.h"
 #include "main/snort_debug.h"
+#include "packet_io/active.h"
 #include "utils/stats.h"
 
 #include "detect_trace.h"
@@ -81,6 +82,9 @@ void ContextSwitcher::start()
         get_packet_number(), idle.back()->get_slot(), idle.size(), busy.size());
     busy.emplace_back(idle.back());
     idle.pop_back();
+
+    busy.back()->packet->active = busy.back()->packet->active_inst;
+    busy.back()->packet->active->reset();
 }
 
 void ContextSwitcher::stop()
@@ -92,6 +96,7 @@ void ContextSwitcher::stop()
     IpsContext* c = busy.back();
     c->clear_context_data();
     idle.emplace_back(c);
+    busy.back()->packet->active = nullptr;
     busy.pop_back();
 }
 
@@ -125,6 +130,7 @@ IpsContext* ContextSwitcher::interrupt()
     assert(!idle.empty());
     trace_logf(detection, TRACE_DETECTION_ENGINE, "%" PRIu64 " cs::interrupt %u (i=%zu, b=%zu)\n",
         idle.back()->packet_number, idle.back()->get_slot(), idle.size(), busy.size());
+
     busy.emplace_back(idle.back());
     idle.pop_back();
     return busy.back();
@@ -139,6 +145,7 @@ IpsContext* ContextSwitcher::complete()
         c->packet_number, busy.back()->get_slot(), idle.size(), busy.size());
 
     c->clear_context_data();
+
     idle.emplace_back(c);
     busy.pop_back();
     return busy.empty() ? nullptr : busy.back();
@@ -170,7 +177,9 @@ void ContextSwitcher::resume(unsigned slot)
 
 IpsContext* ContextSwitcher::get_context() const
 {
-    assert(!busy.empty());
+    if ( busy.empty() )
+        return nullptr;
+
     return busy.back();
 }
 
index 35a025f614902bfc6513db59d5a30fb620e4b5bb..814e777ac332c9defcb0e59a34528b1bd5e66033 100644 (file)
@@ -111,6 +111,8 @@ Packet* DetectionEngine::get_encode_packet()
 // however, rebuild is always in the next context, not current.
 Packet* DetectionEngine::set_next_packet(Packet* parent)
 {
+    static THREAD_LOCAL Active shutdown_active;
+
     IpsContext* c = Snort::get_switcher()->get_next();
     if ( parent )
     {
@@ -126,6 +128,21 @@ Packet* DetectionEngine::set_next_packet(Packet* parent)
     p->data = c->buf;
     p->pkt = c->buf;
 
+    // normal rebuild
+    if ( parent )
+        p->active = parent->active;
+    
+    // processing but parent is already gone (flow cache flush etc..)
+    else if ( Snort::get_switcher()->get_context() )
+        p->active = get_current_packet()->active;
+    
+    // shutdown, so use a dummy so nullchecking is needed everywhere
+    else
+    {
+        p->active = &shutdown_active;
+        shutdown_active.reset();
+    }
+
     p->reset();
     return p;
 }
@@ -147,7 +164,9 @@ void DetectionEngine::finish_inspect(Packet* p, bool inspected)
 {
     log_events(p);
 
-    Active::apply_delayed_action(p);
+    if ( p->active )
+        p->active->apply_delayed_action(p);
+
     p->context->post_detection();
 
     // clear closed sessions here after inspection since non-stream
@@ -428,7 +447,7 @@ void DetectionEngine::inspect(Packet* p)
             if ( SnortConfig::inline_mode() and
                 SnortConfig::checksum_drop(p->ptrs.decode_flags & DECODE_ERR_CKSUM_ALL) )
             {
-                Active::drop_packet(p);
+                p->active->drop_packet(p);
             }
         }
         else
index f898598fe054fe4c5b76e05258db7add393851c8..97a4bcbf80543536d53fe09de44ff0cb41a964a1 100644 (file)
@@ -94,6 +94,8 @@ public:
     void post_detection();
 
 public:
+    std::vector<Replacement> rpl;
+
     Packet* packet;
     Packet* encode_packet;
     DAQ_PktHdr_t* pkth;
@@ -112,8 +114,6 @@ public:
     ActiveRules active_rules;
     bool check_tags;
 
-    std::vector<Replacement> rpl;
-
     static const unsigned buf_size = Codec::PKT_MAX;
     // Only 5 inspectors currently use the ips context data.
     // FIXIT-L This limit should to be updated if any more inspectors/modules use it.
index e74cb0f06053b036efcfe49098675b566a951425..3b0439faabf958b8ba5a61f1de4aad19305e0d3e 100644 (file)
@@ -135,11 +135,11 @@ public:
     virtual void policy_check(Flow*, FileInfo* ) { }
 
     // This is called after file type is known
-    virtual FileVerdict type_lookup(Flow*, FileInfo*)
+    virtual FileVerdict type_lookup(Packet*, FileInfo*)
     { return FILE_VERDICT_UNKNOWN; }
 
     // This is called after file signature is complete
-    virtual FileVerdict signature_lookup(Flow*, FileInfo*)
+    virtual FileVerdict signature_lookup(Packet*, FileInfo*)
     { return FILE_VERDICT_UNKNOWN; }
 
     virtual void log_file_action(Flow*, FileInfo*, FileAction) { }
index 4880b511aaf55ec262ca2bbeaa0c0d0afb0a6f2e..583207d331f66f7ad72be32108129381aab39181 100644 (file)
@@ -193,18 +193,19 @@ FileContext* FileCache::get_file(Flow* flow, uint64_t file_id, bool to_create)
     return get_file(flow, file_id, to_create, lookup_timeout);
 }
 
-FileVerdict FileCache::check_verdict(Flow* flow, FileInfo* file,
+FileVerdict FileCache::check_verdict(Packet* p, FileInfo* file,
     FilePolicyBase* policy)
 {
     assert(file);
+    Flow* flow = p->flow;
 
-    FileVerdict verdict = policy->type_lookup(flow, file);
+    FileVerdict verdict = policy->type_lookup(p, file);
 
     if ( file->get_file_sig_sha256() and
         ((verdict == FILE_VERDICT_UNKNOWN) ||
         (verdict == FILE_VERDICT_STOP_CAPTURE)))
     {
-        verdict = policy->signature_lookup(flow, file);
+        verdict = policy->signature_lookup(p, file);
     }
 
     if ((verdict == FILE_VERDICT_UNKNOWN) ||
@@ -232,11 +233,13 @@ int FileCache::store_verdict(Flow* flow, FileInfo* file, int64_t timeout)
     return 0;
 }
 
-bool FileCache::apply_verdict(Flow* flow, FileInfo* file, FileVerdict verdict,
+bool FileCache::apply_verdict(Packet* p, FileInfo* file, FileVerdict verdict,
     bool resume, FilePolicyBase* policy)
 {
-    file->verdict = verdict;
+    Flow* flow = p->flow;
+    Active* act = p->active;
 
+    file->verdict = verdict;
     switch (verdict)
     {
 
@@ -248,15 +251,15 @@ bool FileCache::apply_verdict(Flow* flow, FileInfo* file, FileVerdict verdict,
         return false;
     case FILE_VERDICT_BLOCK:
          // can't block session inside a session
-         Active::set_delayed_action(Active::ACT_BLOCK, true);
+         act->set_delayed_action(Active::ACT_BLOCK, true);
          break;
 
     case FILE_VERDICT_REJECT:
         // can't reset session inside a session
-        Active::set_delayed_action(Active::ACT_RESET, true);
+        act->set_delayed_action(Active::ACT_RESET, true);
         break;
     case FILE_VERDICT_PENDING:
-        Active::set_delayed_action(Active::ACT_DROP, true);
+        act->set_delayed_action(Active::ACT_DROP, true);
         if (resume)
             policy->log_file_action(flow, file, FILE_RESUME_BLOCK);
         else
@@ -279,9 +282,10 @@ bool FileCache::apply_verdict(Flow* flow, FileInfo* file, FileVerdict verdict,
 
 }
 
-FileVerdict FileCache::cached_verdict_lookup(Flow* flow, FileInfo* file,
+FileVerdict FileCache::cached_verdict_lookup(Packet* p, FileInfo* file,
     FilePolicyBase* policy)
 {
+    Flow* flow = p->flow;
     FileVerdict verdict = FILE_VERDICT_UNKNOWN;
 
     assert(file);
@@ -294,8 +298,8 @@ FileVerdict FileCache::cached_verdict_lookup(Flow* flow, FileInfo* file,
     if (file_found)
     {
         /*Query the file policy in case verdict has been changed*/
-        verdict = check_verdict(flow, file_found, policy);
-        apply_verdict(flow, file_found, verdict, true, policy);
+        verdict = check_verdict(p, file_found, policy);
+        apply_verdict(p, file_found, verdict, true, policy);
     }
 
     return verdict;
index a7cbc7b3f9262127421a324f3713dbde6a18bec8..f9942ede2fa8f50533642eea7defc60ed39c83b2 100644 (file)
@@ -62,16 +62,16 @@ PADDING_GUARD_END
     void set_max_files(int64_t);
 
     snort::FileContext* get_file(snort::Flow*, uint64_t file_id, bool to_create);
-    FileVerdict cached_verdict_lookup(snort::Flow*, snort::FileInfo*,
+    FileVerdict cached_verdict_lookup(snort::Packet*, snort::FileInfo*,
         snort::FilePolicyBase*);
-    bool apply_verdict(snort::Flow*, snort::FileInfo*, FileVerdict, bool resume,
+    bool apply_verdict(snort::Packet*, snort::FileInfo*, FileVerdict, bool resume,
         snort::FilePolicyBase*);
 
 private:
     snort::FileContext* add(const FileHashKey&, int64_t timeout);
     snort::FileContext* find(const FileHashKey&, int64_t);
     snort::FileContext* get_file(snort::Flow*, uint64_t file_id, bool to_create, int64_t timeout);
-    FileVerdict check_verdict(snort::Flow*, snort::FileInfo*, snort::FilePolicyBase*);
+    FileVerdict check_verdict(snort::Packet*, snort::FileInfo*, snort::FilePolicyBase*);
     int store_verdict(snort::Flow*, snort::FileInfo*, int64_t timeout);
 
     /* The hash table of expected files */
index ef7817ac249118eb904ca0786f189ef6552dd399..a380e15ce3b2ffd644ac5eba313789070aef8567 100644 (file)
@@ -63,7 +63,7 @@ namespace snort
     }
 }
 
-void FileFlows::handle_retransmit (Packet*)
+void FileFlows::handle_retransmit(Packet* p)
 {
     if (file_policy == nullptr)
         return;
@@ -72,10 +72,10 @@ void FileFlows::handle_retransmit (Packet*)
     if ((file == nullptr) or (file->verdict != FILE_VERDICT_PENDING))
         return;
 
-    FileVerdict verdict = file_policy->signature_lookup(flow, file);
+    FileVerdict verdict = file_policy->signature_lookup(p, file);
     FileCache* file_cache = FileService::get_file_cache();
     if (file_cache)
-        file_cache->apply_verdict(flow, file, verdict, false, file_policy);
+        file_cache->apply_verdict(p, file, verdict, false, file_policy);
     file->log_file_event(flow, file_policy);
 }
 
@@ -183,7 +183,7 @@ FileContext* FileFlows::get_file_context(uint64_t file_id, bool to_create)
  *    true: continue processing/log/block this file
  *    false: ignore this file
  */
-bool FileFlows::file_process(uint64_t file_id, const uint8_t* file_data,
+bool FileFlows::file_process(Packet* p, uint64_t file_id, const uint8_t* file_data,
     int data_size, uint64_t offset, FileDirection dir)
 {
     int64_t file_depth = FileService::get_max_file_depth();
@@ -214,11 +214,11 @@ bool FileFlows::file_process(uint64_t file_id, const uint8_t* file_data,
         {
             /* Just check file type and signature */
             FilePosition position = SNORT_FILE_FULL;
-            return context->process(flow, file_data, data_size, position, file_policy);
+            return context->process(p, file_data, data_size, position, file_policy);
         }
     }
 
-    return context->process(flow, file_data, data_size, offset, file_policy);
+    return context->process(p, file_data, data_size, offset, file_policy);
 }
 
 /*
@@ -226,7 +226,7 @@ bool FileFlows::file_process(uint64_t file_id, const uint8_t* file_data,
  *    true: continue processing/log/block this file
  *    false: ignore this file
  */
-bool FileFlows::file_process(const uint8_t* file_data, int data_size,
+bool FileFlows::file_process(Packet* p, const uint8_t* file_data, int data_size,
     FilePosition position, bool upload, size_t file_index)
 {
     FileContext* context;
@@ -243,7 +243,7 @@ bool FileFlows::file_process(const uint8_t* file_data, int data_size,
     set_current_file_context(context);
 
     context->set_signature_state(gen_signature);
-    return context->process(flow, file_data, data_size, position, file_policy);
+    return context->process(p, file_data, data_size, position, file_policy);
 }
 
 void FileFlows::set_file_name(const uint8_t* fname, uint32_t name_size)
index 4f794f02c526feedd73aee1621fa6228f4b84aff..fa3ba1214384f95e7e6f9aa69a96e3c1745cd772 100644 (file)
@@ -80,11 +80,11 @@ public:
     void add_pending_file(uint64_t file_id);
 
     // This is used when there is only one file per session
-    bool file_process(const uint8_t* file_data, int data_size, FilePosition,
+    bool file_process(Packet* p, const uint8_t* file_data, int data_size, FilePosition,
         bool upload, size_t file_index = 0);
 
     // This is used for each file context. Support multiple files per session
-    bool file_process(uint64_t file_id, const uint8_t* file_data,
+    bool file_process(Packet* p, uint64_t file_id, const uint8_t* file_data,
         int data_size, uint64_t offset, FileDirection);
 
     static unsigned file_flow_data_id;
index 9e0f1f085115241061bc4c00198e222ee32ae952..b31c327bf681fa64213c5fef7f14716e4f6fe8c3 100644 (file)
@@ -38,6 +38,7 @@
 #include "framework/data_bus.h"
 #include "main/snort_config.h"
 #include "managers/inspector_manager.h"
+#include "protocols/packet.h"
 #include "utils/util.h"
 #include "utils/util_utf.h"
 
@@ -314,29 +315,33 @@ void FileContext::log_file_event(Flow* flow, FilePolicyBase* policy)
     }
 }
 
-FileVerdict FileContext::file_signature_lookup(Flow* flow)
+FileVerdict FileContext::file_signature_lookup(Packet* p)
 {
+    Flow* flow = p->flow;
+
     if (get_file_sig_sha256())
     {
         FilePolicyBase* policy = FileFlows::get_file_policy(flow);
 
         if (policy)
-            return policy->signature_lookup(flow, this);
+            return policy->signature_lookup(p, this);
     }
 
     return FILE_VERDICT_UNKNOWN;
 }
 
-void FileContext::finish_signature_lookup(Flow* flow, bool final_lookup, FilePolicyBase* policy)
+void FileContext::finish_signature_lookup(Packet* p, bool final_lookup, FilePolicyBase* policy)
 {
+    Flow* flow = p->flow;
+
     if (get_file_sig_sha256())
     {
-        verdict = policy->signature_lookup(flow, this);
+        verdict = policy->signature_lookup(p, this);
         if ( verdict != FILE_VERDICT_UNKNOWN || final_lookup )
         {
             FileCache* file_cache = FileService::get_file_cache();
             if (file_cache)
-                file_cache->apply_verdict(flow, this, verdict, false, policy);
+                file_cache->apply_verdict(p, this, verdict, false, policy);
             log_file_event(flow, policy);
             config_file_signature(false);
             file_stats->signatures_processed[get_file_type()][get_file_direction()]++;
@@ -379,9 +384,10 @@ void FileContext::check_policy(Flow* flow, FileDirection dir, FilePolicyBase* po
  *    true: continue processing/log/block this file
  *    false: ignore this file
  */
-bool FileContext::process(Flow* flow, const uint8_t* file_data, int data_size,
+bool FileContext::process(Packet* p, const uint8_t* file_data, int data_size,
     FilePosition position, FilePolicyBase* policy)
 {
+    Flow* flow = p->flow;
 
     if ( config->trace_stream )
     {
@@ -397,7 +403,7 @@ bool FileContext::process(Flow* flow, const uint8_t* file_data, int data_size,
         return false;
     }
 
-    if ((FileService::get_file_cache()->cached_verdict_lookup(flow, this,
+    if ((FileService::get_file_cache()->cached_verdict_lookup(p, this,
         policy) != FILE_VERDICT_UNKNOWN))
         return true;
 
@@ -421,12 +427,12 @@ bool FileContext::process(Flow* flow, const uint8_t* file_data, int data_size,
             config_file_type(false);
             file_stats->files_processed[get_file_type()][get_file_direction()]++;
             //Check file type based on file policy
-            FileVerdict v = policy->type_lookup(flow, this);
+            FileVerdict v = policy->type_lookup(p, this);
             if ( v != FILE_VERDICT_UNKNOWN )
             {
                 FileCache* file_cache = FileService::get_file_cache();
                 if (file_cache)
-                    file_cache->apply_verdict(flow, this, v, false, policy);
+                    file_cache->apply_verdict(p, this, v, false, policy);
             }
 
             log_file_event(flow, policy);
@@ -453,7 +459,7 @@ bool FileContext::process(Flow* flow, const uint8_t* file_data, int data_size,
             process_file_capture(file_data, data_size, position);
         }
 
-        finish_signature_lookup(flow, ( file_state.sig_state != FILE_SIG_FLUSH ), policy);
+        finish_signature_lookup(p, ( file_state.sig_state != FILE_SIG_FLUSH ), policy);
     }
     else
     {
@@ -463,12 +469,12 @@ bool FileContext::process(Flow* flow, const uint8_t* file_data, int data_size,
     return true;
 }
 
-bool FileContext::process(Flow* flow, const uint8_t* file_data, int data_size,
+bool FileContext::process(Packet* p, const uint8_t* file_data, int data_size,
     uint64_t offset, FilePolicyBase* policy)
 {
     if (!file_segments)
         file_segments = new FileSegments(this);
-    return file_segments->process(flow, file_data, data_size, offset, policy);
+    return file_segments->process(p, file_data, data_size, offset, policy);
 }
 
 /*
index e6016035ecee1197abe8957bd6906e76fb5b5f0a..4517ccded56dd2653dfd944e4fb5d94645e1331a 100644 (file)
@@ -110,15 +110,15 @@ public:
     // Return:
     //    true: continue processing/log/block this file
     //    false: ignore this file
-    bool process(Flow*, const uint8_t* file_data, int data_size, FilePosition, FilePolicyBase*);
-    bool process(Flow*, const uint8_t* file_data, int data_size, uint64_t offset, FilePolicyBase*);
+    bool process(Packet*, const uint8_t* file_data, int data_size, FilePosition, FilePolicyBase*);
+    bool process(Packet*, const uint8_t* file_data, int data_size, uint64_t offset, FilePolicyBase*);
     void process_file_type(const uint8_t* file_data, int data_size, FilePosition);
     void process_file_signature_sha256(const uint8_t* file_data, int data_size, FilePosition);
     void update_file_size(int data_size, FilePosition position);
     void stop_file_capture();
     FileCaptureState process_file_capture(const uint8_t* file_data, int data_size, FilePosition);
     void log_file_event(Flow*, FilePolicyBase*);
-    FileVerdict file_signature_lookup(Flow*);
+    FileVerdict file_signature_lookup(Packet*);
 
     void set_signature_state(bool gen_sig);
 
@@ -140,7 +140,7 @@ private:
     FileConfig*  config;
 
     inline void finalize_file_type();
-    inline void finish_signature_lookup(Flow*, bool, FilePolicyBase*);
+    inline void finish_signature_lookup(Packet*, bool, FilePolicyBase*);
 };
 }
 #endif
index e1b6720228b2b390dd4e958ef4baed3cd0c21a26..888cd57b078bc8b3f83bc9ae438f2208857a20a0 100644 (file)
@@ -159,7 +159,7 @@ void FilePolicy::policy_check(Flow*, FileInfo* file)
     file->config_file_capture(capture_enabled);
 }
 
-FileVerdict FilePolicy::type_lookup(Flow*, FileInfo* file)
+FileVerdict FilePolicy::type_lookup(Packet*, FileInfo* file)
 {
     FileRule rule = match_file_rule(nullptr, file);
     file->config_file_signature(rule.use.signature_enabled);
@@ -167,7 +167,7 @@ FileVerdict FilePolicy::type_lookup(Flow*, FileInfo* file)
     return rule.use.verdict;
 }
 
-FileVerdict FilePolicy::signature_lookup(Flow*, FileInfo* file)
+FileVerdict FilePolicy::signature_lookup(Packet*, FileInfo* file)
 {
     FileRule& rule = match_file_rule(nullptr, file);
 
index 71ace2bb628791f3834ff671398bf5e26ad5585d..de91f2527309e71e43300e49418f052a88d799af 100644 (file)
@@ -64,10 +64,10 @@ public:
     void policy_check(snort::Flow*, snort::FileInfo*) override;
 
     // This is called after file type is known
-    FileVerdict type_lookup(snort::Flow*, snort::FileInfo*) override;
+    FileVerdict type_lookup(snort::Packet*, snort::FileInfo*) override;
 
     // This is called after file signature is complete
-    FileVerdict signature_lookup(snort::Flow*, snort::FileInfo*) override;
+    FileVerdict signature_lookup(snort::Packet*, snort::FileInfo*) override;
 
     void insert_file_rule(FileRule&);
     void set_file_type(bool enabled);
index 027189f2e0236b4b25deb3d1fb587fce51247ede..1af9b31a1cc9f953eb82c760527af22b6254a9b5 100644 (file)
@@ -150,22 +150,22 @@ FilePosition FileSegments::get_file_position(uint64_t data_size, uint64_t file_s
     return SNORT_FILE_MIDDLE;
 }
 
-int FileSegments::process_one(snort::Flow* flow, const uint8_t* file_data, int data_size,
+int FileSegments::process_one(snort::Packet* p, const uint8_t* file_data, int data_size,
     snort::FilePolicyBase* policy)
 {
     FilePosition position = get_file_position(data_size, context->get_file_size());
 
-    return context->process(flow, file_data, data_size, position, policy);
+    return context->process(p, file_data, data_size, position, policy);
 }
 
-int FileSegments::process_all(snort::Flow* flow, snort::FilePolicyBase* policy)
+int FileSegments::process_all(snort::Packet* p, snort::FilePolicyBase* policy)
 {
     int ret = 1;
 
     FileSegment* current_segment = head;
     while (current_segment && (current_offset == current_segment->offset))
     {
-        ret = process_one(flow, (const uint8_t*)current_segment->data->data(),
+        ret = process_one(p, (const uint8_t*)current_segment->data->data(),
             current_segment->data->size(), policy);
 
         if (!ret)
@@ -190,7 +190,7 @@ int FileSegments::process_all(snort::Flow* flow, snort::FilePolicyBase* policy)
  *    1: continue processing/log/block this file
  *    0: ignore this file
  */
-int FileSegments::process(snort::Flow* flow, const uint8_t* file_data, uint64_t data_size,
+int FileSegments::process(snort::Packet* p, const uint8_t* file_data, uint64_t data_size,
     uint64_t offset, snort::FilePolicyBase* policy)
 {
     int ret = 0;
@@ -203,7 +203,7 @@ int FileSegments::process(snort::Flow* flow, const uint8_t* file_data, uint64_t
     // Walk through the segments that can be flushed
     if (current_offset == offset)
     {
-        ret =  process_one(flow, file_data, data_size, policy);
+        ret =  process_one(p, file_data, data_size, policy);
         current_offset += data_size;
         if (!ret)
         {
@@ -211,7 +211,7 @@ int FileSegments::process(snort::Flow* flow, const uint8_t* file_data, uint64_t
             return 0;
         }
 
-        ret = process_all(flow, policy);
+        ret = process_all(p, policy);
     }
     else if ((current_offset < context->get_file_size()) && (current_offset < offset))
     {
index c06ba4e919397bd66251e50b7a29c016232bfd0b..978125b5d5b305d6ffdba71533e7c469e5d9dc6c 100644 (file)
@@ -54,7 +54,7 @@ public:
 
     // Process file segments with current_offset specified. If file segment is out of order,
     // it will be put into the file segments queue.
-    int process(snort::Flow*, const uint8_t* file_data, uint64_t data_size, uint64_t offset,
+    int process(snort::Packet*, const uint8_t* file_data, uint64_t data_size, uint64_t offset,
         snort::FilePolicyBase*);
 
 private:
@@ -64,8 +64,8 @@ private:
 
     void add(const uint8_t* file_data, uint64_t data_size, uint64_t offset);
     FilePosition get_file_position(uint64_t data_size, uint64_t file_size);
-    int process_one(snort::Flow*, const uint8_t* file_data, int data_size, snort::FilePolicyBase*);
-    int process_all(snort::Flow*, snort::FilePolicyBase*);
+    int process_one(snort::Packet*, const uint8_t* file_data, int data_size, snort::FilePolicyBase*);
+    int process_all(snort::Packet*, snort::FilePolicyBase*);
 };
 
 #endif
index 99860506ce8a89a1e183c5addf77b9cdce457fd1..a3ec402238acc89483690850de4bf15595db1f3b 100644 (file)
@@ -294,7 +294,7 @@ bool FlowCache::prune_one(PruneReason reason, bool do_cleanup)
 
 unsigned FlowCache::timeout(unsigned num_flows, time_t thetime)
 {
-    // FIXIT-H should Active be suspended here too?
+    ActiveSuspendContext act_susp;
     unsigned retired = 0;
 
     auto flow = static_cast<Flow*>(hash_table->current());
index 868f2a36db9213f6320406c812bb3d9e27bb81e5..0cd821e85250264545ff863d84c9a5c9b3fa3587 100644 (file)
@@ -138,7 +138,7 @@ void FlowControl::timeout_flows(time_t cur_time)
     if ( types.empty() )
         return;
 
-    Active::suspend();
+    ActiveSuspendContext act_susp;
     FlowCache* fc = get_cache(types[next]);
 
     if ( ++next >= types.size() )
@@ -146,8 +146,6 @@ void FlowControl::timeout_flows(time_t cur_time)
 
     if ( fc )
         fc->timeout(1, cur_time);
-
-    Active::resume();
 }
 
 void FlowControl::preemptive_cleanup()
@@ -452,20 +450,20 @@ unsigned FlowControl::process(Flow* flow, Packet* p)
 
     case Flow::FlowState::BLOCK:
         if ( news )
-            Stream::drop_traffic(flow, SSN_DIR_BOTH);
+            Stream::drop_traffic(p, SSN_DIR_BOTH);
         else
-            Active::block_again();
+            p->active->block_again();
 
         DetectionEngine::disable_all(p);
         break;
 
     case Flow::FlowState::RESET:
         if ( news )
-            Stream::drop_traffic(flow, SSN_DIR_BOTH);
+            Stream::drop_traffic(p, SSN_DIR_BOTH);
         else
-            Active::reset_again();
+            p->active->reset_again();
 
-        Stream::blocked_flow(flow, p);
+        Stream::blocked_flow(p);
         DetectionEngine::disable_all(p);
         break;
     }
index 4a89ace1f8114ce3f05bb435dc2e81ab77eb752e..c8dd4e3879e918283e0c8367ca49f0203de5b072 100644 (file)
@@ -56,7 +56,6 @@ struct ICMPHdr;
 
 class Flow;
 struct Layer;
-struct Packet;
 
 // Used by root codecs to add their DLT to their HELP string
 #define ADD_DLT(help, x) help " (DLT " STRINGIFY_MX(x) ")"
@@ -135,9 +134,10 @@ struct CodecData
     uint8_t ip6_extension_count; /* initialized in cd_ipv6.cc */
     uint8_t curr_ip6_extension;  /* initialized in cd_ipv6.cc */
     IpProtocol ip6_csum_proto;      /* initialized in cd_ipv6.cc.  Used for IPv6 checksums */
+    bool tunnel_bypass;
 
     CodecData(ProtocolId init_prot) : next_prot_id(init_prot), lyr_len(0),
-        invalid_bytes(0), proto_bits(0), codec_flags(0), ip_layer_cnt(0)
+        invalid_bytes(0), proto_bits(0), codec_flags(0), ip_layer_cnt(0), tunnel_bypass(false)
     { }
 
     bool inline is_cooked() const
@@ -368,7 +368,7 @@ private:
 //-------------------------------------------------------------------------
 
 // this is the current version of the api
-#define CDAPI_VERSION ((BASE_API_VERSION << 16) | 0)
+#define CDAPI_VERSION ((BASE_API_VERSION << 16) | 1)
 
 typedef Codec* (* CdNewFunc)(Module*);
 typedef void (* CdDelFunc)(Codec*);
index dca96e18f4541eb25131ed9a55741acbee0ceffa..f3a3d3970c2ca6d533d368d02d3adbcdeb9dad10 100644 (file)
@@ -69,9 +69,9 @@ struct Args
     const Event& event;
 };
 
-static void ff_action(Args&)
+static void ff_action(Args& a)
 {
-    TextLog_Puts(csv_log, Active::get_action_string());
+    TextLog_Puts(csv_log, a.pkt->active->get_action_string());
 }
 
 static void ff_class(Args& a)
index 2f44b76b66fe44383d2f78dd90b4a96351bc91da..1990bd7b8973e26cf87592471a8826ab5c09628f 100644 (file)
@@ -214,8 +214,8 @@ void FastLogger::alert(Packet* p, const char* msg, const Event& event)
 {
     LogTimeStamp(fast_log, p);
 
-    if ( Active::get_action() > Active::ACT_PASS )
-        TextLog_Print(fast_log, " [%s]", Active::get_action_string());
+    if ( p->active->packet_was_dropped() )
+        TextLog_Print(fast_log, " [%s]", p->active->get_action_string());
 
     TextLog_Puts(fast_log, " [**] ");
 
index 20b15a50abea81886f056302bcc695785dad6d70..073cadb9a6c7db1b6a690ad4caa04c051b23f39a 100644 (file)
@@ -82,7 +82,7 @@ static void print_label(Args& a, const char* label)
 static bool ff_action(Args& a)
 {
     print_label(a, "action");
-    TextLog_Quote(json_log, Active::get_action_string());
+    TextLog_Quote(json_log, a.pkt->active->get_action_string());
     return true;
 }
 
index d521490affd242c9c215bd3109d66152f025e517..74b950afa2b1247f42a90078bea0b99e8bf4313b 100644 (file)
@@ -221,10 +221,10 @@ static void alert_event(Packet* p, const char*, Unified2Config* config, const Ev
         if ( app_name )
             memcpy_s(u2_event.app_name, sizeof(u2_event.app_name),
                 app_name, strlen(app_name) + 1);
-    }
 
-    u2_event.snort_status = Active::get_status();
-    u2_event.snort_action = Active::get_action();
+        u2_event.snort_status = p->active->get_status();
+        u2_event.snort_action = p->active->get_action();
+    }
 
     Serial_Unified2_Header hdr;
     uint32_t write_len = sizeof(hdr) + sizeof(u2_event);
@@ -599,9 +599,9 @@ static int s_blocked_flag[] =
     U2_BLOCKED_FLAG_BLOCK,
 };
 
-static int GetU2Flags(const Packet*, uint8_t* pimpact)
+static int GetU2Flags(const Packet* p, uint8_t* pimpact)
 {
-    Active::ActiveStatus dispos = Active::get_status();
+    Active::ActiveStatus dispos = p->active->get_status();
 
     if ( dispos > Active::AST_ALLOW )
         *pimpact = U2_FLAG_BLOCKED;
index 3cbb7bd1210f134bf4922266c9975813f1f76825..2537005106112605975e5fcec63e03c40f2b597e 100755 (executable)
@@ -40,6 +40,7 @@
 #include "managers/module_manager.h"
 #include "managers/plugin_manager.h"
 #include "memory/memory_module.h"
+#include "packet_io/active.h"
 #include "packet_io/sfdaq_module.h"
 #include "packet_tracer/packet_tracer_module.h"
 #include "parser/config_file.h"
@@ -869,12 +870,24 @@ static const Parameter active_params[] =
 #define active_help \
     "configure responses"
 
+static PegInfo active_pegs[]
+{
+    { CountType::SUM, "injects", "total crafted packets injected" },
+    { CountType::END, nullptr, nullptr }
+};
+
 class ActiveModule : public Module
 {
 public:
     ActiveModule() : Module("active", active_help, active_params) { }
     bool set(const char*, Value&, SnortConfig*) override;
 
+    const PegInfo* get_pegs() const override
+    { return active_pegs; }
+
+    PegCount* get_counts() const override
+    { return (PegCount*) &active_counts; }
+
     Usage get_usage() const override
     { return GLOBAL; }
 };
index b845e11298000e094eb1fd1fa5dcfd4b3b07c8a6..31445bb4dd6f50b0570d2e5782f461e8c7806d28 100644 (file)
@@ -352,6 +352,8 @@ void Snort::init(int argc, char** argv)
         LogMessage("Snort BPF option: %s\n", SnortConfig::get_conf()->bpf_filter.c_str());
 
     parser_term(SnortConfig::get_conf());
+
+    Active::init(sc);
 }
 
 // this function should only include initialization that must be done as a
@@ -809,7 +811,7 @@ void Snort::thread_init_unprivileged()
 
     // this depends on instantiated daq capabilities
     // so it is done here instead of init()
-    Active::init(SnortConfig::get_conf());
+    Active::thread_init(SnortConfig::get_conf());
 
     InitTag();
     EventTrace_Init();
@@ -870,7 +872,7 @@ void Snort::thread_term()
     PacketTracer::thread_term();
     PacketManager::thread_term();
 
-    Active::term();
+    Active::thread_term();
     delete s_switcher;
     delete[] s_data;
 }
@@ -913,23 +915,24 @@ DAQ_Verdict Snort::process_packet(
             DetectionEngine::onload(p->flow);
     }
 
+    Active* act = p->active;
     // process flow verdicts here
-    if ( Active::packet_retry_requested() )
+    if ( act->packet_retry_requested() )
     {
         return DAQ_VERDICT_RETRY;
     }
-    else if ( Active::session_was_blocked() )
+    else if ( act->session_was_blocked() )
     {
-        if ( !Active::can_block() )
+        if ( !act->can_block() )
             return DAQ_VERDICT_PASS;
 
-        if ( Active::get_tunnel_bypass() )
+        if ( act->get_tunnel_bypass() )
         {
             aux_counts.internal_blacklist++;
             return DAQ_VERDICT_PASS;
         }
 
-        if ( SnortConfig::inline_mode() || Active::packet_force_dropped() )
+        if ( SnortConfig::inline_mode() or act->packet_force_dropped() )
             return DAQ_VERDICT_BLACKLIST;
         else
             return DAQ_VERDICT_IGNORE;
@@ -941,7 +944,7 @@ DAQ_Verdict Snort::process_packet(
 // process (wire-only) packet verdicts here
 static DAQ_Verdict update_verdict(Packet* p, DAQ_Verdict verdict, int& inject)
 {
-    if ( Active::packet_was_dropped() and Active::can_block() )
+    if ( p->active->packet_was_dropped() and p->active->can_block() )
     {
         if ( verdict == DAQ_VERDICT_PASS )
             verdict = DAQ_VERDICT_BLOCK;
@@ -966,7 +969,7 @@ static DAQ_Verdict update_verdict(Packet* p, DAQ_Verdict verdict, int& inject)
     else if ( (p->packet_flags & PKT_IGNORE) ||
         (p->flow && p->flow->get_ignore_direction( ) == SSN_DIR_BOTH) )
     {
-        if ( !Active::get_tunnel_bypass() )
+        if ( !p->active->get_tunnel_bypass() )
         {
             verdict = DAQ_VERDICT_WHITELIST;
         }
@@ -1028,7 +1031,6 @@ DAQ_Verdict Snort::packet_callback(
 
     HighAvailabilityManager::process_update(s_packet->flow, pkthdr);
 
-    Active::reset();
     Stream::timeout_flows(pkthdr->ts.tv_sec);
     HighAvailabilityManager::process_receive();
 
index 6eec1b185f297a0be95fbd4284d34b73b5bf0fb5..2157e2741c4eeac6947196d2bb8ca9651ebf7a9f 100644 (file)
@@ -481,8 +481,9 @@ void MimeSession::reset_mime_state()
 }
 
 const uint8_t* MimeSession::process_mime_data_paf(
-    Flow* flow, const uint8_t* start, const uint8_t* end, bool upload, FilePosition position)
+    Packet* p, const uint8_t* start, const uint8_t* end, bool upload, FilePosition position)
 {
+    Flow* flow = p->flow;
     bool done_data = is_end_of_data(flow);
 
     /* if we've just entered the data state, check for a dot + end of line
@@ -575,7 +576,7 @@ const uint8_t* MimeSession::process_mime_data_paf(
 
         /*Process file type/file signature*/
         FileFlows* file_flows = FileFlows::get_file_flows(flow);
-        if (file_flows && file_flows->file_process(buffer, buf_size, position, upload)
+        if (file_flows && file_flows->file_process(p, buffer, buf_size, position, upload)
             && (isFileStart(position)) && log_state)
         {
             log_state->set_file_name_from_log(flow);
@@ -617,9 +618,10 @@ const uint8_t* MimeSession::process_mime_data_paf(
 
 // Main function for mime processing
 // This should be called when mime data is available
-const uint8_t* MimeSession::process_mime_data(Flow* flow, const uint8_t* start,
+const uint8_t* MimeSession::process_mime_data(Packet* p, const uint8_t* start,
     int data_size, bool upload, FilePosition position)
 {
+    Flow* flow = p->flow;
     const uint8_t* attach_start = start;
     const uint8_t* attach_end;
 
@@ -627,7 +629,7 @@ const uint8_t* MimeSession::process_mime_data(Flow* flow, const uint8_t* start,
 
     if (position != SNORT_FILE_POSITION_UNKNOWN)
     {
-        process_mime_data_paf(flow, attach_start, data_end_marker,
+        process_mime_data_paf(p, attach_start, data_end_marker,
             upload, position);
         return data_end_marker;
     }
@@ -641,7 +643,7 @@ const uint8_t* MimeSession::process_mime_data(Flow* flow, const uint8_t* start,
         {
             attach_end = start;
             finalFilePosition(&position);
-            process_mime_data_paf(flow, attach_start, attach_end,
+            process_mime_data_paf(p, attach_start, attach_end,
                 upload, position);
             data_state = STATE_MIME_HEADER;
             position = SNORT_FILE_START;
@@ -654,7 +656,7 @@ const uint8_t* MimeSession::process_mime_data(Flow* flow, const uint8_t* start,
     if ((start == data_end_marker) && (attach_start < data_end_marker))
     {
         updateFilePosition(&position, get_file_processed_size(flow));
-        process_mime_data_paf(flow, attach_start, data_end_marker,
+        process_mime_data_paf(p, attach_start, data_end_marker,
             upload, position);
     }
 
index 0a70cf09ec32e515679f920869b74b93a6546e95..b2b5d694c80e58874bfd35fbb89fd2d6dc2a4f4f 100644 (file)
@@ -64,7 +64,7 @@ public:
     static void init();
     static void exit();
 
-    const uint8_t* process_mime_data(Flow*, const uint8_t *data, int data_size,
+    const uint8_t* process_mime_data(Packet*, const uint8_t *data, int data_size,
         bool upload, FilePosition);
 
     int get_data_state();
@@ -95,7 +95,7 @@ private:
     void setup_decode(const char* data, int size, bool cnt_xf);
     const uint8_t* process_mime_header(const uint8_t* ptr, const uint8_t* data_end_marker);
     const uint8_t* process_mime_body(const uint8_t* ptr, const uint8_t* data_end,bool is_data_end);
-    const uint8_t* process_mime_data_paf(Flow*, const uint8_t* start, const uint8_t* end,
+    const uint8_t* process_mime_data_paf(Packet*, const uint8_t* start, const uint8_t* end,
         bool upload, FilePosition);
 };
 }
index a1327b656f01ebe814dbd49df6e672479b383566..e869af5b5738ce4767505e6d017360ba09b26d87 100644 (file)
@@ -1,4 +1,4 @@
-#ifndef LOG_MESSGE_MOCK
+#ifndef LOG_MESSAGE_MOCK
 #define LOG_MESSAGE_MOCK
 
 #ifdef HAVE_CONFIG_H
@@ -21,7 +21,7 @@ SO_PUBLIC void ErrorMessage(const char* format,...)
     va_end(ap);
 }
 
-SO_PUBLIC [[noreturn]] void FatalError(const char* format,...)
+[[noreturn]] SO_PUBLIC void FatalError(const char* format,...)
 {
     ErrorMessage(format);
     exit(1);
index 76cdf62fde3302d42f40525658b9d59aec628162..b416bf1a22a4108dc50c51ddc4842793e6dba34a 100644 (file)
@@ -244,7 +244,7 @@ void Normalizer::eval(snort::Packet* p)
 {
     Profile profile(norm_perf_stats);
 
-    if ( !p->is_rebuilt() && !Active::packet_was_dropped() )
+    if ( !p->is_rebuilt() && !p->active->packet_was_dropped() )
         Norm_Packet(&config, p);
 }
 
index 6ecceddd32b4c9b4d17005decd05c9eca635fa87..2f33334df5f2a20faf10acca049eec97c1b70b74 100644 (file)
@@ -265,6 +265,7 @@ static void snort_reputation(ReputationConfig* config, Packet* p)
         return;
 
     decision = reputation_decision(config, p);
+    Active* act = p->active;
 
     if (DECISION_NULL == decision)
         return;
@@ -272,10 +273,10 @@ static void snort_reputation(ReputationConfig* config, Packet* p)
     else if (BLACKLISTED == decision)
     {
         DetectionEngine::queue_event(GID_REPUTATION, REPUTATION_EVENT_BLACKLIST);
-        Active::drop_packet(p, true);
+        act->drop_packet(p, true);
         // disable all preproc analysis and detection for this packet
         DetectionEngine::disable_all(p);
-        Active::block_session(p, true);
+        act->block_session(p, true);
         reputationstats.blacklisted++;
         if (PacketTracer::is_active())
         {
@@ -293,7 +294,7 @@ static void snort_reputation(ReputationConfig* config, Packet* p)
         DetectionEngine::queue_event(GID_REPUTATION, REPUTATION_EVENT_WHITELIST);
         p->packet_flags |= PKT_IGNORE;
         DetectionEngine::disable_all(p);
-        Active::allow_session(p);
+        act->allow_session(p);
         reputationstats.whitelisted++;
     }
 }
index e40637d9239ffde3aa2f01854a16cb5309c5d54f..27e34874fb78bdb1479e6ea64c48e28e5f3e56cc 100644 (file)
@@ -38,20 +38,18 @@ using namespace snort;
 
 #define MAX_ATTEMPTS 20
 
-// these can't be pkt flags because we do the handling
-// of these flags following all processing and the drop
-// or response may have been produced by a pseudopacket.
-THREAD_LOCAL Active::ActiveStatus Active::active_status = Active::AST_ALLOW;
-THREAD_LOCAL Active::ActiveAction Active::active_action = Active::ACT_PASS;
-THREAD_LOCAL Active::ActiveAction Active::delayed_active_action = Active::ACT_PASS;
-
-THREAD_LOCAL int Active::active_tunnel_bypass = 0;
-THREAD_LOCAL bool Active::active_suspend = false;
+const char* Active::act_str[Active::ACT_MAX][Active::AST_MAX] =
+{
+    { "allow", "error", "error", "error" },
+    { "drop", "cant_drop", "would_drop", "force_drop" },
+    { "block", "cant_block", "would_block", "force_block" },
+    { "reset", "cant_reset", "would_reset", "force_reset" },
+};
+bool Active::enabled = false;
 
 THREAD_LOCAL uint8_t Active::s_attempts = 0;
-THREAD_LOCAL uint64_t Active::s_injects = 0;
-
-bool Active::s_enabled = false;
+THREAD_LOCAL bool Active::s_suspend = false;
+THREAD_LOCAL Active::Counts snort::active_counts;
 
 typedef int (* send_t) (
     const DAQ_PktHdr_t* h, int rev, const uint8_t* buf, uint32_t len);
@@ -60,9 +58,6 @@ static THREAD_LOCAL eth_t* s_link = nullptr;
 static THREAD_LOCAL ip_t* s_ipnet = nullptr;
 static THREAD_LOCAL send_t s_send = SFDAQ::inject;
 
-Active::ActiveStatus Active::get_status()
-{ return active_status; }
-
 //--------------------------------------------------------------------
 // helpers
 
@@ -70,7 +65,7 @@ int Active::send_eth(
     const DAQ_PktHdr_t*, int, const uint8_t* buf, uint32_t len)
 {
     ssize_t sent = eth_send(s_link, buf, len);
-    s_injects++;
+    active_counts.injects++;
     return ( (uint32_t)sent != len );
 }
 
@@ -78,7 +73,7 @@ int Active::send_ip(
     const DAQ_PktHdr_t*, int, const uint8_t* buf, uint32_t len)
 {
     ssize_t sent = ip_send(s_ipnet, buf, len);
-    s_injects++;
+    active_counts.injects++;
     return ( (uint32_t)sent != len );
 }
 
@@ -142,33 +137,39 @@ void Active::kill_session(Packet* p, EncodeFlags flags)
         return;
 
     case PktType::TCP:
-        Active::send_reset(p, 0);
+        send_reset(p, 0);
         if ( flags & ENC_FLAG_FWD )
-            Active::send_reset(p, ENC_FLAG_FWD);
+            send_reset(p, ENC_FLAG_FWD);
         break;
 
     default:
-        if ( Active::packet_force_dropped() )
-            Active::send_unreach(p, snort::UnreachResponse::FWD);
+        if ( packet_force_dropped() )
+            send_unreach(p, snort::UnreachResponse::FWD);
         else
-            Active::send_unreach(p, snort::UnreachResponse::PORT);
+            send_unreach(p, snort::UnreachResponse::PORT);
         break;
     }
 }
 
 //--------------------------------------------------------------------
 
-bool Active::init(SnortConfig* sc)
+void Active::init(SnortConfig* sc)
+{
+    if (sc->max_responses > 0)
+        Active::set_enabled();
+}
+
+bool Active::thread_init(SnortConfig* sc)
 {
     s_attempts = sc->respond_attempts;
 
     if ( s_attempts > MAX_ATTEMPTS )
         s_attempts = MAX_ATTEMPTS;
 
-    if ( s_enabled && !s_attempts )
+    if ( enabled && !s_attempts )
         s_attempts = 1;
 
-    if ( s_enabled && (!SFDAQ::can_inject() || !sc->respond_device.empty()) )
+    if ( enabled && (!SFDAQ::can_inject() || !sc->respond_device.empty()) )
     {
         if ( SnortConfig::read_mode() || !open(sc->respond_device.c_str()) )
         {
@@ -180,25 +181,14 @@ bool Active::init(SnortConfig* sc)
         }
     }
 
-    if (sc->max_responses > 0)
-        Active::set_enabled();
-
     return true;
 }
 
-void Active::term()
+void Active::thread_term()
 {
     Active::close();
 }
 
-bool Active::is_enabled()
-{ return s_enabled and s_attempts; }
-
-void Active::set_enabled(bool on_off)
-{
-    s_enabled = on_off;
-}
-
 //--------------------------------------------------------------------
 
 void Active::send_reset(Packet* p, EncodeFlags ef)
@@ -254,7 +244,10 @@ bool Active::send_data(
         seg = PacketManager::encode_response(TcpResponse::RST, tmp_flags, p, plen);
 
         if ( seg )
+        {
             s_send(p->pkth, !(tmp_flags & ENC_FLAG_FWD), seg, plen);
+            active_counts.injects++;
+        }
     }
     flags |= ENC_FLAG_SEQ;
 
@@ -275,6 +268,7 @@ bool Active::send_data(
                 return false;
 
             s_send(p->pkth, !(flags & ENC_FLAG_FWD), seg, plen);
+            active_counts.injects++;
 
             buf += toSend;
             sent += toSend;
@@ -290,6 +284,7 @@ bool Active::send_data(
         return false;
 
     s_send(p->pkth, !(flags & ENC_FLAG_FWD), seg, plen);
+    active_counts.injects++;
 
     if (flags & ENC_FLAG_RST_CLNT)
     {
@@ -299,7 +294,10 @@ bool Active::send_data(
         seg = PacketManager::encode_response(TcpResponse::RST, flags, p, plen);
 
         if ( seg )
+        {
             s_send(p->pkth, !(flags & ENC_FLAG_FWD), seg, plen);
+            active_counts.injects++;
+        }
     }
 
     return true;
@@ -370,7 +368,7 @@ void Active::cant_drop()
 
 void Active::update_status(const Packet* p, bool force)
 {
-    if ( suspended() )
+    if ( s_suspend )
         cant_drop();
 
     else if ( force )
@@ -392,7 +390,7 @@ void Active::update_status(const Packet* p, bool force)
 
 void Active::daq_update_status(const Packet* p)
 {
-    if ( suspended() )
+    if ( s_suspend )
     {
         cant_drop();
     }
@@ -419,12 +417,14 @@ void Active::daq_drop_packet(const Packet* p)
     daq_update_status(p);
 }
 
-bool Active::daq_retry_packet(const Packet *p)
+bool Active::daq_retry_packet(const Packetp)
 {
     bool retry_queued = false;
 
     // FIXIT-M may need to confirm this packet is not a retransmit...2.9.x has a check for that
-    if ( !p->is_rebuilt() && ( active_action == ACT_PASS ) && SFDAQ::can_retry() )
+    if ( !p->is_rebuilt() and
+        ( active_action == ACT_PASS ) and
+         SFDAQ::can_retry() )
     {
         if ( SFDAQ::forwarding_packet(p->pkth) )
         {
@@ -451,8 +451,8 @@ void Active::allow_session(Packet* p)
 
 void Active::block_session(Packet* p, bool force)
 {
-    update_status(p, force);
     active_action = ACT_BLOCK;
+    update_status(p, force);
 
     if ( force or SnortConfig::inline_mode() or SnortConfig::treat_drop_as_ignore() )
         Stream::block_flow(p);
@@ -468,7 +468,7 @@ void Active::reset_session(Packet* p, bool force)
     if ( force or SnortConfig::inline_mode() or SnortConfig::treat_drop_as_ignore() )
         Stream::drop_flow(p);
 
-    if ( s_enabled )
+    if ( enabled )
     {
         ActionManager::queue_reject();
 
@@ -486,7 +486,7 @@ void Active::set_delayed_action(ActiveAction action, bool force)
 {
     delayed_active_action = action;
 
-    if (force)
+    if ( force )
         active_status = AST_FORCE;
 }
 
@@ -494,7 +494,7 @@ void Active::apply_delayed_action(Packet* p)
 {
     bool force = (active_status == AST_FORCE);
 
-    switch (delayed_active_action)
+    switch ( delayed_active_action )
     {
     case ACT_PASS:
         break;
@@ -551,63 +551,10 @@ void Active::close()
     s_ipnet = nullptr;
 }
 
-static const char* act_str[Active::ACT_MAX][Active::AST_MAX] =
+void Active::reset()
 {
-    { "allow", "error", "error", "error" },
-    { "drop", "cant_drop", "would_drop", "force_drop" },
-    { "block", "cant_block", "would_block", "force_block" },
-    { "reset", "cant_reset", "would_reset", "force_reset" },
-};
-
-const char* Active::get_action_string()
-{
-    return act_str[active_action][active_status];
+    active_tunnel_bypass = 0;
+    active_status = AST_ALLOW;
+    active_action = ACT_PASS;
+    delayed_active_action = ACT_PASS;
 }
-
-void Active::suspend()
-{ active_suspend = true; }
-
-void Active::resume()
-{ active_suspend = false; }
-
-bool Active::suspended()
-{ return active_suspend; }
-
-Active::ActiveAction Active::get_action()
-{ return active_action; }
-
-bool Active::can_block()
-{ return active_status == AST_ALLOW or active_status == AST_FORCE; }
-
-void Active::block_again()
-{ active_action = ACT_BLOCK; }
-
-void Active::reset_again()
-{ active_action = ACT_RESET; }
-
-bool Active::packet_was_dropped()
-{ return ( active_action >= ACT_DROP ); }
-
-bool Active::packet_retry_requested()
-{ return ( active_action == ACT_RETRY ); }
-
-bool Active::session_was_blocked()
-{ return ( active_action >= ACT_BLOCK); }
-
-bool Active::packet_would_be_dropped()
-{ return (active_status == AST_WOULD ); }
-
-bool Active::packet_force_dropped()
-{ return (active_status == AST_FORCE ); }
-
-void Active::set_tunnel_bypass()
-{ active_tunnel_bypass++; }
-
-void Active::clear_tunnel_bypass()
-{ active_tunnel_bypass--; }
-
-bool Active::get_tunnel_bypass()
-{ return ( active_tunnel_bypass > 0 ); }
-
-uint64_t Active::get_injects()
-{ return s_injects; }
index 4ebd4be8142331522881f7f247f548ab81a48362..f39214802aa97d6e61510b037fae32ef411df41b 100644 (file)
@@ -35,111 +35,137 @@ struct SnortConfig;
 class SO_PUBLIC Active
 {
 public:
-    enum ActiveStatus
+
+    struct Counts
+    {
+        PegCount injects;
+    };
+
+    enum ActiveStatus : uint8_t
     { AST_ALLOW, AST_CANT, AST_WOULD, AST_FORCE, AST_MAX };
 
-    enum ActiveAction
+    enum ActiveAction : uint8_t
     { ACT_PASS, ACT_DROP, ACT_BLOCK, ACT_RESET, ACT_RETRY, ACT_MAX };
 
 public:
-    static bool init(SnortConfig*);
-    static void term();
+    static void init(SnortConfig*);
+    static bool thread_init(SnortConfig*);
+    static void thread_term();
 
-    static void reset()
-    {
-        active_status = AST_ALLOW;
-        active_action = ACT_PASS;
-        active_tunnel_bypass = 0;
-        delayed_active_action = ACT_PASS;
-    }
+    static void set_enabled(bool on_off = true)
+    { enabled = on_off; }
 
-    static void kill_session(Packet*, EncodeFlags = ENC_FLAG_FWD);
+    static void suspend()
+    { s_suspend = true; }
 
-    static void send_reset(Packet*, EncodeFlags);
-    static void send_unreach(Packet*, snort::UnreachResponse);
-    static bool send_data(Packet*, EncodeFlags, const uint8_t* buf, uint32_t len);
-    static void inject_data(Packet*, EncodeFlags, const uint8_t* buf, uint32_t len);
+    static void resume()
+    { s_suspend = false; }
 
-    static bool is_reset_candidate(const Packet*);
-    static bool is_unreachable_candidate(const Packet*);
+    void send_reset(Packet*, EncodeFlags);
+    void send_unreach(Packet*, snort::UnreachResponse);
+    bool send_data(Packet*, EncodeFlags, const uint8_t* buf, uint32_t len);
+    void inject_data(Packet*, EncodeFlags, const uint8_t* buf, uint32_t len);
 
-    static bool is_enabled();
-    static void set_enabled(bool = true);
+    bool is_reset_candidate(const Packet*);
+    bool is_unreachable_candidate(const Packet*);
 
-    static void suspend();
-    static void resume();
-    static bool suspended();
+    ActiveAction get_action()
+    { return active_action; }
 
-    static ActiveAction get_action();
-    static ActiveStatus get_status();
+    ActiveStatus get_status()
+    { return active_status; }
 
-    static bool can_block();
+    void kill_session(Packet*, EncodeFlags = ENC_FLAG_FWD);
 
-    static const char* get_action_string();
+    bool can_block()
+    { return active_status == AST_ALLOW or active_status == AST_FORCE; }
 
-    static void drop_packet(const Packet*, bool force = false);
-    static void daq_drop_packet(const Packet*);
-    static bool daq_retry_packet(const Packet*);
+    const char* get_action_string()
+    { return act_str[active_action][active_status]; }
 
-    static void allow_session(Packet*);
+    void drop_packet(const Packet*, bool force = false);
+    void daq_drop_packet(const Packet*);
+    bool daq_retry_packet(const Packet*);
 
-    static void block_session(Packet*, bool force = false);
-    static void reset_session(Packet*, bool force = false);
+    void allow_session(Packet*);
+    void block_session(Packet*, bool force = false);
+    void reset_session(Packet*, bool force = false);
 
-    static void block_again();
-    static void reset_again();
+    void block_again()
+    { active_action = ACT_BLOCK; }
 
-    static bool packet_was_dropped();
-    static bool packet_retry_requested();
-    static bool session_was_blocked();
-    static bool packet_would_be_dropped();
-    static bool packet_force_dropped();
+    void reset_again()
+    { active_action = ACT_RESET; }
 
-    static void set_tunnel_bypass();
-    static void clear_tunnel_bypass();
-    static bool get_tunnel_bypass();
+    bool packet_was_dropped()
+    { return active_action >= ACT_DROP; }
 
-    static uint64_t get_injects();
+    bool packet_would_be_dropped()
+    { return active_status == AST_WOULD; }
 
-    static void set_delayed_action(ActiveAction, bool force = false);
-    static void apply_delayed_action(Packet*);
+    bool packet_retry_requested()
+    { return active_action == ACT_RETRY; }
 
-private:
-    static bool open(const char*);
-    static void close();
+    bool session_was_blocked()
+    { return active_action >= ACT_BLOCK; }
 
-    static int send_eth(
-        const DAQ_PktHdr_t*, int, const uint8_t* buf, uint32_t len);
+    bool packet_force_dropped()
+    { return active_status == AST_FORCE; }
 
-    static int send_ip(
-        const DAQ_PktHdr_t*, int, const uint8_t* buf, uint32_t len);
+    void set_tunnel_bypass()
+    { active_tunnel_bypass++; }
 
-    static void update_status(const Packet*, bool force = false);
-    static void daq_update_status(const Packet*);
+    void clear_tunnel_bypass()
+    { active_tunnel_bypass--; }
 
-    static void block_session(const Packet*, ActiveAction, bool force = false);
+    bool get_tunnel_bypass()
+    { return active_tunnel_bypass > 0; }
 
-    static void cant_drop();
+    void set_delayed_action(ActiveAction, bool force = false);
+    void apply_delayed_action(Packet*);
+
+    void reset();
 
 private:
-    static THREAD_LOCAL ActiveStatus active_status;
-    static THREAD_LOCAL ActiveAction active_action;
-    static THREAD_LOCAL ActiveAction delayed_active_action;
+    static bool open(const char*);
+    static void close();
+    static int send_eth(const DAQ_PktHdr_t*, int, const uint8_t* buf, uint32_t len);
+    static int send_ip(const DAQ_PktHdr_t*, int, const uint8_t* buf, uint32_t len);
+
+    void update_status(const Packet*, bool force = false);
+    void daq_update_status(const Packet*);
+
+    void block_session(const Packet*, ActiveAction, bool force = false);
+
+    void cant_drop();
 
-    static THREAD_LOCAL int active_tunnel_bypass;
-    static THREAD_LOCAL bool active_suspend;
 
+private:
+    static const char* act_str[ACT_MAX][AST_MAX];
+    static bool enabled;
     static THREAD_LOCAL uint8_t s_attempts;
-    static THREAD_LOCAL uint64_t s_injects;
+    static THREAD_LOCAL bool s_suspend;
+
+    int active_tunnel_bypass;
 
-    static bool s_enabled;
+    // these can't be pkt flags because we do the handling
+    // of these flags following all processing and the drop
+    // or response may have been produced by a pseudopacket.
+    ActiveStatus active_status;
+    ActiveAction active_action;
+    ActiveAction delayed_active_action;
 };
 
 struct ActiveSuspendContext
 {
-    ActiveSuspendContext() { Active::suspend(); }
-    ~ActiveSuspendContext() { Active::resume(); }
+    ActiveSuspendContext()
+    { Active::suspend(); }
+
+    ~ActiveSuspendContext()
+    { Active::resume(); }
 };
+
+extern THREAD_LOCAL Active::Counts active_counts;
 }
 #endif
 
index d14da71ed0d5e5f2bc1b3c20c6da74146ca95b78..164c0c7b2e035d9466ec4d35c537ec729dcc4bc8 100644 (file)
@@ -27,6 +27,7 @@
 #include "flow/expect_cache.h"
 #include "framework/endianness.h"
 #include "log/obfuscator.h"
+#include "packet_io/active.h"
 #include "managers/codec_manager.h"
 
 #include "packet_manager.h"
@@ -51,7 +52,7 @@ Packet::Packet(bool packet_data)
 
     obfuscator = nullptr;
     endianness = nullptr;
-
+    active_inst = new Active;
     reset();
 }
 
@@ -64,7 +65,7 @@ Packet::~Packet()
         delete pkth;
         delete[] pkt;
     }
-
+    delete active_inst;
     delete[] layers;
 }
 
index b28fd053e9a7cfbcfbbc22d7aa7083c69978eeae..5ef29dc3bc17e387fdd7d42e2c5d8b3fed33a0cd 100644 (file)
@@ -30,6 +30,7 @@
 
 namespace snort
 {
+class Active;
 class Endianness;
 class Flow;
 class IpsContext;
@@ -129,6 +130,8 @@ struct SO_PUBLIC Packet
 
     // Everything beyond this point is set by PacketManager::decode()
     IpsContext* context;   // set by control
+    Active* active;
+    Active* active_inst;
     const DAQ_PktHdr_t* pkth;    // packet meta data
     const uint8_t* pkt;          // raw packet data
 
index 79282c9f14ea08f2e097e775e3c1d7c7c9f8cb4e..fcfd902554ee36fcf1f2c3254988e6f2798645c0 100644 (file)
@@ -100,7 +100,7 @@ void PacketManager::pop_teredo(Packet* p, RawData& raw)
 {
     p->proto_bits &= ~PROTO_BIT__TEREDO;
     if ( SnortConfig::tunnel_bypass_enabled(TUNNEL_TEREDO) )
-        Active::clear_tunnel_bypass();
+        p->active->clear_tunnel_bypass();
 
     const ProtocolIndex mapped_prot = CodecManager::s_proto_map[to_utype(ProtocolId::TEREDO)];
     s_stats[mapped_prot + stat_offset]--;
@@ -165,6 +165,12 @@ void PacketManager::decode(
             CodecManager::s_protocols[mapped_prot]->get_name(),
             static_cast<uint16_t>(codec_data.next_prot_id), pkt, codec_data.lyr_len);
 
+        if ( codec_data.tunnel_bypass )
+        {
+            p->active->set_tunnel_bypass();
+            codec_data.tunnel_bypass = false;
+        }
+
         if ( codec_data.codec_flags & CODEC_ETHER_NEXT )
         {
             if ( codec_data.next_prot_id < ProtocolId::ETHERTYPE_MINIMUM )
index c36988d358e2321165c50563804cd9eff67548bb..abb1f4fa9a80ce989a648d167b1298099ff830fe 100644 (file)
@@ -235,11 +235,12 @@ static inline void DCE2_Smb2ProcessFileData(DCE2_SmbSsnData* ssd, const uint8_t*
         DCE2_FileDetect();
     }
 
-    FileFlows* file_flows = FileFlows::get_file_flows(DetectionEngine::get_current_packet()->flow);
+    Packet* p = DetectionEngine::get_current_packet();
+    FileFlows* file_flows = FileFlows::get_file_flows(p->flow);
     if ( !file_flows )
         return;
 
-    file_flows->file_process(ssd->ftracker.fid_v2, file_data, data_size,
+    file_flows->file_process(p, ssd->ftracker.fid_v2, file_data, data_size,
         ssd->ftracker.tracker.file.file_offset, dir);
 }
 
index f2a8c527cb60bd766c0e99678298abc7524b8aaa..7374fc3ad28a9cf051f65124da2af9de1bd0db97 100644 (file)
@@ -1460,7 +1460,7 @@ static void DCE2_SmbInjectDeletePdu(DCE2_SmbFileTracker* ftracker)
     del_req->smb_bcc = 1 + file_name_len;
     memcpy(del_filename, ftracker->file_name + UTF_16_LE_BOM_LEN, file_name_len);
 
-    Active::inject_data(inject_pkt, 0, (uint8_t*)nb_hdr, len);
+    p->active->inject_data(inject_pkt, 0, (uint8_t*)nb_hdr, len);
 }
 
 static FileVerdict DCE2_SmbLookupFileVerdict()
@@ -1475,7 +1475,7 @@ static FileVerdict DCE2_SmbLookupFileVerdict()
     FileVerdict verdict = file->verdict;
 
     if (verdict == FILE_VERDICT_PENDING)
-        verdict = file->file_signature_lookup(DetectionEngine::get_current_packet()->flow);
+        verdict = file->file_signature_lookup(DetectionEngine::get_current_packet());
 
     return verdict;
 }
@@ -1514,7 +1514,7 @@ static void DCE2_SmbFinishFileAPI(DCE2_SmbSsnData* ssd)
             && (ftracker->ff_bytes_processed != 0))
         {
             Profile profile(dce2_smb_pstat_smb_file_api);
-            if (file_flows->file_process(nullptr, 0, SNORT_FILE_END, upload))
+            if (file_flows->file_process(p, nullptr, 0, SNORT_FILE_END, upload))
             {
                 if (upload)
                 {
@@ -1576,8 +1576,10 @@ static DCE2_Ret DCE2_SmbFileAPIProcess(DCE2_SmbSsnData* ssd,
     }
 
     Profile profile(dce2_smb_pstat_smb_file_api);
-    FileFlows* file_flows = FileFlows::get_file_flows(DetectionEngine::get_current_packet()->flow);
-    if (!file_flows->file_process(data_ptr, (int)data_len, position, upload,
+    Packet* p = DetectionEngine::get_current_packet();
+    DetectionEngine::get_current_packet();
+    FileFlows* file_flows = FileFlows::get_file_flows(p->flow);
+    if (!file_flows->file_process(p, data_ptr, (int)data_len, position, upload,
         DCE2_SmbIsVerdictSuspend(upload, position)))
     {
         trace_logf(dce_smb, "File API returned FAILURE "
index 98ac4f6ef91df27906ffab173a4db0f038fdc30a..08a28432f55d9930ee7b0645cbbf92625c6dec39 100644 (file)
@@ -769,7 +769,8 @@ static void DCE2_SmbProcessCommand(DCE2_SmbSsnData* ssd, const SmbNtHdr* smb_hdr
     {
         if (ssd->block_pdus && (DCE2_SmbType() == SMB_TYPE__REQUEST))
         {
-            Active::drop_packet(DetectionEngine::get_current_packet());
+            Packet* p = DetectionEngine::get_current_packet();
+            p->active->drop_packet(p);
             status = DCE2_RET__IGNORE;
             break;
         }
index b8aeeb744cccf84763dbe1e351fd46501aa888f3..b94d12a0d81aff5d2d1a1525dbca1431f6d22e21 100644 (file)
@@ -59,7 +59,7 @@ static void FTPDataProcess(
 
     if (data_ssn->packet_flags & FTPDATA_FLG_REST)
     {
-        Active::block_again();
+        p->active->block_again();
         return;
     }
 
@@ -75,10 +75,10 @@ static void FTPDataProcess(
     else
         file_flows->set_sig_gen_state( false );
 
-    status = file_flows->file_process(file_data, data_length,
+    status = file_flows->file_process(p, file_data, data_length,
         data_ssn->position, data_ssn->direction);
 
-    if (Active::packet_force_dropped())
+    if ( p->active->packet_force_dropped() )
     {
         FtpFlowData* fd = (FtpFlowData*)Stream::get_flow_data(
                             &data_ssn->ftp_key, FtpFlowData::inspector_id);
index 71c66f3b55cbee38c6657cad1229a8f9421d988c..4f23f9f46eb2de9bb0f3ffa1a2c543b11c5f8f01 100644 (file)
@@ -23,6 +23,7 @@
 
 #include "ftpdata_splitter.h"
 
+#include "detection/detection_engine.h"
 #include "file_api/file_flows.h"
 #include "flow/session.h"
 #include "stream/stream.h"
@@ -109,7 +110,10 @@ bool FtpDataSplitter::finish(Flow* flow)
 
             FileFlows* file_flows = FileFlows::get_file_flows(flow);
             if ( file_flows )
-                file_flows->file_process(nullptr, 0, SNORT_FILE_END, to_server(), 0);
+            {
+                file_flows->file_process(DetectionEngine::get_current_packet(), 
+                    nullptr, 0, SNORT_FILE_END, to_server(), 0);
+            }
         }
     }
 
index 8bc383e64e2fb91ea5ea94247e3b327cef47e990..146d510717675713420535a0cb97cebb7d356e7d 100644 (file)
@@ -201,6 +201,7 @@ void HttpMsgBody::do_js_normalization(const Field& input, Field& output)
 void HttpMsgBody::do_file_processing(Field& file_data)
 {
     // Using the trick that cutter is deleted when regular or chunked body is complete
+    Packet* p = DetectionEngine::get_current_packet();
     const bool front = (body_octets == 0);
     const bool back = (session_data->cutter[source_id] == nullptr) || tcp_close;
 
@@ -231,7 +232,7 @@ void HttpMsgBody::do_file_processing(Field& file_data)
             file_index = request->get_http_uri()->get_file_proc_hash();
         }
 
-        if (file_flows->file_process(file_data.start(), fp_length,
+        if (file_flows->file_process(p, file_data.start(), fp_length,
             file_position, !download, file_index))
         {
             session_data->file_depth_remaining[source_id] -= fp_length;
@@ -258,7 +259,7 @@ void HttpMsgBody::do_file_processing(Field& file_data)
     }
     else
     {
-        session_data->mime_state[source_id]->process_mime_data(flow, file_data.start(),
+        session_data->mime_state[source_id]->process_mime_data(p, file_data.start(),
             fp_length, true, SNORT_FILE_POSITION_UNKNOWN);
 
         session_data->file_depth_remaining[source_id] -= fp_length;
index e2ee8aa5337c453f369d6c975e38f9f430f82bb9..f9bfa345c168a48d47eaa7f484e9232fb40b0d95 100644 (file)
@@ -339,10 +339,11 @@ void HttpMsgHeader::setup_file_processing()
                     // FIXIT-L develop a proper interface for passing the boundary string.
                     // This interface is a leftover from when OHI pushed whole messages through
                     // this interface.
-                    session_data->mime_state[source_id]->process_mime_data(flow,
+                    Packet* p = DetectionEngine::get_current_packet();
+                    session_data->mime_state[source_id]->process_mime_data(p,
                         content_type.start(), content_type.length(), true,
                         SNORT_FILE_POSITION_UNKNOWN);
-                    session_data->mime_state[source_id]->process_mime_data(flow,
+                    session_data->mime_state[source_id]->process_mime_data(p,
                         (const uint8_t*)"\r\n", 2, true, SNORT_FILE_POSITION_UNKNOWN);
                 }
             }
index 4c8f82abf6d54dfcbd1084511893449546284292..d3b845bbe2c6b070d68d67e2f01e8466c28fa7fd 100644 (file)
@@ -33,6 +33,7 @@ using namespace HttpEnums;
 bool HttpStreamSplitter::finish(snort::Flow* flow)
 {
     snort::Profile profile(HttpModule::get_profile_stats());
+    snort::Packet* p = snort::DetectionEngine::get_current_packet();
 
     HttpFlowData* session_data = (HttpFlowData*)flow->get_flow_data(HttpFlowData::inspector_id);
     // FIXIT-M - this assert has been changed to check for null session data and return false if so
@@ -136,11 +137,11 @@ bool HttpStreamSplitter::finish(snort::Flow* flow)
                 }
             }
 
-            file_flows->file_process(nullptr, 0, SNORT_FILE_END, !download, file_index);
+            file_flows->file_process(p, nullptr, 0, SNORT_FILE_END, !download, file_index);
         }
         else
         {
-            session_data->mime_state[source_id]->process_mime_data(flow, nullptr, 0, true,
+            session_data->mime_state[source_id]->process_mime_data(p, nullptr, 0, true,
                 SNORT_FILE_POSITION_UNKNOWN);
             delete session_data->mime_state[source_id];
             session_data->mime_state[source_id] = nullptr;
index 412a5c068e2e5b53d1e3ec3d4ac7067b6604977d..a99903f0e2aca40d828711d845bc08f2b50c8f4a 100644 (file)
@@ -460,7 +460,7 @@ static void IMAP_ProcessServerPacket(Packet* p, IMAPData* imap_ssn)
                 FilePosition position = get_file_position(p);
 
                 int data_len = end - ptr;
-                ptr = imap_ssn->mime_ssn->process_mime_data(p->flow, ptr, data_len, false,
+                ptr = imap_ssn->mime_ssn->process_mime_data(p, ptr, data_len, false,
                     position);
                 if ( ptr < data_end)
                     len = len - (data_end - ptr);
index d76b6cffbaf012b0588fc258fea3a2f3adb488b1..869aaccc0575d1b8de8e2abaf6b29ffae6ca0934 100644 (file)
@@ -432,7 +432,7 @@ static void POP_ProcessServerPacket(Packet* p, POPData* pop_ssn)
             //ptr = POP_HandleData(p, ptr, end);
             FilePosition position = get_file_position(p);
             int len = end - ptr;
-            ptr = pop_ssn->mime_ssn->process_mime_data(p->flow, ptr, len, false, position);
+            ptr = pop_ssn->mime_ssn->process_mime_data(p, ptr, len, false, position);
             continue;
         }
         POP_GetEOL(ptr, end, &eol, &eolm);
index c7bd4538627cf97de6d22ad27d9c41f854e0d9f4..399f54fe055ace06ec6f9bc662956656f0a3e498 100644 (file)
@@ -1003,7 +1003,7 @@ static void SMTP_ProcessClientPacket(SMTP_PROTO_CONF* config, Packet* p, SMTPDat
         case STATE_DATA:
         case STATE_BDATA:
             position = get_file_position(p);
-            ptr = smtp_ssn->mime_ssn->process_mime_data(p->flow, ptr, len, true, position);
+            ptr = smtp_ssn->mime_ssn->process_mime_data(p, ptr, len, true, position);
             //ptr = SMTP_HandleData(p, ptr, end, &(smtp_ssn->mime_ssn));
             break;
         case STATE_XEXCH50:
index 77e2e856eb8b04102e65de2ba1bf3f48fbf4235e..66780fd74ceb3905125598f0bcac63234f911c0d 100644 (file)
@@ -243,7 +243,7 @@ int ParseXLink2State(SMTP_PROTO_CONF* config, snort::Packet* p, SMTPData* smtp_s
         /* Need to drop the packet if we're told to
          * (outside of whether its thresholded). */
         if (config->xlink2state == DROP_XLINK2STATE)
-            snort::Active::reset_session(p);
+            p->active->reset_session(p);
 
         snort::DetectionEngine::queue_event(GID_SMTP, SMTP_XLINK2STATE_OVERFLOW);
         smtp_ssn->session_flags |= SMTP_FLAG_XLINK2STATE_ALERTED;
index 039c3d724f65e00308aa760c4ac4298f0630b051..4ce6b1686ec3fece6f611fcbcda008702fd7a2cf 100644 (file)
@@ -79,7 +79,7 @@ int FileSession::process(Packet* p)
     FileFlows* file_flows = FileFlows::get_file_flows(p->flow);
 
     if (file_flows &&
-        file_flows->file_process(p->data, p->dsize, position(p), c->upload))
+        file_flows->file_process(p, p->data, p->dsize, position(p), c->upload))
     {
         const char* file_name = SFDAQ::get_interface_spec();
         if (file_name)
index 4fc48cb581dcc6d99f308e389e39fa06e3f7aec2..422436858fbc3ab5d9d2654f26dea7946bc122c5 100644 (file)
@@ -974,7 +974,7 @@ void Defrag::process(Packet* p, FragTracker* ft)
     if ( ft->frag_flags & FRAG_DROP_FRAGMENTS )
     {
         DetectionEngine::disable_content(p);
-        Active::daq_drop_packet(p);
+        p->active->daq_drop_packet(p);
         ip_stats.drops++;
     }
 
@@ -1050,7 +1050,7 @@ void Defrag::process(Packet* p, FragTracker* ft)
         if (!(ft->frag_flags & FRAG_BAD))
             FragRebuild(ft, p);
 
-        if (Active::packet_was_dropped())
+        if ( p->active->packet_was_dropped() )
         {
             ft->frag_flags |= FRAG_DROP_FRAGMENTS;
             delete_tracker(ft);
index 9a80d5ab7cf55a6559acca8e191e0a9524953df5..50cc505b9bfec585c12d8c203d55a86918e1c5c0 100644 (file)
@@ -168,7 +168,7 @@ int IpSession::process(Packet* p)
         IpHAManager::process_deletion(flow);
     }
 
-    if ( Stream::blocked_flow(flow, p) || Stream::ignored_flow(flow, p) )
+    if ( Stream::blocked_flow(p) || Stream::ignored_flow(flow, p) )
         return 0;
 
     if ( p->ptrs.decode_flags & DECODE_FRAG )
index 63c9862c31ad4607fad283bc991cb2881c7bfff9..efdda8c4199bc8e0bafe4a242f384c896d05b5ba 100644 (file)
@@ -177,7 +177,7 @@ void Stream::check_flow_closed(Packet* p)
         flow->set_state(Flow::FlowState::BLOCK);
 
         if ( !(p->packet_flags & PKT_STATELESS) )
-            drop_traffic(flow, SSN_DIR_BOTH);
+            drop_traffic(p, SSN_DIR_BOTH);
         flow->session_state &= ~STREAM_STATE_BLOCK_PENDING;
     }
 }
@@ -288,22 +288,24 @@ uint32_t Stream::get_packet_direction(Packet* p)
     return (p->packet_flags & (PKT_FROM_SERVER|PKT_FROM_CLIENT));
 }
 
-void Stream::drop_traffic(Flow* flow, char dir)
+void Stream::drop_traffic(const Packet* p, char dir)
 {
-    if (!flow)
+    Flow* flow = p->flow;
+
+    if ( !flow )
         return;
 
     if ((dir & SSN_DIR_FROM_CLIENT) && !(flow->ssn_state.session_flags & SSNFLAG_DROP_CLIENT))
     {
         flow->ssn_state.session_flags |= SSNFLAG_DROP_CLIENT;
-        if ( Active::packet_force_dropped() )
+        if ( p->active->packet_force_dropped() )
             flow->ssn_state.session_flags |= SSNFLAG_FORCE_BLOCK;
     }
 
     if ((dir & SSN_DIR_FROM_SERVER) && !(flow->ssn_state.session_flags & SSNFLAG_DROP_SERVER))
     {
         flow->ssn_state.session_flags |= SSNFLAG_DROP_SERVER;
-        if ( Active::packet_force_dropped() )
+        if ( p->active->packet_force_dropped() )
             flow->ssn_state.session_flags |= SSNFLAG_FORCE_BLOCK;
     }
 }
@@ -332,7 +334,7 @@ void Stream::drop_flow(const Packet* p)
     flow->set_state(Flow::FlowState::BLOCK);
 
     if ( !(p->packet_flags & PKT_STATELESS) )
-        drop_traffic(flow, SSN_DIR_BOTH);
+        drop_traffic(p, SSN_DIR_BOTH);
 }
 
 //-------------------------------------------------------------------------
@@ -600,7 +602,7 @@ static void active_response(Packet* p, Flow* lwssn)
             (lwssn->session_state & STREAM_STATE_DROP_SERVER) ) ?
             ENC_FLAG_FWD : 0;  // reverse dir is always true
 
-        Active::kill_session(p, flags);
+        p->active->kill_session(p, flags);
         ++lwssn->response_count;
         lwssn->set_expire(p, delay);
 
@@ -608,8 +610,10 @@ static void active_response(Packet* p, Flow* lwssn)
     }
 }
 
-bool Stream::blocked_flow(Flow* flow, Packet* p)
+bool Stream::blocked_flow(Packet* p)
 {
+    Flow* flow = p->flow;
+
     if ( !(flow->ssn_state.session_flags & (SSNFLAG_DROP_CLIENT|SSNFLAG_DROP_SERVER)) )
         return false;
 
@@ -621,7 +625,7 @@ bool Stream::blocked_flow(Flow* flow, Packet* p)
         (flow->ssn_state.session_flags & SSNFLAG_DROP_CLIENT)) )
     {
         DetectionEngine::disable_content(p);
-        Active::drop_packet(p);
+        p->active->drop_packet(p);
         active_response(p, flow);
         return true;
     }
index b408d008f39afddd7e7975e1a8457c941b913991..f1316eb05aac7d6eb44525e275cc4355972357f8 100644 (file)
@@ -119,7 +119,7 @@ public:
 
     // Set Active status to force drop the current packet and set flow state to drop
     // subsequent packets arriving from the direction specified.
-    static void drop_traffic(Flow*, char dir);
+    static void drop_traffic(const Packet*, char dir);
 
     // Mark a flow as dropped, release allocated resources, and set flow state such that any
     // subsequent packets received on this flow are dropped.
@@ -218,7 +218,7 @@ public:
 
     static bool expired_flow(Flow*, Packet*);
     static bool ignored_flow(Flow*, Packet*);
-    static bool blocked_flow(Flow*, Packet*);
+    static bool blocked_flow(Packet*);
 
     // extra data methods
     static void set_extra_data(Flow*, Packet*, uint32_t);
index d4744b8ba8754ad5c9902ab3c230e2306dbf1ed9..de4311fde713b61c0e641d08a465f27e9537b5ea 100644 (file)
@@ -99,7 +99,8 @@ bool TcpNormalizer::packet_dropper(
 
     if (mode == NORM_MODE_ON)
     {
-        Active::drop_packet(tsd.get_pkt());
+        Packet* p = tsd.get_pkt();
+        p->active->drop_packet(p);
         return true;
     }
 
index 7f8f72440e376a28242e8d7ea7039f8334e59cde..2a85e4a57d7530bdde370d9e9193ecda89535603 100644 (file)
@@ -911,7 +911,7 @@ bool TcpSession::is_flow_handling_packets(Packet* p)
         flow_ready = false;
     }
     else
-        flow_ready = !Stream::blocked_flow(flow, p);
+        flow_ready = !Stream::blocked_flow(p);
 
     // FIXIT-L expected flow should be checked by Stream before we get here
     // harmonize this with that and the checks above
index 9fc4aba9ac1f9b5b738a2c7a5e21bd256464cf48..0ecf0de53343c4306fd40465caa4a057f72a77ad 100644 (file)
@@ -84,12 +84,9 @@ public:
 class Active
 {
 public:
-    static void drop_packet(const Packet*, bool force = false);
-
+    void drop_packet(const Packet*, bool force = false) { }
 };
 
-void Active::drop_packet(const Packet* , bool ) { }
-
 bool Normalize_IsEnabled(NormFlags )
 {
     return norm_enabled;
index e9dc9337c7efa9029d74710f9ec1a7b222b0544d..a5dd70b5f1e3442a7cc3da1a720dcb19336baf1c 100644 (file)
@@ -61,7 +61,7 @@ static int ProcessUdp(
 {
     assert(lwssn->pkt_type == PktType::UDP);
 
-    if ( Stream::blocked_flow(lwssn, p) )
+    if ( Stream::blocked_flow(p) )
         return 0;
 
     if ( Stream::ignored_flow(lwssn, p) )
index 5fb87784518cdbf9a87ab766abb6603b8eef0c98..6cad140c1b848c876814ed24ce558c84feea1ce7 100644 (file)
@@ -482,7 +482,7 @@ int UserSession::process(Packet* p)
 
     flow->set_direction(p);
 
-    if ( Stream::blocked_flow(flow, p) || Stream::ignored_flow(flow, p) )
+    if ( Stream::blocked_flow(p) || Stream::ignored_flow(flow, p) )
         return 0;
 
     update(p, flow);