From the perspective of the rest of the system, just above the network itself is libpcap [MLJ94], the packet-capture library used by tcpdump [JLM89]. Using libpcap gains significant advantages: it isolates Bro from details of the network link technology (Ethernet, FDDI, SLIP, etc.); it greatly aids in porting Bro to different Unix variants (which also makes it easier to upgrade to faster hardware as it becomes available); and it means that Bro can also operate on tcpdump save files, making off-line development and analysis easy.
Another major advantage of libpcap is that if the host operating system provides a sufficiently powerful kernel packet filter, such as BPF [MJ93], then libpcap downloads the filter used to reduce the traffic into the kernel. Consequently, rather than having to haul every packet up to user-level merely so the majority can be discarded (if the filter accepts only a small proportion of the traffic), the rejected packets can instead be discarded in the kernel, without suffering a context switch or data copying. Winnowing down the packet stream as soon as possible greatly abets monitoring at high speeds without losing packets.
The key to packet filtering is, of course, judicious selection of which packets to keep and which to discard. For the application protocols that Bro knows about, it captures every packet, so it can analyze how the application is being used. In tcpdump's filtering language, this looks like:
tcp port finger or tcp port ftp or tcp port telnet or port 111That is, the filter accepts any TCP packets with a source or destination port of 79 (Finger), 21 (FTP), or 23 (Telnet), and any TCP or UDP packets with a source or destination port of 111 (Portmapper). In addition, Bro uses:
tcp[13] & 7 != 0to capture any TCP packets with the SYN, FIN, or RST control bits set. These packets delimit the beginning (SYN) and end (FIN or RST) of each TCP connection. Because TCP/IP packet headers contain considerable information about each TCP connection, from just these control packets one can extract connection start time, duration, participating hosts, ports (and hence, generally, the name of the application), and the number of bytes sent in each direction. Thus, by capturing on the order of only 4 packets (the two initial SYN packets exchanged, and the final two FIN packets exchanged), we can determine a great deal about a connection even though we filter out all of its data packets.
When using a packet filter, one must also choose a snapshot length, which determines how much of each packet should be captured. For example, by default tcpdump uses a snapshot length of 68 bytes, which suffices to capture link-layer and TCP/IP headers, but generally discards most of the data in the packet. The smaller the snapshot length, the less data per accepted packet needs to copied up to the user-level by the packet filter, which aids in accelerating packet processing and avoiding loss. On the other hand, to analyze connections at the application level, Bro requires the full data contents of each packet. Consequently, it sets the snapshot length to capture entire packets.