Hopefully the last major script reorganization.

- policy/ renamed to scripts/

- By default BROPATH now contains:
	- scripts/
	- scripts/policy
	- scripts/site

- *Nearly* all tests pass.

- All of scripts/base/ is loaded by main.cc
	- Can be disabled by setting $BRO_NO_BASE_SCRIPTS
	- Scripts in scripts/base/ don't use relative path loading to ease use of BRO_NO_BASE_SCRIPTS (to copy and paste that script).

- The scripts in scripts/base/protocols/ only (or soon will only) do logging and state building.

- The scripts in scripts/base/frameworks/ add functionality without causing any additional overhead.

- All "detection" activity happens through scripts in scripts/policy/.

- Communications framework modified temporarily to need an environment variable to actually enable (ENABLE_COMMUNICATION=1)
	- This is so the communications framework can be loaded as part
	  of the base without causing trouble when it's not needed.
	- This will be removed once a resolution to ticket #540 is reached.
This commit is contained in:
Seth Hall 2011-08-05 23:09:53 -04:00
parent 68171cf179
commit 597a4d6704
257 changed files with 1311 additions and 1225 deletions

View file

@ -176,7 +176,7 @@ include_directories(${CMAKE_CURRENT_BINARY_DIR})
## Recurse on sub-directories
add_subdirectory(src)
add_subdirectory(policy)
add_subdirectory(scripts)
add_subdirectory(doc)
include(CheckOptionalBuildSources)

View file

@ -10,7 +10,7 @@
# BROPATH=`./bro-path-dev` ./src/bro
#
broPolicies=${PROJECT_SOURCE_DIR}/policy:${PROJECT_SOURCE_DIR}/policy/site
broPolicies=${PROJECT_SOURCE_DIR}/scripts:${PROJECT_SOURCE_DIR}/scripts/policy:${PROJECT_SOURCE_DIR}/scripts/site
broGenPolicies=${CMAKE_BINARY_DIR}/src

View file

@ -42,7 +42,7 @@
# is taken as the summary text for a given identifier.
# @load directives are self-documenting
@load frameworks/notice
@load frameworks/software/vulnerable
# "module" statements are self-documenting
module Example;

View file

@ -1 +0,0 @@
@load frameworks/cluster/base

View file

@ -1 +0,0 @@
@load frameworks/communication/base

View file

@ -1 +0,0 @@
@load frameworks/communication/base/main

View file

@ -1 +0,0 @@
@load frameworks/control/base

View file

@ -1,2 +0,0 @@
@load frameworks/control/base/main

View file

@ -1 +0,0 @@
@load frameworks/dpd/base

View file

@ -1 +0,0 @@
@load frameworks/dpd/base/main

View file

@ -1 +0,0 @@
@load frameworks/intel/base

View file

@ -1,3 +0,0 @@
@load frameworks/logging/base
@load frameworks/logging/plugins/ascii

View file

@ -1 +0,0 @@
@load frameworks/metrics/base

View file

@ -1 +0,0 @@
@load frameworks/metrics/base/main

View file

@ -1,5 +0,0 @@
@load ./base
# Load the script to add hostnames to emails by default.
# NOTE: this exposes a memleak in async DNS lookups.
#@load ./extend-email/hostnames

View file

@ -1,131 +0,0 @@
##! A few predefined notice_action_filters.
##! This is completely and utterly not working right now!!!!!
@load ./base
module Notice;
export {
const ignore_tallies_at_shutdown = T &redef;
const notice_once_per_orig_tally_interval = 1hr &redef;
global tallies: table[string] of count &default = 0;
## Reports a specific NoticeType the first time we see it for a source.
## From then on, tally instances per source.
#global notice_once_per_orig: table[Info, addr] of count
# &default=0 &read_expire=5hrs;
global ignore_it: function(nt: Notice::Type): Notice::PolicyItem;
global file_it: function(nt: Notice::Type): Notice::PolicyItem;
global send_email: function(nt: Notice::Type): Notice::PolicyItem;
global send_page: function(nt: Notice::Type): Notice::PolicyItem;
global tally_notice_type: function(nt: Notice::Type): Notice::PolicyItem;
global tally_notice_type_and_ignore: function(nt: Notice::Type): Notice::PolicyItem;
global file_local_bro_notices: function(nt: Notice::Type): Notice::PolicyItem;
global file_if_remote: function(nt: Notice::Type): Notice::PolicyItem;
}
function action2policy_item(nt: Notice::Type, action: Notice::Action): Notice::PolicyItem
{
return [$result=action,
$pred(n: Notice::Info) = { return n$note == nt; },
$priority=5];
}
function ignore_it(nt: Notice::Type): Notice::PolicyItem
{
return action2policy_item(nt, ACTION_IGNORE);
}
function file_it(nt: Notice::Type): Notice::PolicyItem
{
return action2policy_item(nt, ACTION_FILE);
}
function send_email(nt: Notice::Type): Notice::PolicyItem
{
return action2policy_item(nt, ACTION_EMAIL);
}
function send_page_action(nt: Notice::Type): Notice::PolicyItem
{
return action2policy_item(nt, ACTION_PAGE);
}
#function tally_notice(s: string)
# {
# ++tallies[s];
# }
#
#function tally_notice_type(nt: Notice::Type): Notice::PolicyItem
# {
# tally_notice(fmt("%s", n$note));
# return action2policy_item(nt, ACTION_FILE);
# }
#
#function tally_notice_type_and_ignore(nt: Notice::Type): Notice::PolicyItem
# {
# tally_notice(fmt("%s", n$note));
# return action2policy_item(nt, ACTION_IGNORE);
# }
#
#function file_local_bro_notices(nt: Notice::Type): Notice::PolicyItem
# {
# if ( n$src_peer$is_local )
# return action2policy_item(nt, ACTION_FILE);
# else
# return action2policy_item(nt, n$action);
# }
#
#function file_if_remote(nt: Notice::Type): Notice::PolicyItem
# {
# if ( n?$src && ! is_local_addr(n$src) )
# return action2policy_item(nt, ACTION_FILE);
# else
# return action2policy_item(nt, n$action);
# }
#event notice_alarm_per_orig_tally(n: Notice::Info, host: addr)
# {
# local i = notice_once_per_orig[n$note, host];
# if ( i > 1 )
# {
# local msg = fmt("%s seen %d time%s from %s",
# n$note, i, i > 1 ? "s" : "", host);
# NOTICE([$note=Notice_Tally, $msg=msg, $src=host, $n=i]);
# }
# }
#
#function notice_alarm_per_orig(n: Notice::Info, a: Notice::Action): Notice::Action
# {
# local host = n$src;
#
# ++notice_once_per_orig[n$note, host];
#
# if ( notice_once_per_orig[n$note, host] > 1 )
# return ACTION_FILE;
#
# schedule notice_once_per_orig_tally_interval
# { notice_alarm_per_orig_tally(n, host) };
#
# return ACTION_ALARM_ALWAYS;
# }
event bro_done()
{
if ( ignore_tallies_at_shutdown )
return;
for ( s in tallies )
{
local n = tallies[s];
local msg = fmt("%s (%d time%s)", s, n, n > 1 ? "s" : "");
NOTICE([$note=Notice::Tally, $msg=msg, $n=n]);
}
}

