Stream reassembly memcap is regulated by the Init and Cleanup
callbacks. If Init fails due to memcap reached, Cleanup had no
way of knowing and it would decrease the memcap even if it hadn't
been increased by Init. This could lead to too much memory use and
memcap counter underflow.
This patch fixes the issue by not calling Cleanup in this case. It's
fair to see a failed Init the responsibility of Init.
The capture threads can receive packets from the flow manager in their
Threadvars::stream_pq packet queue. This mechanism makes sure the packets
the flow manager injects into the engine are processed by the correct
worker thread.
If the capture thread(s) would not receive packets for a long time, the
Threadvars::stream_pq would not be checked and processed. This could
lead to packet pool depletion in the flow manager. It would also lead
to flows not being timed out/logged until either packets started flowing
again or until the engine was shut down.
The scenario is more likely to happen in a test (e.g. replay) but could
also delay logging on low traffic sensors.
If waiting for N packets move the return stack to the main
stack every time we take the return stack lock.
Make sure we consider enough packets when setting the pending pool
flush logic. This should at least make sure to have the 9 packets
the flow manager requires per run.
Match on JA3S hash using ja3s.hash keyword, e.g:
alert tls any any -> any any (msg:"ja3s.hash test";
ja3s.hash; content:"b26c652e0a402a24b5ca2a660e84f9d5"; sid:1;)
Add Ja3SGetString() to return the content of the JA3S string buffer from
the TLS session.
Example:
function init (args)
local needs = {}
needs["protocol"] = "tls"
return needs
end
function setup (args)
filename = SCLogPath() .. "/ja3s_string.log"
file = assert(io.open(filename, "a"))
end
function log (args)
ja3s_string = Ja3SGetString()
if ja3s_string == nil then
return
end
file:write(ja3s_string .. "\n")
file:flush()
end
function deinit (args)
file:close()
end
Add Ja3SGetHash() to return the content of the JA3S hash buffer from
the TLS session.
Example:
function init (args)
local needs = {}
needs["protocol"] = "tls"
return needs
end
function setup (args)
filename = SCLogPath() .. "/ja3s_hash.log"
file = assert(io.open(filename, "a"))
end
function log (args)
ja3s_hash = Ja3SGetHash()
if ja3s_hash == nil then
return
end
file:write(ja3s_hash .. "\n")
file:flush()
end
function deinit (args)
file:close()
end
In the example above, each JA3S hash is logged to a log file.