mirror of
https://gitlab.com/shorewall/code.git
synced 2025-02-23 21:21:49 +01:00
Use iptables[6]-restore to instantiate the 'stopped' ruleset
Signed-off-by: Tom Eastep <teastep@shorewall.net> git-svn-id: https://shorewall.svn.sourceforge.net/svnroot/shorewall/trunk@9761 fbd18981-670d-0410-9b5c-8dc0c1a9a2bb
This commit is contained in:
parent
7210e8c15e
commit
cddd1b1ae9
@ -156,6 +156,7 @@ our %EXPORT_TAGS = (
|
||||
set_global_variables
|
||||
create_netfilter_load
|
||||
create_chainlist_reload
|
||||
create_stop_load
|
||||
$section
|
||||
%sections
|
||||
%targets
|
||||
@ -2972,4 +2973,97 @@ sub create_chainlist_reload($) {
|
||||
emit "}\n";
|
||||
}
|
||||
|
||||
#
|
||||
# Generate the netfilter input to stop the firewall
|
||||
#
|
||||
sub create_stop_load( $ ) {
|
||||
my $test = shift;
|
||||
|
||||
my @table_list;
|
||||
|
||||
if ( $family == F_IPV4 ) {
|
||||
push @table_list, 'raw' if $capabilities{RAW_TABLE};
|
||||
push @table_list, 'nat' if $capabilities{NAT_ENABLED};
|
||||
push @table_list, 'mangle' if $capabilities{MANGLE_ENABLED} && $config{MANGLE_ENABLED};
|
||||
push @table_list, 'filter';
|
||||
} else {
|
||||
@table_list = qw( raw mangle filter );
|
||||
}
|
||||
|
||||
$mode = NULL_MODE;
|
||||
|
||||
my $utility = $family == F_IPV4 ? 'iptables-restore' : 'ip6tables-restore';
|
||||
my $UTILITY = $family == F_IPV4 ? 'IPTABLES_RESTORE' : 'IP6TABLES_RESTORE';
|
||||
|
||||
emit '';
|
||||
|
||||
emit "exec 3>\${VARDIR}/.${utility}-stop-input";
|
||||
|
||||
enter_cat_mode;
|
||||
|
||||
my $date = localtime;
|
||||
|
||||
unless ( $test ) {
|
||||
emit_unindented '#';
|
||||
emit_unindented "# Generated by Shorewall-perl $globals{VERSION} - $date";
|
||||
emit_unindented '#';
|
||||
}
|
||||
|
||||
for my $table ( @table_list ) {
|
||||
emit_unindented "*$table";
|
||||
|
||||
my @chains;
|
||||
#
|
||||
# iptables-restore seems to be quite picky about the order of the builtin chains
|
||||
#
|
||||
for my $chain ( @builtins ) {
|
||||
my $chainref = $chain_table{$table}{$chain};
|
||||
if ( $chainref ) {
|
||||
assert( $chainref->{cmdlevel} == 0 );
|
||||
emit_unindented ":$chain $chainref->{policy} [0:0]";
|
||||
push @chains, $chainref;
|
||||
}
|
||||
}
|
||||
#
|
||||
# First create the chains in the current table
|
||||
#
|
||||
for my $chain ( grep $chain_table{$table}{$_}->{referenced} , ( sort keys %{$chain_table{$table}} ) ) {
|
||||
my $chainref = $chain_table{$table}{$chain};
|
||||
unless ( $chainref->{builtin} ) {
|
||||
assert( $chainref->{cmdlevel} == 0 );
|
||||
emit_unindented ":$chainref->{name} - [0:0]";
|
||||
push @chains, $chainref;
|
||||
}
|
||||
}
|
||||
#
|
||||
# Then emit the rules
|
||||
#
|
||||
for my $chainref ( @chains ) {
|
||||
emitr $chainref->{name}, $_ for ( grep defined $_, @{$chainref->{rules}} );
|
||||
}
|
||||
#
|
||||
# Commit the changes to the table
|
||||
#
|
||||
enter_cat_mode unless $mode == CAT_MODE;
|
||||
emit_unindented 'COMMIT';
|
||||
}
|
||||
|
||||
enter_cmd_mode;
|
||||
#
|
||||
# Now generate the actual ip[6]tables-restore command
|
||||
#
|
||||
emit( 'exec 3>&-',
|
||||
'',
|
||||
'[ -n "$DEBUG" ] && command=debug_restore_input || command=$' . $UTILITY,
|
||||
'',
|
||||
'progress_message2 "Running $command..."',
|
||||
'',
|
||||
"cat \${VARDIR}/.${utility}-stop-input | \$command # Use this nonsensical form to appease SELinux",
|
||||
'if [ $? != 0 ]; then',
|
||||
qq( fatal_error "$command Failed. Input is in \${VARDIR}/.${utility}-stop-input"),
|
||||
"fi\n"
|
||||
);
|
||||
|
||||
}
|
||||
|
||||
1;
|
||||
|
@ -516,13 +516,6 @@ EOF
|
||||
|
||||
emit "}\n";
|
||||
|
||||
unless ( $test ) {
|
||||
if ( $family == F_IPV4 ) {
|
||||
copy $globals{SHAREDIRPL} . 'prog.footer';
|
||||
} else {
|
||||
copy $globals{SHAREDIRPL} . 'prog.footer6';
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#
|
||||
@ -805,7 +798,17 @@ sub compiler {
|
||||
# S T O P _ F I R E W A L L
|
||||
# (Writes the stop_firewall() function to the compiled script)
|
||||
#
|
||||
compile_stop_firewall;
|
||||
compile_stop_firewall( $test );
|
||||
#
|
||||
# Copy the footer to the object
|
||||
#
|
||||
unless ( $test ) {
|
||||
if ( $family == F_IPV4 ) {
|
||||
copy $globals{SHAREDIRPL} . 'prog.footer';
|
||||
} else {
|
||||
copy $globals{SHAREDIRPL} . 'prog.footer6';
|
||||
}
|
||||
}
|
||||
#
|
||||
# Close, rename and secure the object
|
||||
#
|
||||
|
@ -39,7 +39,6 @@ our @EXPORT = qw( process_tos
|
||||
setup_ecn
|
||||
add_common_rules
|
||||
setup_mac_lists
|
||||
process_criticalhosts
|
||||
process_routestopped
|
||||
process_rules
|
||||
generate_matrix
|
||||
@ -364,52 +363,6 @@ sub setup_blacklist() {
|
||||
}
|
||||
}
|
||||
|
||||
sub process_criticalhosts() {
|
||||
|
||||
my @critical = ();
|
||||
|
||||
my $fn = open_file 'routestopped';
|
||||
|
||||
my $seq = 0;
|
||||
|
||||
first_entry "$doing $fn for critical hosts...";
|
||||
|
||||
while ( read_a_line ) {
|
||||
|
||||
my $routeback = 0;
|
||||
|
||||
my ($interface, $hosts, $options, $proto, $ports, $sports ) = split_line 1, 6, 'routestopped file';
|
||||
|
||||
fatal_error "Unknown interface ($interface)" unless known_interface $interface;
|
||||
|
||||
$hosts = ALLIP unless $hosts ne '-';
|
||||
|
||||
my @hosts;
|
||||
|
||||
$seq++;
|
||||
|
||||
for my $host ( split_list $hosts, 'host' ) {
|
||||
validate_host $host, 1;
|
||||
push @hosts, "$interface|$host|$seq";
|
||||
}
|
||||
|
||||
unless ( $options eq '-' ) {
|
||||
for my $option (split_list $options, 'option' ) {
|
||||
unless ( $option eq 'routeback' || $option eq 'source' || $option eq 'dest' || $option eq 'notrack' ) {
|
||||
if ( $option eq 'critical' ) {
|
||||
fatal_error "PROTO may not be specified with 'critical'" if $proto ne '-';
|
||||
push @critical, @hosts;
|
||||
} else {
|
||||
warning_message "Unknown routestopped option ( $option ) ignored";
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
\@critical;
|
||||
}
|
||||
|
||||
sub process_routestopped() {
|
||||
|
||||
my ( @allhosts, %source, %dest , %notrack, @rule );
|
||||
@ -472,6 +425,7 @@ sub process_routestopped() {
|
||||
}
|
||||
} else {
|
||||
warning_message "Unknown routestopped option ( $option ) ignored" unless $option eq 'critical';
|
||||
warning_message "The 'critical' option is no longer supported (or needed)";
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -479,8 +433,6 @@ sub process_routestopped() {
|
||||
push @allhosts, @hosts;
|
||||
}
|
||||
|
||||
my $tool = $family == F_IPV4 ? '$IPTABLES' : '$IP6TABLES';
|
||||
|
||||
for my $host ( @allhosts ) {
|
||||
my ( $interface, $h, $seq ) = split /\|/, $host;
|
||||
my $source = match_source_net $h;
|
||||
@ -489,24 +441,24 @@ sub process_routestopped() {
|
||||
my $desti = match_dest_dev $interface;
|
||||
my $rule = shift @rule;
|
||||
|
||||
emit "$tool -A INPUT $sourcei $source $rule -j ACCEPT";
|
||||
emit "$tool -A OUTPUT $desti $dest $rule -j ACCEPT" unless $config{ADMINISABSENTMINDED};
|
||||
add_rule $filter_table->{INPUT}, "$sourcei $source $rule -j ACCEPT";
|
||||
add_rule $filter_table->{OUTPUT}, "$desti $dest $rule -j ACCEPT" unless $config{ADMINISABSENTMINDED};
|
||||
|
||||
my $matched = 0;
|
||||
|
||||
if ( $source{$host} ) {
|
||||
emit "$tool -A FORWARD $sourcei $source $rule -j ACCEPT";
|
||||
add_rule $filter_table->{FORWARD}, "$sourcei $source $rule -j ACCEPT";
|
||||
$matched = 1;
|
||||
}
|
||||
|
||||
if ( $dest{$host} ) {
|
||||
emit "$tool -A FORWARD $desti $dest $rule -j ACCEPT";
|
||||
add_rule $filter_table->{FORWARD}, "$desti $dest $rule -j ACCEPT";
|
||||
$matched = 1;
|
||||
}
|
||||
|
||||
if ( $notrack{$host} ) {
|
||||
emit "$tool -t raw -A PREROUTING $sourcei $source $rule -j NOTRACK";
|
||||
emit "$tool -t raw -A OUTPUT $desti $dest $rule -j NOTRACK";
|
||||
add_rule $raw_table->{PREROUTING}, "$sourcei $source $rule -j NOTRACK";
|
||||
add_rule $raw_table->{OUTPUT}, "$desti $dest $rule -j NOTRACK";
|
||||
}
|
||||
|
||||
unless ( $matched ) {
|
||||
@ -515,7 +467,7 @@ sub process_routestopped() {
|
||||
my ( $interface1, $h1 , $seq1 ) = split /\|/, $host1;
|
||||
my $dest1 = match_dest_net $h1;
|
||||
my $desti1 = match_dest_dev $interface1;
|
||||
emit "$tool -A FORWARD $sourcei $desti1 $source $dest1 $rule -j ACCEPT";
|
||||
add_rule $filter_table->{FORWARD}, "$sourcei $desti1 $source $dest1 $rule -j ACCEPT";
|
||||
clearrule;
|
||||
}
|
||||
}
|
||||
@ -2117,7 +2069,8 @@ sub setup_mss( ) {
|
||||
#
|
||||
# Compile the stop_firewall() function
|
||||
#
|
||||
sub compile_stop_firewall() {
|
||||
sub compile_stop_firewall( $ ) {
|
||||
my $test = shift;
|
||||
|
||||
emit <<'EOF';
|
||||
#
|
||||
@ -2126,6 +2079,14 @@ sub compile_stop_firewall() {
|
||||
stop_firewall() {
|
||||
EOF
|
||||
|
||||
Shorewall::Chains::initialize( $family );
|
||||
|
||||
initialize_chain_table;
|
||||
|
||||
if ( $config{ADMINISABSENTMINDED} ) {
|
||||
$filter_table->{OUTPUT}{policy} = 'ACCEPT';
|
||||
}
|
||||
|
||||
if ( $family == F_IPV4 ) {
|
||||
emit( ' deletechain() {',
|
||||
' qt $IPTABLES -L $1 -n && qt $IPTABLES -F $1 && qt $IPTABLES -X $1' );
|
||||
@ -2137,24 +2098,6 @@ EOF
|
||||
emit <<'EOF';
|
||||
}
|
||||
|
||||
deleteallchains() {
|
||||
do_iptables -F
|
||||
do_iptables -X
|
||||
}
|
||||
|
||||
delete_nat() {
|
||||
do_iptables -t nat -F
|
||||
do_iptables -t nat -X
|
||||
|
||||
if [ -f ${VARDIR}/nat ]; then
|
||||
while read external interface; do
|
||||
del_ip_addr $external $interface
|
||||
done < ${VARDIR}/nat
|
||||
|
||||
rm -f ${VARDIR}/nat
|
||||
fi
|
||||
}
|
||||
|
||||
case $COMMAND in
|
||||
stop|clear|restore)
|
||||
;;
|
||||
@ -2211,42 +2154,15 @@ EOF
|
||||
run_stop_exit
|
||||
EOF
|
||||
|
||||
if ( $capabilities{MANGLE_ENABLED} && $config{MANGLE_ENABLED} ) {
|
||||
emit <<'EOF';
|
||||
run_iptables -t mangle -F
|
||||
run_iptables -t mangle -X
|
||||
for chain in PREROUTING INPUT FORWARD POSTROUTING; do
|
||||
qt1 $IPTABLES -t mangle -P $chain ACCEPT
|
||||
done
|
||||
EOF
|
||||
}
|
||||
|
||||
if ( $capabilities{RAW_TABLE} ) {
|
||||
if ( $family == F_IPV4 ) {
|
||||
emit <<'EOF';
|
||||
run_iptables -t raw -F
|
||||
run_iptables -t raw -X
|
||||
for chain in PREROUTING OUTPUT; do
|
||||
qt1 $IPTABLES -t raw -P $chain ACCEPT
|
||||
done
|
||||
EOF
|
||||
} else {
|
||||
emit <<'EOF';
|
||||
run_iptables -t raw -F
|
||||
run_iptables -t raw -X
|
||||
for chain in PREROUTING OUTPUT; do
|
||||
qt1 $IP6TABLES -t raw -P $chain ACCEPT
|
||||
done
|
||||
EOF
|
||||
}
|
||||
}
|
||||
|
||||
if ( $capabilities{NAT_ENABLED} ) {
|
||||
emit <<'EOF';
|
||||
delete_nat
|
||||
for chain in PREROUTING POSTROUTING OUTPUT; do
|
||||
qt1 $IPTABLES -t nat -P $chain ACCEPT
|
||||
done
|
||||
emit<<'EOF';
|
||||
if [ -f ${VARDIR}/nat ]; then
|
||||
while read external interface; do
|
||||
del_ip_addr $external $interface
|
||||
done < ${VARDIR}/nat
|
||||
|
||||
rm -f ${VARDIR}/nat
|
||||
fi
|
||||
EOF
|
||||
}
|
||||
|
||||
@ -2259,9 +2175,10 @@ EOF
|
||||
f=/proc/sys/net/ipv4/conf/$interface/proxy_arp
|
||||
[ -f $f ] && echo 0 > $f
|
||||
done < ${VARDIR}/proxyarp
|
||||
|
||||
rm -f ${VARDIR}/proxyarp
|
||||
fi
|
||||
|
||||
rm -f ${VARDIR}/proxyarp
|
||||
EOF
|
||||
}
|
||||
|
||||
@ -2273,109 +2190,27 @@ EOF
|
||||
'restore_default_route'
|
||||
);
|
||||
|
||||
my $criticalhosts = process_criticalhosts;
|
||||
|
||||
if ( @$criticalhosts ) {
|
||||
if ( $config{ADMINISABSENTMINDED} ) {
|
||||
emit ( 'for chain in INPUT OUTPUT; do',
|
||||
' setpolicy $chain ACCEPT',
|
||||
'done',
|
||||
'',
|
||||
'setpolicy FORWARD DROP',
|
||||
'',
|
||||
'deleteallchains',
|
||||
''
|
||||
);
|
||||
|
||||
for my $hosts ( @$criticalhosts ) {
|
||||
my ( $interface, $host, $seq ) = ( split /\|/, $hosts );
|
||||
my $source = match_source_net $host;
|
||||
my $dest = match_dest_net $host;
|
||||
|
||||
emit( "do_iptables -A INPUT -i $interface $source -j ACCEPT",
|
||||
"do_iptables -A OUTPUT -o $interface $dest -j ACCEPT"
|
||||
);
|
||||
}
|
||||
|
||||
emit( '',
|
||||
'for chain in INPUT OUTPUT; do',
|
||||
' setpolicy $chain DROP',
|
||||
"done\n"
|
||||
);
|
||||
} else {
|
||||
emit( '',
|
||||
'for chain in INPUT OUTPUT; do',
|
||||
' setpolicy $chain ACCEPT',
|
||||
'done',
|
||||
'',
|
||||
'setpolicy FORWARD DROP',
|
||||
'',
|
||||
"deleteallchains\n"
|
||||
);
|
||||
|
||||
for my $hosts ( @$criticalhosts ) {
|
||||
my ( $interface, $host , $seq ) = ( split /|/, $hosts );
|
||||
my $source = match_source_net $host;
|
||||
my $dest = match_dest_net $host;
|
||||
|
||||
emit( "do_iptables -A INPUT -i $interface $source -j ACCEPT",
|
||||
"do_iptables -A OUTPUT -o $interface $dest -j ACCEPT"
|
||||
);
|
||||
}
|
||||
|
||||
emit( "\nsetpolicy INPUT DROP",
|
||||
'',
|
||||
'for chain in INPUT FORWARD; do',
|
||||
' setcontinue $chain',
|
||||
"done\n"
|
||||
);
|
||||
}
|
||||
} elsif ( $config{ADMINISABSENTMINDED} ) {
|
||||
emit( 'for chain in INPUT FORWARD; do',
|
||||
' setpolicy $chain DROP',
|
||||
'done',
|
||||
'',
|
||||
'setpolicy OUTPUT ACCEPT',
|
||||
'',
|
||||
'deleteallchains',
|
||||
'',
|
||||
'for chain in INPUT FORWARD; do',
|
||||
' setcontinue $chain',
|
||||
"done\n",
|
||||
);
|
||||
} else {
|
||||
emit( 'for chain in INPUT OUTPUT FORWARD; do',
|
||||
' setpolicy $chain DROP',
|
||||
'done',
|
||||
'',
|
||||
"deleteallchains\n"
|
||||
);
|
||||
}
|
||||
my @chains = $config{ADMINISABSENTMINDED} ? qw/INPUT FORWARD/ : qw/INPUT OUTPUT FORWARD/;
|
||||
|
||||
add_rule $filter_table->{$_}, '-m state --state ESTABLISHED,RELATED -j ACCEPT' for @chains;
|
||||
|
||||
if ( $family == F_IPV6 ) {
|
||||
emit <<'EOF';
|
||||
#
|
||||
# Enable link local and multi-cast
|
||||
#
|
||||
run_iptables -A INPUT -s ff80::/10 -j ACCEPT
|
||||
run_iptables -A INPUT -d ff80::/10 -j ACCEPT
|
||||
run_iptables -A INPUT -d ff00::/10 -j ACCEPT
|
||||
EOF
|
||||
add_rule $filter_table->{INPUT}, '-s ff80::/10 -j ACCEPT';
|
||||
add_rule $filter_table->{INPUT}, '-d ff80::/10 -j ACCEPT';
|
||||
add_rule $filter_table->{INPUT}, '-d ff00::/10 -j ACCEPT';
|
||||
|
||||
emit <<'EOF' unless $config{ADMINISABSENTMINDED};
|
||||
run_iptables -A OUTPUT -d ff80::/10 -j ACCEPT
|
||||
run_iptables -A OUTPUT -d ff00::/10 -j ACCEPT
|
||||
|
||||
EOF
|
||||
unless ( $config{ADMINISABSENTMINDED} ) {
|
||||
add_rule $filter_table->{OUTPUT}, '-d ff80::/10 -j ACCEPT';
|
||||
add_rule $filter_table->{OUTPUT}, '-d ff00::/10 -j ACCEPT';
|
||||
}
|
||||
}
|
||||
|
||||
process_routestopped;
|
||||
|
||||
emit( 'do_iptables -A INPUT -i lo -j ACCEPT',
|
||||
'do_iptables -A OUTPUT -o lo -j ACCEPT'
|
||||
);
|
||||
add_rule $filter_table->{INPUT}, '-i lo -j ACCEPT';
|
||||
add_rule $filter_table->{INPUT}, '-i lo -j ACCEPT';
|
||||
|
||||
emit 'do_iptables -A OUTPUT -o lo -j ACCEPT' unless $config{ADMINISABSENTMINDED};
|
||||
add_rule $filter_table->{OUTPUT}, '-o lo -j ACCEPT' unless $config{ADMINISABSENTMINDED};
|
||||
|
||||
my $interfaces = find_interfaces_by_option 'dhcp';
|
||||
|
||||
@ -2383,17 +2218,19 @@ EOF
|
||||
my $ports = $family == F_IPV4 ? '67:68' : '546:547';
|
||||
|
||||
for my $interface ( @$interfaces ) {
|
||||
emit "do_iptables -A INPUT -p udp -i $interface --dport $ports -j ACCEPT";
|
||||
emit "do_iptables -A OUTPUT -p udp -o $interface --dport $ports -j ACCEPT" unless $config{ADMINISABSENTMINDED};
|
||||
add_rule $filter_table->{INPUT}, "-p udp -i $interface --dport $ports -j ACCEPT";
|
||||
add_rule $filter_table->{OUTPUT}, "-p udp -o $interface --dport $ports -j ACCEPT" unless $config{ADMINISABSENTMINDED};
|
||||
#
|
||||
# This might be a bridge
|
||||
#
|
||||
emit "do_iptables -A FORWARD -p udp -i $interface -o $interface --dport $ports -j ACCEPT";
|
||||
add_rule $filter_table->{FORWARD}, "-p udp -i $interface -o $interface --dport $ports -j ACCEPT";
|
||||
}
|
||||
}
|
||||
|
||||
emit '';
|
||||
|
||||
create_stop_load $test;
|
||||
|
||||
if ( $family == F_IPV4 ) {
|
||||
if ( $config{IP_FORWARDING} eq 'on' ) {
|
||||
emit( 'echo 1 > /proc/sys/net/ipv4/ip_forward',
|
||||
@ -2426,7 +2263,7 @@ EOF
|
||||
my @ipsets = all_ipsets;
|
||||
|
||||
if ( @ipsets ) {
|
||||
emit <<'EOF'
|
||||
emit <<'EOF';
|
||||
|
||||
if [ -n "$(mywhich ipset)" ]; then
|
||||
if ipset -S > ${VARDIR}/ipsets.tmp; then
|
||||
@ -2435,8 +2272,10 @@ EOF
|
||||
#
|
||||
grep -q '^-N' ${VARDIR}/ipsets.tmp && mv -f ${VARDIR}/ipsets.tmp ${VARDIR}/ipsets.save
|
||||
fi
|
||||
fi
|
||||
EOF
|
||||
|
||||
emit " ipset -X $_" for @ipsets;
|
||||
emit "fi\n";
|
||||
}
|
||||
|
||||
emit '
|
||||
|
@ -10,6 +10,8 @@ Changes in Shorewall 4.3.8
|
||||
|
||||
5) Suppress leading whitespace on certain continuation lines.
|
||||
|
||||
6) Use iptables[6]-restore to stop the firewall.
|
||||
|
||||
Changes in Shorewall 4.3.7
|
||||
|
||||
1) Fix forward treatment of interface options.
|
||||
|
@ -83,6 +83,11 @@ None.
|
||||
address is ignored so the SOURCE column effectively contains
|
||||
"net:206.124.146.177,206.124.147.178,206.124.146.180".
|
||||
|
||||
4) The generated script now uses iptables[6]-restore to instantiate
|
||||
the Netfilter ruleset during processing of the 'stop' command. As a
|
||||
consequence, the 'critical' option in /etc/shorewall/route_stopped
|
||||
is no longer needed and will result in a warning.
|
||||
|
||||
----------------------------------------------------------------------------
|
||||
N E W F E A T U R E S IN 4 . 3
|
||||
----------------------------------------------------------------------------
|
||||
|
Loading…
Reference in New Issue
Block a user