This program provides an TCP socket for sockserv. After a sockserv process has successfully connected a child process is forked off for this communication. The child process consists of two threads. One thread simply receives alerts via the TCP socket and stores them in memory, see picture sockserv/servsock process. The second thread feeds the stored alerts to a database.
To successfully connect there are a few things which must be fullfilled:
If the endianess of the sensor and central server are different then a connection is permanently refused. This does not work.
There is only one remote sensor with the same sensor name (see option -N and interface (see option -I of sockserv) allowed. If
a second sensor with the same sensor name and interface tries to connect the access
is denied.
If there are still not yet processed data from the last connection between the remote sensor and the central server then the connection is as long refused as these data are not stored in the database
If the database is not available if a sockserv process tries to connect then the connection is refused temporarily.
If there is a swap file available, then the connection is temporarily halted until the data of the swap file is read into memory.
Through the threading design and the use of a memory buffer the risk of loosing alerts is minimized. If more alerts are available than servsock can insert into the database[1] the alerts are buffered in memory.
To reduce the problem on memory shortage due to a high overload, the
number of alerts in the buffer can be limited. This is done as with
sockserv via two
parameters, the LowWater and HighWater
marks. If more alerts than the HighWater mark are buffered in memory
as many alerts are dropped until the LowWater mark is reached. All dropped alerts
are written to an unix domain socket. The program drop is able to receive these
alerts and send them via email to a list of recipients.
If either sockserv can not connect to servsock on startup or the connection is closed during runtime the program tries to reopen the connection after a short delay for several times.
All output can be redirected to syslog, using the
facility LOCAL0 and level
INFO. A daemon mode is also supported. Finally,
statistics could be printed on a periodical basis or once by sending a
SIGUSR1 to the servsock master
process. This process will advice all child processes to print the statitistics.
There are several options available:
servsock [-bCdefhlnqTuv] [-Adelay] [-cconfig] [-Ddropsocket] [-HHighWater] [-LLowWater] [-mmode] [-Mpriority] [-pport] [-Ppidfile] [-ssnortsocket] [-Sserver] [-Ualertsocket] [-Varea,level] [-wdir] [-WSwapDir] [-ZTimeZone]
The servsock options in detail
-A delayPrint every
delay seconds statistics about
received, sent and dropped alerts. The change of these values between
delay seconds is printed in
brackets. See also option -l.
-bStart the process in the background: daemon
mode. This automatically activates option -l.
-dDump the actual configuration on startup. This is
useful if both, a configuration file (see ) and command line options are
used in combination and for debbuging purposes
-CSpecifies the use of a red-black tree to cache
sig_id values of the database. This speeds up the INSERTs
in the database but you have to enable it during the configuration run
with the --enable-cache. See also the configure
file option DBCache.
-c
configSpecifies which configuration file should be used. The default is servsock.conf
-D
dropsocketIf there are
more than HighWater alerts buffered then the
newest alerts are dropped to dropsocket until the
LowWater mark is reached.
-eSpecifies the use of PREPARE statements
with the database. This may speeds up the INSERTs
in the database but you have to enable it during the configuration run
with the --enable-prepare. See also the configure
file option DBPrepare.
This works only with the PostgreSQL database.
-fStore additional information in the database so that a pcap file can be created with the program getpacket. Note: You need an extended database schema to use this option. See the file README.payload in the distribution.
-hPrint a help message and exit.
-H HighWaterSets the
HighWater mark, see option -D. There is no default value used.
-lLog statitiscs to syslog instead
of stdout. See also option -A.
-L LowWaterSets the
LowWater mark, see option -D. There is no default value
used.
-m modeSets the umask to
mode for the daemon mode. This
affects the mode for the created unix socket and pid file. The mode
can be either given in ascii,
octal (with leading 0) or
hex (with leading 0x)
format.
-M prioritySets the required priority for alerts to be written to AlertSocket. The program alert is able to read these alerts and send emails to a list of recipients.
-nDo not resolve the full qualified names of the sensors, use the IP addresses instead. This will avoid conflicts with the database if on a new connection the DNS resolution fails or resolves to another name.
-p portDefines on which
port servsock
should listen, see also option -S.
-P pidfileFilename to store the PID. Note: This file must be writeable by the user running servsock!
-qEnable quiet dropping, no dropped alerts were written to the
dropsocket, see option -D.
-rStore additional information in the database so that a pcap file including all tagged packets relating to an alert can be created with the program getpacket. Note: You need an extended database schema to use this option. See the file README.payload in the distribution.
-s
socketnameDefines the
name and directory where the unix domain socket of the
database is opened. A value of
NULL results in an internal
NULL pointer, this is useful in combination with
PostgreSQL. It is also possible to use a TCP
socket via hostname:port.
-S serverDefines the
interface where servsock should listen on. The name
can be either a full qualified domain name[2] or an IP address. The default is
0.0.0.0 to bind on all available and configured
interfaces. See also option -p.
-TEnable trust modus for the database. If set, it is assumed that the alert description is already part of the database. If this is not the case, all these informations are inserted. So it is safe to enable this feature unless the transfer of alert message is disabled in snort. But this (removing of the alert message within snort) is a very experimental feature and is usually disabled by default. (But would save 256 Bytes on the wire!)
-U
alertsocketSpecifies
where the unix domain socket of the alert program can be found, see
also -M.
-uDisables the use of the alertsocket. This is useful if the alert is activated in the configuration file but there is no alert program running. So it is only useful for debugging.
-vPrint version information.
-w dirSets the working
directory in daemon mode to dir. The default is to use the current
working directory. It is useful to choose / to
avoid blocking of mounted filesystems.
-W SwapDirSets the directory where the swap file sensor_SensorName is created and alerts are buffered if the database connection is lost.
-V area,valueSets the debug level of the program. Area
specifies the section of the code which should generate debug output.
value should be between 0 (disabled) and 9 (maximum
output). For further information read the file README.debug.
-Z TimeZoneSpecifies
which timezone should be used to store the time in the database (local
timezone versus UTC). A ZimeZone of
zero means to use the same timezone as localtime, any other value would
result in the use of UTC.
The default is to use the local timezone.
Additionally to the command line arguments there are some options which must be set via the configuration file. At least the database configuration has to be set in the configuration file[3].
The command line options have precedence above the settings in the configuartion file. If an option is mentioned on the command line this value is used regardless of the settings in the configuration file.
On the other hand all parameters of the command line can be set in the
configuration file (except option -u). So the command line
options are more suitable for quick tests.
The format of the file is simple, the first word is a keyword and the second is the value. They are separated by a colon (:) or equal sign (=). White spaces are allowed in any number.
The values can be put in single (') or double (") quotes, all between is used as the value with one exception. This exception is the comment sign (#). All entries after this sign are ignored. To use the command sign it has to be escaped with a backslash: \#.
To use white spaces in a value they must be surrounded by quotes.
So all this results in a value with space, exept the last one without
quotes. This will result in spa:
'spa ce' = "spa ce" = spa ceAll keywords are case insensitive (but not the values!).
The parameters of the configuration file for servsock in detail
DBuser: nameSpecifies the
name of the database user who is allowed to do
INSERTs, SELECTs and
UPDATEs of tables. The default is
snort.
DBpassword: passwordSpecifies the
password used among with the DBuser name to connect to the
database. Note: An empty password has to be
represented by empty quotes, which is the default.
DBname: nameName of the database where servsock should insert the alerts, defaults to snort.
DBtype: nameType of the
database to use. Actually only MySQL and
PostgreSQL
are supported and have to be enabled at compile time of
servsock. No default is set since it is not clear
which database support was enabled at compile
time of servsock.
DBencoding: nameDefines the
encoding scheme wich is used to insert the payload into the
database. Allowed values are
hex, base64 and
ascii. The base64 encoding
requires less memory in the database but it makes
it difficult to search for special entries in the payload. The
ascii[4] encoding stores only ascii characters in the
database, all binary data is replaced by a dot. So the only really
useful option is the hex scheme which is the
default or base64 if saving of database space is desired.
DBtrust: valueA non-zero
value enables the
trust modus for the database. If this modus is
enabled it is assumed that all possible signatures are already part of
the database. This will result in slight faster INSERTs
since less detailed SELECT statements are needed[5]. It is
safe to enable this even if you are not sure, missing signatures will
still be inserted. The equivalent command line is -T.
DBCache: valueA non-zero
value enables the use of a
cache for the sig_id.
Since during inserts the only SELECTs are
done to get the sig_id. The cache is implemented
as a red-black tree. To use this option you have to enable it during
the configure run with --enable-cache. The
equivalent command line to activate the use of the cache
is -C.
DBPrepare: valueA non-zero
value enables the use of
PREPARE with the database. This may speed
up the INSERTs.
To use this option you have to enable it during
the configure run with --enable-prepare.
This works only with the PostgreSQL database.
The equivalent command line to activate this feature is
-e.
DBtrans: valueA non-zero
value enables the use of
transactions together with the database. If you
use the MySQL database you have to use tables of type
InnoDB, otherwise the transactions are simply
ignored.
PIDFile:
pidfile Specifies which
file should be used to store the PID. This file must be writeable by
the user running servsock! This correspond to
option -P.
SocketName:
socketnameThis specifies
where to find the unix domain socket of the database. If the word
NULL (all capital!) is given, the database
libraries find the socket by their own mechanism. This is useful in
combination with the PostgreSQL database. This is
equal to the -s. If socketname
contains a colon (:) the first part is interpreted
as a hostname, the second as a port number and a TCP connection to the database is used.
ServerName: nameDefines on which
interface defined by the address servsock should
listen on. Possible values for name are either full qualified names (not
very useful) or a dotted IP address. The default is
0.0.0.0 to listen on all available
interfaces.
ServerPort: valueDefines the port
where servsock will listen on. The default is port
1234. Compare to option -p.
AlarmDelay: valueWrite every
value seconds statistics of
received, sent and dropped alerts. In braces the differences to the
last output are printed. See option -A.
Syslog: valueIf the
value is non-zero then the
statistics are logged via syslog and not printed
to stdout. The facility is
LOCAL0 and the level is
INFO. Compare to option -l
FQNSensor: valueWith a
value of zero the IP address of
the sensor is used as sensor name in conjunction with the
database. The equivalent command line option is
-n.
AlertSocket:
alertsocketName of the
unix domain socket where alerts with high priority are written to. See
option -U. If alertsocket has the name NULL then the alert feature
is disabled.
UnixPriority: valueThe value
determines the minimum priority where alerts are additionally written
to the AlertSocket[6]. The command line equivalent is the
option -M.
DropSocket:
dropsocketName of the
unix domain socket where alerts are dropped to if the number of queued
alerts reaches the HighWater mark. Compare to
option -H. If dropsocket has the name NULL then the drop feature
is disabled.
DropQuiet:
valueIf value is not zero then all
dropped alerts are not written to the DropSocket. Note: Dropping is not disabled by this parameter.
HighWater: valueIf the number of
queued alerts reaches this value
then servsock begins to drop alerts to the DropSocket. This corresponds
to option -H.
LowWater: valueThis value must be smaller than HighWater[7]. If the HighWater mark is reached so
many alerts are dropped to the DropSocket until this
LowWater value is reached. This corresponds to option
-L.
DaemonMode: valueA non-zero
value enables the daemon
mode, the program forks into the background. This
automatically activates the Syslog option. See option
-b.
Umask: modeSets the
umask to mode
for the DaemonMode. This
affects the mode for the created PIDFile. The mode can be either given in
ascii, octal (with leading
0) or hex (with leading
0x). This is equal to the option -m.
SwapDir:
SwapDirSets the
directory where the swap file sensor_SensorName is created. This file is used to swap out alerts if the database has gone and is read in again if the database is available and the remote sensor connects again. The default is to use /var/tmp. See option -W.
FullPayload: valueStore additional information in the database so that a pcap file can be created with the program getpacket. Note: You need an extended database schema to use this option. See the file README.payload in the distribution and option -f.
Reference: valueStore additional information in the database so that a pcap file including all tagged packets can be created with the program getpacket. Note: You need an extended database schema to use this option. See the file README.payload in the distribution and option -r.
Debug: area,valueSets the debug level of the program. Area
specifies the section of the code which should generate debug output.
value should be between 0 (disabled) and 9 (maximum
output). For further information read the file README.debug. See option -V.
TimeZone: area,valueSpecifies which timezone should be used. A value of zero for
TimeZone results in the use of the timezone of localtime.
Any other value will result in the use of UTC. See also option -Z.
Currently the following signals are used with servsock:
SIGUSR1Print statitics about received, sent and dropped alerts.
SIGINTCancels the master process, prints the final
statistics and makes a clean exit. The socketname and PIDfile are
removed. The child processes dump the buffered alerts to the swap file and exit.
SIGTERMThis signal
results in the same behaviour as SIGINT.
SIGHUP[3]If this signal is received
by the master process then servsock stops each
child process by sending a SIGTERM signal and
restarts itself[8]. First all buffered alerts are written
to the swap files
and the final statistics are printed. Further SocketName and PIDFile are removed to enable
a restart of the program. (Otherwise the program would fail since the
PID did not change!) The child processes simply ignore the
SIGHUP signal.
The actual version of servsock uses a control thread to change some parameters during runtime. This thread is also used to print statistics on a periodically interval instead of using signals.
The drop and alert features
are not enabled by default and have to be compiled in
servsock separately. If it is not compiled
in then the options -D, -L and -H are missing for the
drop and the
options -M, -u and -U are missing for the
alert program
in the output of the -h option.
In contrast to sockserv the LowWater and HighWater marks have to
be choosen with more caution. First there are more processes
running than the servsock processes
especially the database. Further the
bottleneck is not the network, it is usually the
database. So it is quite normal that here
the number of buffered alerts increase rapidly on heavy
attacks.
Since the sensor name is taken from the IP address of the computer running sockserv (the remote sensor) there is only one sockserv instance per IP address allowed. Otherwise there will be a lot of collisions of inserts related to the database. (Two different sensors with the same name try to insert two different alerts with the same database Sensor ID, for example.)
If the connection dies, sockserv opens a
new connection and a new servsock process is
forked off. But if the old servsock thread
feeding the database did not finished yet
there arises a problem like the same sensor is logging twice
times. Therefore servsock has a list of up
to 25 (see the configure option
--with-maxclients to adjust this value)
running child processes with the
sensor name they are dealing with. So if there is still one
process running any new connection of a sockserv process
with the same sensor name is rejected!
On startup a handshake must be fullfilled. During this phase the endianess of both partner, the availability of the database and the presence of a non-zero swap file are checked. Depending on the result a conncetion is either allowed, temporarily rejected or permanently denied.
If a SIGHUP[3] signal is received by the process with the PID stored
in the PIDFile all child
processes are terminated first. If there are buffered alerts it
can take some time until all of them are written to the swap files.
So a time delay on restart is not uncommon.
If either a SIGINT or
SIGTERM is received
by the servsock process handling a connection
then all buffered alerts are written to the swapfile.
Since this are threaded programs this may cause some problems with
Linux using linuxthreads
instead of the newer NTPL implementation. Note,
the NTPL is only available with kernel 2.6.
Nore: With the old linuxthreads you will see two processes for each thread, one in user land and one in kernel land instead of one process. Therefore it may cause some problems with the signal handler, not all PIDs behave the same.
If a PIDFile exists the
program checks for a running process with the id of this file. If one
is found the program exits to avoid running the same program
twice. But there is no check for which program is running, only if
there is one in the process list!
| [1] | Sometimes databases hang on many inserts due to things like internal garbage collection. In addition there are many tables which have to be filled in for each alert. All this will slow down the insert rate of the database. |
| [2] | This not really useful since central server have usually more than on interface or you need a full qualified domain name for only this interface. Most name server resolve IP addresses in a round robin procedure for more than one IP address. So the interface on which servsock bounds would not be unambigous. |
| [3] | Especially the password for the database should not appear in the processlist. |
| [4] | This option should be removed
in the future in favour of using |
| [5] | This behaviour is a little bit different to the default one. Here we check or all values like revision and priority even if they are zero. In the other case we check for |
| [6] | This
keyword should be replaced by |
| [7] | The mimimum difference between this two marks should be at least greater than 10. |
| [8] | This results in a time delay for a restart since first it must be waited until all child processes exit. |