mirror of
https://github.com/zeek/zeek.git
synced 2025-10-02 14:48:21 +00:00

* origin/topic/seth/zeek_init: Some more testing fixes. Update docs and tests for bro_(init|done) -> zeek_(init|done) Implement the zeek_init handler.
229 lines
6.6 KiB
Text
229 lines
6.6 KiB
Text
##! Framework for managing Bro's protocol analyzers.
|
|
##!
|
|
##! The analyzer framework allows to dynamically enable or disable analyzers, as
|
|
##! well as to manage the well-known ports which automatically activate a
|
|
##! particular analyzer for new connections.
|
|
##!
|
|
##! Protocol analyzers are identified by unique tags of type
|
|
##! :bro:type:`Analyzer::Tag`, such as :bro:enum:`Analyzer::ANALYZER_HTTP`.
|
|
##! These tags are defined internally by
|
|
##! the analyzers themselves, and documented in their analyzer-specific
|
|
##! description along with the events that they generate.
|
|
|
|
@load base/frameworks/packet-filter/utils
|
|
|
|
module Analyzer;
|
|
|
|
export {
|
|
## If true, all available analyzers are initially disabled at startup.
|
|
## One can then selectively enable them with
|
|
## :bro:id:`Analyzer::enable_analyzer`.
|
|
global disable_all = F &redef;
|
|
|
|
## Enables an analyzer. Once enabled, the analyzer may be used for analysis
|
|
## of future connections as decided by Bro's dynamic protocol detection.
|
|
##
|
|
## tag: The tag of the analyzer to enable.
|
|
##
|
|
## Returns: True if the analyzer was successfully enabled.
|
|
global enable_analyzer: function(tag: Analyzer::Tag) : bool;
|
|
|
|
## Disables an analyzer. Once disabled, the analyzer will not be used
|
|
## further for analysis of future connections.
|
|
##
|
|
## tag: The tag of the analyzer to disable.
|
|
##
|
|
## Returns: True if the analyzer was successfully disabled.
|
|
global disable_analyzer: function(tag: Analyzer::Tag) : bool;
|
|
|
|
## Registers a set of well-known ports for an analyzer. If a future
|
|
## connection on one of these ports is seen, the analyzer will be
|
|
## automatically assigned to parsing it. The function *adds* to all ports
|
|
## already registered, it doesn't replace them.
|
|
##
|
|
## tag: The tag of the analyzer.
|
|
##
|
|
## ports: The set of well-known ports to associate with the analyzer.
|
|
##
|
|
## Returns: True if the ports were successfully registered.
|
|
global register_for_ports: function(tag: Analyzer::Tag, ports: set[port]) : bool;
|
|
|
|
## Registers an individual well-known port for an analyzer. If a future
|
|
## connection on this port is seen, the analyzer will be automatically
|
|
## assigned to parsing it. The function *adds* to all ports already
|
|
## registered, it doesn't replace them.
|
|
##
|
|
## tag: The tag of the analyzer.
|
|
##
|
|
## p: The well-known port to associate with the analyzer.
|
|
##
|
|
## Returns: True if the port was successfully registered.
|
|
global register_for_port: function(tag: Analyzer::Tag, p: port) : bool;
|
|
|
|
## Returns a set of all well-known ports currently registered for a
|
|
## specific analyzer.
|
|
##
|
|
## tag: The tag of the analyzer.
|
|
##
|
|
## Returns: The set of ports.
|
|
global registered_ports: function(tag: Analyzer::Tag) : set[port];
|
|
|
|
## Returns a table of all ports-to-analyzer mappings currently registered.
|
|
##
|
|
## Returns: A table mapping each analyzer to the set of ports
|
|
## registered for it.
|
|
global all_registered_ports: function() : table[Analyzer::Tag] of set[port];
|
|
|
|
## Translates an analyzer type to a string with the analyzer's name.
|
|
##
|
|
## tag: The analyzer tag.
|
|
##
|
|
## Returns: The analyzer name corresponding to the tag.
|
|
global name: function(tag: Analyzer::Tag) : string;
|
|
|
|
## Translates an analyzer's name to a tag enum value.
|
|
##
|
|
## name: The analyzer name.
|
|
##
|
|
## Returns: The analyzer tag corresponding to the name.
|
|
global get_tag: function(name: string): Analyzer::Tag;
|
|
|
|
## Schedules an analyzer for a future connection originating from a
|
|
## given IP address and port.
|
|
##
|
|
## orig: The IP address originating a connection in the future.
|
|
## 0.0.0.0 can be used as a wildcard to match any originator address.
|
|
##
|
|
## resp: The IP address responding to a connection from *orig*.
|
|
##
|
|
## resp_p: The destination port at *resp*.
|
|
##
|
|
## analyzer: The analyzer ID.
|
|
##
|
|
## tout: A timeout interval after which the scheduling request will be
|
|
## discarded if the connection has not yet been seen.
|
|
##
|
|
## Returns: True if successful.
|
|
global schedule_analyzer: function(orig: addr, resp: addr, resp_p: port,
|
|
analyzer: Analyzer::Tag, tout: interval) : bool;
|
|
|
|
## Automatically creates a BPF filter for the specified protocol based
|
|
## on the data supplied for the protocol through the
|
|
## :bro:see:`Analyzer::register_for_ports` function.
|
|
##
|
|
## tag: The analyzer tag.
|
|
##
|
|
## Returns: BPF filter string.
|
|
global analyzer_to_bpf: function(tag: Analyzer::Tag): string;
|
|
|
|
## Create a BPF filter which matches all of the ports defined
|
|
## by the various protocol analysis scripts as "registered ports"
|
|
## for the protocol.
|
|
global get_bpf: function(): string;
|
|
|
|
## A set of analyzers to disable by default at startup. The default set
|
|
## contains legacy analyzers that are no longer supported.
|
|
global disabled_analyzers: set[Analyzer::Tag] = {
|
|
ANALYZER_INTERCONN,
|
|
ANALYZER_STEPPINGSTONE,
|
|
ANALYZER_BACKDOOR,
|
|
ANALYZER_TCPSTATS,
|
|
} &redef;
|
|
}
|
|
|
|
@load base/bif/analyzer.bif
|
|
|
|
global ports: table[Analyzer::Tag] of set[port];
|
|
|
|
event zeek_init() &priority=5
|
|
{
|
|
if ( disable_all )
|
|
__disable_all_analyzers();
|
|
|
|
for ( a in disabled_analyzers )
|
|
disable_analyzer(a);
|
|
}
|
|
|
|
function enable_analyzer(tag: Analyzer::Tag) : bool
|
|
{
|
|
return __enable_analyzer(tag);
|
|
}
|
|
|
|
function disable_analyzer(tag: Analyzer::Tag) : bool
|
|
{
|
|
return __disable_analyzer(tag);
|
|
}
|
|
|
|
function register_for_ports(tag: Analyzer::Tag, ports: set[port]) : bool
|
|
{
|
|
local rc = T;
|
|
|
|
for ( p in ports )
|
|
{
|
|
if ( ! register_for_port(tag, p) )
|
|
rc = F;
|
|
}
|
|
|
|
return rc;
|
|
}
|
|
|
|
function register_for_port(tag: Analyzer::Tag, p: port) : bool
|
|
{
|
|
if ( ! __register_for_port(tag, p) )
|
|
return F;
|
|
|
|
if ( tag !in ports )
|
|
ports[tag] = set();
|
|
|
|
add ports[tag][p];
|
|
return T;
|
|
}
|
|
|
|
function registered_ports(tag: Analyzer::Tag) : set[port]
|
|
{
|
|
return tag in ports ? ports[tag] : set();
|
|
}
|
|
|
|
function all_registered_ports(): table[Analyzer::Tag] of set[port]
|
|
{
|
|
return ports;
|
|
}
|
|
|
|
function name(atype: Analyzer::Tag) : string
|
|
{
|
|
return __name(atype);
|
|
}
|
|
|
|
function get_tag(name: string): Analyzer::Tag
|
|
{
|
|
return __tag(name);
|
|
}
|
|
|
|
function schedule_analyzer(orig: addr, resp: addr, resp_p: port,
|
|
analyzer: Analyzer::Tag, tout: interval) : bool
|
|
{
|
|
return __schedule_analyzer(orig, resp, resp_p, analyzer, tout);
|
|
}
|
|
|
|
function analyzer_to_bpf(tag: Analyzer::Tag): string
|
|
{
|
|
# Return an empty string if an undefined analyzer was given.
|
|
if ( tag !in ports )
|
|
return "";
|
|
|
|
local output = "";
|
|
for ( p in ports[tag] )
|
|
output = PacketFilter::combine_filters(output, "or", PacketFilter::port_to_bpf(p));
|
|
return output;
|
|
}
|
|
|
|
function get_bpf(): string
|
|
{
|
|
local output = "";
|
|
for ( tag in ports )
|
|
{
|
|
output = PacketFilter::combine_filters(output, "or", analyzer_to_bpf(tag));
|
|
}
|
|
return output;
|
|
}
|
|
|