diff --git a/src/analyzer/protocol/tcp/TCP_Endpoint.cc b/src/analyzer/protocol/tcp/TCP_Endpoint.cc index 904518138b..1389e58bed 100644 --- a/src/analyzer/protocol/tcp/TCP_Endpoint.cc +++ b/src/analyzer/protocol/tcp/TCP_Endpoint.cc @@ -275,9 +275,11 @@ bool TCP_Endpoint::CheckHistory(uint32_t mask, char code) // since if those elicit anything, it should be a RST. // // Thus, at this stage we go ahead and flip the connection. - // We then fix up the history (which will initially be "H^"). + // We then fix up the history (which will initially be "H^") and + // pretend we have actually seen that missing first packet. conn->FlipRoles(); conn->ReplaceHistory("^h"); + tcp_analyzer->SetFirstPacketSeen(true); } if ( ! IsOrig() ) diff --git a/src/packet_analysis/protocol/tcp/TCPSessionAdapter.cc b/src/packet_analysis/protocol/tcp/TCPSessionAdapter.cc index a85545a407..eaf64b9b8e 100644 --- a/src/packet_analysis/protocol/tcp/TCPSessionAdapter.cc +++ b/src/packet_analysis/protocol/tcp/TCPSessionAdapter.cc @@ -787,6 +787,11 @@ void TCPSessionAdapter::SetPartialStatus(analyzer::tcp::TCP_Flags flags, bool is } } +void TCPSessionAdapter::SetFirstPacketSeen(bool is_orig) + { + first_packet_seen |= (is_orig ? ORIG : RESP); + } + void TCPSessionAdapter::UpdateInactiveState(double t, analyzer::tcp::TCP_Endpoint* endpoint, analyzer::tcp::TCP_Endpoint* peer, uint32_t base_seq, uint32_t ack_seq, int len, bool is_orig, @@ -829,6 +834,7 @@ void TCPSessionAdapter::UpdateInactiveState(double t, analyzer::tcp::TCP_Endpoin is_partial = 0; Conn()->FlipRoles(); peer->SetState(analyzer::tcp::TCP_ENDPOINT_ESTABLISHED); + SetFirstPacketSeen(true); } else @@ -913,6 +919,7 @@ void TCPSessionAdapter::UpdateInactiveState(double t, analyzer::tcp::TCP_Endpoin // as partial and instead establish the connection. endpoint->SetState(analyzer::tcp::TCP_ENDPOINT_ESTABLISHED); is_partial = 0; + SetFirstPacketSeen(is_orig); } else diff --git a/src/packet_analysis/protocol/tcp/TCPSessionAdapter.h b/src/packet_analysis/protocol/tcp/TCPSessionAdapter.h index d20b28765b..e14c3eb659 100644 --- a/src/packet_analysis/protocol/tcp/TCPSessionAdapter.h +++ b/src/packet_analysis/protocol/tcp/TCPSessionAdapter.h @@ -80,6 +80,7 @@ public: protected: friend class analyzer::tcp::TCP_ApplicationAnalyzer; + friend class analyzer::tcp::TCP_Endpoint; friend class analyzer::tcp::TCP_Reassembler; friend class analyzer::pia::PIA_TCP; friend class packet_analysis::TCP::TCPAnalyzer; @@ -95,6 +96,7 @@ protected: bool IsReuse(double t, const u_char* pkt) override; void SetPartialStatus(analyzer::tcp::TCP_Flags flags, bool is_orig); + void SetFirstPacketSeen(bool is_orig); // Update the state machine of the TCPs based on the activity. This // includes our pseudo-states such as TCP_ENDPOINT_PARTIAL. diff --git a/testing/btest/Baseline/core.tcp.flip-without-syn/conn.log b/testing/btest/Baseline/core.tcp.flip-without-syn/conn.log new file mode 100644 index 0000000000..d058edc5de --- /dev/null +++ b/testing/btest/Baseline/core.tcp.flip-without-syn/conn.log @@ -0,0 +1,11 @@ +### BTest baseline data generated by btest-diff. Do not edit. Use "btest -U/-u" to update. Requires BTest >= 0.63. +#separator \x09 +#set_separator , +#empty_field (empty) +#unset_field - +#path conn +#open XXXX-XX-XX-XX-XX-XX +#fields ts uid id.orig_h id.orig_p id.resp_h id.resp_p proto service duration orig_bytes resp_bytes conn_state local_orig local_resp missed_bytes history orig_pkts orig_ip_bytes resp_pkts resp_ip_bytes tunnel_parents +#types time string addr port addr port enum string interval count count string bool bool count string count count count count set[string] +XXXXXXXXXX.XXXXXX CHhAvVGS1DHFjwGM9 141.142.228.5 6669 192.150.187.43 80 tcp http 0.141744 136 5007 SF - - 0 ^hADadFf 6 456 7 5371 - +#close XXXX-XX-XX-XX-XX-XX diff --git a/testing/btest/Traces/tcp/http-on-irc-port-missing-syn.pcap b/testing/btest/Traces/tcp/http-on-irc-port-missing-syn.pcap new file mode 100644 index 0000000000..c622ad9192 Binary files /dev/null and b/testing/btest/Traces/tcp/http-on-irc-port-missing-syn.pcap differ diff --git a/testing/btest/core/tcp/flip-without-syn.zeek b/testing/btest/core/tcp/flip-without-syn.zeek new file mode 100644 index 0000000000..992fbbf4d7 --- /dev/null +++ b/testing/btest/core/tcp/flip-without-syn.zeek @@ -0,0 +1,4 @@ +# @TEST-EXEC: zeek -r $TRACES/tcp/http-on-irc-port-missing-syn.pcap %INPUT +# @TEST-EXEC: btest-diff conn.log + +# @TEST-DOC: Regression test for #2191: missing SYN and misleading well-known port. Zeek flips, and DPD still figures out the protocol ok.