]> git.ipfire.org Git - ipfire-2.x.git/blame - config/suricata/convert-snort
Merge branch 'next'
[ipfire-2.x.git] / config / suricata / convert-snort
CommitLineData
5b0b4182
SS
1#!/usr/bin/perl
2###############################################################################
3# #
4# IPFire.org - A linux based firewall #
5# Copyright (C) 2019 IPFire Development Team <info@ipfire.org> #
6# #
7# This program is free software: you can redistribute it and/or modify #
8# it under the terms of the GNU General Public License as published by #
9# the Free Software Foundation, either version 3 of the License, or #
10# (at your option) any later version. #
11# #
12# This program is distributed in the hope that it will be useful, #
13# but WITHOUT ANY WARRANTY; without even the implied warranty of #
14# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the #
15# GNU General Public License for more details. #
16# #
17# You should have received a copy of the GNU General Public License #
18# along with this program. If not, see <http://www.gnu.org/licenses/>. #
19# #
20###############################################################################
21
22use strict;
23
24require '/var/ipfire/general-functions.pl';
25require "${General::swroot}/ids-functions.pl";
26
27# Snort settings file, which contains the settings from the WUI.
28my $snort_settings_file = "${General::swroot}/snort/settings";
29
30# Main snort config file.
31my $snort_config_file = "/etc/snort/snort.conf";
32
33# Snort rules tarball.
34my $snort_rules_tarball = "/var/tmp/snortrules.tar.gz";
35
5b0b4182
SS
36#
37## Step 1: Setup directory and file layout, if not present and set correct
38## ownership. The converter runs as a privileged user, but the files
39## needs to be full access-able by the WUI user and group (nobody:nobody).
40#
41
5b0b4182
SS
42# Check if the settings directory exists.
43unless (-d $IDS::settingsdir) {
44 # Create the directory.
45 mkdir($IDS::settingsdir);
46}
47
48# Check if the rules directory exists.
49unless (-d $IDS::rulespath) {
50 # Create the directory.
51 mkdir($IDS::rulespath);
52}
53
5b0b4182
SS
54# Create file layout, if not exists yet.
55&IDS::check_and_create_filelayout();
56
36e69d34
SS
57# Set correct ownership for settingsdir and rulespath.
58&IDS::set_ownership("$IDS::settingsdir");
59&IDS::set_ownership("$IDS::rulespath");
5b0b4182 60
78690361
SS
61# Check if a snort settings file exists.
62unless( -f "$snort_settings_file") {
63 print "$snort_settings_file not found - Nothing to do. Exiting!\n";
64 exit(0);
65}
66
67# Check if the snort settings file is empty.
68if (-z "$snort_settings_file") {
69 print "$snort_settings_file is empty - Nothing to do. Exiting!\n";
70 exit(0);
71}
72
5b0b4182
SS
73#
74## Step 2: Import snort settings and convert to the required format for the new IDS
75## (suricata).
76#
77
78# Hash which contains the "old" snort settings.
79my %snortsettings;
80
81# Hash which contains the IDS (suricata) settings.
82#
83# Add default value for MONITOR_TRAFFIC_ONLY which will be "on"
84# when migrating from snort to the new IDS.
85my %idssettings = (
86 "MONITOR_TRAFFIC_ONLY" => "on",
87);
88
89# Hash which contains the RULES settings.
90#
91# Set default value for UPDATE_INTERVAL to weekly.
92my %rulessettings = (
93 "AUTOUPDATE_INTERVAL" => "weekly",
94);
95
96# Get all available network zones.
97my @network_zones = &IDS::get_available_network_zones();
98
99# Read-in snort settings file.
100&General::readhash("$snort_settings_file", \%snortsettings);
101
102# Loop through the array of network zones.
103foreach my $zone (@network_zones) {
104 # Convert current zone into upper case.
105 my $zone_upper = uc($zone);
106
107 # Check if the current network zone is "red".
108 if($zone eq "red") {
109 # Check if snort was enabled and enabled on red.
110 if ($snortsettings{"ENABLE_SNORT"} eq "on") {
111 # Enable the IDS.
112 $idssettings{"ENABLE_IDS"} = "on";
113
114 # Enable the IDS on RED.
115 $idssettings{"ENABLE_IDS_$zone_upper"} = "on";
116 }
117 } else {
118 # Check if snort was enabled on the current zone.
119 if ($snortsettings{"ENABLE_SNORT_$zone_upper"} eq "on") {
120 # Enable the IDS on this zone too.
121 $idssettings{"ENABLE_IDS_$zone_upper"} = "on";
122 }
123 }
124}
125
126# Grab the choosen ruleset from snort settings hash and store it in the rules
127# settings hash.
128$rulessettings{"RULES"} = $snortsettings{"RULES"};
129
130# Check if an oinkcode has been provided.
131if($snortsettings{"OINKCODE"}) {
132 # Take the oinkcode from snort settings hash and store it in the rules
133 # settings hash.
134 $rulessettings{"OINKCODE"} = $snortsettings{"OINKCODE"};
135}
136
137#
138## Step 3: Import guardian settings and whitelist if the addon is installed.
139#
140
141# Pakfire meta file for owncloud.
142# (File exists when the addon is installed.)
143my $guardian_meta = "/opt/pakfire/db/installed/meta-guardian";
144
145# Check if the guardian addon is installed.
146if (-f $guardian_meta) {
147 # File which contains the taken setting for guardian.
148 my $guardian_settings_file = "${General::swroot}/guardian/settings";
149
150 # File which contains the white-listed hosts.
151 my $guardian_ignored_file = "${General::swroot}/guardian/ignored";
152
153 # Hash which will contain the settings of guardian.
154 my %guardiansettings;
155
156 # Check if the settings file of guardian is empty.
157 unless (-z $guardian_settings_file) {
158 # Read-in settings.
159 &General::readhash("$guardian_settings_file", \%guardiansettings);
160 }
161
162 # Check if guardian is not configured to take actions on snort events.
163 if ($guardiansettings{"GUARDIAN_MONITOR_SNORT"} eq "on") {
164 # Change the IDS into MONITOR_TRAFFIC_ONLY mode.
165 $idssettings{"MONITOR_TRAFFIC_ONLY"} = "off";
166 }
167
168 # Check if guardian has any white-listed hosts configured.
169 unless (-z $guardian_ignored_file) {
170 # Temporary hash to store the ignored hosts.
171 my %ignored_hosts;
172
173 # Read-in white-listed hosts and store them in the hash.
174 &General::readhasharray($guardian_ignored_file, \%ignored_hosts);
175
176 # Write-out the white-listed hosts for the IDS system.
177 &General::writehasharray($IDS::ignored_file, \%ignored_hosts);
178
179 # Call subfunction to generate the file for white-listing the hosts.
180 &IDS::generate_ignored_file();
181 }
182
183}
184
185#
186## Step 4: Save IDS and rules settings.
187#
188
189# Write IDS settings.
190&General::writehash("$IDS::ids_settings_file", \%idssettings);
191
192# Write rules settings.
193&General::writehash("$IDS::rules_settings_file", \%rulessettings);
194
195#
196## Step 5: Generate and write the file to modify the ruleset.
197#
198
5b0b4182 199# Call subfunction and pass the desired IDS action.
f1add9a8 200&IDS::write_modify_sids_file();
5b0b4182 201
5d7d8749
SS
202# Set correct ownership.
203&IDS::set_ownership("$IDS::modify_sids_file");
204
5b0b4182
SS
205#
206## Step 6: Move rulestarball to its new location.
207#
208
209# Check if a rulestarball has been downloaded yet.
210if (-f $snort_rules_tarball) {
211 # Load perl module which contains the move command.
212 use File::Copy;
213
214 # Move the rulestarball to the new location.
215 move($snort_rules_tarball, $IDS::rulestarball);
216
217 # Set correct ownership.
b09c13f1 218 &IDS::set_ownership("$IDS::rulestarball");
cc636c47
SS
219
220# In case no tarball is present, try to download the ruleset.
221} else {
222 # Check if enought disk space is available.
223 if(&IDS::checkdiskspace()) {
e4bc9b8b
SS
224 # Print error message.
225 print "Could not download ruleset - Not enough free diskspace available.\n";
226 } else {
cc636c47
SS
227 # Call the download function and grab the new ruleset.
228 &IDS::downloadruleset();
229 }
5b0b4182
SS
230}
231
232#
233## Step 7: Call oinkmaster to extract and setup the rules structures.
234#
235
236# Check if a rulestarball is present.
237if (-f $IDS::rulestarball) {
238 # Launch oinkmaster by calling the subfunction.
239 &IDS::oinkmaster();
cc636c47
SS
240
241 # Set correct ownership for the rulesdir and files.
242 &IDS::set_ownership("$IDS::rulespath");
5b0b4182
SS
243}
244
245#
ee82349a
SS
246## Step 8: Generate file for the HOME Net.
247#
248
249# Call subfunction to generate the file.
250&IDS::generate_home_net_file();
251
25d42438
SS
252# Set correct ownership for the homenet file.
253&IDS::set_ownership("$IDS::homenet_file");
254
ee82349a 255#
bb2696da
SS
256## Step 9: Generate file for the DNS servers.
257#
258
259# Call subfunction to generate the file.
260&IDS::generate_dns_servers_file();
261
262# Set correct ownership for the dns_servers_file.
263&IDS::set_ownership("$IDS::dns_servers_file");
264
265#
266## Step 10: Setup automatic ruleset updates.
ee82349a
SS
267#
268
269# Check if a ruleset is configured.
270if($rulessettings{"RULES"}) {
271 # Call suricatactrl and setup the periodic update mechanism.
272 &IDS::call_suricatactrl("cron", $rulessettings{'AUTOUPDATE_INTERVAL'});
273}
274
275#
bb2696da 276## Step 11: Grab used ruleset files from snort config file and convert
5b0b4182
SS
277## them into the new format.
278#
279
280# Check if the snort config file exists.
281unless (-f $snort_config_file) {
282 print "$snort_config_file does not exist - Nothing to do. Exiting!\n";
283 exit(0);
284}
285
286# Array to store the enabled rules files.
287my @enabled_rule_files;
288
289# Open snort config file.
290open(SNORTCONF, $snort_config_file) or die "Could not open $snort_config_file. $!\n";
291
292# Loop through the file content.
293while (my $line = <SNORTCONF>) {
294 # Skip comments.
295 next if ($line =~ /\#/);
296
297 # Skip blank lines.
298 next if ($line =~ /^\s*$/);
299
300 # Remove newlines.
301 chomp($line);
302
303 # Check for a line with .rules
304 if ($line =~ /\.rules$/) {
305 # Parse out rule file name
306 my $rulefile = $line;
307 $rulefile =~ s/\$RULE_PATH\///i;
308 $rulefile =~ s/ ?include ?//i;
309
310 # Add the enabled rulefile to the array of enabled rule files.
311 push(@enabled_rule_files, $rulefile);
312 }
313}
314
315# Close filehandle.
316close(SNORTCONF);
317
318# Pass the array of enabled rule files to the subfunction and write the file.
319&IDS::write_used_rulefiles_file(@enabled_rule_files);
320
5b0b4182 321#
bb2696da 322## Step 12: Start the IDS if enabled.
5b0b4182
SS
323#
324
325# Check if the IDS should be started.
326if($idssettings{"ENABLE_IDS"} eq "on") {
327 # Call suricatactrl and launch the IDS.
328 &IDS::call_suricatactrl("start");
329}