Man Linux: Main Page and Category List

NAME

       libnids - network intrusion detection system E-box library

SYNOPSIS

       #include <nids.h>

       extern struct nids_prm nids_params;
       extern char nids_errbuf[];

       int
       nids_init(void);

       void
       nids_register_ip_frag(void (*ip_frag_func)(struct ip *pkt, int len));

       void
       nids_unregister_ip_frag(void (*ip_frag_func)(struct ip *pkt, int len));

       void
       nids_register_ip(void (*ip_func)(struct ip *pkt, int len));

       void
       nids_unregister_ip(void (*ip_func)(struct ip *pkt, int len));

       void
       nids_register_udp(void (*udp_func)(struct tuple4 *addr, u_char *data, int len, struct ip *pkt));

       void
       nids_unregister_udp(void (*udp_func)(struct tuple4 *addr, u_char *data, int len, struct ip *pkt));

       void
       nids_register_tcp(void (*tcp_func)(struct tcp_stream *ts, void **param));

       void
       nids_unregister_tcp(void (*tcp_func)(struct tcp_stream *ts, void **param));

       void
       nids_killtcp(struct tcp_stream *ts);

       void
       nids_discard(struct tcp_stream *ts, int numbytes);

       void
       nids_run(void);

       int
       nids_dispatch(int cnt);

       int
       nids_next(void);

       int
       nids_getfd(void);

       void
       nids_register_chksum_ctl(struct nids_chksum_ctl *, int);

       void
       nids_pcap_handler(u_char *par, struct pcap_pkthdr *hdr, u_char *data);

       struct tcp_stream *
       nids_find_tcp_stream(struct tuple4 *addr);

DESCRIPTION

       libnids  provides  the  functionality  of a network intrusion detection
       system (NIDS) E-box component. It currently performs:

            1. IP defragmentation
            2. TCP stream reassembly
            3. TCP port scan detection

       libnids performs TCP/IP reassembly in exactly the  same  way  as  Linux
       2.0.36 kernels, and correctly handles all of the attacks implemented in
       fragrouter(8) (plus many other attacks as well).

