]> git.ipfire.org Git - thirdparty/snort3.git/commitdiff
Merge pull request #2411 in SNORT/snort3 from ~KBHANDAN/snort3:cant_drop_keep_flow...
authorNaveen Gujje (ngujje) <ngujje@cisco.com>
Wed, 28 Oct 2020 05:24:57 +0000 (05:24 +0000)
committerNaveen Gujje (ngujje) <ngujje@cisco.com>
Wed, 28 Oct 2020 05:24:57 +0000 (05:24 +0000)
Squashed commit of the following:

commit 6e55f9f908a913e223d29a5dc7c6722a15927437
Author: Kaushal Bhandankar <kbhandan@cisco.com>
Date:   Wed Aug 19 15:09:58 2020 -0400

    flow: do not remove the flow during pruning/reload during IPS event with block action

15 files changed:
src/detection/detection_engine.cc
src/flow/flow.cc
src/flow/flow.h
src/flow/flow_cache.cc
src/flow/flow_cache.h
src/flow/session.h
src/flow/test/flow_cache_test.cc
src/flow/test/flow_control_test.cc
src/network_inspectors/packet_tracer/packet_tracer.h
src/packet_io/active.cc
src/packet_io/active.h
src/stream/stream.cc
src/stream/tcp/tcp_ha.cc
src/stream/tcp/tcp_session.cc
src/stream/tcp/tcp_stream_session.h

index 95ded1d8727663f89a96e97cbaa3385353de0859..0a4a0c9da1c6731fd1e03a39b3f672561a671526 100644 (file)
@@ -218,7 +218,15 @@ void DetectionEngine::finish_inspect(Packet* p, bool inspected)
     log_events(p);
 
     if ( p->active )
+    {
+        if ( p->active->session_was_blocked() and ( p->active->keep_pruned_flow() or
+            ( p->active->keep_timedout_flow() and ( p->is_tcp() or p->pseudo_type == PSEUDO_PKT_TCP ) ) ) )
+        {
+            p->flow->ssn_state.session_flags |= SSNFLAG_KEEP_FLOW;
+        }
+
         p->active->apply_delayed_action(p);
+    }
 
     p->context->post_detection();
 
index 16810e6f6ae096222e4adeada675545f7c4d6de9..a3d724e207a0d7715adfe628e8a271ce8e5d3a3f 100644 (file)
@@ -141,6 +141,28 @@ inline void Flow::clean()
     filtering_state.clear();
 }
 
