-Pending - build 142
+15/03/18 - build 142
+-- apply defaults from parameter tables instead of relying on ctors etc.
-- fix static analysis issues reported by xcode
-- change policy names with a-b form to a_b for consistency
-- make all warnings optional
$my_path/bin/snort -c $my_path/etc/snort/snort.lua -R $my_path/etc/snort/sample.rules \
--pcap-filter \*.pcap --pcap-dir pcaps/ -A alert_fast --max-packet-threads 8
+Additional examples are given in doc/usage.txt.
+
DOCUMENTATION
Take a look at the manual, parts of which are generated by the code so it
+++ /dev/null
--- The following includes information for prioritizing rules
---
--- Each classification includes a shortname, a description, and a default
--- priority for that classification.
---
--- This allows alerts to be classified and prioritized. You can specify
--- what priority each classification has. Any rule can override the default
--- priority for that rule.
---
--- Here are a few example rules:
---
--- alert TCP any any -> any 80 (msg: "EXPLOIT ntpdx overflow";
--- dsize: > 128; classtype:attempted-admin; priority:10;
---
--- alert TCP any any -> any 25 (msg:"SMTP expn root"; flags:A+; \
--- content:"expn root"; nocase; classtype:attempted-recon;)
---
--- The first rule will set its type to "attempted-admin" and override
--- the default priority for that type to 10.
---
--- The second rule set its type to "attempted-recon" and set its
--- priority to the default for that type.
-
-classifications =
-{
- { name = 'not-suspicious', priority = 3,
- text = 'Not Suspicious Traffic' },
-
- { name = 'unknown', priority = 3,
- text = 'Unknown Traffic' },
-
- { name = 'bad-unknown', priority = 2,
- text = 'Potentially Bad Traffic' },
-
- { name = 'attempted-recon', priority = 2,
- text = 'Attempted Information Leak' },
-
- { name = 'successful-recon-limited', priority = 2,
- text = 'Information Leak' },
-
- { name = 'successful-recon-largescale', priority = 2,
- text = 'Large Scale Information Leak' },
-
- { name = 'attempted-dos', priority = 2,
- text = 'Attempted Denial of Service' },
-
- { name = 'successful-dos', priority = 2,
- text = 'Denial of Service' },
-
- { name = 'attempted-user', priority = 1,
- text = 'Attempted User Privilege Gain' },
-
- { name = 'unsuccessful-user', priority = 1,
- text = 'Unsuccessful User Privilege Gain' },
-
- { name = 'successful-user', priority = 1,
- text = 'Successful User Privilege Gain' },
-
- { name = 'attempted-admin', priority = 1,
- text = 'Attempted Administrator Privilege Gain' },
-
- { name = 'successful-admin', priority = 1,
- text = 'Successful Administrator Privilege Gain' },
-
- { name = 'rpc-portmap-decode', priority = 2,
- text = 'Decode of an RPC Query' },
-
- { name = 'shellcode-detect', priority = 1,
- text = 'Executable code was detected' },
-
- { name = 'string-detect', priority = 3,
- text = 'A suspicious string was detected' },
-
- { name = 'suspicious-filename-detect', priority = 2,
- text = 'A suspicious filename was detected' },
-
- { name = 'suspicious-login', priority = 2,
- text = 'An attempted login using a suspicious username was detected' },
-
- { name = 'system-call-detect', priority = 2,
- text = 'A system call was detected' },
-
- { name = 'tcp-connection', priority = 4,
- text = 'A TCP connection was detected' },
-
- { name = 'trojan-activity', priority = 1,
- text = 'A Network Trojan was detected' },
-
- { name = 'unusual-client-port-connection', priority = 2,
- text = 'A client was using an unusual port' },
-
- { name = 'network-scan', priority = 3,
- text = 'Detection of a Network Scan' },
-
- { name = 'denial-of-service', priority = 2,
- text = 'Detection of a Denial of Service Attack' },
-
- { name = 'non-standard-protocol', priority = 2,
- text = 'Detection of a non-standard protocol or event' },
-
- { name = 'protocol-command-decode', priority = 3,
- text = 'Generic Protocol Command Decode' },
-
- { name = 'web-application-activity', priority = 2,
- text = 'access to a potentially vulnerable web application' },
-
- { name = 'web-application-attack', priority = 1,
- text = 'Web Application Attack' },
-
- { name = 'misc-activity', priority = 3,
- text = 'Misc activity' },
-
- { name = 'misc-attack', priority = 2,
- text = 'Misc Attack' },
-
- { name = 'icmp-event', priority = 3,
- text = 'Generic ICMP event' },
-
- { name = 'inappropriate-content', priority = 1,
- text = 'Inappropriate Content was Detected' },
-
- { name = 'policy-violation', priority = 1,
- text = 'Potential Corporate Privacy Violation' },
-
- { name = 'default-login-attempt', priority = 2,
- text = 'Attempt to login by a default username and password' },
-
- { name = 'sdf', priority = 2,
- text = 'Senstive Data' },
-
- { name = 'file-format', priority = 1,
- text = 'Known malicious file or file based exploit' },
-
- { name = 'malware-cnc', priority = 1,
- text = 'Known malware command and control traffic' },
-
- { name = 'client-side-exploit', priority = 1,
- text = 'Known client side exploit attempt' }
-}
-
+++ /dev/null
--- The following defines URLs for the references found in the rules
-
-references =
-{
- { name = 'bugtraq', url = 'http://www.securityfocus.com/bid/' },
- { name = 'cve', url = 'http://cve.mitre.org/cgi-bin/cvename.cgi?name=' },
- { name = 'arachNIDS', url = 'http://www.whitehats.com/info/IDS' },
- { name = 'osvdb', url = 'http://osvdb.org/show/osvdb/' },
-
- -- Note, this one needs a suffix as well.... lets add that in a bit.
- { name = 'McAfee', url = 'http://vil.nai.com/vil/content/v_' },
-
- { name = 'nessus', url = 'http://cgi.nessus.org/plugins/dump.php3?id=' },
- { name = 'url', url = 'http://' },
- { name = 'msb', url = 'http://technet.microsoft.com/en-us/security/bulletin/' }
-}
-
end
dofile(conf_dir .. '/snort_defaults.lua')
-dofile(conf_dir .. '/classification.lua')
-dofile(conf_dir .. '/reference.lua')
---------------------------------------------------------------------------
-- configure modules
}
---------------------------------------------------------------------------
--- default wizard
+-- default http profiles
---------------------------------------------------------------------------
-http_methods = -- build from default_http_methods
-{
- 'GET', 'POST', 'PUT', 'SEARCH', 'MKCOL', 'COPY', 'MOVE', 'LOCK', 'UNLOCK',
- 'NOTIFY', 'POLL', 'BCOPY', 'BDELETE', 'BMOVE', 'LINK', 'UNLINK', 'OPTIONS',
- 'HEAD', 'DELETE', 'TRACE', 'TRACK', 'CONNECT', 'SOURCE', 'SUBSCRIBE',
- 'UNSUBSCRIBE', 'PROPFIND', 'PROPPATCH', 'BPROPFIND', 'BPROPPATCH',
- 'RPC_CONNECT', 'PROXY_SUCCESS', 'BITS_POST', 'CCM_POST', 'SMS_POST',
- 'RPC_IN_DATA', 'RPC_OUT_DATA', 'RPC_ECHO_DATA'
-}
-
http_profile_default =
{
profile_type = 'default',
whitespace_chars ='0x9 0xb 0xc 0xd'
}
+---------------------------------------------------------------------------
+-- default wizard
+---------------------------------------------------------------------------
+
+http_methods = -- build from default_http_methods
+{
+ 'GET', 'POST', 'PUT', 'SEARCH', 'MKCOL', 'COPY', 'MOVE', 'LOCK', 'UNLOCK',
+ 'NOTIFY', 'POLL', 'BCOPY', 'BDELETE', 'BMOVE', 'LINK', 'UNLINK', 'OPTIONS',
+ 'HEAD', 'DELETE', 'TRACE', 'TRACK', 'CONNECT', 'SOURCE', 'SUBSCRIBE',
+ 'UNSUBSCRIBE', 'PROPFIND', 'PROPPATCH', 'BPROPFIND', 'BPROPPATCH',
+ 'RPC_CONNECT', 'PROXY_SUCCESS', 'BITS_POST', 'CCM_POST', 'SMS_POST',
+ 'RPC_IN_DATA', 'RPC_OUT_DATA', 'RPC_ECHO_DATA'
+}
+
ftp_commands = -- build from ftp_default_commands
{
'ABOR', 'ACCT', 'ADAT', 'ALLO', 'APPE', 'AUTH', 'CCC', 'CDUP', 'CEL',
}
}
+---------------------------------------------------------------------------
+-- default references
+---------------------------------------------------------------------------
+
+references =
+{
+ { name = 'bugtraq', url = 'http://www.securityfocus.com/bid/' },
+ { name = 'cve', url = 'http://cve.mitre.org/cgi-bin/cvename.cgi?name=' },
+ { name = 'arachNIDS', url = 'http://www.whitehats.com/info/IDS' },
+ { name = 'osvdb', url = 'http://osvdb.org/show/osvdb/' },
+ { name = 'McAfee', url = 'http://vil.nai.com/vil/content/v_' },
+ { name = 'nessus', url = 'http://cgi.nessus.org/plugins/dump.php3?id=' },
+ { name = 'url', url = 'http://' },
+ { name = 'msb', url = 'http://technet.microsoft.com/en-us/security/bulletin/' }
+}
+
+---------------------------------------------------------------------------
+-- default classifications
+---------------------------------------------------------------------------
+
+classifications =
+{
+ { name = 'not-suspicious', priority = 3,
+ text = 'Not Suspicious Traffic' },
+
+ { name = 'unknown', priority = 3,
+ text = 'Unknown Traffic' },
+
+ { name = 'bad-unknown', priority = 2,
+ text = 'Potentially Bad Traffic' },
+
+ { name = 'attempted-recon', priority = 2,
+ text = 'Attempted Information Leak' },
+
+ { name = 'successful-recon-limited', priority = 2,
+ text = 'Information Leak' },
+
+ { name = 'successful-recon-largescale', priority = 2,
+ text = 'Large Scale Information Leak' },
+
+ { name = 'attempted-dos', priority = 2,
+ text = 'Attempted Denial of Service' },
+
+ { name = 'successful-dos', priority = 2,
+ text = 'Denial of Service' },
+
+ { name = 'attempted-user', priority = 1,
+ text = 'Attempted User Privilege Gain' },
+
+ { name = 'unsuccessful-user', priority = 1,
+ text = 'Unsuccessful User Privilege Gain' },
+
+ { name = 'successful-user', priority = 1,
+ text = 'Successful User Privilege Gain' },
+
+ { name = 'attempted-admin', priority = 1,
+ text = 'Attempted Administrator Privilege Gain' },
+
+ { name = 'successful-admin', priority = 1,
+ text = 'Successful Administrator Privilege Gain' },
+
+ { name = 'rpc-portmap-decode', priority = 2,
+ text = 'Decode of an RPC Query' },
+
+ { name = 'shellcode-detect', priority = 1,
+ text = 'Executable code was detected' },
+
+ { name = 'string-detect', priority = 3,
+ text = 'A suspicious string was detected' },
+
+ { name = 'suspicious-filename-detect', priority = 2,
+ text = 'A suspicious filename was detected' },
+
+ { name = 'suspicious-login', priority = 2,
+ text = 'An attempted login using a suspicious username was detected' },
+
+ { name = 'system-call-detect', priority = 2,
+ text = 'A system call was detected' },
+
+ { name = 'tcp-connection', priority = 4,
+ text = 'A TCP connection was detected' },
+
+ { name = 'trojan-activity', priority = 1,
+ text = 'A Network Trojan was detected' },
+
+ { name = 'unusual-client-port-connection', priority = 2,
+ text = 'A client was using an unusual port' },
+
+ { name = 'network-scan', priority = 3,
+ text = 'Detection of a Network Scan' },
+
+ { name = 'denial-of-service', priority = 2,
+ text = 'Detection of a Denial of Service Attack' },
+
+ { name = 'non-standard-protocol', priority = 2,
+ text = 'Detection of a non-standard protocol or event' },
+
+ { name = 'protocol-command-decode', priority = 3,
+ text = 'Generic Protocol Command Decode' },
+
+ { name = 'web-application-activity', priority = 2,
+ text = 'access to a potentially vulnerable web application' },
+
+ { name = 'web-application-attack', priority = 1,
+ text = 'Web Application Attack' },
+
+ { name = 'misc-activity', priority = 3,
+ text = 'Misc activity' },
+
+ { name = 'misc-attack', priority = 2,
+ text = 'Misc Attack' },
+
+ { name = 'icmp-event', priority = 3,
+ text = 'Generic ICMP event' },
+
+ { name = 'inappropriate-content', priority = 1,
+ text = 'Inappropriate Content was Detected' },
+
+ { name = 'policy-violation', priority = 1,
+ text = 'Potential Corporate Privacy Violation' },
+
+ { name = 'default-login-attempt', priority = 2,
+ text = 'Attempt to login by a default username and password' },
+
+ { name = 'sdf', priority = 2,
+ text = 'Senstive Data' },
+
+ { name = 'file-format', priority = 1,
+ text = 'Known malicious file or file based exploit' },
+
+ { name = 'malware-cnc', priority = 1,
+ text = 'Known malware command and control traffic' },
+
+ { name = 'client-side-exploit', priority = 1,
+ text = 'Known client side exploit attempt' }
+}
+
static const Parameter s_params[] =
{
- { "msg", Parameter::PT_BOOL, nullptr, nullptr,
+ { "msg", Parameter::PT_BOOL, nullptr, "false",
" use rule message in response page" },
{ "page", Parameter::PT_STRING, nullptr, nullptr,
#include <assert.h>
#include <string.h>
+#include <stdlib.h>
#include "utils/dnet_header.h"
#include <string>
return pt2str[type];
}
+bool Parameter::get_bool() const
+{
+ if ( !deflt )
+ return false;
+
+ return ( strchr(deflt, 't') || strchr(deflt, 'T') );
+}
+
+double Parameter::get_number() const
+{
+ if ( !deflt )
+ return 0;
+
+ return strtod(deflt, nullptr);
+}
+
+const char* Parameter::get_string() const
+{
+ return deflt ? deflt : "";
+}
+
const Parameter* Parameter::find(const Parameter* p, const char* s)
{
while ( p->name )
bool is_quoted() const
{ return ( type > PT_PORT ); }
+ bool get_bool() const;
+ double get_number() const;
+ const char* get_string() const;
+
static const Parameter* find(const Parameter*, const char*);
};
{ "bytes", Parameter::PT_INT, "1:", nullptr,
"Number of base64 encoded bytes to decode." },
- { "offset", Parameter::PT_INT, "0:", nullptr,
+ { "offset", Parameter::PT_INT, "0:", "0",
"Bytes past start of buffer to start decoding." },
{ "relative", Parameter::PT_IMPLIED, nullptr, nullptr,
{ "relative", Parameter::PT_IMPLIED, nullptr, nullptr,
"offset from cursor instead of start of buffer" },
- { "multiplier", Parameter::PT_INT, "1:65535", nullptr,
+ { "multiplier", Parameter::PT_INT, "1:65535", "1",
"scale extracted value by given amount" },
- { "align", Parameter::PT_INT, "0:4", nullptr,
+ { "align", Parameter::PT_INT, "0:4", "0",
"round the number of converted bytes up to the next 2- or 4-byte boundary" },
{ "big", Parameter::PT_IMPLIED, nullptr, nullptr,
{ "from_beginning", Parameter::PT_IMPLIED, nullptr, nullptr,
"jump from start of buffer instead of cursor" },
- { "multiplier", Parameter::PT_INT, "1:65535", nullptr,
+ { "multiplier", Parameter::PT_INT, "1:65535", "1",
"scale extracted value by given amount" },
- { "align", Parameter::PT_INT, "0:4", nullptr,
+ { "align", Parameter::PT_INT, "0:4", "0",
"round the number of converted bytes up to the next 2- or 4-byte boundary" },
- { "post_offset", Parameter::PT_INT, "-65535:65535", nullptr,
+ { "post_offset", Parameter::PT_INT, "-65535:65535", "0",
"also skip forward or backwards (positive of negative value) this number of bytes" },
{ "big", Parameter::PT_IMPLIED, nullptr, nullptr,
{ "fast_pattern", Parameter::PT_IMPLIED, nullptr, nullptr,
"use this content in the fast pattern matcher instead of the content selected by default" },
- { "fast_pattern_offset", Parameter::PT_INT, nullptr, nullptr,
+ { "fast_pattern_offset", Parameter::PT_INT, "0:", "0",
"number of leading characters of this content the fast pattern matcher should exclude" },
{ "fast_pattern_length", Parameter::PT_INT, "1:", nullptr,
static const Parameter ex_params[] =
{
- { "file", Parameter::PT_BOOL, nullptr, "stdout",
+ { "file", Parameter::PT_BOOL, nullptr, "false",
"output to " F_NAME " instead of stdout" },
{ "msg", Parameter::PT_BOOL, nullptr, "false",
// //
//-----------------------------------------------//
-#define BUILD "141"
+#define BUILD "142"
static const Parameter profile_rule_params[] =
{
{ "count", Parameter::PT_INT, "-1:", "-1",
- "print results to given level (-1 = all, 0 = off?)" },
+ "print results to given level (-1 = all, 0 = off)" },
{ "sort", Parameter::PT_ENUM,
"checks | avg_ticks | total_ticks | matches | no_matches | "
static const Parameter profile_module_params[] =
{
{ "count", Parameter::PT_INT, "-1:", "-1",
- "print results to given level (-1 = all, 0 = off?)" },
+ "print results to given level (-1 = all, 0 = off)" },
{ "sort", Parameter::PT_ENUM,
"checks | avg_ticks | total_ticks", "avg_ticks",
{ "-S", Parameter::PT_STRING, nullptr, nullptr,
"<n=v> set rules file variable n equal to value v" },
- { "-s", Parameter::PT_INT, "68:65535", nullptr,
+ { "-s", Parameter::PT_INT, "68:65535", "1514",
"<snap> (same as --snaplen)" },
{ "-T", Parameter::PT_IMPLIED, nullptr, nullptr,
{ "-y", Parameter::PT_IMPLIED, nullptr, nullptr,
"include year in timestamp in the alert and log files" },
- { "-z", Parameter::PT_INT, "1:", nullptr,
- "<count> maximum number of packet threads (same as --max-packet-threads)" },
+ { "-z", Parameter::PT_INT, "0:", "1",
+ "<count> maximum number of packet threads (same as --max-packet-threads)\n"
+ " 0 gets the number of CPU cores reported by the system" },
{ "--alert-before-pass", Parameter::PT_IMPLIED, nullptr, nullptr,
"process alert, drop, sdrop, or reject before pass; "
{ "--markup", Parameter::PT_IMPLIED, nullptr, nullptr,
"output help in asciidoc compatible format" },
- { "--max-packet-threads", Parameter::PT_INT, "0:", nullptr,
- "<count> configure maximum number of packet threads (same as -z)" },
+ { "--max-packet-threads", Parameter::PT_INT, "0:", "1",
+ "<count> configure maximum number of packet threads (same as -z)\n"
+ " 0 gets the number of CPU cores reported by the system" },
{ "--nostamps", Parameter::PT_IMPLIED, nullptr, nullptr,
"don't include timestamps in log file names" },
{ "--skip", Parameter::PT_INT, "0:", nullptr,
"<n> skip 1st n packets", },
- { "--snaplen", Parameter::PT_INT, "68:65535", nullptr,
+ { "--snaplen", Parameter::PT_INT, "68:65535", "1514",
"<snap> set snaplen of packet (same as -s)", },
{ "--stdin-rules", Parameter::PT_IMPLIED, nullptr, nullptr,
typedef list<ModHook*> ModuleList;
static ModuleList s_modules;
static unsigned s_errors = 0;
+
static string s_current;
static string s_name;
static string s_type;
// for callbacks from Lua
static SnortConfig* s_config = nullptr;
+// forward decls
+extern "C"
+{
+ bool open_table(const char*, int);
+ void close_table(const char*, int);
+
+ bool set_bool(const char* fqn, bool val);
+ bool set_number(const char* fqn, double val);
+ bool set_string(const char* fqn, const char* val);
+ bool set_alias(const char* from, const char* to);
+}
+
//-------------------------------------------------------------------------
// ModHook foo
//-------------------------------------------------------------------------
// set methods
//-------------------------------------------------------------------------
-static const Parameter* get_params(const string& sfx, const Parameter* p)
+static const Parameter* get_params(
+ const string& sfx, const Parameter* p, int idx = 1)
{
size_t pos = sfx.find_first_of('.');
std::string new_fqn;
p->type != Parameter::PT_LIST )
return p;
- if (new_fqn.find_first_of('.') == std::string::npos)
+ if ( new_fqn.find_first_of('.') == std::string::npos )
{
- if (p->type == Parameter::PT_LIST)
+ if ( idx && p->type == Parameter::PT_LIST )
{
const Parameter* tmp_p =
reinterpret_cast<const Parameter*>(p->range);
}
p = (const Parameter*)p->range;
- return get_params(new_fqn, p);
+ return get_params(new_fqn, p, idx);
}
// FIXIT-M vars may have been defined on command line
}
//-------------------------------------------------------------------------
-// ffi methods
+// defaults - set all parameter table defaults for each configured module
+// but there are no internal default list or list items. since Lua calls
+// open table for each explicitly configured table only, here is what we
+// do:
+//
+// -- on open_table(), call Module::begin() for each module, list, and list
+// item
+// -- recursively set all defaults after calling Module::begin(), skipping
+// lists and list items
+// -- on close_table(), call Module::begin() for each module, list, and list
+// item
//-------------------------------------------------------------------------
-extern "C"
+static bool top_level(const char* s)
+{ return !strchr(s, '.'); }
+
+static bool begin(Module* m, const Parameter* p, const char* s, int idx, int depth)
{
- bool open_table(const char*, int);
- void close_table(const char*, int);
+ if ( !p )
+ {
+ p = m->get_parameters();
+ assert(p);
+ }
- bool set_bool(const char* fqn, bool val);
- bool set_number(const char* fqn, double val);
- bool set_string(const char* fqn, const char* val);
- bool set_alias(const char* from, const char* to);
+ // Module::begin() top-level, lists, and list items only
+ if ( top_level(s) or
+ (!idx and p->type == Parameter::PT_LIST) or
+ (idx and p->type != Parameter::PT_LIST) )
+ {
+ //printf("begin %s %d\n", s, idx);
+ if ( !m->begin(s, idx, s_config) )
+ return false;
+ }
+ // don't set list defaults
+ if ( m->is_list() or p->type == Parameter::PT_LIST )
+ {
+ if ( !idx )
+ return true;
+ }
+
+ // set list item defaults only if explicitly configured
+ // (this is why it is done here and not in the loop below)
+ if ( p->type == Parameter::PT_LIST )
+ {
+ const Parameter* t =
+ reinterpret_cast<const Parameter*>(p->range);
+
+ return begin(m, t, s, idx, depth+1);
+ }
+
+ // don't begin subtables again
+ if ( !top_level(s) && !depth )
+ return true;
+
+ while ( p->name )
+ {
+ string fqn = s;
+ fqn += '.';
+ fqn += p->name;
+
+ switch ( p->type )
+ {
+ // traverse subtables only to set defaults
+ case Parameter::PT_TABLE:
+ {
+ const Parameter* t =
+ reinterpret_cast<const Parameter*>(p->range);
+
+ if ( !begin(m, t, fqn.c_str(), idx, depth+1) )
+ return false;
+ }
+ break;
+
+ // skip lists, they must be configured explicitly
+ case Parameter::PT_LIST:
+ case Parameter::PT_MAX:
+ break;
+
+ case Parameter::PT_BOOL:
+ if ( p->deflt )
+ {
+ bool b = p->get_bool();
+ //printf("set default %s = %s\n", fqn.c_str(), p->deflt);
+ set_bool(fqn.c_str(), b);
+ }
+ break;
+
+ case Parameter::PT_INT:
+ case Parameter::PT_PORT:
+ case Parameter::PT_REAL:
+ if ( p->deflt )
+ {
+ double d = p->get_number();
+ //printf("set default %s = %f\n", fqn.c_str(), d);
+ set_number(fqn.c_str(), d);
+ }
+ break;
+
+ // everything else is a string of some sort
+ default:
+ if ( p->deflt )
+ {
+ //printf("set default %s = %s\n", fqn.c_str(), p->deflt);
+ set_string(fqn.c_str(), p->deflt);
+ }
+ break;
+ }
+ ++p;
+ }
+ return true;
}
+// no need to recurse here; we only call Module::end() for
+// top-level, lists, and list items
+static bool end(Module* m, const Parameter* p, const char* s, int idx)
+{
+ bool top_param = !p;
+
+ if ( !p )
+ {
+ p = m->get_parameters();
+ assert(p);
+ }
+ // same as begin() but we must include top_param to catch
+ // top-level lists
+ if ( top_level(s) or
+ (top_param and p->type != Parameter::PT_TABLE) or
+ (!idx and p->type == Parameter::PT_LIST) or
+ (idx and p->type != Parameter::PT_LIST) )
+ {
+ //printf("end %s %d\n", s, idx);
+ return m->end(s, idx, s_config);
+ }
+ return true;
+}
+
+//-------------------------------------------------------------------------
+// ffi methods
+//-------------------------------------------------------------------------
+
SO_PUBLIC bool set_alias(const char* from, const char* to)
{
s_name = from;
SO_PUBLIC bool open_table(const char* s, int idx)
{
+ //printf("open %s %d\n", s, idx);
+
const char* orig = s;
string fqn = s;
set_type(fqn);
if ( snort_is_reloading() && h && h->api && h->api->type != PT_INSPECTOR )
return false;
- //printf("open %s %d\n", s, idx);
Module* m = h->mod;
+ const Parameter* p = nullptr;
- if (strcmp(m->get_name(), s))
+ if ( strcmp(m->get_name(), s) )
{
std::string fqn = s;
- const Parameter* const p = get_params(fqn, m->get_parameters());
+ p = get_params(fqn, m->get_parameters(), idx);
if ( !p )
{
s_current = key;
}
- if ( !m->begin(s, idx, s_config) )
+ if ( !begin(m, p, s, idx, 0) )
{
ParseError("can't open %s", m->get_name());
return false;
SO_PUBLIC void close_table(const char* s, int idx)
{
+ //printf("close %s %d\n", s, idx);
+
string fqn = s;
set_type(fqn);
s = fqn.c_str();
string key = fqn;
set_top(key);
- //printf("close %s %d\n", s, idx);
-
if ( ModHook* h = get_hook(key.c_str()) )
{
- if ( !h->mod->end(s, idx, s_config) )
+ if ( !end(h->mod, nullptr, s, idx) )
ParseError("can't close %s", h->mod->get_name());
else if ( !s_name.empty() )
{
// FIXIT when.policy_id should be an arbitrary string auto converted
// into index for binder matching and lookups
- { "policy_id", Parameter::PT_INT, "0:", nullptr,
+ { "policy_id", Parameter::PT_INT, "0:", "0",
"unique ID for selection of this config by external logic" },
{ "ifaces", Parameter::PT_BIT_LIST, "255", nullptr,
{ "type", Parameter::PT_STRING, nullptr, nullptr,
"select module for binding" },
- { "name", Parameter::PT_STRING, nullptr, "defaults to type",
- "symbol name" },
+ { "name", Parameter::PT_STRING, nullptr, nullptr,
+ "symbol name (defaults to type)" },
{ nullptr, Parameter::PT_MAX, nullptr, nullptr, nullptr }
};
static const Parameter proto_params[] =
{
- { "memcap", Parameter::PT_INT, "0:", nullptr,
+ { "memcap", Parameter::PT_INT, "0:", "0",
"maximum cache memory" },
{ "idle_timeout", Parameter::PT_INT, "1:", "60",