ROUTINES

       nids_init() initializes the application  for  sniffing,  based  on  the
       values set in the global variable nids_params, declared as follows:

       struct nids_prm {
            int  n_tcp_streams;
            int  n_hosts;
            char *device;
            char *filename;
            int  sk_buff_size;
            int  dev_addon;
            void (*syslog)(int type, int err, struct ip *iph, void *data);
            int  syslog_level;
            int  scan_num_hosts;
            int  scan_num_ports;
            int  scan_delay;
            void (*no_mem)(void);
            int  (*ip_filter)(struct ip *iph);
            char *pcap_filter;
            int  promisc;
            int  one_loop_less;
            int  pcap_timeout;
            int  multiproc;
            int  queue_limit;
            int  tcp_workarounds;
            pcap_t    *pcap_desc;
       } nids_params;

       The members of this structure are:

       n_tcp_streams
              Size   of  the  hash  table  used  for  storing  TCP  connection
              information ( a maximum of 3/4 * n_tcp_streams  TCP  connections
              will be followed simultaneously). Default value: 1024

       n_hosts
              Size  of  the  hash  table  used  for storing IP defragmentation
              information. Default value: 256

       filename
              It this variable is set,  libnids  will  call  pcap_open_offline
              with    this    variable    as    the   argument   (instead   of
              pcap_open_live()). Default value: NULL

       device Interface to monitor. Default value:  NULL  (in  which  case  an
              appropriate   device   is  determined  automatically).  If  this
              variable is assigned value all, libnids will attempt to  capture
              packets on all interfaces (which works on Linux only)

       sk_buff_size
              Size  of struct sk_buff (used for queuing packets), which should
              be set to match the value on the hosts being monitored.  Default
              value: 168

       dev_addon
              Number  of  bytes  in  struct  sk_buff  reserved  for link-layer
              information. Default value: -1 (in  which  case  an  appropriate
              offset if determined automatically based on link-layer type)

       syslog Syslog  callback  function,  used  to report unusual conditions,
              such as port scan  attempts,  invalid  TCP  header  flags,  etc.
              Default  value:  nids_syslog  (which logs messages via syslog(3)
              without regard for message rate per second or free disk space)

       syslog_level
              Log  level  used  by  nids_syslog  for  reporting   events   via
              syslog(3). Default value: LOG_ALERT

       scan_num_hosts
              Size  of  hash  table used for storing portscan information (the
              maximum number portscans that will be detected  simultaneously).
              If set to 0, portscan detection will be disabled. Default value:
              256

       scan_num_ports
              Minimum number of ports that  must  be  scanned  from  the  same
              source host before it is identifed as a portscan. Default value:
              10

       scan_delay
              Maximum delay (in milliseconds) between connections to different
              ports  for  them to be identified as part of a portscan. Default
              value: 3000

       no_mem Out-of-memory callback function, used to terminate  the  calling
              process gracefully.

       ip_filter
              IP  filtering  callback function, used to selectively discard IP
              packets, inspected after reassembly. If the function  returns  a
              non-zero  value,  the  packet  is  processed;  otherwise,  it is
              discarded. Default value: nids_ip_filter (which  always  returns
              1)

       pcap_filter
              pcap(3)   filter   string   applied   to  the  link-layer  (raw,
              unassembled) packets. Note: filters like  ‘‘tcp  dst  port  23’’
              will NOT correctly handle appropriately fragmented traffic, e.g.
              8-byte IP fragments; one should add "or (ip[6:2] & 0x1fff != 0)"
              at the end of the filter to process reassembled packets. Default
              value: NULL

       promisc
              If non-zero, libnids will set the interface(s) it listens on  to
              promiscuous mode. Default value: 1

       one_loop_less
              Disabled by default; see comments in API.html file

       pcap_timeout
              Sets the pcap read timeout, which may or may not be supported by
              your platform.  Default value: 1024.

       multiproc
              If nonzero, creates a separate thread  for  packets  processing.
              See API.html.  Default value: 0.

       queue_limit
              If  multiproc  is nonzero, this is the maximum number of packets
              queued in the thread which reads packets from  libpcap.  Default
              value: 20000

       tcp_workarounds
              Enables  extra  checks for faulty implementations of TCP such as
              the ones which allow connections to be closed despite  the  fact
              that  there should be retransmissions for lost packets first (as
              stated by RFC 793, section 3.5).  If non-zero, libnids will  set
              the   NIDS_TIMED_OUT  state  for  savagely  closed  connections.
              Default value: 0

       pcap_desc
              It  this  variable   is   set,   libnids   will   call   neither
              pcap_open_live  nor pcap_open_offline, but will use a pre-opened
              PCAP descriptor; use this with nids_pcap_handler() in  order  to
              interactively feed packets to libnids. Default value: NULL

       Returns  1 on success, 0 on failure (in which case nids_errbuf contains
       an appropriate error message).

       nids_register_ip_frag() registers a user-defined callback  function  to
       process  all  incoming IP packets (including IP fragments, packets with
       invalid checksums, etc.).

       nids_unregister_ip_frag() unregisters a user-defined callback  function
       to process all incoming IP packets.

       nids_register_ip()   registers  a  user-defined  callback  function  to
       process IP packets validated and reassembled by libnids.

       nids_unregister_ip() unregisters a user-defined  callback  function  to
       process IP packets.

       nids_register_udp()  registers  a  user-defined  callback  function  to
       process UDP packets validated and reassembled by libnids.

       nids_unregister_udp() unregisters a user-defined callback  function  to
       process UDP packets.

       nids_register_tcp()  registers  a  user-defined  callback  function  to
       process  TCP  streams  validated  and  reassembled  by   libnids.   The
       tcp_stream structure is defined as follows:

       struct tcp_stream {
            struct tuple4 {
                 u_short source;
                 u_short   dest;
                 u_int     saddr;
                 u_int     daddr;
            } addr;
            char           nids_state;
            struct half_stream {
                 char state;
                 char collect;
                 char collect_urg;
                 char *data;
                 u_char    urgdata;
                 int  count;
                 int  offset;
                 int  count_new;
                 char count_new_urg;
                 ...
            } client;
            struct half_stream  server;
            ...
            void           *user;
       };

       The members of the tuple4 structure identify a unique TCP connection:

       source, dest
              Client and server port numbers

       saddr, daddr
              Client and server IP addresses

       The  members  of  the half_stream structure describe each half of a TCP
       connection (client and server):

       state  Socket state (e.g. TCP_ESTABLISHED).

       collect
              A boolean which specifies whether to collect data for this  half
              of the connection in the data buffer.

       collect_urg
              A boolean which specifies whether to collect urgent data pointed
              to by the TCP urgent pointer for this half of the connection  in
              the urgdata buffer.

       data   Buffer for normal data.

       urgdata
              One-byte buffer for urgent data.

       count  The  number  of bytes appended to data since the creation of the
              connection.

       offset The current offset from  the  first  byte  stored  in  the  data
              buffer, identifying the start of newly received data.

       count_new
              The  number  of bytes appended to data since the last invocation
              of the TCP callback function (if 0, no new data arrived).

       count_new_urg
              The  number  of  bytes  appended  to  urgdata  since  the   last
              invocation  of  the  TCP  callback function (if 0, no new urgent
              data arrived).

       The value of the nids_state field provides information about the  state
       of the TCP connection, to be used by the TCP callback function:

       NIDS_JUST_EST
              Connection  just  established. Connection parameters in the addr
              structure are available for inspection.  If  the  connection  is
              interesting, the TCP callback function may specify which data it
              wishes to receive in the future by setting non-zero  values  for
              the  collect  or collect_urg variables in the appropriate client
              or server half_stream structure members.

       NIDS_DATA
              New data has arrived on a connection. The half_stream structures
              contain buffers of data.

       NIDS_CLOSE, NIDS_RESET, NIDS_TIMED_OUT
              Connection has closed. The TCP callback function should free any
              resources it may have allocated for this connection.

       The param pointer passed by libnids as argument  to  the  TCP  callback
       function  may  be  set  to  save  a pointer to user-defined connection-
       specific data to pass to subsequent invocations  of  the  TCP  callback
       function  (ex.  the  current  working  directory  for  an  FTP  control
       connection, etc.).

       The user pointer in the  tcp_stream  structure  has  the  same  purpose
       except  it  is  global  to  the  stream,  whereas  the param pointer is
       different from one callback function to the other even though they were
       called for the same stream.

       nids_unregister_tcp()  unregisters  a user-defined callback function to
       process TCP streams.

       nids_killtcp() tears down the specified TCP connection  with  symmetric
       RST packets between client and server.

       nids_discard()  may be called from the TCP callback function to specify
       the number of bytes to discard from the beginning of  the  data  buffer
       (updating the offset value accordingly) after the TCP callback function
       exits. Otherwise, the new data  (totalling  count_new  bytes)  will  be
       discarded by default.

       nids_run()  starts the packet-driven application, reading packets in an
       endless loop, and invoking registered callback functions to handle  new
       data as it arrives. This function does not return.

       nids_dispatch()  attempts to process cnt packets before returning, with
       a cnt of -1 understood as all packets available in one pcap buffer,  or
       all  packets  in  a file when reading offline.  On success, returns the
       count of packets processed, which may be zero upon EOF  (offline  read)
       or  upon  hitting  pcap_timeout  (if  supported  by your platform).  On
       failure,  returns  -1,  putting  an  appropriate   error   message   in
       nids_errbuf.

       nids_next()   process  the  next  available  packet  before  returning.
       Returns 1 on success, 0 if no packet was processed, setting nids_effbuf
       appropriately if an error prevented packet processing.

       nids_getfd()  may  be  used  by an application sleeping in select(2) to
       snoop for a socket file descriptor present in the read fd_set.  Returns
       the   file  descriptor  on  success,  -1  on  failure  (in  which  case
       nids_errbuf contains an appropriate error message).

       nids_register_chksum_ctl()  takes  as  arguments  an  array  of  struct
       nids_chksum_ctl  elements  and  the number of elements in the array.  A
       nids_chksum_ctl element is defined as follows:

       struct nids_chksum_ctl {
            u_int netaddr;
            u_int mask;
            u_int action;
            /* private members */
       };

       Internal checksumming functions will first check elements of this array
       one  by one, and if the source ip SRCIP of the current packet satisfies
       condition

              (SRCIP&chksum_ctl_array[i].mask)==chksum_ctl_array[i].netaddr

       then if  the  action  field  is  NIDS_DO_CHKSUM,  the  packet  will  be
       checksummed;  if  the action field is NIDS_DONT_CHKSUM, the packet will
       not be checksummed.  If the packet matches none of the array  elements,
       the default action is to perform checksumming.

       nids_pcap_handler()  may  be  used  by an application already running a
       capture with libpcap, in order to pass frames to libnids  interactively
       (frame per frame) instead of having libnids itself do the capture.

       nids_find_tcp_stream()  returns  a  pointer to the tcp_stream structure
       corresponding to the tuple passed as argument if  libnids  knows  about
       this TCP connection already, otherwise it returns NULL.

       nids_free_tcp_stream()  removes  the  given tcp_stream from the list of
       streams tracked by libnids.  Warning: its usage can result in  crashes!
       See comments in the API.html file.

SEE ALSO

       pcap(3), libnet(3), fragrouter(8)

AUTHOR

       Rafal Wojtczuk <nergal@icm.edu.pl>

       Manpage  by  Dug  Song  <dugsong@monkey.org>,  minor updates by Michael
       Pomraning <mjp@pilcrow.madison.wi.us>