+void Flow::flush(bool do_cleanup)
+{
+    if ( session )
+    {
+        DetectionEngine::onload(this);
+
+        if ( do_cleanup )
+        {
+            DetectionEngine::set_next_packet();
+            DetectionEngine de;
+
+            session->flush();
+            de.get_context()->clear_callbacks();
+        }
+        else
+            session->clear();
+    }
+
+    if ( was_blocked() )
+        free_flow_data();
+}
+
 void Flow::reset(bool do_cleanup)
 {
     if ( session )
index f6d3d766e503b42136014464c01317112a7f656c..e90ee0686875594b9ee94f7363c63aca7ca9cdb7 100644 (file)
@@ -77,6 +77,7 @@
 #define SSNFLAG_ABORT_SERVER        0x20000000
 
 #define SSNFLAG_HARD_EXPIRATION     0x40000000
+#define SSNFLAG_KEEP_FLOW           0x80000000
 
 #define SSNFLAG_NONE                0x00000000 /* nothing, an MT bag of chips */
 
@@ -93,8 +94,8 @@
 #define STREAM_STATE_MIDSTREAM         0x0040
 #define STREAM_STATE_TIMEDOUT          0x0080
 #define STREAM_STATE_UNREACH           0x0100
-#define STREAM_STATE_CLOSED            0x0800
-#define STREAM_STATE_BLOCK_PENDING     0x1000
+#define STREAM_STATE_CLOSED            0x0200
+#define STREAM_STATE_BLOCK_PENDING     0x0400
 
 class BitOp;
 class Session;
@@ -172,6 +173,7 @@ public:
     void init(PktType);
     void term();
 
+    void flush(bool do_cleanup = true);
     void reset(bool do_cleanup = true);
     void restart(bool dump_flow_data = true);
     void clear(bool dump_flow_data = true);
@@ -230,6 +232,9 @@ public:
     uint32_t clear_session_flags(uint32_t ssn_flags)
     { return ssn_state.session_flags &= ~ssn_flags; }
 
+    uint32_t clear_session_state(uint32_t ssn_state)
+    { return session_state &= ~ssn_state; }
+
     void set_to_client_detection(bool enable);
     void set_to_server_detection(bool enable);
 
index ee29e4335eb83942b1cdea6c788f5ae929cb07d4..e46324a6ec5dc551bf39e007f751b62c05977723 100644 (file)
 
 #include "flow/flow_cache.h"
 
+#include "detection/detection_engine.h"
 #include "hash/hash_defs.h"
 #include "hash/zhash.h"
 #include "helpers/flag_context.h"
 #include "ips_options/ips_flowbits.h"
 #include "memory/memory_cap.h"
 #include "packet_io/active.h"
+#include "packet_tracer/packet_tracer.h"
 #include "time/packet_time.h"
 #include "utils/stats.h"
 
@@ -170,11 +172,22 @@ void FlowCache::remove(Flow* flow)
         memory::MemoryCap::update_deallocations(config.proto[to_utype(flow->key->pkt_type)].cap_weight);
 }
 
-void FlowCache::release(Flow* flow, PruneReason reason, bool do_cleanup)
+bool FlowCache::release(Flow* flow, PruneReason reason, bool do_cleanup)
 {
+    if ( !flow->was_blocked() )
+    {
+        flow->flush(do_cleanup);
+        if ( flow->ssn_state.session_flags & SSNFLAG_KEEP_FLOW )
+        {
+            flow->ssn_state.session_flags &= ~SSNFLAG_KEEP_FLOW;
+            return false;
+        }
+    }
+
     flow->reset(do_cleanup);
     prune_stats.update(reason);
     remove(flow);
+    return true;
 }
 
 void FlowCache::retire(Flow* flow)
@@ -192,36 +205,43 @@ unsigned FlowCache::prune_stale(uint32_t thetime, const Flow* save_me)
     unsigned pruned = 0;
     auto flow = static_cast<Flow*>(hash_table->lru_first());
 
-    while ( flow and pruned <= cleanup_flows )
     {
-#if 0
-        // FIXIT-RC this loops forever if 1 flow in cache
-        if (flow == save_me)
+        PacketTracerSuspend pt_susp;
+
+        while ( flow and pruned <= cleanup_flows )
         {
-            break;
-            if ( hash_table->get_count() == 1 )
+#if 0
+            // FIXIT-RC this loops forever if 1 flow in cache
+            if (flow == save_me)
+            {
                 break;
+                if ( hash_table->get_count() == 1 )
+                    break;
 
-            hash_table->lru_touch();
-        }
+                hash_table->lru_touch();
+            }
 #else
-        // Reached the current flow. This *should* be the newest flow
-        if ( flow == save_me )
-            break;
+            // Reached the current flow. This *should* be the newest flow
+            if ( flow == save_me )
+                break;
 #endif
-        if ( flow->is_suspended() )
-            break;
+            if ( flow->is_suspended() )
+                break;
 
-        if ( flow->last_data_seen + config.pruning_timeout >= thetime )
-            break;
+            if ( flow->last_data_seen + config.pruning_timeout >= thetime )
+                break;
 
-        flow->ssn_state.session_flags |= SSNFLAG_TIMEDOUT;
-        release(flow, PruneReason::IDLE);
-        ++pruned;
+            flow->ssn_state.session_flags |= SSNFLAG_TIMEDOUT;
+            if ( release(flow, PruneReason::IDLE) )
+                ++pruned;
 
-        flow = static_cast<Flow*>(hash_table->lru_first());
+            flow = static_cast<Flow*>(hash_table->lru_first());
+        }
     }
 
