From ff0d33c5bc702c201abd93600b1b2cd7e46646cd Mon Sep 17 00:00:00 2001 From: Scott Ullrich Date: Tue, 10 Mar 2009 23:25:00 -0400 Subject: [PATCH] * Share code instead of using copy/paste/code duplication. * Fixes a large number of bugs, especially in the AJAX-based dynamic log viewer. * Picks up some more detail from the logs, and more accurately determines the protocol of a given log entry. * Adds a CLI log parser --- usr/local/www/diag_logs_filter.php | 133 ++----------- usr/local/www/diag_logs_filter_dynamic.php | 210 ++++----------------- 2 files changed, 47 insertions(+), 296 deletions(-) diff --git a/usr/local/www/diag_logs_filter.php b/usr/local/www/diag_logs_filter.php index 59cfbeb4e3..70cec8b2bb 100755 --- a/usr/local/www/diag_logs_filter.php +++ b/usr/local/www/diag_logs_filter.php @@ -32,12 +32,15 @@ require("guiconfig.inc"); +/* In an effort to reduce duplicate code, many shared functions have been moved here. */ +require_once("includes/log.inc.php"); + if($_GET['getrulenum'] or $_POST['getrulenum']) { if($_GET['getrulenum']) $rulenum = escapeshellarg($_GET['getrulenum']); if($_POST['getrulenum']) $rulenum = escapeshellarg($_POST['getrulenum']); - $rule = `pfctl -vvsr | grep '^@{$rulenum} '`; + $rule = find_rule_by_number($rulenum); echo "The rule that triggered this action is:\n\n{$rule}"; exit; } @@ -54,123 +57,6 @@ if ($_POST['clear']) { system_syslogd_start(); } -/* format filter logs */ -function conv_clog($logfile, $tail = 50) { - global $config, $nentries, $g; - $logarr = ""; - /* make interface/port table */ - $iftable = array(); - $iftable[$config['interfaces']['lan']['if']] = "LAN"; - $iftable[get_real_wan_interface()] = "WAN"; - for ($i = 1; isset($config['interfaces']['opt' . $i]); $i++) - $iftable[$config['interfaces']['opt' . $i]['if']] = $config['interfaces']['opt' . $i]['descr']; - - exec("/usr/sbin/clog {$logfile} | /usr/bin/tail -r -n 500", $logarr); - - $filterlog = array(); - - $counter = 1; - - foreach ($logarr as $logent) { - - if($counter > $nentries) - break; - - $log_split = ""; - - - preg_match("/(\b(?:\d{1,3}\.){3}\d{1,3}(\.\w+)?)\s.*\s(\b(?:\d{1,3}\.){3}\d{1,3}(\.\w+)?)/", $logent, $log_split); - - $flent['src'] = convert_port_period_to_colon($log_split[1]); - $flent['dst'] = convert_port_period_to_colon($log_split[3]); - - preg_match("/(.*)\s.*\spf:\s.*\srule\s(.*)\(match\)\:\s(.*)\s\w+\son\s(\w+)\:\s(.*)\s>\s(.*)\:\s.*/", $logent, $log_split); - - $beforeupper = $logent; - $logent = strtoupper($logent); - - if(stristr(strtoupper($logent), "UDP") == true) - $flent['proto'] = "UDP"; - else if(stristr(strtoupper($logent), "TCP") == true) - $flent['proto'] = "TCP"; - else if(stristr(strtoupper($logent), "ICMP") == true) - $flent['proto'] = "ICMP"; - else if(stristr(strtoupper($logent), "HSRP") == true) - $flent['proto'] = "HSRP"; - else if(stristr(strtoupper($logent), "ESP") == true) - $flent['proto'] = "ESP"; - else if(stristr(strtoupper($logent), "AH") == true) - $flent['proto'] = "AH"; - else if(stristr(strtoupper($logent), "GRE") == true) - $flent['proto'] = "GRE"; - else if(stristr(strtoupper($logent), "IGMP") == true) - $flent['proto'] = "IGMP"; - else if(stristr(strtoupper($logent), "CARP") == true) - $flent['proto'] = "CARP"; - else if(stristr(strtoupper($logent), "VRRP") == true) - $flent['proto'] = "VRRP"; - else if(stristr(strtoupper($logent), "PFSYNC") == true) - $flent['proto'] = "PFSYNC"; - else if(stristr($logent, "sack") == true) - $flent['proto'] = "TCP"; - else - $flent['proto'] = "TCP"; - - $flent['time'] = $log_split[1]; - $flent['act'] = $log_split[3]; - - $friendly_int = convert_real_interface_to_friendly_interface_name($log_split[4]); - - $flent['interface'] = strtoupper($friendly_int); - - if($config['interfaces'][$friendly_int]['descr'] <> "") - $flent['interface'] = "{$config['interfaces'][$friendly_int]['descr']}"; - - $tmp = split("/", $log_split[2]); - $flent['rulenum'] = $tmp[0]; - - $shouldadd = true; - - if(trim($flent['src']) == "") - $shouldadd = false; - if(trim($flent['dst']) == "") - $shouldadd = false; - if(trim($flent['time']) == "") - $shouldadd = false; - - if($shouldadd == true) { - $counter++; - $filterlog[] = $flent; - } else { - if($g['debug']) { - log_error("There was a error parsing rule: $beforeupper . Please report to mailing list or forum."); - } - } - - } - - return isset($config['syslog']['reverse']) ? $filterlog : array_reverse($filterlog); -} - -function convert_port_period_to_colon($addr) { - $addr_split = split("\.", $addr); - if($addr_split[4] == "") - $newvar = $addr_split[0] . "." . $addr_split[1] . "." . $addr_split[2] . "." . $addr_split[3]; - else - $newvar = $addr_split[0] . "." . $addr_split[1] . "." . $addr_split[2] . "." . $addr_split[3] . ":" . $addr_split[4]; - if($newvar == "...") - return $addr; - return $newvar; -} - -function format_ipf_ip($ipfip) { - list($ip,$port) = explode(",", $ipfip); - if (!$port) - return $ip; - - return $ip . ", port " . $port; -} - $pgtitle = "Diagnostics: System logs: Firewall"; include("head.inc"); @@ -200,11 +86,11 @@ include("head.inc");
+ Last firewall log entries. (Switch to dynamic view) @@ -231,6 +117,10 @@ include("head.inc"); + @@ -290,6 +180,9 @@ function outputrule(req) { alert(req.content); } + +

