From: Russ Combs (rucombs) Date: Fri, 14 Oct 2016 00:41:29 +0000 (-0400) Subject: Merge pull request #619 in SNORT/snort3 from standard_opt to master X-Git-Tag: 3.0.0-233~221 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=127945e5c4da014fbee9e07d8a020165a7bbda05;p=thirdparty%2Fsnort3.git Merge pull request #619 in SNORT/snort3 from standard_opt to master Squashed commit of the following: commit 48c221dffad83fe29c8426f4d8d3be21dc774de1 Author: Carter Waxman Date: Tue Aug 30 13:58:04 2016 -0400 Added standard options to Module class. Added trace debugging. Implemented trace in stream ip --- diff --git a/src/framework/module.cc b/src/framework/module.cc index 9bc2da332..ed142f4c5 100644 --- a/src/framework/module.cc +++ b/src/framework/module.cc @@ -21,8 +21,12 @@ #include "parameter.h" #include "utils/stats.h" -static const Parameter null_params[] = + +static const Parameter defaults[] = { + { "trace", Parameter::PT_INT, nullptr, nullptr, + "mask for enabling debug traces in module" }, + { nullptr, Parameter::PT_MAX, nullptr, nullptr, nullptr } }; @@ -46,7 +50,8 @@ void Module::init(const char* s, const char* h) { name = s; help = h; - params = null_params; + params = &defaults[(sizeof(defaults) / sizeof(Parameter)) - 1]; + default_params = params; list = false; num_counts = -1; } @@ -54,11 +59,28 @@ void Module::init(const char* s, const char* h) Module::Module(const char* s, const char* h) { init(s, h); } -Module::Module(const char* s, const char* h, const Parameter* p, bool is_list) +Module::Module(const char* s, const char* h, const Parameter* p, bool is_list, Trace* t) { init(s, h); - params = p; list = is_list; + trace = t; + params = p; + + // FIXIT-L: This will not be valid after adding more default options + if ( t ) + default_params = defaults; +} + +bool Module::set(const char*, Value& v, SnortConfig*) +{ + if ( v.is("trace") ) + { + if ( trace ) + *trace = v.get_long(); + } + else + return false; + return true; } void Module::sum_stats() diff --git a/src/framework/module.h b/src/framework/module.h index 22e1e19a2..17e78aa08 100644 --- a/src/framework/module.h +++ b/src/framework/module.h @@ -41,10 +41,12 @@ #include #include +#include "main/snort_debug.h" #include "main/snort_types.h" #include "framework/value.h" #include "framework/parameter.h" #include "framework/counts.h" +#include "main/snort_debug.h" #include "utils/stats.h" using LuaCFunction = int(*)(struct lua_State*); @@ -83,8 +85,7 @@ public: virtual bool end(const char*, int, SnortConfig*) { return true; } - virtual bool set(const char*, Value&, SnortConfig*) - { return false; } + virtual bool set(const char*, Value&, SnortConfig*); // ips events: virtual unsigned get_gid() const @@ -115,6 +116,9 @@ public: const Parameter* get_parameters() const { return params; } + const Parameter* get_default_parameters() const + { return default_params; } + virtual const Command* get_commands() const { return nullptr; } @@ -152,7 +156,8 @@ public: protected: Module(const char* name, const char* help); - Module(const char* name, const char* help, const Parameter*, bool is_list = false); + Module(const char* name, const char* help, const Parameter*, + bool is_list = false, Trace* = nullptr); private: friend class ModuleManager; @@ -162,10 +167,12 @@ private: const char* help; const Parameter* params; + const Parameter* default_params = nullptr; bool list; std::vector counts; int num_counts; + Trace* trace; }; #endif diff --git a/src/framework/parameter.cc b/src/framework/parameter.cc index f48c5c007..7122c3374 100644 --- a/src/framework/parameter.cc +++ b/src/framework/parameter.cc @@ -450,8 +450,21 @@ const char* Parameter::get_string() const return deflt ? deflt : ""; } +const Parameter* Parameter::find(const Parameter* p, const Parameter* d, const char* s) +{ + auto ret = find(p, s); + + if ( !ret ) + ret = find(d, s); + + return ret; +} + const Parameter* Parameter::find(const Parameter* p, const char* s) { + if ( !p ) + return nullptr; + while ( p->name ) { if ( !strcmp(p->name, s) || p->is_wild_card() ) diff --git a/src/framework/parameter.h b/src/framework/parameter.h index cc56b7591..232115c54 100644 --- a/src/framework/parameter.h +++ b/src/framework/parameter.h @@ -84,6 +84,7 @@ struct SO_PUBLIC Parameter double get_number() const; const char* get_string() const; + static const Parameter* find(const Parameter*, const Parameter*, const char*); static const Parameter* find(const Parameter*, const char*); // 0-based; -1 if not found; list is | delimited diff --git a/src/main/snort_debug.cc b/src/main/snort_debug.cc index b0e6ba6ce..4c4fb0055 100644 --- a/src/main/snort_debug.cc +++ b/src/main/snort_debug.cc @@ -29,6 +29,7 @@ #include "snort_types.h" #include "snort_config.h" +#include "utils/safec.h" bool Debug::init = false; uint64_t Debug::mask = 0; @@ -86,3 +87,217 @@ void Debug::print( va_end(ap); } + +bool trace_enabled(Trace mask, Trace flags) +{ return mask & flags; } + +bool trace_enabled(Trace mask) +{ return mask; } + +template +static inline void trace_vprintf(const char* name, Trace mask, const char* file, int line, + Trace flags, const char* fmt, va_list ap) +{ + if ( !trace_enabled(mask, flags) ) + return; + + char buf[STD_BUF]; + int buf_len = sizeof(buf); + char* buf_ptr = buf; + + int size = snprintf(buf, buf_len, "%s: ", name); + if ( size > 0 && size < buf_len ) + { + buf_ptr += size; + buf_len -= size; + } + + if ( file ) + { + size = snprintf(buf_ptr, buf_len, "%s:%d: ", file, line); + if ( size > 0 && size < buf_len ) + { + buf_ptr += size; + buf_len -= size; + } + } + + vsnprintf(buf_ptr, buf_len, fmt, ap); + + if ( snort_conf and SnortConfig::log_syslog() ) + syslog(LOG_DAEMON | LOG_DEBUG, "%s", buf); + else + output(buf, stdout); +} + +void trace_vprintf(const char* name, Trace mask, const char* file, int line, + Trace flags, const char* fmt, va_list ap) +{ + trace_vprintf(name, mask, file, line, flags, fmt, ap); +} + +#ifdef UNIT_TEST +#include + +//stringify the expansion of the macro +#define sx(code) sm(code) + +//stringify the macro +#define sm(code) #code + +#define TRACE_SECTION_1 0x0000000000000001 +#define TRACE_SECTION_2 0x0000000000000002 +#define TRACE_SECTION_3 0x0000000000000004 +#define TRACE_SECTION_4 0x0000000000000008 + +struct TestCase +{ + const char* test; + const char* expected; +}; + +static char testing_dump[STD_BUF]; +static int test_fputs(const char* str, FILE*) +{ + memcpy_s(testing_dump, STD_BUF, str, STD_BUF); + + return 0; +} + +TEST_CASE("macros", "[trace]") +{ + const Trace my_flags = TRACE_SECTION_1 | TRACE_SECTION_2 | TRACE_SECTION_3; + + TestCase cases[] = + { + { + sx(trace_log(testing, "my message")), + "trace_print(\"testing\", testing_trace, nullptr, 0, \"my message\")" + }, + { + sx(trace_log(testing, my_flags, "my message")), + "trace_print(\"testing\", testing_trace, nullptr, 0, my_flags, \"my message\")" + }, + { + sx(trace_logf(testing, "%s %s", "my", "message")), + "trace_printf(\"testing\", testing_trace, nullptr, 0, \"%s %s\", \"my\", \"message\")" + }, + { + sx(trace_logf(testing, my_flags, "%s %s", "my", "message")), + "trace_printf(\"testing\", testing_trace, nullptr, 0, my_flags, \"%s %s\", \"my\", \"message\")" + }, + { + sx(trace_debug(testing, "my message")), "trace_print(\"testing\", testing_trace, " sx(__FILE__) ", " sx(__LINE__) ", \"my message\")" + }, + { + sx(trace_debug(testing, my_flags, "my message")), "trace_print(\"testing\", testing_trace, " sx(__FILE__) ", " sx(__LINE__) ", my_flags, \"my message\")" + }, + { + sx(trace_debugf(testing, "%s %s", "my", "message")), "trace_printf(\"testing\", testing_trace, " sx(__FILE__) ", " sx(__LINE__) ", \"%s %s\", \"my\", \"message\")" + }, + { + sx(trace_debugf(testing, my_flags, "%s %s", "my", "message")), "trace_printf(\"testing\", testing_trace, " sx(__FILE__) ", " sx(__LINE__) ", my_flags, \"%s %s\", \"my\", \"message\")" + } + }; + + CHECK( !strcmp(cases[0].expected, cases[0].test) ); + CHECK( !strcmp(cases[1].expected, cases[1].test) ); + CHECK( !strcmp(cases[2].expected, cases[2].test) ); + CHECK( !strcmp(cases[3].expected, cases[3].test) ); + CHECK( !strcmp(cases[4].expected, cases[4].test) ); + CHECK( !strcmp(cases[5].expected, cases[5].test) ); + CHECK( !strcmp(cases[6].expected, cases[6].test) ); + CHECK( !strcmp(cases[7].expected, cases[7].test) ); +} + +#undef trace_print +#undef trace_printf + +//These templates expand to replace the default expansion of trace_vprintf. +//This custom expansion replaces output (expands to fputs in snort_debug.h macros) +//with test_fputs for capturing what would be passed to the console. +#define trace_print trace_print> +#define trace_printf trace_printf> + +TEST_CASE("trace_log", "[trace]") +{ + Trace TRACE_NAME(testing) = TRACE_SECTION_2 | TRACE_SECTION_3; + + testing_dump[0] = '\0'; + trace_log(testing, "my message"); + CHECK( !strcmp(testing_dump, "testing: my message") ); + + testing_dump[0] = '\0'; + trace_log(testing, TRACE_SECTION_1, "my masked message"); + CHECK( testing_dump[0] == '\0' ); + + testing_dump[0] = '\0'; + trace_log(testing, TRACE_SECTION_2, "my other masked message"); + CHECK( !strcmp(testing_dump, "testing: my other masked message") ); +} + +TEST_CASE("trace_logf", "[trace]") +{ + Trace TRACE_NAME(testing) = TRACE_SECTION_2 | TRACE_SECTION_3; + + testing_dump[0] = '\0'; + trace_logf(testing, "%s %s", "my", "message"); + CHECK( !strcmp(testing_dump, "testing: my message") ); + + testing_dump[0] = '\0'; + trace_logf(testing, TRACE_SECTION_1, "%s %s %s", "my", "masked", "message"); + CHECK( testing_dump[0] == '\0' ); + + testing_dump[0] = '\0'; + trace_logf(testing, TRACE_SECTION_2, "%s %s %s %s", "my", "other", "masked", "message"); + CHECK( !strcmp(testing_dump, "testing: my other masked message") ); +} + +TEST_CASE("trace_debug", "[trace]") +{ + Trace TRACE_NAME(testing) = TRACE_SECTION_2 | TRACE_SECTION_3; + + testing_dump[0] = '\0'; + trace_debug(testing, "my message"); CHECK( !strcmp(testing_dump, "testing: " __FILE__ ":" sx(__LINE__) ": my message") ); + + testing_dump[0] = '\0'; + trace_debug(testing, TRACE_SECTION_1, "my masked message"); + CHECK( testing_dump[0] == '\0' ); + + testing_dump[0] = '\0'; + trace_debug(testing, TRACE_SECTION_2, "my other masked message"); CHECK( !strcmp(testing_dump, "testing: " __FILE__ ":" sx(__LINE__) ": my other masked message") ); +} + +TEST_CASE("trace_debugf", "[trace]") +{ + Trace TRACE_NAME(testing) = TRACE_SECTION_2 | TRACE_SECTION_3; + + testing_dump[0] = '\0'; + trace_debugf(testing, "%s %s", "my", "message"); CHECK( !strcmp(testing_dump, "testing: " __FILE__ ":" sx(__LINE__) ": my message") ); + + testing_dump[0] = '\0'; + trace_debugf(testing, TRACE_SECTION_1, "%s %s %s", "my", "masked", "message"); + CHECK( testing_dump[0] == '\0' ); + + testing_dump[0] = '\0'; + trace_debugf(testing, TRACE_SECTION_2, "%s %s %s %s", "my", "other", "masked", "message"); CHECK( !strcmp(testing_dump, "testing: " __FILE__ ":" sx(__LINE__) ": my other masked message") ); +} + +TEST_CASE("safety", "[trace]") +{ + Trace TRACE_NAME(testing) = TRACE_SECTION_2 | TRACE_SECTION_3; + + char* message = new char[STD_BUF + 1]; + + for( int i = 0; i < STD_BUF; i++ ) + message[i] = 'A'; + message[STD_BUF] = '\0'; + + testing_dump[0] = '\0'; + trace_log(testing, message); + CHECK( strlen(testing_dump) == STD_BUF - 1 ); + + delete message; +} + +#endif diff --git a/src/main/snort_debug.h b/src/main/snort_debug.h index 4f9ebf288..f52471afe 100644 --- a/src/main/snort_debug.h +++ b/src/main/snort_debug.h @@ -30,6 +30,8 @@ #include "config.h" #endif +#include +#include #include #include @@ -96,8 +98,79 @@ #define DEBUG_DCE_UDP 0x1000000000000000LL +typedef uint64_t Trace; + +bool trace_enabled(Trace mask); +bool trace_enabled(Trace mask, Trace flags); + +#define TRACE_NAME(name) name##_trace + #ifdef DEBUG_MSGS +void trace_vprintf(const char* name, Trace mask, const char* file, int line, + Trace flags, const char* fmt, va_list); + +template +static inline void trace_printf(const char* name, Trace mask, const char* file, int line, + Trace flags, const char* fmt, ...) __attribute__((format (printf, 6, 7))); + +template +static inline void trace_printf(const char* name, Trace mask, const char* file, int line, + Trace flags, const char* fmt, ...) +{ + va_list ap; + va_start(ap, fmt); + + trace_vprintf(name, mask, file, line, flags, fmt, ap); + + va_end(ap); +} + +template +static inline void trace_printf(const char* name, Trace mask, const char* file, + int line, const char* fmt, ...) __attribute__((format (printf, 5, 6))); + +template +static inline void trace_printf(const char* name, Trace mask, const char* file, + int line, const char* fmt, ...) +{ + va_list ap; + va_start(ap, fmt); + + trace_vprintf(name, mask, file, line, UINT64_MAX, fmt, ap); + + va_end(ap); +} + +template +static inline void trace_print(const char* name, Trace mask, const char* file, + int line, const char* msg) +{ + trace_printf(name, mask, file, line, UINT64_MAX, "%s", msg); +} + +template +static inline void trace_print(const char* name, Trace mask, const char* file, + int line, Trace flags, const char* msg) +{ + trace_printf(name, mask, file, line, flags, "%s", msg); +} + +#define trace_print trace_print +#define trace_printf trace_printf + +#define trace_log(tracer, ...) \ + trace_print(#tracer, tracer##_trace, nullptr, 0, __VA_ARGS__) + +#define trace_logf(tracer, ...) \ + trace_printf(#tracer, tracer##_trace, nullptr, 0, __VA_ARGS__) + +#define trace_debug(tracer, ...) \ + trace_print(#tracer, tracer##_trace, __FILE__, __LINE__, __VA_ARGS__) + +#define trace_debugf(tracer, ...) \ + trace_printf(#tracer, tracer##_trace, __FILE__, __LINE__, __VA_ARGS__) + class SO_PUBLIC Debug { public: @@ -122,6 +195,11 @@ private: #define DEBUG_WRAP(code) code #else +#define trace_log(tracer, ...) +#define trace_logf(tracer, ...) +#define trace_debug(tracer, ...) +#define trace_debugf(tracer, ...) + #define DebugFormat(dbg, fmt, ...) #define DebugFormatNoFileLine(dbg, fmt, ...) #define DebugMessage(dbg, msg) diff --git a/src/managers/module_manager.cc b/src/managers/module_manager.cc index df9b4c988..44971469e 100644 --- a/src/managers/module_manager.cc +++ b/src/managers/module_manager.cc @@ -310,7 +310,7 @@ static void dump_table(string& key, const char* pfx, const Parameter* p, bool li dump_field_lua(fqn, p, true); } } - while ( p->name ) + while ( p && p->name ) dump_field(key, pfx, p++, list); } @@ -460,6 +460,9 @@ static bool set_value(const char* fqn, Value& v) string s = fqn; const Parameter* p = get_params(s, mod->get_parameters()); + if ( !p ) + p = get_params(s, mod->get_default_parameters()); + if ( !p ) { // FIXIT-L handle things like x = { 1 } where x is a table not a @@ -668,6 +671,9 @@ SO_PUBLIC bool open_table(const char* s, int idx) std::string sfqn = s; p = get_params(sfqn, m->get_parameters(), idx); + if ( !p ) + p = get_params(sfqn, m->get_default_parameters(), idx); + if ( !p ) { ParseError("can't find %s", s); @@ -908,13 +914,14 @@ void ModuleManager::show_module(const char* name) cout << endl << "Type: " << mod_type(p->api) << endl; - if ( const Parameter* params = m->get_parameters() ) + const Parameter* params = m->get_parameters(); + const Parameter* def_params = m->get_default_parameters(); + + if ( ( params and params->type < Parameter::PT_MAX ) || + ( def_params and params->type < Parameter::PT_MAX ) ) { - if ( params->type < Parameter::PT_MAX ) - { - cout << endl << "Configuration: " << endl << endl; - show_configs(name, true); - } + cout << endl << "Configuration: " << endl << endl; + show_configs(name, true); } if ( m->get_commands() ) @@ -985,6 +992,12 @@ void ModuleManager::show_configs(const char* pfx, bool exact) { dump_field(s, pfx, m->params); } + + s = m->name; + + if ( m->default_params ) + dump_table(s, pfx, m->default_params); + if ( !pfx ) cout << endl; diff --git a/src/parser/cmd_line.cc b/src/parser/cmd_line.cc index 802e1f3fc..d480f4fbd 100644 --- a/src/parser/cmd_line.cc +++ b/src/parser/cmd_line.cc @@ -138,8 +138,7 @@ static void set( key = k.c_str(); Module* m = get_snort_module(); - const Parameter* p = m->get_parameters(); - p = Parameter::find(p, key); + const Parameter* p = Parameter::find(m->get_parameters(), key); if ( !p ) ParseError("unknown option %s %s", key, val); diff --git a/src/stream/ip/ip_defrag.cc b/src/stream/ip/ip_defrag.cc index cc7cdc285..55e5070a0 100644 --- a/src/stream/ip/ip_defrag.cc +++ b/src/stream/ip/ip_defrag.cc @@ -418,7 +418,7 @@ static inline int FragCheckFirstLast(const Packet* const p, { ft->frag_flags |= FRAG_GOT_FIRST; - DebugMessage(DEBUG_FRAG, "Got first frag\n"); + trace_log(stream_ip, "Got first frag\n"); } else if ((!(p->ptrs.decode_flags & DECODE_MF)) && (frag_offset > 0)) /* set for last frag too */ @@ -433,7 +433,7 @@ static inline int FragCheckFirstLast(const Packet* const p, if (ft->frag_flags & FRAG_GOT_LAST) { - DebugMessage(DEBUG_FRAG, "Got last frag again!\n"); + trace_log(stream_ip, "Got last frag again!\n"); switch (ft->frag_policy) { case FRAG_POLICY_BSD: @@ -498,7 +498,7 @@ static inline int FragCheckFirstLast(const Packet* const p, { ft->calculated_size = endOfThisFrag; - DebugFormat(DEBUG_FRAG, "Got last frag, Bytes: %u, " + trace_logf(stream_ip, "Got last frag, Bytes: %u, " "Calculated size: %u\n", ft->frag_bytes, ft->calculated_size); @@ -510,7 +510,7 @@ static inline int FragCheckFirstLast(const Packet* const p, ft->frag_flags |= FRAG_NO_BSD_VULN; } - DebugFormat(DEBUG_FRAG, "Frag Status: %s:%s\n", + trace_logf(stream_ip, "Frag Status: %s:%s\n", ft->frag_flags&FRAG_GOT_FIRST ? "FIRST" : "No FIRST", ft->frag_flags&FRAG_GOT_LAST ? "LAST" : "No LAST"); return retVal; @@ -618,7 +618,7 @@ static inline int checkTinyFragments( { if (p->dsize <= engine->min_fragment_length) { - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "Frag: Received fragment size(%d) is not more than configured min_fragment_length (%u)\n", p->dsize, engine->min_fragment_length); EventTinyFragments(engine); @@ -628,7 +628,7 @@ static inline int checkTinyFragments( ///detect tiny fragments after processing overlaps. if (trimmedLength <= engine->min_fragment_length) { - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "Frag: # of New octets in Received fragment(%u) is not more than configured min_fragment_length (%u)\n", trimmedLength, engine->min_fragment_length); EventTinyFragments(engine); @@ -652,7 +652,7 @@ int drop_all_fragments( //drop this and all following fragments if (ft && !(ft->frag_flags & FRAG_DROP_FRAGMENTS)) { - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, "Frag: Will drop all fragments on this packet\n"); ft->frag_flags |= FRAG_DROP_FRAGMENTS; } @@ -671,7 +671,7 @@ int drop_all_fragments( */ static inline int FragIsComplete(FragTracker* ft) { - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, "[$] Checking completion criteria\n"); /* @@ -680,7 +680,7 @@ static inline int FragIsComplete(FragTracker* ft) if ((ft->frag_flags & FRAG_GOT_FIRST) && (ft->frag_flags & FRAG_GOT_LAST)) { - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, " Got First and Last frags\n"); /* @@ -689,7 +689,7 @@ static inline int FragIsComplete(FragTracker* ft) */ if (ft->frag_bytes == ft->calculated_size) { - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, " [!] frag_bytes = calculated_size!\n"); ip_stats.trackers_completed++; @@ -699,7 +699,7 @@ static inline int FragIsComplete(FragTracker* ft) if (ft->frag_bytes > ft->calculated_size) { - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, " [!] frag_bytes > calculated_size!\n"); ip_stats.trackers_completed++; @@ -707,7 +707,7 @@ static inline int FragIsComplete(FragTracker* ft) return 1; } - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, " Calc size (%u) != frag bytes (%u)\n", ft->calculated_size, ft->frag_bytes); @@ -717,7 +717,7 @@ static inline int FragIsComplete(FragTracker* ft) return 0; } - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, " Missing First or Last frags (frag_flags: 0x%X)\n", ft->frag_flags); @@ -770,7 +770,7 @@ static void FragRebuild(FragTracker* ft, Packet* p) /* Adjust the IP header size in pseudo packet for the new length */ uint8_t new_ip_hlen = ip::IP4_HEADER_LEN + ft->ip_options_len; - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "Adjusting IP Header to %d bytes\n", new_ip_hlen); iph->set_hlen(new_ip_hlen >> 2); @@ -792,6 +792,8 @@ static void FragRebuild(FragTracker* ft, Packet* p) iph->ip_off = 0x0000; dpkt->ptrs.decode_flags &= ~DECODE_FRAG; + trace_log(stream_ip, + "[^^] Walking fraglist:\n"); DebugMessage(DEBUG_FRAG, "[^^] Walking fraglist:\n"); } @@ -801,7 +803,7 @@ static void FragRebuild(FragTracker* ft, Packet* p) */ for (frag = ft->fraglist; frag; frag = frag->next) { - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, " frag: %p\n" " frag->data: %p\n" " frag->offset: %d\n" @@ -879,7 +881,7 @@ static void FragRebuild(FragTracker* ft, Packet* p) /* * process the packet through the detection engine */ - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, "Processing rebuilt packet:\n"); ip_stats.reassembles++; @@ -890,7 +892,7 @@ static void FragRebuild(FragTracker* ft, Packet* p) * Note, that this won't print out the IP Options or any other * data that is established when the packet is decoded. */ - if ( Debug::enabled(DEBUG_FRAG) ) + if ( stream_ip.enabled(1) ) LogIPPkt(dpkt); #endif @@ -901,7 +903,7 @@ static void FragRebuild(FragTracker* ft, Packet* p) SnortEventqPop(); encap_frag_cnt--; - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, "Done with rebuilt packet, marking rebuilt...\n"); ft->frag_flags = ft->frag_flags | FRAG_REBUILT; @@ -975,7 +977,7 @@ static void delete_frag(Fragment* frag) */ static inline void delete_node(FragTracker* ft, Fragment* node) { - DebugFormat(DEBUG_FRAG, "Deleting list node %p (p %p n %p)\n", + trace_logf(stream_ip, "Deleting list node %p (p %p n %p)\n", (void*) node, (void*) node->prev, (void*) node->next); if (node->prev) @@ -1013,7 +1015,7 @@ static void delete_tracker(FragTracker* ft) Fragment* idx = ft->fraglist; /* pointer to the fraglist to delete */ Fragment* dump_me = NULL; /* ptr to the Fragment element to drop */ - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "delete_tracker %d nodes to dump\n", ft->fraglist_count); /* @@ -1139,7 +1141,7 @@ void Defrag::process(Packet* p, FragTracker* ft) #ifdef DEBUG_MSGS if ( p->is_ip4() ) { - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "[FRAG] Fragment discarded due to low TTL " "[0x%X->0x%X], TTL: %d " "Offset: %d Length: %hu\n", ntohl(p->ptrs.ip_api.get_ip4h()->get_src()), @@ -1204,7 +1206,7 @@ void Defrag::process(Packet* p, FragTracker* ft) switch (insert_return) { case FRAG_INSERT_FAILED: - DebugFormat(DEBUG_FRAG, "WARNING: Insert into Fraglist failed, " + trace_logf(stream_ip, "WARNING: Insert into Fraglist failed, " "(offset: %hu).\n", frag_offset); return; @@ -1213,7 +1215,7 @@ void Defrag::process(Packet* p, FragTracker* ft) #ifdef DEBUG_MSGS if ( p->is_ip4() ) { - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "[FRAG] Fragment discarded due to large TTL Delta " "[0x%X->0x%X], TTL: %d orig TTL: %d " "Offset: %hu Length: %hu\n", @@ -1232,12 +1234,12 @@ void Defrag::process(Packet* p, FragTracker* ft) return; case FRAG_INSERT_TIMEOUT: - DebugFormat(DEBUG_FRAG, "WARNING: Insert into Fraglist failed due to timeout, " + trace_logf(stream_ip, "WARNING: Insert into Fraglist failed due to timeout, " "(offset: %hu).\n", frag_offset); return; case FRAG_INSERT_OVERLAP_LIMIT: - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "WARNING: Excessive IP fragment overlap, " "(More: %d, offset: %d, offsetSize: %hu).\n", (p->ptrs.decode_flags & DECODE_MF), @@ -1255,7 +1257,7 @@ void Defrag::process(Packet* p, FragTracker* ft) */ if (FragIsComplete(ft)) { - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, "[*] Fragment is complete, rebuilding!\n"); /* @@ -1389,7 +1391,7 @@ int Defrag::insert(Packet* p, FragTracker* ft, FragEngine* fe) /* * bonk/boink/jolt/etc attack... */ - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, "[..] Short frag (Bonk, etc) attack!\n"); EventAnomShortFrag(fe); @@ -1413,7 +1415,7 @@ int Defrag::insert(Packet* p, FragTracker* ft, FragEngine* fe) if (ft->frag_flags & FRAG_GOT_LAST) { /* oversize frag attack */ - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, "[..] Oversize frag pkt!\n"); EventAnomOversize(fe); @@ -1429,7 +1431,7 @@ int Defrag::insert(Packet* p, FragTracker* ft, FragEngine* fe) /* * zero size frag... */ - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, "[..] Zero size frag!\n"); EventAnomZeroFrag(fe); @@ -1442,7 +1444,7 @@ int Defrag::insert(Packet* p, FragTracker* ft, FragEngine* fe) /* * oversize pkt... */ - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, "[..] Oversize frag!\n"); EventAnomBadsizeLg(fe); @@ -1461,7 +1463,7 @@ int Defrag::insert(Packet* p, FragTracker* ft, FragEngine* fe) ft->frag_pkts++; - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "Walking frag list (%d nodes), new frag %d@%d\n", ft->fraglist_count, fragLength, frag_offset); @@ -1474,7 +1476,7 @@ int Defrag::insert(Packet* p, FragTracker* ft, FragEngine* fe) i++; right = idx; - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "%d right o %d s %d ptr %p prv %p nxt %p\n", i, right->offset, right->size, (void*) right, (void*) right->prev, (void*) right->next); @@ -1498,7 +1500,7 @@ int Defrag::insert(Packet* p, FragTracker* ft, FragEngine* fe) */ if (left) { - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "Dealing with previous (left) frag %d@%d\n", left->size, left->offset); @@ -1525,7 +1527,7 @@ int Defrag::insert(Packet* p, FragTracker* ft, FragEngine* fe) /* * teardrop attack... */ - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, "[..] Teardrop attack!\n"); EventAttackTeardrop(fe); @@ -1555,7 +1557,7 @@ int Defrag::insert(Packet* p, FragTracker* ft, FragEngine* fe) frag_offset += (int16_t)overlap; slide = (int16_t)overlap; - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "left overlap, new frag moves: %d bytes, " "slide: %d\n", overlap, slide); @@ -1564,7 +1566,7 @@ int Defrag::insert(Packet* p, FragTracker* ft, FragEngine* fe) /* * zero size frag */ - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, "zero size frag\n"); EventAnomZeroFrag(fe); @@ -1572,7 +1574,7 @@ int Defrag::insert(Packet* p, FragTracker* ft, FragEngine* fe) return FRAG_INSERT_ANOMALY; } - DebugFormat(DEBUG_FRAG, "left overlap, " + trace_logf(stream_ip, "left overlap, " "truncating new pkt (slide: %d)\n", slide); break; @@ -1627,7 +1629,7 @@ int Defrag::insert(Packet* p, FragTracker* ft, FragEngine* fe) } left_overlap_last: - DebugFormat(DEBUG_FRAG, "[!!] left overlap, " + trace_logf(stream_ip, "[!!] left overlap, " "truncating old pkt (offset: %d overlap: %d)\n", left->offset, overlap); @@ -1635,7 +1637,7 @@ left_overlap_last: { dump_me = left; - DebugFormat(DEBUG_FRAG, "retrans, " + trace_logf(stream_ip, "retrans, " "dumping old frag (offset: %d overlap: %d)\n", dump_me->offset, overlap); @@ -1652,7 +1654,7 @@ left_overlap_last: */ if (frag_end < frag_offset) { - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, "frag_end < frag_offset!"); EventAnomBadsizeSm(fe); @@ -1662,13 +1664,13 @@ left_overlap_last: } else { - DebugMessage(DEBUG_FRAG, "No left overlap!\n"); + trace_log(stream_ip, "No left overlap!\n"); } } if ((uint16_t)fragLength > pkt_snaplen) { - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "Overly large fragment %d 0x%x 0x%x %d\n", fragLength, p->ptrs.ip_api.dgram_len(), p->ptrs.ip_api.off(), net_frag_offset); @@ -1683,7 +1685,7 @@ left_overlap_last: */ while (right && (right->offset < frag_end) && !done) { - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "Next (right)fragment %d@%d\n", right->size, right->offset); @@ -1701,7 +1703,7 @@ left_overlap_last: /* * teardrop attack... */ - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, "[..] Teardrop attack!\n"); EventAttackTeardrop(fe); @@ -1721,7 +1723,7 @@ left_overlap_last: ip_stats.overlaps++; ft->overlap_count++; - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "Right-side overlap %d bytes\n", overlap); /* @@ -1748,16 +1750,16 @@ left_overlap_last: right->size -= (int16_t)overlap; ft->frag_bytes -= (int16_t)overlap; } - DebugFormat(DEBUG_FRAG, "[!!] right overlap, " + trace_logf(stream_ip, "[!!] right overlap, " "truncating old frag (offset: %d, " "overlap: %d)\n", right->offset, overlap); - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, "Exiting right overlap loop...\n"); if (right->size <= 0) { dump_me = right; - DebugFormat(DEBUG_FRAG, "retrans, " + trace_logf(stream_ip, "retrans, " "dumping old frag (offset: %d overlap: %d)\n", dump_me->offset, overlap); @@ -1775,11 +1777,11 @@ left_overlap_last: case FRAG_POLICY_SOLARIS: case FRAG_POLICY_BSD_RIGHT: trunc = (int16_t)overlap; - DebugFormat(DEBUG_FRAG, "[!!] right overlap, " + trace_logf(stream_ip, "[!!] right overlap, " "truncating new frag (offset: %d " "overlap: %d)\n", right->offset, overlap); - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, "Exiting right overlap loop...\n"); break; } @@ -1828,7 +1830,7 @@ left_overlap_last: dump_me = right; ft->frag_bytes -= right->size; - DebugFormat(DEBUG_FRAG, "retrans, " + trace_logf(stream_ip, "retrans, " "dumping old frag (offset: %d overlap: %d)\n", dump_me->offset, overlap); @@ -1876,7 +1878,7 @@ left_overlap_last: trunc = (int16_t)overlap; } - DebugFormat(DEBUG_FRAG, "right overlap, " + trace_logf(stream_ip, "right overlap, " "rejecting new overlap data (overlap: %d, " "trunc: %d)\n", overlap, trunc); @@ -1885,7 +1887,7 @@ left_overlap_last: /* * zero size frag */ - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "zero size frag (len: %d overlap: %d)\n", fragLength, overlap); @@ -1972,7 +1974,7 @@ right_overlap_last: dump_me = right; ft->frag_bytes -= right->size; - DebugFormat(DEBUG_FRAG, "retrans, " + trace_logf(stream_ip, "retrans, " "dumping old frag (offset: %d overlap: %d)\n", dump_me->offset, overlap); @@ -1992,7 +1994,7 @@ right_overlap_last: (ft->overlap_count >= fe->max_overlaps)) { // overlap limit exceeded. Raise event on all subsequent fragments - DebugMessage(DEBUG_FRAG, "Reached overlap limit.\n"); + trace_log(stream_ip, "Reached overlap limit.\n"); EventExcessiveOverlap(fe); @@ -2006,11 +2008,11 @@ right_overlap_last: } else { - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, "Fully truncated right overlap\n"); } - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, "insert(): returning normally\n"); return ret; @@ -2043,7 +2045,7 @@ int Defrag::new_tracker(Packet* p, FragTracker* ft) /* Just to double check */ if (fragLength > pkt_snaplen) { - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "Overly large fragment length:%d(0x%x) off:0x%x(%d)\n", fragLength, p->ptrs.ip_api.dgram_len(), p->ptrs.ip_api.off(), p->ptrs.ip_api.off()); @@ -2126,7 +2128,7 @@ int Defrag::new_tracker(Packet* p, FragTracker* ft) /* * bonk/boink/jolt/etc attack... */ - DebugMessage(DEBUG_FRAG, + trace_log(stream_ip, "[..] Short frag (Bonk, etc) attack!\n"); EventAnomShortFrag(&engine); @@ -2199,7 +2201,7 @@ int Defrag::add_frag_node( /* * zero size frag */ - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "zero size frag after left & right trimming " "(len: %d slide: %d trunc: %d)\n", len, slide, trunc); @@ -2210,7 +2212,7 @@ int Defrag::add_frag_node( newfrag = ft->fraglist; while (newfrag) { - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "Size: %d, offset: %d, len %d, " "Prev: 0x%p, Next: 0x%p, This: 0x%p, Ord: %d, %s\n", newfrag->size, newfrag->offset, @@ -2257,7 +2259,7 @@ int Defrag::add_frag_node( newfrag->offset = frag_offset; newfrag->last = lastfrag; - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "[+] Adding new frag, offset %d, size %d\n" " nf->data = nf->fptr(%p) + slide (%d)\n" " nf->size = len(%d) - slide(%d) - trunc(%d)\n", @@ -2269,7 +2271,7 @@ int Defrag::add_frag_node( */ add_node(ft, left, newfrag); - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "[*] Inserted new frag %d@%d ptr %p data %p prv %p nxt %p\n", newfrag->size, newfrag->offset, (void*) newfrag, newfrag->data, (void*) newfrag->prev, (void*) newfrag->next); @@ -2279,7 +2281,7 @@ int Defrag::add_frag_node( */ ft->frag_bytes += newfrag->size; - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "[#] accumulated bytes on FragTracker %u, count" " %d\n", ft->frag_bytes, ft->fraglist_count); @@ -2342,7 +2344,7 @@ int Defrag::dup_frag_node( */ add_node(ft, left, newfrag); - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "[*] Inserted new frag %d@%d ptr %p data %p prv %p nxt %p\n", newfrag->size, newfrag->offset, (void*) newfrag, newfrag->data, (void*) newfrag->prev, (void*) newfrag->next); @@ -2352,7 +2354,7 @@ int Defrag::dup_frag_node( */ ft->frag_bytes += newfrag->size; - DebugFormat(DEBUG_FRAG, + trace_logf(stream_ip, "[#] accumulated bytes on FragTracker %u, count" " %d\n", ft->frag_bytes, ft->fraglist_count); diff --git a/src/stream/ip/ip_module.cc b/src/stream/ip/ip_module.cc index fc1096c29..30d04b08a 100644 --- a/src/stream/ip/ip_module.cc +++ b/src/stream/ip/ip_module.cc @@ -79,6 +79,8 @@ FragEngine::FragEngine() // stream_ip module //------------------------------------------------------------------------- +Trace TRACE_NAME(stream_ip); + static const RuleMap stream_ip_rules[] = { { DEFRAG_IPOPTIONS, DEFRAG_IPOPTIONS_STR }, @@ -120,10 +122,8 @@ static const Parameter s_params[] = }; StreamIpModule::StreamIpModule() : - Module(MOD_NAME, MOD_HELP, s_params) -{ - config = nullptr; -} + Module(MOD_NAME, MOD_HELP, s_params, false, &TRACE_NAME(stream_ip)) +{ config = nullptr; } StreamIpModule::~StreamIpModule() { @@ -169,7 +169,7 @@ StreamIpConfig* StreamIpModule::get_data() return temp; } -bool StreamIpModule::set(const char*, Value& v, SnortConfig*) +bool StreamIpModule::set(const char* f, Value& v, SnortConfig* c) { if ( v.is("max_frags") ) config->frag_engine.max_frags = v.get_long(); @@ -193,7 +193,7 @@ bool StreamIpModule::set(const char*, Value& v, SnortConfig*) config->frag_engine.frag_timeout = v.get_long(); } else - return false; + return Module::set(f, v, c); return true; } diff --git a/src/stream/ip/ip_module.h b/src/stream/ip/ip_module.h index 1aa5215f9..6d440effa 100644 --- a/src/stream/ip/ip_module.h +++ b/src/stream/ip/ip_module.h @@ -21,6 +21,7 @@ #ifndef IP_MODULE_H #define IP_MODULE_H +#include "main/snort_debug.h" #include "main/snort_types.h" #include "main/thread.h" #include "flow/session.h" @@ -85,6 +86,7 @@ extern THREAD_LOCAL ProfileStats ip_perf_stats; extern THREAD_LOCAL ProfileStats fragPerfStats; extern THREAD_LOCAL ProfileStats fragInsertPerfStats; extern THREAD_LOCAL ProfileStats fragRebuildPerfStats; +extern Trace TRACE_NAME(stream_ip); //------------------------------------------------------------------------- // stream_ip module