+    if ( PacketTracer::is_active() and pruned )
+        PacketTracer::log("Flow: Pruned %u flows\n", pruned);
+
     return pruned;
 }
 
@@ -235,24 +255,31 @@ unsigned FlowCache::prune_unis(PktType pkt_type)
     unsigned pruned = 0;
     FlowUniList* uni_list;
 
-    if ( pkt_type == PktType::IP )
-        uni_list = uni_ip_flows;
-    else
-        uni_list = uni_flows;
-
-    Flow* flow = uni_list->get_oldest_uni();
-    while ( (uni_list->get_count() > max_uni) && flow && (pruned < cleanup_flows) )
     {
-        Flow* prune_me = flow;
-        flow = uni_list->get_prev(prune_me);
+        PacketTracerSuspend pt_susp;
 
-        if ( prune_me->was_blocked() )
-            continue;
+        if ( pkt_type == PktType::IP )
+            uni_list = uni_ip_flows;
+        else
+            uni_list = uni_flows;
+
+        Flow* flow = uni_list->get_oldest_uni();
+        while ( (uni_list->get_count() > max_uni) && flow && (pruned < cleanup_flows) )
+        {
+            Flow* prune_me = flow;
+            flow = uni_list->get_prev(prune_me);
 
-        release(prune_me, PruneReason::UNI);
-        ++pruned;
+            if ( prune_me->was_blocked() )
+                continue;
+
+            if ( release(prune_me, PruneReason::UNI) )
+                ++pruned;
+        }
     }
 
+    if ( PacketTracer::is_active() and pruned )
+        PacketTracer::log("Flow: Pruned %u flows\n", pruned);
+
     return pruned;
 }
 
@@ -264,44 +291,51 @@ unsigned FlowCache::prune_excess(const Flow* save_me)
     assert(max_cap > 0);
 
     unsigned pruned = 0;
-    unsigned blocks = 0;
 
     // initially skip offloads but if that doesn't work the hash table is iterated from the
     // beginning again. prune offloads at that point.
     unsigned ignore_offloads = hash_table->get_num_nodes();
 
-    while ( hash_table->get_num_nodes() > max_cap and hash_table->get_num_nodes() > blocks )
     {
-        auto flow = static_cast<Flow*>(hash_table->lru_first());
-        assert(flow); // holds true because hash_table->get_count() > 0
+        PacketTracerSuspend pt_susp;
+        unsigned blocks = 0;
 
-        if ( (save_me and flow == save_me) or flow->was_blocked() or
-            (flow->is_suspended() and ignore_offloads) )
+        while ( hash_table->get_num_nodes() > max_cap and hash_table->get_num_nodes() > blocks )
         {
-            // check for non-null save_me above to silence analyzer
-            // "called C++ object pointer is null" here
-            if ( flow->was_blocked() )
-                ++blocks;
-
-            // FIXIT-M we should update last_data_seen upon touch to ensure
-            // the hash_table LRU list remains sorted by time
-            hash_table->lru_touch();
+            auto flow = static_cast<Flow*>(hash_table->lru_first());
+            assert(flow); // holds true because hash_table->get_count() > 0
+
+            if ( (save_me and flow == save_me) or flow->was_blocked() or
+                    (flow->is_suspended() and ignore_offloads) )
+            {
+                // check for non-null save_me above to silence analyzer
+                // "called C++ object pointer is null" here
+                if ( flow->was_blocked() )
+                    ++blocks;
+
+                // FIXIT-M we should update last_data_seen upon touch to ensure
+                // the hash_table LRU list remains sorted by time
+                hash_table->lru_touch();
+            }
+            else
+            {
+                flow->ssn_state.session_flags |= SSNFLAG_PRUNED;
+                if ( release(flow, PruneReason::EXCESS) )
+                    ++pruned;
+            }
+            if ( ignore_offloads > 0 )
+                --ignore_offloads;
         }
-        else
+
+        if (!pruned and hash_table->get_num_nodes() > max_cap)
         {
-            flow->ssn_state.session_flags |= SSNFLAG_PRUNED;
-            release(flow, PruneReason::EXCESS);
+            prune_one(PruneReason::EXCESS, true);
             ++pruned;
         }
-        if ( ignore_offloads > 0 )
-            --ignore_offloads;
     }
 
