]> git.ipfire.org Git - thirdparty/snort3.git/commitdiff
Pull request #3661: flow: add an event for retry packets
authorRon Dempster (rdempste) <rdempste@cisco.com>
Wed, 23 Nov 2022 12:37:35 +0000 (12:37 +0000)
committerRon Dempster (rdempste) <rdempste@cisco.com>
Wed, 23 Nov 2022 12:37:35 +0000 (12:37 +0000)
Merge in SNORT/snort3 from ~RDEMPSTE/snort3:retry_event to master

Squashed commit of the following:

commit db8fdde4cdffb84cae3af426ed19c6b371eff14f
Author: Ron Dempster (rdempste) <rdempste@cisco.com>
Date:   Tue Oct 25 17:09:44 2022 -0400

    flow: add an event for retry packets

src/flow/flow.h
src/flow/flow_control.cc
src/flow/test/flow_cache_test.cc
src/flow/test/flow_control_test.cc
src/main/analyzer.cc
src/main/analyzer.h
src/pub_sub/CMakeLists.txt
src/pub_sub/packet_events.h [new file with mode: 0644]
src/stream/tcp/tcp_stream_tracker.cc

index 578aead7c0960b5cbeb772263dad90b00871d90f..82e4edd3577422522dffcf0a9d50dde0548768a0 100644 (file)
@@ -494,6 +494,7 @@ public:  // FIXIT-M privatize if possible
         bool snort_proto_id_set_by_ha : 1;
         bool efd_flow : 1;  // Indicate that current flow is an elephant flow
         bool svc_event_generated : 1; // Set if FLOW_NO_SERVICE_EVENT was generated for this flow
+        bool retry_queued : 1; // Set if a packet was queued for retry for this flow
     } flags;
 
     FlowState flow_state;
index 35699d3f27aba086e2c6892989b3d9f349b1245d..38bc6c5771ceb9e799d894b21754ea22bb56e58b 100644 (file)
@@ -33,6 +33,7 @@
 #include "protocols/tcp.h"
 #include "protocols/udp.h"
 #include "protocols/vlan.h"
+#include "pub_sub/packet_events.h"
 #include "stream/stream.h"
 #include "utils/util.h"
 
@@ -453,6 +454,19 @@ unsigned FlowControl::process(Flow* flow, Packet* p)
         }
         p->filtering_state = flow->filtering_state;
         update_stats(flow, p);
+        if (p->is_retry())
+        {
+            RetryPacketEvent retry_event(p);
+            DataBus::publish(PKT_RETRY_EVENT, retry_event);
+            flow->flags.retry_queued = false;
+        }
+        else if ( flow->flags.retry_queued and ( !p->is_cooked() or p->is_defrag() ) )
+        {
+            RetryPacketEvent retry_event(p);
+            DataBus::publish(PKT_RETRY_EVENT, retry_event);
+            if ( !retry_event.is_still_pending() )
+                flow->flags.retry_queued = false;
+        }
     }
     else
     {
index 99db6eacf529b08dbd6caec33a776183136c718b..27ac992fa702e1ff63b033bdd6de6cad131a2a1a 100644 (file)
@@ -83,6 +83,7 @@ void Flow::term() { }
 void Flow::flush(bool) { }
 void Flow::reset(bool) { }
 void Flow::free_flow_data() { }
+void DataBus::publish(const char*, DataEvent&, Flow*) { }
 void DataBus::publish(const char*, const uint8_t*, unsigned, Flow*) { }
 void DataBus::publish(const char*, Packet*, Flow*) { }
 const SnortConfig* SnortConfig::get_conf() { return nullptr; }
index c941b78bdf2ed4f3470944f6ad0e764bfb0a9588..d021bab34931127e675d4e4a904b0c9311fafb6d 100644 (file)
@@ -85,6 +85,7 @@ size_t FlowCache::uni_flows_size() const { return 0; }
 size_t FlowCache::uni_ip_flows_size() const { return 0; }
 size_t FlowCache::flows_size() const { return 0; }
 void Flow::init(PktType) { }
+void DataBus::publish(const char*, DataEvent&, Flow*) { }
 void DataBus::publish(const char*, const uint8_t*, unsigned, Flow*) { }
 void DataBus::publish(const char*, Packet*, Flow*) { }
 const SnortConfig* SnortConfig::get_conf() { return nullptr; }
index ea18f3f4b0cec90a0ec0a0b7a5ee4d0221e98845..639a47cead8f10f44f4bc3a839e0609f35aae01d 100644 (file)
@@ -313,9 +313,11 @@ static void packet_trace_dump(Packet* p, DAQ_Verdict verdict, bool msg_was_held)
     PacketTracer::dump(p);
 }
 
