From: Michael Altizer (mialtize) Date: Fri, 6 Oct 2017 21:00:39 +0000 (-0400) Subject: Merge pull request #1031 in SNORT/snort3 from binder_zones to master X-Git-Tag: 3.0.0-240~22 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=5186baf38eb8ee49c7769e7621bf5f7cff805c6f;p=thirdparty%2Fsnort3.git Merge pull request #1031 in SNORT/snort3 from binder_zones to master Squashed commit of the following: commit 08bd025019ff9a61a035fc9f8faa99d48bc6f132 Author: Carter Waxman Date: Fri Oct 6 10:46:02 2017 -0400 fixed build issues on OSX commit 5bb5412170ab5c01714a71fd01b762883899e71d Author: Carter Waxman Date: Tue Oct 3 15:47:59 2017 -0400 snort2lua: removed port dce proxy bindings to fix http_inspect conflicts commit 54a5be5daf20ce10fc404b92d897b3a4c700dd1d Author: Carter Waxman Date: Fri Sep 29 12:12:55 2017 -0400 snort2lua: added nap.rules zone translation commit c09df9d2a008f0e319f697de41dd86cc14396657 Author: Carter Waxman Date: Thu Oct 5 08:56:05 2017 -0400 binder: check interface on packet instead of flow commit b6f365f960d42b97ebf7b396508699e0c2670b09 Author: Carter Waxman Date: Thu Sep 28 15:37:13 2017 -0400 binder: added zones --- diff --git a/src/decompress/file_decomp.h b/src/decompress/file_decomp.h index 69dc0e2b5..c4ad6f1bb 100644 --- a/src/decompress/file_decomp.h +++ b/src/decompress/file_decomp.h @@ -138,7 +138,7 @@ struct fd_session_t of the underlying decompression engine context. */ #ifndef SYNC_IN #define SYNC_IN(dest) \ - dest->next_in = const_cast(SessionPtr->Next_In); \ + dest->next_in = (Bytef*)(SessionPtr->Next_In); \ (dest)->avail_in = SessionPtr->Avail_In; \ (dest)->total_in = SessionPtr->Total_In; \ (dest)->next_out = SessionPtr->Next_Out; \ diff --git a/src/flow/flow.h b/src/flow/flow.h index c8aa42a8c..135a79e12 100644 --- a/src/flow/flow.h +++ b/src/flow/flow.h @@ -328,9 +328,6 @@ public: // FIXIT-M privatize if possible unsigned ips_policy_id; unsigned network_policy_id; - int32_t iface_in; - int32_t iface_out; - uint16_t client_port; uint16_t server_port; diff --git a/src/managers/so_manager.cc b/src/managers/so_manager.cc index 078f68d36..c02afd084 100644 --- a/src/managers/so_manager.cc +++ b/src/managers/so_manager.cc @@ -88,7 +88,7 @@ static const uint8_t* compress(const string& text, unsigned& len) if ( ret != Z_OK ) return nullptr; - stream.next_in = (z_const Bytef*)s; + stream.next_in = (Bytef*)s; stream.avail_in = text.size(); stream.next_out = so_buf; @@ -121,7 +121,7 @@ static const char* expand(const uint8_t* data, unsigned len) if ( inflateInit2(&stream, window_bits) != Z_OK ) return nullptr; - stream.next_in = const_cast(data); + stream.next_in = (Bytef*)data; stream.avail_in = (uInt)len; stream.next_out = (Bytef*)so_buf; diff --git a/src/network_inspectors/binder/bind_module.cc b/src/network_inspectors/binder/bind_module.cc index f58c973a9..8bf6e40de 100644 --- a/src/network_inspectors/binder/bind_module.cc +++ b/src/network_inspectors/binder/bind_module.cc @@ -52,6 +52,7 @@ static const PegInfo bind_pegs[] = // binder module //------------------------------------------------------------------------- +#define INT32_MAX_STR "2147483647" static const Parameter binder_when_params[] = { // FIXIT-L when.policy_id should be an arbitrary string auto converted @@ -87,6 +88,12 @@ static const Parameter binder_when_params[] = { "dst_ports", Parameter::PT_BIT_LIST, "65535", nullptr, "list of destination ports" }, + { "src_zone", Parameter::PT_INT, "0:" INT32_MAX_STR, nullptr, + "source zone" }, + + { "dst_zone", Parameter::PT_INT, "0:" INT32_MAX_STR, nullptr, + "destination zone" }, + { "role", Parameter::PT_ENUM, "client | server | any", "any", "use the given configuration on one or any end of a session" }, @@ -219,6 +226,12 @@ bool BinderModule::set(const char* fqn, Value& v, SnortConfig*) work->when.split_ports = true; } + else if ( v.is("src_zone") ) + work->when.src_zone = v.get_long(); + + else if ( v.is("dst_zone") ) + work->when.dst_zone = v.get_long(); + else if ( v.is("role") ) work->when.role = (BindWhen::Role)v.get_long(); diff --git a/src/network_inspectors/binder/binder.cc b/src/network_inspectors/binder/binder.cc index c75bdee99..3269adac7 100644 --- a/src/network_inspectors/binder/binder.cc +++ b/src/network_inspectors/binder/binder.cc @@ -30,6 +30,8 @@ #include "managers/inspector_manager.h" #include "profiler/profiler.h" #include "protocols/packet.h" +#include "protocols/tcp.h" +#include "protocols/udp.h" #include "stream/stream.h" #include "stream/stream_splitter.h" #include "target_based/sftarget_reader.h" @@ -66,7 +68,10 @@ Binding::Binding() when.protos = (unsigned)PktType::ANY; when.vlans.set(); - when.ifaces.set(); + when.ifaces.reset(); + + when.src_zone = DAQ_PKTHDR_UNKNOWN; + when.dst_zone = DAQ_PKTHDR_UNKNOWN; when.ips_id = 0; when.role = BindWhen::BR_EITHER; @@ -128,28 +133,6 @@ bool Binding::check_addr(const Flow* flow) const return false; } -Binding::DirResult Binding::check_split_addr(const Flow* flow) const -{ - if ( !when.split_nets ) - return Binding::DR_ANY_MATCH; - - if ( !when.src_nets && !when.dst_nets ) - return Binding::DR_ANY_MATCH; - - bool client_in_src = !when.src_nets or sfvar_ip_in(when.src_nets, &flow->client_ip); - bool client_in_dst = !when.dst_nets or sfvar_ip_in(when.dst_nets, &flow->client_ip); - bool server_in_src = !when.src_nets or sfvar_ip_in(when.src_nets, &flow->server_ip); - bool server_in_dst = !when.dst_nets or sfvar_ip_in(when.dst_nets, &flow->server_ip); - - if ( client_in_src and server_in_dst ) - return Binding::DR_CLIENT_SRC; - - if ( server_in_src and client_in_dst ) - return Binding::DR_SERVER_SRC; - - return Binding::DR_NO_MATCH; -} - bool Binding::check_proto(const Flow* flow) const { if ( when.protos & (unsigned)flow->pkt_type ) @@ -158,16 +141,18 @@ bool Binding::check_proto(const Flow* flow) const return false; } -bool Binding::check_iface(const Flow* flow) const +bool Binding::check_iface(const Packet* p) const { - int i = flow->iface_in < 0 ? 0 : flow->iface_in; - - if ( when.ifaces.test(i) ) + if ( !p or when.ifaces.none() ) return true; - i = flow->iface_out < 0 ? 0 : flow->iface_out; + auto in = p->pkth->ingress_index; + auto out = p->pkth->egress_index; + + if ( in > 0 and when.ifaces.test(out) ) + return true; - if ( when.ifaces.test(i) ) + if ( out > 0 and when.ifaces.test(out) ) return true; return false; @@ -198,58 +183,145 @@ bool Binding::check_port(const Flow* flow) const return false; } -bool Binding::check_split_port(const Flow* flow, const DirResult dr) const +bool Binding::check_service(const Flow* flow) const { - if ( !when.split_ports ) + if ( !flow->service ) + return when.svc.empty(); + + if ( when.svc == flow->service ) return true; - bool client_in_src = false; - bool client_in_dst = false; - bool server_in_src = false; - bool server_in_dst = false; + return false; +} + +// we want to correlate src_zone to src_nets and src_ports, and dst_zone to dst_nets and +// dst_ports. it doesn't matter if the packet is actually moving in the opposite direction as +// binder is only evaluated once per flow and we need to capture the correct binding from +// either side of the conversation +template +Binding::DirResult directional_match(const When& when_src, const When& when_dst, + const Traffic& traffic_src, const Traffic& traffic_dst, + const Binding::DirResult dr, const Compare& compare) +{ + bool src_in_src = false; + bool src_in_dst = false; + bool dst_in_src = false; + bool dst_in_dst = false; + bool forward_match = false; + bool reverse_match = false; switch ( dr ) { case Binding::DR_ANY_MATCH: - client_in_src = when.src_ports.test(flow->client_port); - client_in_dst = when.dst_ports.test(flow->client_port); - server_in_src = when.src_ports.test(flow->server_port); - server_in_dst = when.dst_ports.test(flow->server_port); - return ( client_in_src and server_in_dst ) or ( server_in_src and client_in_dst ); - - case Binding::DR_CLIENT_SRC: - client_in_src = when.src_ports.test(flow->client_port); - server_in_dst = when.dst_ports.test(flow->server_port); - return client_in_src and server_in_dst; - - case Binding::DR_SERVER_SRC: - server_in_src = when.src_ports.test(flow->server_port); - client_in_dst = when.dst_ports.test(flow->client_port); - return server_in_src and client_in_dst; + src_in_src = compare(when_src, traffic_src); + src_in_dst = compare(when_dst, traffic_src); + dst_in_src = compare(when_src, traffic_dst); + dst_in_dst = compare(when_dst, traffic_dst); + + forward_match = src_in_src and dst_in_dst; + reverse_match = dst_in_src and src_in_dst; + + if ( forward_match and reverse_match ) + return dr; + + if ( forward_match ) + return Binding::DR_FORWARD; + + if ( reverse_match ) + return Binding::DR_REVERSE; + + return Binding::DR_NO_MATCH; + + case Binding::DR_FORWARD: + src_in_src = compare(when_src, traffic_src); + dst_in_dst = compare(when_dst, traffic_dst); + return src_in_src and dst_in_dst ? dr : Binding::DR_NO_MATCH; + + case Binding::DR_REVERSE: + src_in_dst = compare(when_dst, traffic_src); + dst_in_src = compare(when_src, traffic_dst); + return src_in_dst and dst_in_src ? dr : Binding::DR_NO_MATCH; default: break; } - return false; + + return Binding::DR_NO_MATCH; } -bool Binding::check_service(const Flow* flow) const +Binding::DirResult Binding::check_split_addr(const Flow* flow, const Packet* p, + const Binding::DirResult dr) const { - if ( !flow->service ) - return when.svc.empty(); + if ( !when.split_nets ) + return dr; - if ( when.svc == flow->service ) - return true; + if ( !when.src_nets && !when.dst_nets ) + return dr; + + const SfIp* src_ip = &flow->client_ip; + const SfIp* dst_ip = &flow->server_ip; - return false; + if ( p && p->ptrs.ip_api.is_ip() ) + { + src_ip = p->ptrs.ip_api.get_src(); + dst_ip = p->ptrs.ip_api.get_dst(); + } + + return directional_match(when.src_nets, when.dst_nets, src_ip, dst_ip, dr, + [](sfip_var_t* when_val, const SfIp* traffic_val) + { return when_val ? sfvar_ip_in(when_val, traffic_val) : true; }); + +} + +Binding::DirResult Binding::check_split_port(const Flow* flow, const Packet* p, + const Binding::DirResult dr) const +{ + if ( !when.split_ports ) + return dr; + + uint16_t src_port = flow->client_port; + uint16_t dst_port = flow->server_port; + + if ( p ) + { + if ( p->is_tcp() ) + { + src_port = p->ptrs.tcph->src_port(); + dst_port = p->ptrs.tcph->dst_port(); + } + else if ( p->is_udp() ) + { + src_port = p->ptrs.udph->src_port(); + dst_port = p->ptrs.udph->dst_port(); + } + else + return dr; + } + + return directional_match(when.src_ports, when.dst_ports, src_port, dst_port, dr, + [](const PortBitSet& when_val, uint16_t traffic_val) + { return when_val.test(traffic_val); }); +} + +Binding::DirResult Binding::check_zone(const Packet* p, const Binding::DirResult dr) const +{ + if ( !p ) + return dr; + + return directional_match(when.src_zone, when.dst_zone, + p->pkth->ingress_group, p->pkth->egress_group, dr, + [](int32_t when_val, int32_t zone) + { return when_val == DAQ_PKTHDR_UNKNOWN or when_val == zone; }); } -bool Binding::check_all(const Flow* flow) const +bool Binding::check_all(const Flow* flow, Packet* p) const { + Binding::DirResult dir = Binding::DR_ANY_MATCH; + if ( !check_ips_policy(flow) ) return false; - if ( !check_iface(flow) ) + if ( !check_iface(p) ) return false; if ( !check_vlan(flow) ) @@ -259,7 +331,7 @@ bool Binding::check_all(const Flow* flow) const if ( !check_addr(flow) ) return false; - auto dir = check_split_addr(flow); + dir = check_split_addr(flow, p, dir); if ( dir == Binding::DR_NO_MATCH ) return false; @@ -269,12 +341,17 @@ bool Binding::check_all(const Flow* flow) const if ( !check_port(flow) ) return false; - if ( !check_split_port(flow, dir) ) + dir = check_split_port(flow, p, dir); + if ( dir == Binding::DR_NO_MATCH ) return false; if ( !check_service(flow) ) return false; + dir = check_zone(p, dir); + if ( dir == Binding::DR_NO_MATCH ) + return false; + return true; } @@ -501,7 +578,7 @@ private: void apply(const Stuff&, Flow*); void set_binding(SnortConfig*, Binding*); - void get_bindings(Flow*, Stuff&); + void get_bindings(Flow*, Stuff&, Packet* = nullptr); // may be null when dealing with HA flows void apply(Flow*, Stuff&); Inspector* find_gadget(Flow*); int exec_handle_gadget(void*); @@ -569,12 +646,10 @@ void Binder::update(SnortConfig*, const char* name) void Binder::eval(Packet* p) { + Stuff stuff; Flow* flow = p->flow; - flow->iface_in = p->pkth->ingress_index; - flow->iface_out = p->pkth->egress_index; - Stuff stuff; - get_bindings(flow, stuff); + get_bindings(flow, stuff, p); apply(flow, stuff); ++bstats.verdicts[stuff.action]; @@ -674,7 +749,7 @@ void Binder::set_binding(SnortConfig*, Binding* pb) // FIXIT-P this is a simple linear search until functionality is nailed // down. performance should be the focus of the next iteration. -void Binder::get_bindings(Flow* flow, Stuff& stuff) +void Binder::get_bindings(Flow* flow, Stuff& stuff, Packet* p) { Binding* pb; unsigned i, sz = bindings.size(); @@ -683,7 +758,7 @@ void Binder::get_bindings(Flow* flow, Stuff& stuff) { pb = bindings[i]; - if ( !pb->check_all(flow) ) + if ( !pb->check_all(flow, p) ) continue; if ( !pb->use.ips_index && !pb->use.inspection_index ) @@ -723,7 +798,7 @@ void Binder::get_bindings(Flow* flow, Stuff& stuff) if ( sub ) { - sub->get_bindings(flow, stuff); + sub->get_bindings(flow, stuff, p); return; } } diff --git a/src/network_inspectors/binder/binding.h b/src/network_inspectors/binder/binding.h index 69e191038..289ec15aa 100644 --- a/src/network_inspectors/binder/binding.h +++ b/src/network_inspectors/binder/binding.h @@ -26,7 +26,7 @@ #include "sfip/sf_ipvar.h" class Flow; - +struct Packet; struct BindWhen { enum Role @@ -47,6 +47,9 @@ struct BindWhen bool split_ports; PortBitSet src_ports; PortBitSet dst_ports; + + int32_t src_zone; + int32_t dst_zone; }; struct BindUse @@ -72,7 +75,21 @@ struct BindUse struct Binding { enum DirResult - { DR_NO_MATCH, DR_ANY_MATCH, DR_CLIENT_SRC, DR_SERVER_SRC }; + { + // Did not match + DR_NO_MATCH, + + // Matched but direction could not be determined + DR_ANY_MATCH, + + // On flow: src_* matched client, dst_* matched server + // On packet: src_* matched p->src_*, dst_* matched p->dst_* + DR_FORWARD, + + // On flow: src_* matched server, dst_* matched client + // On packet: src_* matched p->dst_*, dst_* matched p->src_* + DR_REVERSE, + }; BindWhen when; BindUse use; @@ -80,16 +97,17 @@ struct Binding Binding(); ~Binding(); - bool check_all(const Flow*) const; + bool check_all(const Flow*, Packet*) const; bool check_ips_policy(const Flow*) const; - bool check_iface(const Flow*) const; + bool check_iface(const Packet*) const; bool check_vlan(const Flow*) const; bool check_addr(const Flow*) const; - DirResult check_split_addr(const Flow*) const; + DirResult check_split_addr(const Flow*, const Packet*, const DirResult) const; bool check_proto(const Flow*) const; bool check_port(const Flow*) const; - bool check_split_port(const Flow*, const DirResult) const; + DirResult check_split_port(const Flow*, const Packet*, const DirResult) const; bool check_service(const Flow*) const; + DirResult check_zone(const Packet*, const DirResult) const; }; #endif diff --git a/src/service_inspectors/http_inspect/http_stream_splitter_reassemble.cc b/src/service_inspectors/http_inspect/http_stream_splitter_reassemble.cc index 57fb53ac5..ccec9be84 100644 --- a/src/service_inspectors/http_inspect/http_stream_splitter_reassemble.cc +++ b/src/service_inspectors/http_inspect/http_stream_splitter_reassemble.cc @@ -141,7 +141,7 @@ void HttpStreamSplitter::decompress_copy(uint8_t* buffer, uint32_t& offset, cons { if ((compression == CMP_GZIP) || (compression == CMP_DEFLATE)) { - compress_stream->next_in = const_cast(data); + compress_stream->next_in = (Bytef*)data; compress_stream->avail_in = length; compress_stream->next_out = buffer + offset; compress_stream->avail_out = MAX_OCTETS - offset; @@ -185,7 +185,7 @@ void HttpStreamSplitter::decompress_copy(uint8_t* buffer, uint32_t& offset, cons static constexpr char zlib_header[2] = { 0x78, 0x01 }; inflateReset(compress_stream); - compress_stream->next_in = (z_const Bytef*)zlib_header; + compress_stream->next_in = (Bytef*)zlib_header; compress_stream->avail_in = sizeof(zlib_header); inflate(compress_stream, Z_SYNC_FLUSH); diff --git a/tools/snort2lua/helpers/util_binder.cc b/tools/snort2lua/helpers/util_binder.cc index 1d5ed0ca3..c24e0fb4b 100644 --- a/tools/snort2lua/helpers/util_binder.cc +++ b/tools/snort2lua/helpers/util_binder.cc @@ -24,7 +24,7 @@ using namespace std; -Binder::Binder(TableApi& t) : table_api(t), printed(false), when_ips_policy_id(-1) +Binder::Binder(TableApi& t) : table_api(t) { } Binder::~Binder() @@ -69,6 +69,12 @@ void Binder::add_to_configuration() for ( const auto& p : ports ) table_api.add_list("ports", p); + if ( has_src_zone() ) + table_api.add_option("src_zone", std::stoi(when_src_zone)); + + if ( has_dst_zone() ) + table_api.add_option("dst_zone", std::stoi(when_dst_zone)); + if ( has_proto() ) table_api.add_option("proto", when_proto); @@ -122,6 +128,12 @@ void Binder::add_to_configuration() table_api.close_table(); // "binder" } +void Binder::set_priority(unsigned p) +{ priority = p; } + +unsigned Binder::get_priority() +{ return priority; } + void Binder::set_when_ips_policy_id(int id) { when_ips_policy_id = id; } @@ -155,6 +167,12 @@ void Binder::add_when_dst_port(const std::string& port) void Binder::add_when_port(const std::string& port) { ports.push_back(port); } +void Binder::set_when_src_zone(const std::string& zone) +{ when_src_zone = zone; } + +void Binder::set_when_dst_zone(const std::string& zone) +{ when_dst_zone = zone; } + void Binder::clear_ports() { ports.clear(); } @@ -212,8 +230,16 @@ bool operator<(const shared_ptr& left, const shared_ptr& right) if ( (left) > (right) ) return true; \ } - //By priorities of options + // By predetermined order + FIRST_IF_LT(left->get_priority(), right->get_priority()); + + // By priorities of options FIRST_IF_GT(left->has_ips_policy_id(), right->has_ips_policy_id()) + + auto left_zone_specs = left->has_src_zone() + left->has_dst_zone(); + auto right_zone_specs = right->has_src_zone() + right->has_dst_zone(); + FIRST_IF_GT(left_zone_specs, right_zone_specs); + FIRST_IF_GT(left->has_vlans(), right->has_vlans()) FIRST_IF_GT(left->has_service(), right->has_service()) @@ -231,7 +257,7 @@ bool operator<(const shared_ptr& left, const shared_ptr& right) FIRST_IF_GT(left->has_proto(), right->has_proto()) FIRST_IF_GT(left->has_role(), right->has_role()) - //By values of options. Fewer specs = more specific. + // By values of options. Fewer specs = more specific. if ( left->has_vlans() && right->has_vlans() ) FIRST_IF_LT(left->vlans.size(), right->vlans.size()) @@ -243,7 +269,7 @@ bool operator<(const shared_ptr& left, const shared_ptr& right) if ( left->has_ports() && right->has_ports() ) FIRST_IF_LT(left->ports.size(), right->ports.size()) - //Sorted by value for readability if all else is equal + // Sorted by value for readability if all else is equal if ( left->has_ips_policy_id() && right->has_ips_policy_id() ) FIRST_IF_LT(left->when_ips_policy_id, right->when_ips_policy_id) @@ -265,7 +291,7 @@ bool operator<(const shared_ptr& left, const shared_ptr& right) void print_binder_priorities() { - static unsigned const num_combos = 2 << 10; + static unsigned const num_combos = 2 << 12; vector> binders; TableApi t; @@ -278,33 +304,39 @@ void print_binder_priorities() binders.back()->set_when_ips_policy_id(1); if ( i & (1 << 1) ) - binders.back()->add_when_vlan("a"); + binders.back()->set_when_src_zone("0"); if ( i & (1 << 2) ) - binders.back()->set_when_service("a"); + binders.back()->set_when_dst_zone("0"); if ( i & (1 << 3) ) - binders.back()->add_when_src_net("a"); + binders.back()->add_when_vlan("a"); if ( i & (1 << 4) ) - binders.back()->add_when_dst_net("a"); + binders.back()->set_when_service("a"); if ( i & (1 << 5) ) - binders.back()->add_when_net("a"); + binders.back()->add_when_src_net("a"); if ( i & (1 << 6) ) - binders.back()->add_when_src_port("a"); + binders.back()->add_when_dst_net("a"); if ( i & (1 << 7) ) - binders.back()->add_when_dst_port("a"); + binders.back()->add_when_net("a"); if ( i & (1 << 8) ) - binders.back()->add_when_port("a"); + binders.back()->add_when_src_port("a"); if ( i & (1 << 9) ) - binders.back()->set_when_proto("a"); + binders.back()->add_when_dst_port("a"); if ( i & (1 << 10) ) + binders.back()->add_when_port("a"); + + if ( i & (1 << 11) ) + binders.back()->set_when_proto("a"); + + if ( i & (1 << 12) ) binders.back()->set_when_role("a"); } @@ -318,6 +350,12 @@ void print_binder_priorities() if ( b->has_vlans() ) cout << "vlan "; + if ( b->has_src_zone() ) + cout << "src_zone "; + + if ( b->has_dst_zone() ) + cout << "dst_zone "; + if ( b->has_service() ) cout << "service "; diff --git a/tools/snort2lua/helpers/util_binder.h b/tools/snort2lua/helpers/util_binder.h index f52bacee0..bdf4b941c 100644 --- a/tools/snort2lua/helpers/util_binder.h +++ b/tools/snort2lua/helpers/util_binder.h @@ -20,6 +20,7 @@ #ifndef HELPERS_PPS_BINDER_H #define HELPERS_PPS_BINDER_H +#include #include #include #include @@ -50,6 +51,9 @@ public: void print_binding(bool should_print) { printed = !should_print; } + void set_priority(unsigned); + unsigned get_priority(); + void set_when_ips_policy_id(int); void set_when_service(const std::string&); void set_when_role(const std::string&); @@ -61,6 +65,8 @@ public: void add_when_port(const std::string&); void add_when_src_port(const std::string&); void add_when_dst_port(const std::string&); + void set_when_src_zone(const std::string&); + void set_when_dst_zone(const std::string&); void clear_ports(); int get_when_ips_policy_id() const @@ -99,6 +105,12 @@ public: bool has_ports() const { return !ports.empty(); } + bool has_src_zone() const + { return !when_src_zone.empty(); } + + bool has_dst_zone() const + { return !when_dst_zone.empty(); } + void set_use_type(const std::string& module_name); void set_use_name(const std::string& struct_name); void set_use_file(const std::string& file_name, IncludeType = IT_FILE); @@ -122,10 +134,12 @@ public: private: TableApi& table_api; - bool printed; // ensures that the binding is added once, - // by either the destructor or user + bool printed = false; // ensures that the binding is added once, + // by either the destructor or user - int when_ips_policy_id; + unsigned priority = UINT_MAX; + + int when_ips_policy_id = -1; std::string when_service; std::string when_role; std::string when_proto; @@ -136,6 +150,8 @@ private: std::vector ports; std::vector src_ports; std::vector dst_ports; + std::string when_src_zone; + std::string when_dst_zone; std::string use_type; std::string use_name; diff --git a/tools/snort2lua/preprocessor_states/pps_dcerpc_server.cc b/tools/snort2lua/preprocessor_states/pps_dcerpc_server.cc index 0c3a72d94..ebfcebcd7 100644 --- a/tools/snort2lua/preprocessor_states/pps_dcerpc_server.cc +++ b/tools/snort2lua/preprocessor_states/pps_dcerpc_server.cc @@ -653,6 +653,11 @@ bool DcerpcServer::convert(std::istringstream& data_stream) bind["http_proxy"] = &bind_http_proxy; bind["http_server"] = &bind_http_server; + // FIXIT-N add when there is a way to make this play with http_inspect bindings + // port 80 should not be added by default. If explicitly configured and conflicting + // with other bindings, punt to wizard + bind["http_proxy"]->print_binding(false); + for (const auto& type : transport) { bind[type]->set_when_proto("tcp"); diff --git a/tools/snort2lua/preprocessor_states/pps_nap_selector.cc b/tools/snort2lua/preprocessor_states/pps_nap_selector.cc index af30d74d4..f9c935d79 100644 --- a/tools/snort2lua/preprocessor_states/pps_nap_selector.cc +++ b/tools/snort2lua/preprocessor_states/pps_nap_selector.cc @@ -58,10 +58,10 @@ public: std::string ips_policy; TRY_FIELD(action); // ignore since nap rules don't drop - TRY_FIELD(src_zone); // FIXIT-M parse zones when implemented + TRY_FIELD(src_zone); TRY_FIELD(src_net); TRY_FIELD(src_port); - TRY_FIELD(dst_zone); // FIXIT-M parse zones when implemented + TRY_FIELD(dst_zone); TRY_FIELD(dst_net); TRY_FIELD(dst_port); TRY_FIELD(vlan); @@ -100,12 +100,20 @@ public: auto& bind = cv.make_pending_binder(policy_id); + bind.set_priority(order++); + + if ( src_zone != "any" ) + bind.set_when_src_zone(src_zone); + if ( src_net != "any" ) bind.add_when_src_net(src_net); if ( src_port != "any" ) bind.add_when_src_port(src_port); + if ( dst_zone != "any" ) + bind.set_when_dst_zone(dst_zone); + if ( dst_net != "any" ) bind.add_when_dst_net(dst_net); @@ -135,6 +143,9 @@ public: return true; } + +private: + unsigned order = 0; }; class NapSelectorState : public ConversionState