-    if (!pruned and hash_table->get_num_nodes() > max_cap)
-    {
-        prune_one(PruneReason::EXCESS, true);
-        ++pruned;
-    }
+    if ( PacketTracer::is_active() and pruned )
+        PacketTracer::log("Flow: Pruned %u flows\n", pruned);
 
     return pruned;
 }
@@ -325,38 +359,45 @@ bool FlowCache::prune_one(PruneReason reason, bool do_cleanup)
 unsigned FlowCache::timeout(unsigned num_flows, time_t thetime)
 {
     ActiveSuspendContext act_susp(Active::ASP_TIMEOUT);
+
     unsigned retired = 0;
 
-    auto flow = static_cast<Flow*>(hash_table->lru_current());
+    {
+        PacketTracerSuspend pt_susp;
 
-    if ( !flow )
-        flow = static_cast<Flow*>(hash_table->lru_first());
+        auto flow = static_cast<Flow*>(hash_table->lru_current());
 
-    while ( flow and (retired < num_flows) )
-    {
-        if ( flow->is_hard_expiration() )
-        {
-            if ( flow->expire_time > (uint64_t) thetime )
-                break;
-        }
-        else if ( flow->last_data_seen + config.proto[to_utype(flow->key->pkt_type)].nominal_timeout > thetime )
-            break;
+        if ( !flow )
+            flow = static_cast<Flow*>(hash_table->lru_first());
 
-        if ( HighAvailabilityManager::in_standby(flow) or
-            flow->is_suspended() )
+        while ( flow and (retired < num_flows) )
         {
-            flow = static_cast<Flow*>(hash_table->lru_next());
-            continue;
-        }
+            if ( flow->is_hard_expiration() )
+            {
+                if ( flow->expire_time > (uint64_t) thetime )
+                    break;
+            }
+            else if ( flow->last_data_seen + config.proto[to_utype(flow->key->pkt_type)].nominal_timeout > thetime )
+                break;
 
-        flow->ssn_state.session_flags |= SSNFLAG_TIMEDOUT;
-        release(flow, PruneReason::IDLE);
+            if ( HighAvailabilityManager::in_standby(flow) or
+                    flow->is_suspended() )
+            {
+                flow = static_cast<Flow*>(hash_table->lru_next());
+                continue;
+            }
 
-        ++retired;
+            flow->ssn_state.session_flags |= SSNFLAG_TIMEDOUT;
+            if ( release(flow, PruneReason::IDLE) )
+                ++retired;
 
-        flow = static_cast<Flow*>(hash_table->lru_current());
+            flow = static_cast<Flow*>(hash_table->lru_current());
+        }
     }
 
+    if ( PacketTracer::is_active() and retired )
+        PacketTracer::log("Flow: Timed out %u flows\n", retired);
+
     return retired;
 }
 
