Implement enable and disable commands for IPv4

Signed-off-by: Tom Eastep <teastep@shorewall.net>
This commit is contained in:
Tom Eastep 2011-08-25 16:00:27 -07:00
parent f6920cf061
commit 528f2b0aa2
6 changed files with 338 additions and 12 deletions

View File

@ -263,9 +263,9 @@ sub generate_script_2() {
push_indent;
if ( $global_variables & NOT_RESTORE ) {
emit( 'start|restart|refresh)' );
emit( 'start|restart|refresh|enable)' );
} else {
emit( 'start|restart|refresh|restore)' );
emit( 'start|restart|refresh|enable|restore)' );
}
push_indent;
@ -719,9 +719,9 @@ sub compiler {
);
push_indent;
setup_providers;
}
setup_providers;
#
# TCRules and Traffic Shaping
#

View File

@ -1937,6 +1937,9 @@ EOF
refresh)
logger -p kern.err "ERROR:$g_product refresh failed"
;;
enable)
logger -p kern.err "ERROR: 'enable $g_interface' failed"
;;
esac
if [ "$RESTOREFILE" = NONE ]; then

View File

@ -546,22 +546,47 @@ sub add_a_provider( ) {
emit "\nadd_${table}_routing_rules";
emit "add_${table}_routes";
emit qq(\nprogress_message " Provider $table ($number) Added"\n);
emit( '',
'if [ $COMMAND = enable ]; then'
);
my ( $tbl, $weight );
if ( $balance || $default ) {
$tbl = $default || $config{USE_DEFAULT_RT} ? DEFAULT_TABLE : MAIN_TABLE;
$weight = $balance ? $balance : $default;
push_indent;
if ( $gateway ) {
emit qq(add_gateway "nexthop via $gateway dev $physical weight $weight $realm" ) . $tbl;
} else {
emit qq(add_gateway "nexthop dev $physical weight $weight $realm" ) . $tbl;
}
pop_indent;
}
emit ( qq( progress_message " Provider $table ($number) Started"),
'else',
qq( progress_message2 " Provider $table ($number) Started"),
"fi\n"
);
pop_indent;
emit 'else';
if ( $optional ) {
if ( $shared ) {
emit ( " error_message \"WARNING: Gateway $gateway is not reachable -- Provider $table ($number) not Added\"" );
emit ( " error_message \"WARNING: Gateway $gateway is not reachable -- Provider $table ($number) not Started\"" );
} else {
emit ( " error_message \"WARNING: Interface $physical is not usable -- Provider $table ($number) not Added\"" );
emit ( " error_message \"WARNING: Interface $physical is not usable -- Provider $table ($number) not Started\"" );
}
} else {
if ( $shared ) {
emit( " fatal_error \"Gateway $gateway is not reachable -- Provider $table ($number) Cannot be Added\"" );
emit( " fatal_error \"Gateway $gateway is not reachable -- Provider $table ($number) Cannot be Started\"" );
} else {
emit( " fatal_error \"Interface $physical is not usable -- Provider $table ($number) Cannot be Added\"" );
emit( " fatal_error \"Interface $physical is not usable -- Provider $table ($number) Cannot be Started\"" );
}
}
@ -569,7 +594,48 @@ sub add_a_provider( ) {
pop_indent;
emit "}\n";
emit "} # End of start_provider_$table()";
if ( $optional ) {
emit( '',
'#',
"# Stop provider $table",
'#',
"stop_provider_$table() {" );
push_indent;
my $undo = "\${VARDIR}/undo_${table}_routing";
emit( "if [ -f $undo ]; then",
" . $undo",
" > $undo" );
if ( $balance || $default ) {
$tbl = $fallback || $config{USE_DEFAULT_RT} ? DEFAULT_TABLE : MAIN_TABLE;
$weight = $balance ? $balance : $default;
my $via = 'via';
$via .= " $gateway" if $gateway;
$via .= " dev $physical";
$via .= " weight $weight";
$via .= " $realm" if $realm;
emit( qq( delete_gateway "$via" ) . $tbl );
}
emit( " progress_message2 \"Provider $table stopped\"",
'else',
" startup_error \"$undo does not exist\"",
'fi'
);
pop_indent;
emit '}';
}
push @providers, $table;
@ -885,6 +951,80 @@ sub process_providers() {
pop_indent;
emit '}';
}
emit << 'EOF';;
#
# Enable an optional provider
#
enable_provider() {
g_interface=$1;
case $g_interface in
EOF
push_indent;
push_indent;
for my $provider (@providers ) {
my $providerref = $providers{$provider};
emit( "$providerref->{physical})",
" if [ -z \"`\$IP -$family route ls table $providerref->{number}`\" ]; then",
" start_provider_$provider",
' else',
' startup_error "Interface $g_interface is already enabled"',
' fi',
' ;;'
) if $providerref->{optional};
}
pop_indent;
pop_indent;
emit << 'EOF';;
*)
startup_error "$g_interface is not an optional provider interface"
;;
esac
}
#
# Disable an optional provider
#
disable_provider() {
g_interface=$1;
case $g_interface in
EOF
push_indent;
push_indent;
for my $provider (@providers ) {
my $providerref = $providers{$provider};
emit( "$providerref->{physical})",
" if [ -n \"`\$IP -$family route ls table $providerref->{number}`\" ]; then",
" stop_provider_$provider",
' else',
' startup_error "Interface $g_interface is already disabled"',
' fi',
' ;;'
) if $providerref->{optional};
}
pop_indent;
pop_indent;
emit << 'EOF';;
*)
startup_error "$g_interface is not an optional provider interface"
;;
esac
}
EOF
}
sub setup_providers() {

View File

@ -5,7 +5,21 @@
# Give Usage Information
#
usage() {
echo "Usage: $0 [ options ] [ start|stop|clear|down|reset|refresh|restart|status|up|version ]"
echo "Usage: $0 [ options ] <command>"
echo
echo "<command> is one of:"
echo " start"
echo " stop"
echo " clear"
echo " disable <interface>"
echo " down <interface>"
echo " enable <interface>"
echo " reset"
echo " refresh"
echo " restart"
echo " status"
echo " up <interface>"
echo " version"
echo
echo "Options are:"
echo
@ -295,6 +309,25 @@ case "$COMMAND" in
updown $@
status=0;
;;
enable)
detect_configuration
[ $# -eq 1 ] && exit 0
shift
[ $# -ne 1 ] && usage 2
if shorewall_is_started; then
enable_provider $1
fi
status=0
;;
disable)
[ $# -eq 1 ] && exit 0
shift
[ $# -ne 1 ] && usage 2
if shorewal_is_started; then
disable_provider $1
fi
status=0
;;
version)
[ $# -ne 1 ] && usage 2
echo $SHOREWALL_VERSION

View File

@ -111,6 +111,17 @@ find_device() {
done
}
#
# Find the value 'weight' in the passed arguments then echo the next value
#
find_weight() {
while [ $# -gt 1 ]; do
[ "x$1" = xweight ] && echo $2 && return
shift
done
}
#
# Find the value 'via' in the passed arguments then echo the next value
#
@ -581,6 +592,71 @@ restore_default_route() # $1 = USE_DEFAULT_RT
return $result
}
#
# Add an additional gateway to the default route
#
add_gateway() # $1 = Delta $2 = Table Number
{
local route
local weight
local delta
route=`$IP -4 -o route ls table $2 | grep ^default | sed 's/default //'`
if [ -z "$route" ]; then
run_ip route add default scope global table $2 $1
find_weight $1 > ${VARDIR}/weight
else
delta=$1
if ! echo $route | fgrep -q ' nexthop '; then
route=`echo $route | sed 's/via/nexthop via/'`
if [ -f ${VARDIR}/weight ]; then
weight=`cat ${VARDIR}/weight`
route="$route weight $weight"
rm -f ${VARDIR}/weight
fi
fi
run_ip route replace default scope global table $2 $route $delta
fi
}
#
# Remove a gateway from the default route
#
delete_gateway() # $! = Description of the Gateway $2 = table number
{
local route
local gateway
local newroute
route=`$IP -4 -o route ls table $2 | grep ^default`
gateway=$1
if [ -n "$route" ]; then
if echo $route | fgrep -q ' nexthop '; then
gateway="nexthop $gateway"
fi
eval route=\`echo $route \| sed \'s/$gateway/ /\'\`
if echo $route | fgrep -q ' via '; then
run_ip route replace table $2 $route
else
run_ip route delete default table $2
fi
newroute=`$IP -4 -o route ls table $2 | grep ^default`
if echo $newroute | fgrep -q ' nexthop '; then
rm -f ${VARDIR}/weight
else
find_weight $route > ${VARDIR}/weight
fi
fi
}
#
# Determine the MAC address of the passed IP through the passed interface
#

View File

@ -1803,7 +1803,81 @@ echo $state &gt; ${VARDIR}/${DEVICE}.status
exit 0
#EOF</programlisting>:</para>
#EOF</programlisting>Beginning with Shorewall 4.4.23, it is not necessary to
restart the firewall when an interface transitions between the usable
and unusable
states.<filename>/etc/lsm/script</filename><programlisting>#!/bin/sh
#
# (C) 2009 Mika Ilmaranta &lt;ilmis@nullnet.fi&gt;
# (C) 2009 Tom Eastep &lt;teastep@shorewall.net&gt;
#
# License: GPLv2
#
STATE=${1}
NAME=${2}
CHECKIP=${3}
DEVICE=${4}
WARN_EMAIL=${5}
REPLIED=${6}
WAITING=${7}
TIMEOUT=${8}
REPLY_LATE=${9}
CONS_RCVD=${10}
CONS_WAIT=${11}
CONS_MISS=${12}
AVG_RTT=${13}
if [ -f /usr/share/shorewall-lite/lib.base ]; then
VARDIR=/var/lib/shorewall-lite
STATEDIR=/etc/shorewall-lite
else
VARDIR=/var/lib/shorewall
STATEDIR=/etc/shorewall
fi
[ -f ${STATEDIR}/vardir ] &amp;&amp; . ${STATEDIR}/vardir
cat &lt;&lt;EOM | mail -s "${NAME} ${STATE}, DEV ${DEVICE}" ${WARN_EMAIL}
Hi,
Connection ${NAME} is now ${STATE}.
Following parameters were passed:
newstate = ${STATE}
name = ${NAME}
checkip = ${CHECKIP}
device = ${DEVICE}
warn_email = ${WARN_EMAIL}
Packet counters:
replied = ${REPLIED} packets replied
waiting = ${WAITING} packets waiting for reply
timeout = ${TIMEOUT} packets that have timed out (= packet loss)
reply_late = ${REPLY_LATE} packets that received a reply after timeout
cons_rcvd = ${CONS_RCVD} consecutively received replies in sequence
cons_wait = ${CONS_WAIT} consecutive packets waiting for reply
cons_miss = ${CONS_MISS} consecutive packets that have timed out
avg_rtt = ${AVG_RTT} average rtt, notice that waiting and timed out packets have rtt = 0 when calculating this
Your LSM Daemon
EOM
<emphasis role="bold">if [ ${STATE} = up ]; then
echo 0 &gt; ${VARDIR}/${DEVICE}.status
${VARDIR}/firewall enable ${DEVICE}
else
echo 1 &gt; ${VARDIR}/${DEVICE}.status
${VARDIR}/firewall disable ${DEVICE}
fi
</emphasis>
/sbin/shorewall show routing &gt;&gt; /var/log/lsm
exit 0
#EOF</programlisting></para>
</section>
</section>