mirror of
https://github.com/zeek/zeek.git
synced 2025-10-12 19:48:20 +00:00
Add check_subnet bif that allows exact membership test for subnet tables.
This commit also fixes a few small bugs introduced in the last patricia tree commit.
This commit is contained in:
parent
7ef431808d
commit
692662abcc
4 changed files with 82 additions and 5 deletions
|
@ -106,7 +106,7 @@ list<IPPrefix> PrefixTable::FindAll(const IPAddr& addr, int width) const
|
||||||
|
|
||||||
list<IPPrefix> PrefixTable::FindAll(const SubNetVal* value) const
|
list<IPPrefix> PrefixTable::FindAll(const SubNetVal* value) const
|
||||||
{
|
{
|
||||||
return FindAll(value->AsSubNet().Prefix(), value->AsSubNet().LengthIPv6());
|
return FindAll(value->AsSubNet().Prefix(), value->AsSubNet().Length());
|
||||||
}
|
}
|
||||||
|
|
||||||
void* PrefixTable::Lookup(const IPAddr& addr, int width, bool exact) const
|
void* PrefixTable::Lookup(const IPAddr& addr, int width, bool exact) const
|
||||||
|
@ -132,12 +132,12 @@ void* PrefixTable::Lookup(const Val* value, bool exact) const
|
||||||
|
|
||||||
switch ( value->Type()->Tag() ) {
|
switch ( value->Type()->Tag() ) {
|
||||||
case TYPE_ADDR:
|
case TYPE_ADDR:
|
||||||
return Lookup(value->AsAddr(), 128, exact);
|
return Lookup(value->AsAddr(), value->AsAddr().GetFamily() == IPv4 ? 32 : 128, exact);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case TYPE_SUBNET:
|
case TYPE_SUBNET:
|
||||||
return Lookup(value->AsSubNet().Prefix(),
|
return Lookup(value->AsSubNet().Prefix(),
|
||||||
value->AsSubNet().LengthIPv6(), exact);
|
value->AsSubNet().Length(), exact);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
|
@ -171,12 +171,12 @@ void* PrefixTable::Remove(const Val* value)
|
||||||
|
|
||||||
switch ( value->Type()->Tag() ) {
|
switch ( value->Type()->Tag() ) {
|
||||||
case TYPE_ADDR:
|
case TYPE_ADDR:
|
||||||
return Remove(value->AsAddr(), 128);
|
return Remove(value->AsAddr(), value->AsAddr().GetFamily() == IPv4 ? 32 : 128);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case TYPE_SUBNET:
|
case TYPE_SUBNET:
|
||||||
return Remove(value->AsSubNet().Prefix(),
|
return Remove(value->AsSubNet().Prefix(),
|
||||||
value->AsSubNet().LengthIPv6());
|
value->AsSubNet().Length());
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
|
|
30
src/bro.bif
30
src/bro.bif
|
@ -1065,6 +1065,36 @@ function matching_subnets%(search: subnet, t: any%): subnet_vec
|
||||||
return result_v;
|
return result_v;
|
||||||
%}
|
%}
|
||||||
|
|
||||||
|
## Checks if a specific subnet is a member of a set/table[subnet].
|
||||||
|
## In difference to the in operator, this performs an exact match, not
|
||||||
|
## a longest prefix match
|
||||||
|
##
|
||||||
|
## search: the subnet to search for.
|
||||||
|
##
|
||||||
|
## t: the set[subnet] or table[subnet].
|
||||||
|
##
|
||||||
|
##
|
||||||
|
## Returns: True if the exact subnet is a member, false otherwise.
|
||||||
|
function check_subnet%(search: subnet, t: any%): bool
|
||||||
|
%{
|
||||||
|
if ( t->Type()->Tag() != TYPE_TABLE || ! t->Type()->AsTableType()->IsSubNetIndex() )
|
||||||
|
{
|
||||||
|
reporter->Error("matching_subnets needs to be called on a set[subnet]/table[subnet].");
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
const PrefixTable* pt = t->AsTableVal()->Subnets();
|
||||||
|
if ( !pt )
|
||||||
|
{
|
||||||
|
reporter->Error("matching_subnets encountered nonexisting prefix table.");
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
void* res = pt->Lookup(search, true);
|
||||||
|
|
||||||
|
return new Val (res != nullptr, TYPE_BOOL);
|
||||||
|
%}
|
||||||
|
|
||||||
## Checks whether two objects reference the same internal object. This function
|
## Checks whether two objects reference the same internal object. This function
|
||||||
## uses equality comparison of C++ raw pointer values to determine if the two
|
## uses equality comparison of C++ raw pointer values to determine if the two
|
||||||
## objects are the same.
|
## objects are the same.
|
||||||
|
|
8
testing/btest/Baseline/bifs.check_subnet/output
Normal file
8
testing/btest/Baseline/bifs.check_subnet/output
Normal file
|
@ -0,0 +1,8 @@
|
||||||
|
in says: 10.2.0.2/32 is member
|
||||||
|
check_subnet says: 10.2.0.2/32 is no member
|
||||||
|
in says: 10.2.0.2/31 is member
|
||||||
|
check_subnet says: 10.2.0.2/31 is member
|
||||||
|
in says: 10.0.0.0/9 is member
|
||||||
|
check_subnet says: 10.0.0.0/9 is no member
|
||||||
|
in says: 10.0.0.0/8 is member
|
||||||
|
check_subnet says: 10.0.0.0/8 is member
|
39
testing/btest/bifs/check_subnet.bro
Normal file
39
testing/btest/bifs/check_subnet.bro
Normal file
|
@ -0,0 +1,39 @@
|
||||||
|
# @TEST-EXEC: bro -b %INPUT >output
|
||||||
|
# @TEST-EXEC: btest-diff output
|
||||||
|
|
||||||
|
global testt: set[subnet] = {
|
||||||
|
10.0.0.0/8,
|
||||||
|
10.2.0.0/16,
|
||||||
|
10.2.0.2/31,
|
||||||
|
10.1.0.0/16,
|
||||||
|
10.3.0.0/16,
|
||||||
|
5.0.0.0/8,
|
||||||
|
5.5.0.0/25,
|
||||||
|
5.2.0.0/32,
|
||||||
|
7.2.0.0/32,
|
||||||
|
[2607:f8b0:4008:807::200e]/64,
|
||||||
|
[2607:f8b0:4007:807::200e]/64,
|
||||||
|
[2607:f8b0:4007:807::200e]/128
|
||||||
|
};
|
||||||
|
|
||||||
|
function check_member(s: subnet)
|
||||||
|
{
|
||||||
|
if ( s in testt )
|
||||||
|
print fmt("in says: %s is member", s);
|
||||||
|
else
|
||||||
|
print fmt("in says: %s is no member", s);
|
||||||
|
|
||||||
|
if ( check_subnet(s, testt) )
|
||||||
|
print fmt("check_subnet says: %s is member", s);
|
||||||
|
else
|
||||||
|
print fmt("check_subnet says: %s is no member", s);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
event bro_init()
|
||||||
|
{
|
||||||
|
check_member(10.2.0.2/32);
|
||||||
|
check_member(10.2.0.2/31);
|
||||||
|
check_member(10.6.0.0/9);
|
||||||
|
check_member(10.2.0.0/8);
|
||||||
|
}
|
Loading…
Add table
Add a link
Reference in a new issue