@@ -368,7 +409,7 @@ unsigned FlowCache::delete_active_flows(unsigned mode, unsigned num_to_delete, u
         auto flow = static_cast<Flow*>(hash_table->lru_first());
         assert(flow);
         if ( (mode == ALLOWED_FLOWS_ONLY and (flow->was_blocked() || flow->is_suspended()))
-            or (mode == OFFLOADED_FLOWS_TOO and flow->was_blocked()) )
+                or (mode == OFFLOADED_FLOWS_TOO and flow->was_blocked()) )
         {
             hash_table->lru_touch();
             continue;
@@ -404,25 +445,32 @@ unsigned FlowCache::delete_flows(unsigned num_to_delete)
 
     unsigned deleted = 0;
 
-    // delete from the free list first...
-    while ( num_to_delete )
     {
-        Flow* flow = (Flow*)hash_table->pop();
-        if ( !flow )
-            break;
+        PacketTracerSuspend pt_susp;
 
-        delete flow;
-        delete_stats.update(FlowDeleteState::FREELIST);
-        memory::MemoryCap::update_deallocations(sizeof(HashNode) + sizeof(FlowKey));
+        // delete from the free list first...
+        while ( num_to_delete )
+        {
+            Flow* flow = (Flow*)hash_table->pop();
+            if ( !flow )
+                break;
 
-        --flows_allocated;
-        ++deleted;
-        --num_to_delete;
+            delete flow;
+            delete_stats.update(FlowDeleteState::FREELIST);
+            memory::MemoryCap::update_deallocations(sizeof(HashNode) + sizeof(FlowKey));
+
+            --flows_allocated;
+            ++deleted;
+            --num_to_delete;
+        }
+
+        unsigned mode = ALLOWED_FLOWS_ONLY;
+        while ( num_to_delete && mode <= ALL_FLOWS )
+            num_to_delete = delete_active_flows(mode++, num_to_delete, deleted);
     }
 
-    unsigned mode = ALLOWED_FLOWS_ONLY;
-    while ( num_to_delete && mode <= ALL_FLOWS )
-        num_to_delete = delete_active_flows(mode++, num_to_delete, deleted);
+    if ( PacketTracer::is_active() and deleted )
+        PacketTracer::log("Flow: Deleted %u flows\n", deleted);
 
     return deleted;
 }
index f84d1fbcd0504fd60975033643d12c161582df32..750569c98c9c4663f67925052c55c6cf94dea786 100644 (file)
@@ -53,7 +53,7 @@ public:
     snort::Flow* find(const snort::FlowKey*);
     snort::Flow* allocate(const snort::FlowKey*);
 
-    void release(snort::Flow*, PruneReason = PruneReason::NONE, bool do_cleanup = true);
+    bool release(snort::Flow*, PruneReason = PruneReason::NONE, bool do_cleanup = true);
 
     unsigned prune_stale(uint32_t thetime, const snort::Flow* save_me);
     unsigned prune_excess(const snort::Flow* save_me);
index 0fcd598fb20ff1d8ac1f787f5a2713b803b8e827..ac4d478a070b875fac66bf3a32df2a7ff663d9e2 100644 (file)
@@ -59,6 +59,7 @@ public:
         snort::Packet*, uint32_t /*gid*/, uint32_t /*sid*/,
         uint32_t /*event_id*/, uint32_t /*event_second*/) { return 0; }
 
+    virtual void flush() { }
     virtual void flush_client(snort::Packet*) { }
     virtual void flush_server(snort::Packet*) { }
     virtual void flush_talker(snort::Packet*, bool /*final_flush */ = false) { }
index fe5936835b3486d7259485443e885c43fccd42fc..ce16061bea97574b23fcae4ce6db6fdedc6ae666 100644 (file)
@@ -60,6 +60,8 @@ void PacketTracer::log(const char*, ...) { }
 void PacketTracer::open_file() { }
 void PacketTracer::dump_to_daq(Packet*) { }
 void PacketTracer::reset() { }
+void PacketTracer::pause() { }
+void PacketTracer::unpause() { }
 void Active::set_drop_reason(char const*) { }
 Packet::Packet(bool) { }
 Packet::~Packet() { }
@@ -70,6 +72,7 @@ ExpectCache::~ExpectCache() { }
 DetectionEngine::~DetectionEngine() { }
 void Flow::init(PktType) { }
 void Flow::term() { }
+void Flow::flush(bool) { }
 void Flow::reset(bool) { }
 void Flow::free_flow_data() { }
 void set_network_policy(const SnortConfig*, unsigned) { }