View file

@ -1 +0,0 @@
@load frameworks/packet-filter/base

View file

@ -1 +0,0 @@
@load frameworks/packet-filter/base/main

View file

@ -1 +0,0 @@
@load frameworks/reporter/base

View file

@ -1,3 +0,0 @@
@load frameworks/signatures/base
redef signature_files += "frameworks/signatures/detect-windows-shells.sig";

View file

@ -1 +0,0 @@
@load frameworks/software/base

View file

@ -1 +0,0 @@
@load frameworks/software/base/main

View file

@ -1,2 +0,0 @@
@load protocols/conn/base

View file

@ -1,3 +0,0 @@
@load protocols/conn/base/main
@load protocols/conn/base/contents
@load protocols/conn/base/inactivity

View file

@ -1 +0,0 @@
@load protocols/dns/base

View file

@ -1,4 +0,0 @@
@load protocols/dns/base/consts
@load protocols/dns/base/main
@load protocols/dns/base/detect

View file

@ -1,5 +0,0 @@
@load protocols/ftp/utils-commands
@load protocols/ftp/base
@load protocols/ftp/detect
@load protocols/ftp/software
@load protocols/ftp/file-extract

View file

@ -1,4 +0,0 @@
##! This script is the wrapper script for HTTP analysis.
##! :Author: Seth Hall <seth@icir.org> - Inspired by the work of many others.
@load protocols/http/base

View file

@ -1,7 +0,0 @@
@load protocols/http/base/main
@load protocols/http/base/detect-sqli
@load protocols/http/base/detect-intel
@load protocols/http/base/file-ident
@load protocols/http/base/file-hash
@load protocols/http/base/file-extract
@load protocols/http/base/software

View file