-void Analyzer::add_to_retry_queue(DAQ_Msg_h daq_msg)
+void Analyzer::add_to_retry_queue(DAQ_Msg_h daq_msg, Flow* flow)
 {
     retry_queue->put(daq_msg);
+    if (flow)
+        flow->flags.retry_queued = true;
 }
 
 /*
@@ -331,7 +333,7 @@ void Analyzer::post_process_daq_pkt_msg(Packet* p)
 
     if (p->active->packet_retry_requested())
     {
-        add_to_retry_queue(p->daq_msg);
+        add_to_retry_queue(p->daq_msg, p->flow);
         daq_stats.retries_queued++;
     }
     else
index 2c2e354daed5116970db9e4a3751962dd9d5155d..fda12345a2cf3403baa20eb866c1430660db7311 100644 (file)
@@ -43,6 +43,7 @@ class Swapper;
 namespace snort
 {
 class AnalyzerCommand;
+class Flow;
 class SFDAQInstance;
 struct Packet;
 struct SnortConfig;
@@ -96,7 +97,7 @@ public:
     bool process_rebuilt_packet(snort::Packet*, const DAQ_PktHdr_t*, const uint8_t* pkt, uint32_t pktlen);
     SO_PUBLIC bool inspect_rebuilt(snort::Packet*);
     void finalize_daq_message(DAQ_Msg_h, DAQ_Verdict);
-    void add_to_retry_queue(DAQ_Msg_h);
+    void add_to_retry_queue(DAQ_Msg_h, snort::Flow*);
 
     // Functions called by analyzer commands
     void start();
index 0d83a7123f37ab1ddc666962f7e326f3669a0a52..351bad7567e180c2703ce036bcfd5a6a217c7af4 100644 (file)
@@ -14,6 +14,7 @@ set (PUB_SUB_INCLUDES
     http_request_body_event.h
     netflow_event.h
     opportunistic_tls_event.h
+    packet_events.h
     reputation_events.h
     rna_events.h
     sip_events.h
diff --git a/src/pub_sub/packet_events.h b/src/pub_sub/packet_events.h
new file mode 100644 (file)
index 0000000..98ffce1
--- /dev/null
@@ -0,0 +1,53 @@
+//--------------------------------------------------------------------------
+// Copyright (C) 2022-2022 Cisco and/or its affiliates. All rights reserved.
+//
+// This program is free software; you can redistribute it and/or modify it
+// under the terms of the GNU General Public License Version 2 as published
+// by the Free Software Foundation.  You may not use, modify or distribute
+// this program under any other version of the GNU General Public License.
+//
+// This program is distributed in the hope that it will be useful, but
+// WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with this program; if not, write to the Free Software Foundation, Inc.,
+// 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+//--------------------------------------------------------------------------
+// packet_events.h author Ron Dempster <rdempste@cisco.com>
+
+#ifndef PACKET_EVENTS_H
+#define PACKET_EVENTS_H
+
+#include "framework/data_bus.h"
+
+// A retry packet is being processed
+#define PKT_RETRY_EVENT "retry_packet"
+
+namespace snort
+{
+
+class RetryPacketEvent : public DataEvent
+{
+public:
+    explicit RetryPacketEvent(const Packet* p) : pkt(p)
+    { }
+
+    const Packet* get_packet() const override
+    { return pkt; }
+
+    void set_still_pending()
+    { still_pending = true; }
+
+    bool is_still_pending() const
+    { return still_pending; }
+
+private:
+    const Packet* pkt;
+    bool still_pending = false;
+};
+
+}
+
+#endif
index 152af86ece14db73e206f5e2d39fc3d863a9a1cd..cfef5f3e11d0c2f92ce0057d835934df755810f7 100644 (file)
@@ -729,7 +729,7 @@ void TcpStreamTracker::finalize_held_packet(Packet* cp)
             if ( cp->active->packet_retry_requested() )
             {
                 tcpStats.held_packet_retries++;
-                Analyzer::get_local_analyzer()->add_to_retry_queue(msg);
+                Analyzer::get_local_analyzer()->add_to_retry_queue(msg, cp->flow);
             }
             else
             {