index 09cdb7de703e799e202a98a6379fab51e73ba8fb..5515374f1633a254fb8441aa0b6a1a57577cef6d 100644 (file)
@@ -169,7 +169,7 @@ int ExpectCache::add_flow(const Packet*,
     return 1;
 }
 
-void FlowCache::release(Flow*, PruneReason, bool) { }
+bool FlowCache::release(Flow*, PruneReason, bool) { }
 
 TEST_GROUP(stale_flow) { };
 
index 1477e798d2fbf48fe6444e1ba27c643f7128ceb9..6aaf92863cc4d88dc22e6025c5ad3beeaa9fcd69 100644 (file)
@@ -112,6 +112,14 @@ SO_PUBLIC extern THREAD_LOCAL PacketTracer* s_pkt_trace;
 inline bool PacketTracer::is_active()
 { return s_pkt_trace ? s_pkt_trace->active : false; }
 
-}
+struct PacketTracerSuspend
+{
+    PacketTracerSuspend()
+    { PacketTracer::pause(); }
 
+    ~PacketTracerSuspend()
+    { PacketTracer::unpause(); }
+};
+
+}
 #endif
index 0eb6a80857bd6e1cfc59a148699b89cdf6fcca02..de39b0e4b7045bab29b5a5131b9f6685bd79db40 100644 (file)
@@ -549,14 +549,12 @@ void Active::update_status(const Packet* p, bool force)
     {
         update_status_actionable(p);
 
-        if(!active_status)
+        if ( !active_status )
             cant_drop();
     }
-
     else if ( force )
         active_status = AST_FORCE;
-
-    else if ( active_status != AST_FORCE)
+    else if ( active_status != AST_FORCE )
     {
         update_status_actionable(p);
     }
@@ -568,7 +566,7 @@ void Active::daq_update_status(const Packet* p)
     {
         update_status_actionable(p);
 
-        if(!active_status)
+        if ( !active_status )
             cant_drop();
     }
     else if ( active_status != AST_FORCE )
@@ -838,7 +836,7 @@ void Active::map_drop_reason_id(const char* verdict_reason, uint8_t id)
 
 void Active::set_drop_reason(const char* reason)
 {
-    if ( drop_reason == nullptr )
+    if ( !drop_reason and !is_suspended() )
         drop_reason = reason;
 }
 
@@ -853,7 +851,7 @@ int Active::get_drop_reason_id()
 
 void Active::send_reason_to_daq(Packet& p)
 {
-    if ( drop_reason == nullptr )
+    if ( !drop_reason )
         return;
 
     int reason = get_drop_reason_id();
index 20cd1faccd6348e4a5f7e412a2bfa0065af02877..051b17a48cd1af0596d9cd276a925f2065acf717 100644 (file)
@@ -73,6 +73,9 @@ public:
         s_suspend_reason = suspend_reason;
     }
 
+    static bool is_suspended()
+    { return s_suspend; }
+
     static void resume()
     {
         s_suspend = false;
@@ -153,6 +156,12 @@ public:
     bool can_partial_block_session() const
     { return active_status == AST_CANT and s_suspend_reason > ASP_NONE and s_suspend_reason != ASP_TIMEOUT; }
 
+    bool keep_pruned_flow() const
+    { return ( s_suspend_reason == ASP_PRUNE ) or ( s_suspend_reason == ASP_RELOAD ); }
+
+    bool keep_timedout_flow() const
+    { return ( s_suspend_reason == ASP_TIMEOUT ); }
+
     bool packet_retry_requested() const
     { return active_action == ACT_RETRY; }
 
index 90f5781a9cee614d395fa6a4003dde1f53b60f2c..2d106997bdad6b234ed0239b97d1fd9eb37ccfb7 100644 (file)
@@ -225,7 +225,7 @@ void Stream::check_flow_closed(Packet* p)
             if (PacketTracer::is_active())
                 PacketTracer::log("Stream: pending block, drop\n");
         }