@ -1,54 +0,0 @@
##! SQL injection detection in HTTP.
@load frameworks/metrics
@load ./main
module HTTP;
export {
redef enum Notice::Type += {
SQL_Injection_Attacker,
SQL_Injection_Attack,
};
redef enum Metrics::ID += {
SQL_ATTACKER,
SQL_ATTACK_AGAINST,
};
redef enum Tags += {
## Indicator of a URI based SQL injection attack.
URI_SQLI,
## Indicator of client body based SQL injection attack. This is
## typically the body content of a POST request. Not implemented yet!
POST_SQLI,
## Indicator of a cookie based SQL injection attack. Not implemented yet!
COOKIE_SQLI,
};
## This regular expression is used to match URI based SQL injections
const match_sql_injection_uri =
/[\?&][^[:blank:]\|]+?=[\-0-9%]+([[:blank:]]|\/\*.*?\*\/)*['"]?([[:blank:]]|\/\*.*?\*\/|\)?;)+([hH][aA][vV][iI][nN][gG]|[uU][nN][iI][oO][nN]|[eE][xX][eE][cC]|[sS][eE][lL][eE][cC][tT]|[dD][eE][lL][eE][tT][eE]|[dD][rR][oO][pP]|[dD][eE][cC][lL][aA][rR][eE]|[cC][rR][eE][aA][tT][eE]|[iI][nN][sS][eE][rR][tT])[^a-zA-Z&]/
| /[\?&][^[:blank:]\|]+?=[\-0-9%]+([[:blank:]]|\/\*.*?\*\/)*['"]?([[:blank:]]|\/\*.*?\*\/|\)?;)+([xX]?[oO][rR]|[aA][nN][dD])([[:blank:]]|\/\*.*?\*\/)+['"]?[^a-zA-Z&]+?=/
| /[\?&][^[:blank:]]+?=[\-0-9%]*([[:blank:]]|\/\*.*?\*\/)*['"]([[:blank:]]|\/\*.*?\*\/)*(\-|\+|\|\|)([[:blank:]]|\/\*.*?\*\/)*([0-9]|\(?[cC][oO][nN][vV][eE][rR][tT]|[cC][aA][sS][tT])/
| /[\?&][^[:blank:]\|]+?=([[:blank:]]|\/\*.*?\*\/)*['"]([[:blank:]]|\/\*.*?\*\/|;)*([xX]?[oO][rR]|[aA][nN][dD]|[hH][aA][vV][iI][nN][gG]|[uU][nN][iI][oO][nN]|[eE][xX][eE][cC]|[sS][eE][lL][eE][cC][tT]|[dD][eE][lL][eE][tT][eE]|[dD][rR][oO][pP]|[dD][eE][cC][lL][aA][rR][eE]|[cC][rR][eE][aA][tT][eE]|[rR][eE][gG][eE][xX][pP]|[iI][nN][sS][eE][rR][tT]|\()[^a-zA-Z&]/
| /[\?&][^[:blank:]]+?=[^\.]*?([cC][hH][aA][rR]|[aA][sS][cC][iI][iI]|[sS][uU][bB][sS][tT][rR][iI][nN][gG]|[tT][rR][uU][nN][cC][aA][tT][eE]|[vV][eE][rR][sS][iI][oO][nN]|[lL][eE][nN][gG][tT][hH])\(/ &redef;
}
event bro_init()
{
Metrics::add_filter(SQL_ATTACKER, [$break_interval=5mins, $note=SQL_Injection_Attack]);
Metrics::add_filter(SQL_ATTACK_AGAINST, [$break_interval=5mins, $note=SQL_Injection_Attack]);
}
event http_request(c: connection, method: string, original_URI: string,
unescaped_URI: string, version: string) &priority=3
{
if ( match_sql_injection_uri in unescaped_URI )
{
add c$http$tags[URI_SQLI];
Metrics::add_data(SQL_ATTACKER, [$host=c$id$orig_h], 1);
Metrics::add_data(SQL_ATTACK_AGAINST, [$host=c$id$resp_h], 1);
}
}

View file

@ -1,2 +0,0 @@
@load protocols/irc/base
@load protocols/irc/dcc-send

View file

@ -1,4 +0,0 @@
@load protocols/smtp/base
# This should be optional
@load protocols/smtp/detect-suspicious-orig

View file

@ -1,2 +0,0 @@
@load protocols/smtp/base/main
@load protocols/smtp/base/software

View file

@ -1,2 +0,0 @@
@load protocols/ssh/base
@load protocols/ssh/software

View file

@ -1,4 +0,0 @@
@load protocols/ssl/consts
@load protocols/ssl/base
@load protocols/ssl/mozilla-ca-list
@load protocols/ssl/known-certs

View file

@ -1,351 +0,0 @@
##! SSL connections
@load notice
@load ssl-ciphers
@load ssl-errors
module SSL;
redef enum Notice::Type += {
## Blanket X509 error
SSL_X509Violation,
## Session data not consistent with connection
SSL_SessConIncon,
};
redef enum Log::ID += { SSL };
export {
type Tags: enum {
WEAK_CLIENT_CIPHER,
WEAK_SERVER_CIPHER,
WEAK_CIPHER_AGREED
};
type Info: record {
ts: time &log;
id: conn_id &log;
## This is the session ID. It's optional because SSLv2 doesn't have it.
sid: string &log &optional;
# TODO: dga 3/11 The following 2 fields are not yet picked up
#not_valid_before: time &log &optional; ##< certificate valid time constraint
#not_valid_after: time &log &optional; ##< certificate valid time constraint
version: string &log &default="UNKNOWN"; ##< SSL/TLS version number
client_cert: X509 &log &optional; ##< client certificate
server_cert: X509 &log &optional; ##< server certificate
handshake_cipher: string &log &optional; ##< agreed-upon cipher for session/conn.
tags: set[Tags] &log;
};
type SessionInfo: record {
## This tracks the number of times this session has been used.
num_use: count &default=1;
version: string &default=""; # version associated with connection
client_cert: X509 &optional; # client certificate
server_cert: X509 &optional; # server certificate
handshake_cipher: string &default=""; # agreed-upon cipher for session/conn.
};
## Certificates presented by which hosts to record.
## Choices are: LOCAL_HOSTS, REMOTE_HOSTS, ALL_HOSTS, NO_HOSTS
const asset_tracking = default_asset_tracking &redef;
# If set to T, this will split local and remote certs
# into separate files. F merges everything into a single file.
#const split_log_file = F &redef;
# If true, Bro stores the client and server cipher specs and performs
# additional tests. This costs an extra amount of memory (normally
# only for a short time) but enables detecting of non-intersecting
# cipher sets, for example.
const ssl_compare_cipherspecs = T &redef;
# Whether to analyze certificates seen in SSL connections.
const ssl_analyze_certificates = T &redef;
# If we analyze SSL certificates, we can choose to store them.
const ssl_store_certificates = T &redef;
# Path where we dump the certificates into. If it's empty,
# use the current directory.
const ssl_store_cert_path = "certs" &redef;
# If we analyze SSL certificates, we can choose to verify them.
const ssl_verify_certificates = T &redef;
# This is the path where OpenSSL looks after the trusted certificates.
# If empty, the default path will be used.
const x509_trusted_cert_path = "" &redef;
# Whether to store key-material exchanged in the handshaking phase.
const ssl_store_key_material = F &redef;
## The list of all detected X509 certs.
global certs: set[addr, port, string] &create_expire=1day &synchronized;
## Recent TLS session IDs
global recent_sessions: table[string] of SessionInfo &read_expire=1hr;
global log_ssl: event(rec: Info);
## This is the set of SSL/TLS ciphers are are seen as weak to attack.
const weak_ciphers: set[count] = {
SSLv20_CK_RC4_128_EXPORT40_WITH_MD5,
SSLv20_CK_RC2_128_CBC_EXPORT40_WITH_MD5,
SSLv20_CK_DES_64_CBC_WITH_MD5,
TLS_NULL_WITH_NULL_NULL,
TLS_RSA_WITH_NULL_MD5,
TLS_RSA_WITH_NULL_SHA,
TLS_RSA_EXPORT_WITH_RC4_40_MD5,
TLS_RSA_EXPORT_WITH_RC2_CBC_40_MD5,
TLS_RSA_EXPORT_WITH_DES40_CBC_SHA,
TLS_RSA_WITH_DES_CBC_SHA,
TLS_DH_DSS_EXPORT_WITH_DES40_CBC_SHA,
TLS_DH_DSS_WITH_DES_CBC_SHA,
TLS_DH_RSA_EXPORT_WITH_DES40_CBC_SHA,
TLS_DH_RSA_WITH_DES_CBC_SHA,
TLS_DHE_DSS_EXPORT_WITH_DES40_CBC_SHA,
TLS_DHE_DSS_WITH_DES_CBC_SHA,
TLS_DHE_RSA_EXPORT_WITH_DES40_CBC_SHA,
TLS_DHE_RSA_WITH_DES_CBC_SHA,
TLS_DH_ANON_EXPORT_WITH_RC4_40_MD5,
TLS_DH_ANON_WITH_RC4_128_MD5,
TLS_DH_ANON_EXPORT_WITH_DES40_CBC_SHA,
TLS_DH_ANON_WITH_DES_CBC_SHA,
TLS_DH_ANON_WITH_3DES_EDE_CBC_SHA,
} &redef;
const SSLv2 = 0x0002;
const SSLv3 = 0x0300;
const TLSv10 = 0x0301;
const TLSv11 = 0x0302;
const version_strings: table[count] of string = {
[SSLv2] = "SSLv2",
[SSLv3] = "SSLv3",
[TLSv10] = "TLSv10",
[TLSv11] = "TLSv11",
} &default="UNKNOWN";
}
redef record connection += {
ssl: Info &optional;
};
# NOTE: this is a 'local' port format for your site
# --- well-known ports for ssl ---------
redef capture_filters += {
["ssl"] = "tcp port 443",
["nntps"] = "tcp port 563",
["imap4-ssl"] = "tcp port 585",
["sshell"] = "tcp port 614",
["ldaps"] = "tcp port 636",
["ftps-data"] = "tcp port 989",
["ftps"] = "tcp port 990",
["telnets"] = "tcp port 992",
["imaps"] = "tcp port 993",
["ircs"] = "tcp port 994",
["pop3s"] = "tcp port 995"
};
global ssl_ports = {
443/tcp, 563/tcp, 585/tcp, 614/tcp, 636/tcp,
989/tcp, 990/tcp, 992/tcp, 993/tcp, 995/tcp,
};
redef dpd_config += { [ANALYZER_SSL] = [$ports = ssl_ports] };
redef dpd_config += { [ANALYZER_SSL_BINPAC] = [$ports = ssl_ports] };
event bro_init()
{
Log::create_stream(SSL, [$columns=Info, $ev=log_ssl] );
# The event engine will generate a run-time if this fails for
# reasons other than that the directory already exists.
if ( ssl_store_cert_path != "" )
mkdir(ssl_store_cert_path);
}
const x509_ignore_errors: set[int] = {
X509_V_OK,
# X509_V_ERR_UNABLE_TO_VERIFY_LEAF_SIGNATURE
};
const x509_hot_errors: set[int] = {
X509_V_ERR_CRL_SIGNATURE_FAILURE,
X509_V_ERR_CERT_NOT_YET_VALID,
X509_V_ERR_CERT_HAS_EXPIRED,
X509_V_ERR_CERT_REVOKED,
X509_V_ERR_SUBJECT_ISSUER_MISMATCH,
# X509_V_ERR_UNABLE_TO_VERIFY_LEAF_SIGNATURE # for testing
};
@ifdef ( Weird::weird_file )
redef Weird::weird_action += {
[["SSLv2: Unknown CIPHER-SPEC in CLIENT-HELLO!",
"SSLv2: Client has CipherSpecs > MAX_CIPHERSPEC_SIZE",
"unexpected_SSLv3_record",
"SSLv3_data_without_full_handshake"]] = Weird::WEIRD_IGNORE
};
@endif
function set_session(c: connection)
{
local id = c$id;
if ( ! c?$ssl )
{
local info: Info;
info$ts=network_time();
info$id=id;
c$ssl = info;
}
}
function get_session_info(s: SSL_sessionID): SessionInfo
{
local sess_info: SessionInfo;
local index = md5_hash(s);
recent_sessions[index] = sess_info;
return sess_info;
}
event ssl_certificate(c: connection, cert: X509, is_server: bool)
{
set_session(c);
if ( [c$id$resp_h, c$id$resp_p, cert$subject] !in certs )
add certs[c$id$resp_h, c$id$resp_p, cert$subject];
if( is_server )
{
c$ssl$server_cert = cert;
# We have not filled in the field for the master session
# for this connection. Do it now, but only if this is not a
# SSLv2 connection (no session information in that case).
if ( c$ssl$sid in recent_sessions &&
recent_sessions[c$ssl$sid]?$server_cert )
recent_sessions[c$ssl$sid]$server_cert$subject = cert$subject;
}
else
{
c$ssl$client_cert = cert;
}
}
event ssl_conn_attempt(c: connection, version: count, ciphers: cipher_suites_list)
{
set_session(c);
c$ssl$version = version_strings[version];
for ( cs in ciphers )
{
if ( cs in weak_ciphers )
{
add c$ssl$tags[WEAK_CLIENT_CIPHER];
#event ssl_conn_weak(
# fmt("SSL client supports weak cipher: %s (0x%x)",
# ssl_cipher_desc[cs], cs), c);
}
}
}
event ssl_conn_server_reply(c: connection, version: count,
ciphers: cipher_suites_list)
{
set_session(c);
#conn$log$version = version_strings[version];
for ( cs in ciphers )
{
if ( cs in weak_ciphers )
{
add c$ssl$tags[WEAK_SERVER_CIPHER];
}
}
}
event ssl_conn_established(c: connection, version: count, cipher_suite: count) &priority=1
{
set_session(c);
c$ssl$version = version_strings[version];
if ( cipher_suite in weak_ciphers )
add c$ssl$tags[WEAK_CIPHER_AGREED];
# log the connection
Log::write(SSL, c$ssl);
}
event process_X509_extensions(c: connection, ex: X509_extension)
{
set_session(c);
#local msg = fmt( "%.6f X.509 extensions: ", network_time() );
#for ( i in ex )
# msg = fmt("%s, %s", msg, ex[i]);
}
event ssl_session_insertion(c: connection, id: SSL_sessionID)
{
set_session(c);
local cid = c$id;
c$ssl$sid=md5_hash(id);
# This will create a new session if one doesn't already exist.
local session = get_session_info(id);
session$version=c$ssl$version;
if ( c$ssl?$client_cert ) session$client_cert=c$ssl$client_cert;
if ( c$ssl?$server_cert ) session$server_cert=c$ssl$server_cert;
if ( c$ssl?$handshake_cipher )session$handshake_cipher=c$ssl$handshake_cipher;
}
event ssl_conn_reused(c: connection, session_id: SSL_sessionID)
{
set_session(c);
# We cannot track sessions with SSLv2.
if ( c$ssl$version == version_strings[SSLv2] )
return;
local session = get_session_info(session_id);
++session$num_use;
# At this point, the connection values have been set. We can then
# compare session and connection values with some confidence.
if ( session$version != c$ssl$version ||
session$handshake_cipher != c$ssl$handshake_cipher )
{
NOTICE([$note=SSL_SessConIncon, $conn=c, $msg="session violation"]);
}
}
event ssl_X509_error(c: connection, err: int, err_string: string)
{
if ( err in x509_ignore_errors )
return;
set_session(c);
local error =
err in x509_errors ? x509_errors[err] : "unknown X.509 error";
local severity = "warning";
if ( err in x509_hot_errors )
{
NOTICE([$note=SSL_X509Violation, $conn=c, $msg=error]);
severity = "error";
}
}

View file

@ -1,2 +0,0 @@
@load protocols/syslog/consts
@load protocols/syslog/base

View file

@ -1,32 +0,0 @@
##! Local site policy. Customize as appropriate.
# DPD should typically be loaded. It enables the subsystem for detecting
# protocols on non-standard ports and attaching the appropriate analyzer.
@load frameworks/dpd
# Load some of the commonly used frameworks.
@load frameworks/notice
@load frameworks/signatures
@load frameworks/metrics
@load frameworks/intel
@load frameworks/software
@load frameworks/reporter
# Load a few extra scripts that aren't loaded by default.
@load frameworks/packet-filter/netstats
@load misc/loaded-scripts
# Load most of the protocol analysis scripts.
@load protocols/conn
@load protocols/dns
@load protocols/ftp
@load protocols/http
@load protocols/irc
@load protocols/mime
@load protocols/smtp
@load protocols/ssh
@load protocols/ssl
@load protocols/syslog
# Apply the default tuning scripts for common tuning settings.
@load tuning/defaults

View file

@ -1,113 +0,0 @@
# This file loads ALL policy scripts that are part of the Bro distribution.
#
# This is rarely makes sense, and is for testing only.
#
# Note that we have unit test that makes sure that all policy files shipped are
# actually loaded here. If we have files that are part of the distribution yet
# can't be loaded here, these must still be listed here with their load command
# commented out.
@load all.bro
# @load test-all.bro
@load tuning/__load__.bro
@load tuning/defaults/__load__.bro
@load tuning/defaults/packet-fragments.bro
@load tuning/defaults/remove-high-volume-notices.bro
@load tuning/track-all-assets.bro
@load utils/addrs.bro
@load utils/conn-ids.bro
@load utils/directions-and-hosts.bro
@load utils/files.bro
@load utils/numbers.bro
@load utils/paths.bro
@load utils/pattern.bro
@load utils/strings.bro
@load utils/thresholds.bro
# @load frameworks/communication/__load__.bro
# @load frameworks/communication/base.bro
# @load frameworks/communication/listen-clear.bro
# @load frameworks/communication/listen-ssl.bro
@load frameworks/dpd/__load__.bro
@load frameworks/dpd/base/main.bro
@load frameworks/dpd/packet-segment-logging.bro
@load frameworks/intel/__load__.bro
@load frameworks/intel/base.bro
@load frameworks/logging/__load__.bro
@load frameworks/logging/base.bro
@load frameworks/logging/plugins/ascii.bro
@load frameworks/metrics/__load__.bro
@load frameworks/metrics/base/main.bro
@load frameworks/notice/__load__.bro
# @load frameworks/notice/action-filters.bro
# @load frameworks/notice/base.bro
# @load frameworks/notice/weird.bro
@load frameworks/packet-filter/__load__.bro
@load frameworks/packet-filter/netstats.bro
@load frameworks/signatures/__load__.bro
@load frameworks/signatures/base.bro
@load frameworks/software/__load__.bro
@load frameworks/software/base/main.bro
@load frameworks/software/vulnerable.bro
# @load hot.conn.bro
@load integration/barnyard2/__load__.bro
@load integration/barnyard2/base.bro
@load integration/barnyard2/event.bro
@load integration/barnyard2/types.bro
@load protocols/conn/__load__.bro
@load protocols/conn/base/main.bro
@load protocols/conn/base/contents.bro
@load protocols/conn/base/inactivity.bro
@load protocols/conn/known-hosts.bro
@load protocols/conn/known-services.bro
@load protocols/dns/__load__.bro
@load protocols/dns/auth-addl.bro
@load protocols/dns/base/main.bro
@load protocols/dns/base/consts.bro
@load protocols/dns/base/detect.bro
@load protocols/ftp/__load__.bro
@load protocols/ftp/base.bro
@load protocols/ftp/detect.bro
@load protocols/ftp/file-extract.bro
@load protocols/ftp/software.bro
@load protocols/ftp/utils-commands.bro
@load protocols/http/__load__.bro
@load protocols/http/base/main.bro
@load protocols/http/base/detect-intel.bro
@load protocols/http/base/detect-sqli.bro
@load protocols/http/base/file-extract.bro
@load protocols/http/base/file-hash.bro
@load protocols/http/base/file-ident.bro
@load protocols/http/base/software.bro
@load protocols/http/base/utils.bro
@load protocols/http/detect-MHR.bro
@load protocols/http/detect-webapps.bro
@load protocols/http/headers.bro
#@load protocols/http/partial-content.bro
@load protocols/http/var-extraction-cookies.bro
@load protocols/http/var-extraction-uri.bro
@load protocols/irc/__load__.bro
@load protocols/irc/base.bro
@load protocols/irc/dcc-send.bro
@load protocols/mime/__load__.bro
@load protocols/mime/base.bro
@load protocols/mime/file-extract.bro
@load protocols/mime/file-hash.bro
@load protocols/mime/file-ident.bro
@load protocols/smtp/__load__.bro
@load protocols/smtp/base/main.bro
@load protocols/smtp/base/software.bro
@load protocols/smtp/detect-suspicious-orig.bro
@load protocols/ssh/__load__.bro
@load protocols/ssh/base.bro
@load protocols/ssh/software.bro
@load protocols/ssl/__load__.bro
@load protocols/ssl/base.bro
@load protocols/ssl/consts.bro
@load protocols/ssl/known-certs.bro
@load protocols/ssl/mozilla-ca-list.bro
# @load protocols/ssl/ssl-old.bro
@load protocols/syslog/__load__.bro
@load protocols/syslog/base.bro
@load protocols/syslog/consts.bro
@load protocols/rpc/base.bro
@load site/local

View file

@ -1,2 +0,0 @@
@load ./remove-high-volume-notices
@load ./packet-fragments

View file

@ -1,7 +1,6 @@
include(InstallPackageConfigFile)
install(DIRECTORY ./ DESTINATION ${POLICYDIR} FILES_MATCHING
PATTERN "summaries" EXCLUDE
PATTERN "all.bro" EXCLUDE
PATTERN "site/local.bro" EXCLUDE
PATTERN "bro.init"

View file

@ -1,15 +1,15 @@
##! This script only aims at loading all of the base analysis scripts.
@load protocols/conn
@load protocols/dns
@load protocols/ftp
@load protocols/http
@load protocols/irc
@load protocols/mime
@load protocols/smtp
@load protocols/ssh
#@load protocols/conn
#@load protocols/dns
#@load protocols/ftp
#@load protocols/http
#@load protocols/irc
#@load protocols/mime
#@load protocols/smtp
#@load protocols/ssh
@load protocols/ssl
@load protocols/syslog
#@load protocols/syslog
@load frameworks/metrics
@load frameworks/notice

44
scripts/base/all.bro Normal file
View file

@ -0,0 +1,44 @@
##! This script loads everything in the base/ script directory. If you want
##! to run Bro without all of these scripts loaded by default, you can define
##! the BRO_NO_BASE_SCRIPTS environment variable to any value. You can also
##! copy the "@load" lines from this script to your own script to load only
##! the scripts that you actually want.
@if ( getenv("BRO_NO_BASE_SCRIPTS") == "" )
@load base/utils/site
@load base/utils/addrs
@load base/utils/conn-ids
@load base/utils/directions-and-hosts
@load base/utils/files
@load base/utils/numbers
@load base/utils/paths
@load base/utils/patterns
@load base/utils/strings
@load base/utils/thresholds
# This has some weird interplay between types and BiFs so it's loaded in bro.init
#@load base/frameworks/logging
@load base/frameworks/notice
@load base/frameworks/dpd
@load base/frameworks/signatures
@load base/frameworks/packet-filter
@load base/frameworks/software
@load base/frameworks/intel
@load base/frameworks/metrics
@load base/frameworks/communication
@load base/frameworks/control
@load base/frameworks/cluster
@load base/frameworks/reporter
@load base/protocols/conn
@load base/protocols/dns
@load base/protocols/ftp
@load base/protocols/http
@load base/protocols/irc
@load base/protocols/smtp
@load base/protocols/ssh
@load base/protocols/ssl
@load base/protocols/syslog
@endif

View file

@ -343,7 +343,7 @@ function add_signature_file(sold: string, snew: string): string
}
global signature_files = "" &add_func = add_signature_file;
const passive_fingerprint_file = "signatures/p0f.fp" &redef;
const passive_fingerprint_file = "base/misc/p0f.fp" &redef;
# TODO: testing to see if I can remove these without causing problems.
#const ftp = 21/tcp;
@ -1483,11 +1483,6 @@ const skip_http_data = F &redef;
# UDP tunnels. See also: udp_tunnel_port, policy/udp-tunnel.bro.
const parse_udp_tunnels = F &redef;
# Load the site utilities.
@load utils/site
# Load the logging framework.
@load frameworks/logging
# Load the packet filtering framework.
@load frameworks/packet-filter
# Load the logging framework here because it uses fairly deep integration with
# BiFs and script-land defined types.
@load base/frameworks/logging

View file

@ -1,5 +1,5 @@
# Load the core cluster support.
@load frameworks/cluster/base/main
@load ./main
@if ( Cluster::node != "" )
@ -9,10 +9,6 @@ redef peer_description = Cluster::node;
# Add a cluster prefix.
@prefixes += cluster
# Only load the communication framework if it really looks like someone is
# trying to start up a cluster node.
@load frameworks/communication
# Make this a controllable node since all cluster nodes are inherently
# controllable.
@load frameworks/control/controllee
@ -25,7 +21,7 @@ redef peer_description = Cluster::node;
@if ( Cluster::node in Cluster::nodes )
@load frameworks/cluster/base/setup-connections
@load ./setup-connections
# Don't start the listening process until we're a bit more sure that the
# cluster framework is actually being enabled.
@ -35,15 +31,15 @@ redef peer_description = Cluster::node;
redef Communication::listen_port_clear = Cluster::nodes[Cluster::node]$p;
@if ( Cluster::nodes[Cluster::node]$node_type == Cluster::MANAGER )
@load frameworks/cluster/base/node/manager
@load ./nodes/manager
@endif
@if ( Cluster::nodes[Cluster::node]$node_type == Cluster::PROXY )
@load frameworks/cluster/base/node/proxy
@load ./nodes/proxy
@endif
@if ( Cluster::nodes[Cluster::node]$node_type == Cluster::WORKER )
@load frameworks/cluster/base/node/worker
@load ./nodes/worker
@endif
@endif

View file

@ -1,7 +1,3 @@
@load utils/numbers
@load frameworks/notice
@load frameworks/control
module Cluster;
@ -60,6 +56,7 @@ export {
event bro_init()
{
# If a node is given, but it's an unknown name we need to fail.
if ( node != "" && node !in nodes )
{
local msg = "You didn't supply a valid node in the Cluster::nodes configuration.";

View file

@ -2,7 +2,8 @@
##!
##! The manager is passive (the workers connect to us), and once connected
##! the manager registers for the events on the workers that are needed
##! to get the desired data from the workers.
##! to get the desired data from the workers. This script will be
##! automatically loaded if necessary based on the type of node being started.
##! This is where the cluster manager sets it's specific settings for other
##! frameworks and in the core.

View file

@ -1,6 +1,3 @@
@load ./main
@load frameworks/communication
module Cluster;
event bro_init() &priority=9

View file

@ -0,0 +1,5 @@
# TODO: get rid of this as soon as the Expr.cc hack is changed.
@if ( getenv("ENABLE_COMMUNICATION") != "" )
@load ./main
@endif

View file

@ -1,8 +1,6 @@
##! Connect to remote Bro or Broccoli instances to share state and/or transfer
##! events.
@load frameworks/packet-filter
module Communication;
export {

View file

@ -0,0 +1 @@
@load ./main

View file

@ -6,7 +6,7 @@
##! bro <scripts> frameworks/control/controller Control::host=<host_addr> Control::port=<host_port> Control::cmd=<command> [Control::arg=<arg>]
##!
##! A controllee only needs to load the controllee script in addition
##! to the specific analysis scripts desired. It may also need a noded
##! to the specific analysis scripts desired. It may also need a node
##! configured as a controller node in the communications nodes configuration.
##! bro <scripts> frameworks/control/controllee
##!

View file

@ -0,0 +1 @@
@load ./main

View file

@ -1,12 +1,10 @@
##! Activates port-independent protocol detection and selectively disables
##! analyzers if protocol violations occur.
@load frameworks/signatures
module DPD;
## Add the DPD signatures to the signature framework.
redef signature_files += "frameworks/dpd/base/dpd.sig";
redef signature_files += "base/frameworks/dpd/dpd.sig";
export {
redef enum Log::ID += { DPD };

View file

@ -0,0 +1 @@
@load ./main

View file

@ -20,8 +20,6 @@
# canary
# friend
@load frameworks/notice
module Intel;
export {

View file

@ -0,0 +1,3 @@
@load ./main
@load ./writers/ascii

View file

@ -140,8 +140,6 @@ global filters: table[ID, string] of Filter;
@load logging.bif.bro # Needs Filter and Stream defined.
module Log;
function default_rotation_path_func(info: RotationInfo) : string
{
local date_fmt = rotation_control[info$writer, info$path]$date_fmt;

View file

@ -0,0 +1 @@
@load ./main

View file

@ -1,5 +1,4 @@
@load frameworks/metrics
@load protocols/http
redef enum Metrics::ID += {
HTTP_REQUESTS_BY_STATUS_CODE,

View file

@ -7,3 +7,6 @@
@load ./actions/email_admin
@load ./actions/page
# Load the script to add hostnames to emails by default.
# NOTE: this exposes a memleak in async DNS lookups.
#@load ./extend-email/hostnames

View file

@ -77,9 +77,7 @@ export {
## Textual description for the peer that raised this notice.
peer_descr: string &log &optional;
## The actions that are to be applied to this notice. The set[count]
## is to indicate which :bro:id:`Notice::policy` items
## triggered the action being added to the notice.
## The actions which have been applied to this notice.
actions: set[Notice::Action] &log &optional;
## These are policy items that returned T and applied their action

View file

@ -1,5 +1,3 @@
@load frameworks/notice
@load utils/conn-ids
module Weird;

View file

@ -0,0 +1,2 @@
@load ./main
@load ./netstats

View file

@ -4,8 +4,6 @@
##! open filter and all filters defined in Bro scripts with the
##! :bro:id:`capture_filters` and :bro:id:`restrict_filters` variables.
@load frameworks/notice
module PacketFilter;
export {

View file

@ -1,7 +1,5 @@
##! This script reports on packet loss from the various packet sources.
@load frameworks/notice
module PacketFilter;
export {

View file

@ -0,0 +1 @@
@load ./main

View file

@ -0,0 +1 @@
@load ./main

View file

@ -1,6 +1,4 @@
##! Script level signature support script.
@load frameworks/notice
##! Script level signature support.
module Signatures;
@ -266,7 +264,8 @@ event signature_match(state: signature_state, msg: string, data: string)
orig, vcount, resp);
Log::write(SIGNATURES,
[$note=Multiple_Signatures,
[$ts=network_time(),
$note=Multiple_Signatures,
$src_addr=orig,
$dst_addr=resp, $sig_id=sig_id, $sig_count=vcount,
$event_msg=fmt("%s different signatures triggered", vcount),

View file

@ -0,0 +1 @@
@load ./main

View file

@ -4,20 +4,9 @@
##! that they analyze. The entry point for providing new software detections
##! to this framework is through the :bro:id:`Software::found` function.
@load frameworks/notice
@load utils/directions-and-hosts
@load utils/numbers
module Software;
export {
redef enum Notice::Type += {
## For certain softwares, a version changing may matter. In that case,
## this notice will be generated. Software that matters if the version
## changes can be configured with the
## :bro:id:`Software::interesting_version_changes` variable.
Software_Version_Change,
};
redef enum Log::ID += { SOFTWARE };
@ -58,7 +47,8 @@ export {
## default, only software that is "interesting" due to a change
## in version or it being currently unknown is sent to the
## logging framework. This can be set to T to force the record
## to be sent to the logging framework.
## to be sent to the logging framework if some amount of this tracking
## needs to happen in a specific way to the software.
force_log: bool &default=F;
};
@ -66,17 +56,6 @@ export {
## Choices are: LOCAL_HOSTS, REMOTE_HOSTS, ALL_HOSTS, NO_HOSTS
const asset_tracking = LOCAL_HOSTS &redef;
## Some software is more interesting when the version changes and this
## a set of all software that should raise a notice when a different
## version is seen on a host.
const interesting_version_changes: set[string] = {
"SSH"
} &redef;
## Some software is more interesting when the version changes and this
## a set of all software that should raise a notice when a different
## version is seen on a host.
const interesting_type_changes: set[string] = set();
## Other scripts should call this function when they detect software.
## unparsed_version: This is the full string from which the
@ -384,7 +363,8 @@ event software_register(id: conn_id, info: Info)
tracked[info$host] = table();
local ts = tracked[info$host];
# Software already registered for this host?
# Software already registered for this host? We don't want to endlessly
# log the same thing.
if ( info$name in ts )
{
local old = ts[info$name];
@ -394,17 +374,6 @@ event software_register(id: conn_id, info: Info)
# But if the $force_log value is set then we'll continue.
if ( ! info$force_log && cmp_versions(old$version, info$version) == 0 )
return;
# Is it a potentially interesting version change?
if ( info$name in interesting_version_changes )
{
local msg = fmt("%.6f %s switched from %s to %s (%s)",
network_time(), software_endpoint_name(id, info$host),
software_fmt_version(old$version),
software_fmt(info), info$software_type);
NOTICE([$note=Software_Version_Change, $id=id,
$msg=msg, $sub=software_fmt(info)]);
}
}
Log::write(SOFTWARE, info);

View file

@ -0,0 +1,3 @@
@load ./main
@load ./contents
@load ./inactivity

View file

@ -8,8 +8,6 @@
##! This script does not work well in a cluster context unless it has a
##! remotely mounted disk to write the content files to.
@load utils/files
module Conn;
export {

View file

@ -77,7 +77,7 @@ redef record connection += {
conn: Info &optional;
};
event bro_init()
event bro_init() &priority=5
{
Log::create_stream(CONN, [$columns=Info, $ev=log_conn]);
}

View file

@ -0,0 +1,2 @@
@load ./consts
@load ./main

View file

@ -1,6 +1,4 @@
@load ./consts
module DNS;
export {

View file

@ -0,0 +1,3 @@
@load ./utils-commands
@load ./main
@load ./file-extract

View file

@ -1,9 +1,5 @@
##! File extraction for FTP.
@load protocols/ftp
@load utils/conn-ids
@load utils/files
module FTP;
export {

View file

@ -7,10 +7,6 @@
##!
##! * Handle encrypted sessions correctly (get an example?)
@load utils/paths
@load utils/numbers
@load ./utils-commands
module FTP;
export {
@ -93,7 +89,7 @@ redef dpd_config += { [ANALYZER_FTP] = [$ports = ports] };
# Establish the variable for tracking expected connections.
global ftp_data_expected: table[addr, port] of ExpectedConn &create_expire=5mins;
event bro_init()
event bro_init() &priority=5
{
Log::create_stream(FTP, [$columns=Info, $ev=log_ftp]);
}

View file

@ -0,0 +1,5 @@
@load ./main
@load ./utils
@load ./file-ident
@load ./file-hash
@load ./file-extract

View file

@ -1,9 +1,6 @@
##! Extracts the items from HTTP traffic, one per file. At this time only
##! the message body from the server can be extracted with this script.
@load protocols/http
@load utils/files
module HTTP;
export {

View file

@ -1,9 +1,5 @@
##! Calculate hashes for HTTP body transfers.
@load ./main
@load ./utils
@load ./file-ident
module HTTP;
export {

View file

@ -1,12 +1,8 @@
##! This script is involved in the identification of file types in HTTP
##! response bodies.
@load ./main
@load ./utils
@load frameworks/notice
@load frameworks/signatures
redef signature_files += "protocols/http/base/file-ident.sig";
# Add the magic number signatures to the core signature set.
redef signature_files += "base/protocols/http/file-ident.sig";
# Ignore the signatures used to match files
redef Signatures::ignored_ids += /^matchfile-/;

Some files were not shown because too many files have changed in this diff Show more