[2/3] suricata: Handle ipset based whitelist in initscript.
Commit Message
Signed-off-by: Stefan Schantl <stefan.schantl@ipfire.org>
---
src/initscripts/system/suricata | 42 +++++++++++++++++++++++++++++++++
1 file changed, 42 insertions(+)
@@ -44,6 +44,15 @@ enabled_ips_zones=()
# PID file of suricata.
PID_FILE="/var/run/suricata.pid"
+# File which contains the ipset of whitelisted hosts.
+WHITELIST_FILE="/var/ipfire/suricata/whitelist.conf"
+
+# Name of the ipset set
+IPSET_SET="IPSWHITELIST"
+
+IPS_BYPASS_MARK="0x40000000"
+IPS_BYPASS_MASK="0x40000000"
+
# Function to get the amount of CPU cores of the system.
function get_cpu_count {
CPUCOUNT=0
@@ -135,16 +144,44 @@ function generate_fw_rules {
# Flush the firewall chains.
flush_fw_chain
+ if [ -s "$WHITELIST_FILE" ]; then
+ # Load the whitelist file.
+ ipset restore -f "$WHITELIST_FILE"
+ fi
+
# Check if the array of enabled_ips_zones contains any elements.
if [[ ${enabled_ips_zones[@]} ]]; then
# Loop through the array and create firewall rules.
for enabled_ips_zone in "${enabled_ips_zones[@]}"; do
+ # Check if the whitelist file is not empty.
+ if [ -s "$WHITELIST_FILE" ]; then
+ # Create rules to handle whitelisted hosts.
+ iptables -w -A "$IPS_INPUT_CHAIN" -i "$enabled_ips_zone" -m set --match-set $IPSET_SET src -j CONNMARK --set-xmark $IPS_BYPASS_MARK/$IPS_BYPASS_MASK
+ iptables -w -A "$IPS_INPUT_CHAIN" -i "$enabled_ips_zone" -m set --match-set $IPSET_SET dst -j CONNMARK --set-xmark $IPS_BYPASS_MARK/$IPS_BYPASS_MASK
+ iptables -w -A "$IPS_INPUT_CHAIN" -i "$enabled_ips_zone" -m connmark --mark $IPS_BYPASS_MARK/$IPS_BYPASS_MASK -j RETURN
+
+ iptables -w -A "$IPS_OUTPUT_CHAIN" -o "$enabled_ips_zone" -m set --match-set $IPSET_SET src -j CONNMARK --set-xmark $IPS_BYPASS_MARK/$IPS_BYPASS_MASK
+ iptables -w -A "$IPS_OUTPUT_CHAIN" -o "$enabled_ips_zone" -m set --match-set $IPSET_SET src -j CONNMARK --set-xmark $IPS_BYPASS_MARK/$IPS_BYPASS_MASK
+ iptables -w -A "$IPS_OUTPUT_CHAIN" -o "$enabled_ips_zone" -m connmark --mark $IPS_BYPASS_MARK/$IPS_BYPASS_MASK -j RETURN
+ fi
+
# Create rules queue input and output related traffic and pass it to the IPS.
iptables -w -A "$IPS_INPUT_CHAIN" -i "$enabled_ips_zone" -j NFQUEUE $NFQ_OPTIONS
iptables -w -A "$IPS_OUTPUT_CHAIN" -o "$enabled_ips_zone" -j NFQUEUE $NFQ_OPTIONS
# Create rules which are required to handle forwarded traffic.
for enabled_ips_zone_forward in "${enabled_ips_zones[@]}"; do
+ # Check if the whetelist file is not empty.
+ if [ -s "$WHITELIST_FILE" ]; then
+ # Create rules to handle whitelisted hosts.
+ iptables -w -A "$IPS_FORWARD_CHAIN" -i "$enabled_ips_zone" -o "$enabled_ips_zone_forward" \
+ -m set --match-set $IPSET_SET src -j CONNMARK --set-xmark $IPS_BYPASS_MARK/$IPS_BYPASS_MASK
+ iptables -w -A "$IPS_FORWARD_CHAIN" -i "$enabled_ips_zone" -o "$enabled_ips_zone_forward" \
+ -m set --match-set $IPSET_SET dst -j CONNMARK --set-xmark $IPS_BYPASS_MARK/$IPS_BYPASS_MASK
+ iptables -w -A "$IPS_FORWARD_CHAIN" -i "$enabled_ips_zone" -o "$enabled_ips_zone_forward" \
+ -m connmark --mark $IPS_BYPASS_MARK/$IPS_BYPASS_MASK
+ fi
+
iptables -w -A "$IPS_FORWARD_CHAIN" -i "$enabled_ips_zone" -o "$enabled_ips_zone_forward" -j NFQUEUE $NFQ_OPTIONS
done
done
@@ -188,6 +225,11 @@ case "$1" in
# Flush firewall chain.
flush_fw_chain
+ # Unload the ipset set.
+ if [ -s "$WHITELIST_FILE" ]; then
+ ipset destroy $IPSET_SET 2>/dev/null
+ fi
+
# Sometimes suricata not correct shutdown. So killall.
killall -KILL /usr/bin/suricata 2>/dev/null