-        flow->session_state &= ~STREAM_STATE_BLOCK_PENDING;
+        flow->clear_session_state(STREAM_STATE_BLOCK_PENDING);
     }
 }
 
@@ -621,7 +621,7 @@ static void active_response(Packet* p, Flow* lwssn)
         ++lwssn->response_count;
         lwssn->set_expire(p, delay);
 
-        lwssn->session_state &= ~(STREAM_STATE_DROP_CLIENT|STREAM_STATE_DROP_SERVER);
+        lwssn->clear_session_state(STREAM_STATE_DROP_CLIENT|STREAM_STATE_DROP_SERVER);
     }
 }
 
index 1ad16a654814f5ae0246ee2df745bc3aa16d4bad..edc32c4a9bc3f1a1e44b82c85c39c568f733bbc9 100644 (file)
@@ -50,8 +50,8 @@ void TcpHA::deactivate_session(Flow* flow)
     if ( flow->session )
         ((TcpSession*)(flow->session))->clear_session(true, true, false);
 
-    flow->session_state &= ~( STREAM_STATE_SYN | STREAM_STATE_SYN_ACK |
-            STREAM_STATE_ACK | STREAM_STATE_ESTABLISHED );
+    flow->clear_session_state(STREAM_STATE_SYN | STREAM_STATE_SYN_ACK |
+        STREAM_STATE_ACK | STREAM_STATE_ESTABLISHED);
 
     assert( flow->ha_state );
     flow->clear_session_flags( SSNFLAG_SEEN_CLIENT | SSNFLAG_SEEN_SERVER );
index 3d1a4e0919433e1a709faceca28b238dfba02c15..7d622cf98bfefb216c3c4b86b76a57cdab6e76de 100644 (file)
@@ -911,6 +911,22 @@ void TcpSession::flush_talker(Packet* p, bool final_flush)
         flush_tracker( client, p, PKT_FROM_SERVER, final_flush);
 }
 
+void TcpSession::flush()
+{
+    if ( !tcp_init )
+        return;
+
+    //FIXIT-L Cleanup tcp_init and lws_init as they have some side effect in TcpSession::clear_session
+    lws_init = false;
+    tcp_init = false;
+
+    client.reassembler.flush_queued_segments(flow, true);
+    server.reassembler.flush_queued_segments(flow, true);
+
+    lws_init = true;
+    tcp_init = true;
+}
+
 void TcpSession::set_extra_data(Packet* p, uint32_t xid)
 {
     TcpStreamTracker& st = p->ptrs.ip_api.get_src()->equals(flow->client_ip) ? server : client;
@@ -1099,17 +1115,3 @@ int TcpSession::process(Packet* p)
 
     return process_tcp_packet(tsd, p);
 }
-
-void TcpSession::flush()
-{
-    if ( ( server.reassembler.is_segment_pending_flush() ) ||
-        (client.reassembler.is_segment_pending_flush() ) )
-    {
-       // FIXIT-L flush_queued_segments is basically a noop when the 'clear' parameter
-       //         is passed in as false... review what happens in 2.9.x probably related
-       //         to ssl encryption support
-        server.reassembler.flush_queued_segments(flow, false);
-        client.reassembler.flush_queued_segments(flow, false);
-    }
-}
-
index b9aa98ccd109977eed7c9142a0197bc02bfbcaf5..6ad83b3ff36a361ee774d29398ed67ba7df0462d 100644 (file)
@@ -70,7 +70,6 @@ public:
     virtual void update_perf_base_state(char) = 0;
     virtual void clear_session(
         bool free_flow_data, bool flush_segments, bool restart, snort::Packet* p = nullptr) = 0;
-    virtual void flush() = 0;
     virtual TcpStreamTracker::TcpState get_talker_state(TcpSegmentDescriptor&) = 0;
     virtual TcpStreamTracker::TcpState get_listener_state(TcpSegmentDescriptor&) = 0;
     TcpStreamTracker::TcpState get_peer_state(TcpStreamTracker* me)