Building an SEC Ruleset for Attack Correlations

 

All of the SEC files on pkirack3 are all in /usr/share/prelude/sec and its subdirectories.

The ruleset files are in /usr/share/prelude/sec/rules and have a .sec extension.

sec.pl should normally be started as a daemon as a Prelude agent…

But for testing purposes start it from a terminal using the following:

 

./sec.pl -conf=rules/*.sec --module=Prelude["--server-addr 141.142.234.4"]

 

This will run SEC with whatever rulesets are in .../sec/rules specifying that the input

Is from Prelude (IDMEF format) and the prelude-manager is on pkirack3 (141.142.234.4).

Prelude-manager will route all of alert messages that it gets from its sensors to SEC.

 

Basic IDMEF pattern matching:

The ‘pattern’ is a series of regex expressions that represent values from the ‘alert’ namespace’

(see the Mithril internal document ‘alert’ namespace for IDMEF pattern matching in SEC)

The order of the lines is unimportant. The entire ‘pattern’ stream is matched line-by-line.

If a line matches, the appropriate parameter(s) is/are assigned to $1, $2, $3…

 

If all the lines match… the rule is successful and the ‘action’ is performed.

The following is a very simple example which catches and matches all alerts.

 

type=Single

ptype=IDMEF

pattern=classification.text: (.*);

desc=The classification text is $1

action=write –  %s

 

Typically however… the ‘classification.text:’ parameter would be specified to match an alert.

 

The ‘action’ sends the value for ‘desc’ to standard output (indicated by ‘-‘).

The following is an example which detects a portscan followed by an SSH login attempt.

The relationship between the two rules is that they occur within the same hour.

 

For testing I have been running the following from pkirack2 to generate a number of alerts on pkirack3…

nmap -n -vvv -sS -T Insane -p 1-65535 pkirack3.ncsa.uiuc.edu

ssh someuser@pkirack3

 

# ncsa-portscan_ssh.sec

# this ruleset detects a portscan followed by an SSH login

# attempt from the same sourceIP address within the same hour

 

# upon detection of portscan create the appropriate context

# this case will be a portscan followed by a invalid user attempt

type=Single

ptype=IDMEF

pattern=classification.text: [(]portscan[)] TCP Portscan; \

            messageid: (\d+); \

            source(0).node.address(0).address: (.*); \

            target(0).node.address(0).address: (.*); \

            analyzer(-1).analyzerid: (.*); \

            analyzer(-2).analyzerid: (.*); \

            source(0).user.user_id(0).name: (.*);

continue=TakeNext

desc=TCP Portscan  messageID: $2 sourceIP: $3 targetIP: $4 analyzerID1: $5 analyzerID2: $6

action=add PORTSCAN_SSH_$3 %s; \

           set PORTSCAN_SSH_$3 3600

 

# upon detection of an SSH login attempt

# check if the context exists

# if it exists... create the correlation

type=Single

ptype=IDMEF

pattern=classification.text: [Ll]ogin|[Aa]uthentication; \

            messageid: (.+); \

            assessment.impact.completion: (.+); \

            source(0).node.address(0).address: (.*); \

            target(0).node.address(0).address: (.*); \

            analyzer(-1).analyzerid: (.*); \

            analyzer(-2).analyzerid: (.*);

continue=DontCont

context=PORTSCAN_SSH_$3

desc=correlation_alert.name=Portscan_SSH_invalid; \

         correlation_alert.alertident(>>).alertident=$1; \

         correlation_alert.alertident(-1).analyzerid=$6;

action=add PORTSCAN_SSH_$3 %s; \

           copy PORTSCAN_SSH_$3 %CONTENT; \

           prelude %CONTENT; \

           delete PORTSCAN_SSH_$3