TCP Flags: F - FIN, S - SYN, A or . - ACK, R - RST, P - PSH, U - URG, E - ECE, C - CWR

+ diff --git a/usr/local/www/diag_logs_filter_dynamic.php b/usr/local/www/diag_logs_filter_dynamic.php index 0b986b8da1..d8fe8b26e9 100755 --- a/usr/local/www/diag_logs_filter_dynamic.php +++ b/usr/local/www/diag_logs_filter_dynamic.php @@ -32,14 +32,16 @@ require("guiconfig.inc"); +/* In an effort to reduce duplicate code, many shared functions have been moved here. */ +require_once("includes/log.inc.php"); + $filter_logfile = "{$g['varlog_path']}/filter.log"; /* AJAX related routines */ -handle_ajax(); +handle_ajax(100, true); -$nentries = $config['syslog']['nentries']; -if (!$nentries) - $nentries = 50; +/* Hardcode this. AJAX doesn't do so well with large numbers */ +$nentries = 50; if ($_POST['clear']) { exec("killall syslogd"); @@ -47,111 +49,7 @@ if ($_POST['clear']) { system_syslogd_start(); } -/* format filter logs */ -function conv_clog_filter($logfile, $tail = 50) { - global $config, $nentries, $logfile; - - $logfile = "/var/log/filter.log"; - - /* make interface/port table */ - $iftable = array(); - $iftable[$config['interfaces']['lan']['if']] = "LAN"; - $iftable[get_real_wan_interface()] = "WAN"; - for ($i = 1; isset($config['interfaces']['opt' . $i]); $i++) - $iftable[$config['interfaces']['opt' . $i]['if']] = $config['interfaces']['opt' . $i]['descr']; - - $logarr = ""; - exec("/usr/sbin/clog {$logfile} | /usr/bin/tail -r -n {$tail}", $logarr); - - $filterlog = array(); - - $counter = 0; - - foreach ($logarr as $logent) { - - if($counter > $nentries) - break; - - $log_split = ""; - - //old reg ex - //preg_match("/(.*)\s.*\spf:\s.*\srule\s(.*)\(match\)\:\s(.*)\s\w+\son\s(\w+)\:\s(.*)\s>\s(.*)\:\s.*/", $logent, $log_split); - - preg_match("/(.*)\s.*\spf:\s.*\srule\s(.*)\(match\)\:\s(.*)\s\w+\son\s(\w+)\:\s.*\slength\:.*\s(.*)\s>\s(.*)\:\s.*/", $logent, $log_split); - - $logent = strtoupper($logent); - - $do_not_display = false; - - if(stristr(strtoupper($logent), "UDP") == true) - $flent['proto'] = "UDP"; - else if(stristr(strtoupper($logent), "TCP") == true) - $flent['proto'] = "TCP"; - else if(stristr(strtoupper($logent), "ICMP") == true) - $flent['proto'] = "ICMP"; - else if(stristr(strtoupper($logent), "HSRP") == true) - $flent['proto'] = "HSRP"; - else if(stristr(strtoupper($logent), "ESP") == true) - $flent['proto'] = "ESP"; - else if(stristr(strtoupper($logent), "AH") == true) - $flent['proto'] = "AH"; - else if(stristr(strtoupper($logent), "GRE") == true) - $flent['proto'] = "GRE"; - else if(stristr(strtoupper($logent), "IGMP") == true) - $flent['proto'] = "IGMP"; - else if(stristr(strtoupper($logent), "CARP") == true) - $flent['proto'] = "CARP"; - else if(stristr(strtoupper($logent), "PFSYNC") == true) - $flent['proto'] = "PFSYNC"; - else - $flent['proto'] = "TCP"; - - $flent['time'] = $log_split[1]; - $flent['act'] = $log_split[3]; - - $friendly_int = convert_real_interface_to_friendly_interface_name($log_split[4]); - - $flent['interface'] = strtoupper($friendly_int); - - if($config['interfaces'][$friendly_int]['descr'] <> "") - $flent['interface'] = "{$config['interfaces'][$friendly_int]['descr']}"; - - $flent['src'] = convert_port_period_to_colon($log_split[5]); - $flent['dst'] = convert_port_period_to_colon($log_split[6]); - - $flent['dst'] = str_replace(": NBT UDP PACKET(137)", "", $flent['dst']); - - $tmp = split("/", $log_split[2]); - $flent['rulenum'] = $tmp[0]; - - $counter++; - $filterlog[] = $flent; - - } - - return isset($config['syslog']['reverse']) ? $filterlog : array_reverse($filterlog); -} - -function convert_port_period_to_colon($addr) { - $addr_split = split("\.", $addr); - if($addr_split[4] == "") - $newvar = $addr_split[0] . "." . $addr_split[1] . "." . $addr_split[2] . "." . $addr_split[3]; - else - $newvar = $addr_split[0] . "." . $addr_split[1] . "." . $addr_split[2] . "." . $addr_split[3] . ":" . $addr_split[4]; - if($newvar == "...") - return $addr; - return $newvar; -} - -function format_ipf_ip($ipfip) { - list($ip,$port) = explode(",", $ipfip); - if (!$port) - return $ip; - - return $ip . ", port " . $port; -} - -$filterlog = conv_clog_filter($filter_logfile, $nentries); +$filterlog = conv_clog_filter($filter_logfile, $nentries, $nentries + 100); $pgtitle = "Diagnostics: System logs: Firewall"; include("head.inc"); @@ -170,9 +68,9 @@ include("head.inc"); var isPaused = false;
@@ -208,7 +106,7 @@ include("head.inc");
- Last firewall log entries
Act
- Last records + Last records (Switch to regular view)
@@ -230,13 +128,13 @@ include("head.inc"); } else { /* non-reverse logging */ - if($counter == count($filterlog)) + if($counter == count($filterlog) - 1) $activerow = " id=\"firstrow\""; else $activerow = ""; } ?> -
> +
> +
@@ -322,14 +224,12 @@ function fetch_new_rules_callback(callback_data) { /* loop through rows */ row_split = data_split[x].split("||"); var line = ''; - line = '
'; - line += ' ' + row_split[0] + ''; + line = ' ' + row_split[0] + ''; line += ' ' + row_split[1] + ''; line += ' ' + row_split[2] + ''; line += ' ' + row_split[3] + ''; line += ' ' + row_split[4] + ''; line += ' ' + row_split[5] + ''; - line += '
'; lastsawtime = row_split[6]; new_data_to_add[new_data_to_add.length] = line; } @@ -352,26 +252,23 @@ function update_div_rows(data) { //alert(data.length); for(var x=0; x 0; i--) { nextrecord = i + 1; if(nextrecord < numrows) rows[nextrecord].innerHTML = rows[i].innerHTML; } - appearatrow = 1; - //} + } var item = document.getElementById('firstrow'); if(x == data.length-1) { /* nothing */ @@ -380,11 +277,11 @@ function update_div_rows(data) { showanim = false; } if (showanim) { - rows[appearatrow].style.display = 'none'; - rows[appearatrow].innerHTML = data[x]; - new Effect.Appear(rows[appearatrow]); + item.style.display = 'none'; + item.innerHTML = data[x]; + new Effect.Appear(item); } else { - rows[appearatrow].innerHTML = data[x]; + item.innerHTML = data[x]; } } /* rechedule AJAX interval */ @@ -402,52 +299,13 @@ function toggle_pause() { lastsawtime = ';'; timer = setInterval('fetch_new_rules()', updateDelay); + +

TCP Flags: F - FIN, S - SYN, A or . - ACK, R - RST, P - PSH, U - URG, E - ECE, C - CWR

+ "; - else if(strstr(strtolower($filterent['act']), "r")) - $img = ""; - else - $img = ""; - //echo "{$time_regex[1]} - $row_time > $lastsawtime

"; - if($row_time > $lastsawtime) - $new_rules .= "{$img}||{$log_row['time']}||{$log_row['interface']}||{$log_row['src']}||{$log_row['dst']}||{$log_row['proto']}||" . time() . "||\n"; - } - echo $new_rules; - exit; - } -} ?> \ No newline at end of file