mirror of
https://github.com/zeek/zeek.git
synced 2025-10-07 00:58:19 +00:00
Initial import of svn+ssh:://svn.icir.org/bro/trunk/bro as of r7088
This commit is contained in:
commit
61757ac78b
1383 changed files with 380824 additions and 0 deletions
196
src/Discard.cc
Normal file
196
src/Discard.cc
Normal file
|
@ -0,0 +1,196 @@
|
|||
// $Id: Discard.cc 6219 2008-10-01 05:39:07Z vern $
|
||||
//
|
||||
// See the file "COPYING" in the main distribution directory for copyright.
|
||||
|
||||
#include "config.h"
|
||||
|
||||
#include "Net.h"
|
||||
#include "Var.h"
|
||||
#include "Discard.h"
|
||||
|
||||
Discarder::Discarder()
|
||||
{
|
||||
ip_hdr = internal_type("ip_hdr")->AsRecordType();
|
||||
tcp_hdr = internal_type("tcp_hdr")->AsRecordType();
|
||||
udp_hdr = internal_type("udp_hdr")->AsRecordType();
|
||||
icmp_hdr = internal_type("icmp_hdr")->AsRecordType();
|
||||
|
||||
check_ip = internal_func("discarder_check_ip");
|
||||
check_tcp = internal_func("discarder_check_tcp");
|
||||
check_udp = internal_func("discarder_check_udp");
|
||||
check_icmp = internal_func("discarder_check_icmp");
|
||||
|
||||
discarder_maxlen = static_cast<int>(opt_internal_int("discarder_maxlen"));
|
||||
}
|
||||
|
||||
Discarder::~Discarder()
|
||||
{
|
||||
}
|
||||
|
||||
int Discarder::IsActive()
|
||||
{
|
||||
return check_ip || check_tcp || check_udp || check_icmp;
|
||||
}
|
||||
|
||||
int Discarder::NextPacket(const IP_Hdr* ip, int len, int caplen)
|
||||
{
|
||||
int discard_packet = 0;
|
||||
|
||||
const struct ip* ip4 = ip->IP4_Hdr();
|
||||
|
||||
if ( check_ip )
|
||||
{
|
||||
val_list* args = new val_list;
|
||||
args->append(BuildHeader(ip4));
|
||||
discard_packet = check_ip->Call(args)->AsBool();
|
||||
delete args;
|
||||
|
||||
if ( discard_packet )
|
||||
return discard_packet;
|
||||
}
|
||||
|
||||
int proto = ip4->ip_p;
|
||||
if ( proto != IPPROTO_TCP && proto != IPPROTO_UDP &&
|
||||
proto != IPPROTO_ICMP )
|
||||
// This is not a protocol we understand.
|
||||
return 0;
|
||||
|
||||
// XXX shall we only check the first packet???
|
||||
uint32 frag_field = ntohs(ip4->ip_off);
|
||||
if ( (frag_field & 0x3fff) != 0 )
|
||||
// Never check any fragment.
|
||||
return 0;
|
||||
|
||||
int ip_hdr_len = ip4->ip_hl * 4;
|
||||
len -= ip_hdr_len; // remove IP header
|
||||
caplen -= ip_hdr_len;
|
||||
|
||||
int is_tcp = (proto == IPPROTO_TCP);
|
||||
int is_udp = (proto == IPPROTO_UDP);
|
||||
int min_hdr_len = is_tcp ?
|
||||
sizeof(struct tcphdr) :
|
||||
(is_udp ? sizeof(struct udphdr) : sizeof(struct icmp));
|
||||
|
||||
if ( len < min_hdr_len || caplen < min_hdr_len )
|
||||
// we don't have a complete protocol header
|
||||
return 0;
|
||||
|
||||
// Where the data starts - if this is a protocol we know about,
|
||||
// this gets advanced past the transport header.
|
||||
const u_char* data = ((u_char*) ip4 + ip_hdr_len);
|
||||
|
||||
if ( is_tcp )
|
||||
{
|
||||
if ( check_tcp )
|
||||
{
|
||||
const struct tcphdr* tp = (const struct tcphdr*) data;
|
||||
int th_len = tp->th_off * 4;
|
||||
|
||||
val_list* args = new val_list;
|
||||
args->append(BuildHeader(ip4));
|
||||
args->append(BuildHeader(tp, len));
|
||||
args->append(BuildData(data, th_len, len, caplen));
|
||||
discard_packet = check_tcp->Call(args)->AsBool();
|
||||
delete args;
|
||||
}
|
||||
}
|
||||
|
||||
else if ( is_udp )
|
||||
{
|
||||
if ( check_udp )
|
||||
{
|
||||
const struct udphdr* up = (const struct udphdr*) data;
|
||||
int uh_len = sizeof (struct udphdr);
|
||||
|
||||
val_list* args = new val_list;
|
||||
args->append(BuildHeader(ip4));
|
||||
args->append(BuildHeader(up));
|
||||
args->append(BuildData(data, uh_len, len, caplen));
|
||||
discard_packet = check_udp->Call(args)->AsBool();
|
||||
delete args;
|
||||
}
|
||||
}
|
||||
|
||||
else
|
||||
{
|
||||
if ( check_icmp )
|
||||
{
|
||||
const struct icmp* ih = (const struct icmp*) data;
|
||||
|
||||
val_list* args = new val_list;
|
||||
args->append(BuildHeader(ip4));
|
||||
args->append(BuildHeader(ih));
|
||||
discard_packet = check_icmp->Call(args)->AsBool();
|
||||
delete args;
|
||||
}
|
||||
}
|
||||
|
||||
return discard_packet;
|
||||
}
|
||||
|
||||
Val* Discarder::BuildHeader(const struct ip* ip)
|
||||
{
|
||||
RecordVal* hdr = new RecordVal(ip_hdr);
|
||||
|
||||
hdr->Assign(0, new Val(ip->ip_hl * 4, TYPE_COUNT));
|
||||
hdr->Assign(1, new Val(ip->ip_tos, TYPE_COUNT));
|
||||
hdr->Assign(2, new Val(ntohs(ip->ip_len), TYPE_COUNT));
|
||||
hdr->Assign(3, new Val(ntohs(ip->ip_id), TYPE_COUNT));
|
||||
hdr->Assign(4, new Val(ip->ip_ttl, TYPE_COUNT));
|
||||
hdr->Assign(5, new Val(ip->ip_p, TYPE_COUNT));
|
||||
hdr->Assign(6, new AddrVal(ip->ip_src.s_addr));
|
||||
hdr->Assign(7, new AddrVal(ip->ip_dst.s_addr));
|
||||
|
||||
return hdr;
|
||||
}
|
||||
|
||||
Val* Discarder::BuildHeader(const struct tcphdr* tp, int tcp_len)
|
||||
{
|
||||
RecordVal* hdr = new RecordVal(tcp_hdr);
|
||||
|
||||
hdr->Assign(0, new PortVal(ntohs(tp->th_sport), TRANSPORT_TCP));
|
||||
hdr->Assign(1, new PortVal(ntohs(tp->th_dport), TRANSPORT_TCP));
|
||||
hdr->Assign(2, new Val(uint32(ntohl(tp->th_seq)), TYPE_COUNT));
|
||||
hdr->Assign(3, new Val(uint32(ntohl(tp->th_ack)), TYPE_COUNT));
|
||||
|
||||
int tcp_hdr_len = tp->th_off * 4;
|
||||
|
||||
hdr->Assign(4, new Val(tcp_hdr_len, TYPE_COUNT));
|
||||
hdr->Assign(5, new Val(tcp_len - tcp_hdr_len, TYPE_COUNT));
|
||||
|
||||
hdr->Assign(6, new Val(tp->th_flags, TYPE_COUNT));
|
||||
hdr->Assign(7, new Val(ntohs(tp->th_win), TYPE_COUNT));
|
||||
|
||||
return hdr;
|
||||
}
|
||||
|
||||
Val* Discarder::BuildHeader(const struct udphdr* up)
|
||||
{
|
||||
RecordVal* hdr = new RecordVal(udp_hdr);
|
||||
|
||||
hdr->Assign(0, new PortVal(ntohs(up->uh_sport), TRANSPORT_UDP));
|
||||
hdr->Assign(1, new PortVal(ntohs(up->uh_dport), TRANSPORT_UDP));
|
||||
hdr->Assign(2, new Val(ntohs(up->uh_ulen), TYPE_COUNT));
|
||||
|
||||
return hdr;
|
||||
}
|
||||
|
||||
Val* Discarder::BuildHeader(const struct icmp* icmp)
|
||||
{
|
||||
RecordVal* hdr = new RecordVal(icmp_hdr);
|
||||
|
||||
hdr->Assign(0, new Val(icmp->icmp_type, TYPE_COUNT));
|
||||
|
||||
return hdr;
|
||||
}
|
||||
|
||||
Val* Discarder::BuildData(const u_char* data, int hdrlen, int len, int caplen)
|
||||
{
|
||||
len -= hdrlen;
|
||||
caplen -= hdrlen;
|
||||
data += hdrlen;
|
||||
|
||||
len = max(min(min(len, caplen), discarder_maxlen), 0);
|
||||
|
||||
return new StringVal(new BroString(data, len, 1));
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue