firewall: - fix ip6tables rules when icmp_type option is set - add "family" option to zones, forwardings, redirects and rules to selectively apply rules to iptables and/or ip6tables

SVN-Revision: 21508
This commit is contained in:
Jo-Philipp Wich 2010-05-19 21:35:23 +00:00
parent 359f611957
commit 40ad9defcc
7 changed files with 105 additions and 41 deletions

View File

@ -9,7 +9,7 @@ include $(TOPDIR)/rules.mk
PKG_NAME:=firewall PKG_NAME:=firewall
PKG_VERSION:=2 PKG_VERSION:=2
PKG_RELEASE:=3 PKG_RELEASE:=4
include $(INCLUDE_DIR)/package.mk include $(INCLUDE_DIR)/package.mk

View File

@ -7,6 +7,7 @@ fw_config_get_forwarding() {
string name "" \ string name "" \
string src "" \ string src "" \
string dest "" \ string dest "" \
string family "" \
} || return } || return
[ -n "$forwarding_name" ] || forwarding_name=$forwarding__name [ -n "$forwarding_name" ] || forwarding_name=$forwarding__name
} }
@ -26,7 +27,9 @@ fw_load_forwarding() {
target=zone_${forwarding_dest}_ACCEPT target=zone_${forwarding_dest}_ACCEPT
} }
fw add i f $chain $target ^ local mode=$(fw_get_family_mode ${forwarding_family:-x} ${forwarding_dest:-${forwarding_src:--}} i)
fw add $mode f $chain $target ^
# propagate masq zone flag # propagate masq zone flag
[ -n "$forwarding_src" ] && list_contains CONNTRACK_ZONES $forwarding_src && { [ -n "$forwarding_src" ] && list_contains CONNTRACK_ZONES $forwarding_src && {

View File

@ -4,6 +4,8 @@
FW_INITIALIZED= FW_INITIALIZED=
FW_ZONES= FW_ZONES=
FW_ZONES4=
FW_ZONES6=
FW_CONNTRACK_ZONES= FW_CONNTRACK_ZONES=
FW_NOTRACK_DISABLED= FW_NOTRACK_DISABLED=
@ -140,6 +142,7 @@ fw_config_get_zone() {
boolean conntrack 0 \ boolean conntrack 0 \
boolean mtu_fix 0 \ boolean mtu_fix 0 \
boolean custom_chains "$FW_ADD_CUSTOM_CHAINS" \ boolean custom_chains "$FW_ADD_CUSTOM_CHAINS" \
string family "" \
} || return } || return
[ -n "$zone_name" ] || zone_name=$zone_NAME [ -n "$zone_name" ] || zone_name=$zone_NAME
[ -n "$zone_network" ] || zone_network=$zone_name [ -n "$zone_network" ] || zone_network=$zone_name
@ -158,46 +161,67 @@ fw_load_zone() {
[ $zone_conntrack = 1 -o $zone_masq = 1 ] && \ [ $zone_conntrack = 1 -o $zone_masq = 1 ] && \
append FW_CONNTRACK_ZONES "$zone_NAME" append FW_CONNTRACK_ZONES "$zone_NAME"
local mode
case "$zone_family" in
*4)
mode=4
append FW_ZONES4 $zone_name
uci_set_state firewall core ${zone_name}_ipv4 1
;;
*6)
mode=6
append FW_ZONES6 $zone_name
uci_set_state firewall core ${zone_name}_ipv6 1
;;
*)
mode=i
append FW_ZONES4 $zone_name
append FW_ZONES6 $zone_name
uci_set_state firewall core ${zone_name}_ipv4 1
uci_set_state firewall core ${zone_name}_ipv6 1
;;
esac
local chain=zone_${zone_name} local chain=zone_${zone_name}
fw add i f ${chain}_ACCEPT fw add $mode f ${chain}_ACCEPT
fw add i f ${chain}_DROP fw add $mode f ${chain}_DROP
fw add i f ${chain}_REJECT fw add $mode f ${chain}_REJECT
fw add i f ${chain}_MSSFIX fw add $mode f ${chain}_MSSFIX
# TODO: Rename to ${chain}_input # TODO: Rename to ${chain}_input
fw add i f ${chain} fw add $mode f ${chain}
fw add i f ${chain} ${chain}_${zone_input} $ fw add $mode f ${chain} ${chain}_${zone_input} $
fw add i f ${chain}_forward fw add $mode f ${chain}_forward
fw add i f ${chain}_forward ${chain}_${zone_forward} $ fw add $mode f ${chain}_forward ${chain}_${zone_forward} $
# TODO: add ${chain}_output # TODO: add ${chain}_output
fw add i f output ${chain}_${zone_output} $ fw add $mode f output ${chain}_${zone_output} $
# TODO: Rename to ${chain}_MASQUERADE # TODO: Rename to ${chain}_MASQUERADE
fw add i n ${chain}_nat fw add $mode n ${chain}_nat
fw add i n ${chain}_prerouting fw add $mode n ${chain}_prerouting
fw add i r ${chain}_notrack fw add $mode r ${chain}_notrack
[ $zone_masq == 1 ] && \ [ $zone_masq == 1 ] && \
fw add i n POSTROUTING ${chain}_nat $ fw add $mode n POSTROUTING ${chain}_nat $
[ $zone_mtu_fix == 1 ] && \ [ $zone_mtu_fix == 1 ] && \
fw add i f FORWARD ${chain}_MSSFIX ^ fw add $mode f FORWARD ${chain}_MSSFIX ^
[ $zone_custom_chains == 1 ] && { [ $zone_custom_chains == 1 ] && {
[ $FW_ADD_CUSTOM_CHAINS == 1 ] || \ [ $FW_ADD_CUSTOM_CHAINS == 1 ] || \
fw_die "zone ${zone_name}: custom_chains globally disabled" fw_die "zone ${zone_name}: custom_chains globally disabled"
fw add i f input_${zone_name} fw add $mode f input_${zone_name}
fw add i f ${chain} input_${zone_name} ^ fw add $mode f ${chain} input_${zone_name} ^
fw add i f forwarding_${zone_name} fw add $mode f forwarding_${zone_name}
fw add i f ${chain}_forward forwarding_${zone_name} ^ fw add $mode f ${chain}_forward forwarding_${zone_name} ^
fw add i n prerouting_${zone_name} fw add $mode n prerouting_${zone_name}
fw add i n ${chain}_prerouting prerouting_${zone_name} ^ fw add $mode n ${chain}_prerouting prerouting_${zone_name} ^
} }
fw_callback post zone fw_callback post zone

View File

@ -17,23 +17,26 @@ fw_configure_interface() {
fw__do_rules() { fw__do_rules() {
local action=$1 local action=$1
local chain=$2 local zone=$2
local chain=zone_${zone}
local ifname=$3 local ifname=$3
fw $action i f ${chain}_ACCEPT ACCEPT ^ { -o "$ifname" } local mode=$(fw_get_family_mode x $zone i)
fw $action i f ${chain}_ACCEPT ACCEPT ^ { -i "$ifname" }
fw $action i f ${chain}_DROP DROP ^ { -o "$ifname" }
fw $action i f ${chain}_DROP DROP ^ { -i "$ifname" }
fw $action i f ${chain}_REJECT reject ^ { -o "$ifname" }
fw $action i f ${chain}_REJECT reject ^ { -i "$ifname" }
fw $action i n ${chain}_nat MASQUERADE ^ { -o "$ifname" } fw $action $mode f ${chain}_ACCEPT ACCEPT ^ { -o "$ifname" }
fw $action i f ${chain}_MSSFIX TCPMSS ^ { -o "$ifname" -p tcp --tcp-flags SYN,RST SYN --clamp-mss-to-pmtu } fw $action $mode f ${chain}_ACCEPT ACCEPT ^ { -i "$ifname" }
fw $action $mode f ${chain}_DROP DROP ^ { -o "$ifname" }
fw $action $mode f ${chain}_DROP DROP ^ { -i "$ifname" }
fw $action $mode f ${chain}_REJECT reject ^ { -o "$ifname" }
fw $action $mode f ${chain}_REJECT reject ^ { -i "$ifname" }
fw $action i f input ${chain} $ { -i "$ifname" } fw $action $mode n ${chain}_nat MASQUERADE ^ { -o "$ifname" }
fw $action i f forward ${chain}_forward $ { -i "$ifname" } fw $action $mode f ${chain}_MSSFIX TCPMSS ^ { -o "$ifname" -p tcp --tcp-flags SYN,RST SYN --clamp-mss-to-pmtu }
fw $action i n PREROUTING ${chain}_prerouting ^ { -i "$ifname" }
fw $action i r PREROUTING ${chain}_notrack ^ { -i "$ifname" } fw $action $mode f input ${chain} $ { -i "$ifname" }
fw $action $mode f forward ${chain}_forward $ { -i "$ifname" }
fw $action $mode n PREROUTING ${chain}_prerouting ^ { -i "$ifname" }
fw $action $mode r PREROUTING ${chain}_notrack ^ { -i "$ifname" }
} }
local old_zones old_ifname local old_zones old_ifname
@ -42,7 +45,7 @@ fw_configure_interface() {
config_get old_ifname core "${iface}_ifname" config_get old_ifname core "${iface}_ifname"
for z in $old_zones; do for z in $old_zones; do
fw_log info "removing $iface ($old_ifname) from zone $z" fw_log info "removing $iface ($old_ifname) from zone $z"
fw__do_rules del zone_$z $old_ifname fw__do_rules del $z $old_ifname
ACTION=remove ZONE="$z" INTERFACE="$iface" DEVICE="$ifname" /sbin/hotplug-call firewall ACTION=remove ZONE="$z" INTERFACE="$iface" DEVICE="$ifname" /sbin/hotplug-call firewall
done done
@ -57,7 +60,7 @@ fw_configure_interface() {
list_contains zone_network "$iface" || return list_contains zone_network "$iface" || return
fw_log info "adding $iface ($ifname) to zone $zone_name" fw_log info "adding $iface ($ifname) to zone $zone_name"
fw__do_rules add zone_${zone_name} "$ifname" fw__do_rules add ${zone_name} "$ifname"
append new_zones $zone_name append new_zones $zone_name
ACTION=add ZONE="$zone_name" INTERFACE="$iface" DEVICE="$ifname" /sbin/hotplug-call firewall ACTION=add ZONE="$zone_name" INTERFACE="$iface" DEVICE="$ifname" /sbin/hotplug-call firewall

View File

@ -16,6 +16,7 @@ fw_config_get_redirect() {
string dest_mac "" \ string dest_mac "" \
string dest_port "" \ string dest_port "" \
string proto "tcpudp" \ string proto "tcpudp" \
string family "" \
} || return } || return
[ -n "$redirect_name" ] || redirect_name=$redirect__name [ -n "$redirect_name" ] || redirect_name=$redirect__name
} }
@ -29,6 +30,8 @@ fw_load_redirect() {
fw_die "redirect ${redirect_name}: needs src and dest_ip" fw_die "redirect ${redirect_name}: needs src and dest_ip"
} }
local mode=$(fw_get_family_mode ${redirect_family:-x} $redirect_src I)
local nat_dest_port=$redirect_dest_port local nat_dest_port=$redirect_dest_port
redirect_dest_port=$(fw_get_port_range $redirect_dest_port) redirect_dest_port=$(fw_get_port_range $redirect_dest_port)
redirect_src_port=$(fw_get_port_range $redirect_src_port) redirect_src_port=$(fw_get_port_range $redirect_src_port)
@ -37,7 +40,7 @@ fw_load_redirect() {
[ "$redirect_proto" == "tcpudp" ] && redirect_proto="tcp udp" [ "$redirect_proto" == "tcpudp" ] && redirect_proto="tcp udp"
for redirect_proto in $redirect_proto; do for redirect_proto in $redirect_proto; do
fw add I n zone_${redirect_src}_prerouting DNAT $ { $redirect_src_ip $redirect_dest_ip } { \ fw add $mode n zone_${redirect_src}_prerouting DNAT $ { $redirect_src_ip $redirect_dest_ip } { \
${redirect_proto:+-p $redirect_proto} \ ${redirect_proto:+-p $redirect_proto} \
${redirect_src_ip:+-s $redirect_src_ip} \ ${redirect_src_ip:+-s $redirect_src_ip} \
${redirect_src_dip:+-d $redirect_src_dip} \ ${redirect_src_dip:+-d $redirect_src_dip} \
@ -47,7 +50,7 @@ fw_load_redirect() {
--to-destination ${redirect_dest_ip}${redirect_dest_port:+:$nat_dest_port} \ --to-destination ${redirect_dest_ip}${redirect_dest_port:+:$nat_dest_port} \
} }
fw add I f zone_${redirect_src}_forward ACCEPT ^ { $redirect_src_ip $redirect_dest_ip } { \ fw add $mode f zone_${redirect_src}_forward ACCEPT ^ { $redirect_src_ip $redirect_dest_ip } { \
-d $redirect_dest_ip \ -d $redirect_dest_ip \
${redirect_proto:+-p $redirect_proto} \ ${redirect_proto:+-p $redirect_proto} \
${redirect_src_ip:+-s $redirect_src_ip} \ ${redirect_src_ip:+-s $redirect_src_ip} \

View File

@ -16,6 +16,7 @@ fw_config_get_rule() {
string icmp_type "" \ string icmp_type "" \
string proto "tcpudp" \ string proto "tcpudp" \
string target "" \ string target "" \
string family "" \
} || return } || return
[ -n "$rule_name" ] || rule_name=$rule__name [ -n "$rule_name" ] || rule_name=$rule__name
[ "$rule_proto" == "icmp" ] || rule_icmp_type= [ "$rule_proto" == "icmp" ] || rule_icmp_type=
@ -49,9 +50,11 @@ fw_load_rule() {
local rule_pos local rule_pos
eval 'rule_pos=$((++FW__RULE_COUNT_'$chain'))' eval 'rule_pos=$((++FW__RULE_COUNT_'$chain'))'
local mode=$(fw_get_family_mode ${rule_family:-x} $rule_src I)
[ "$rule_proto" == "tcpudp" ] && rule_proto="tcp udp" [ "$rule_proto" == "tcpudp" ] && rule_proto="tcp udp"
for rule_proto in $rule_proto; do for rule_proto in $rule_proto; do
fw add I f $chain $target $rule_pos { $rule_src_ip $rule_dest_ip } { \ fw add $mode f $chain $target $rule_pos { $rule_src_ip $rule_dest_ip } { \
${rule_proto:+-p $rule_proto} \ ${rule_proto:+-p $rule_proto} \
${rule_src_ip:+-s $rule_src_ip} \ ${rule_src_ip:+-s $rule_src_ip} \
${rule_src_port:+--sport $rule_src_port} \ ${rule_src_port:+--sport $rule_src_port} \

View File

@ -155,7 +155,14 @@ fw__exec() { # <action> <family> <table> <chain> <target> <position> { <rules> }
fi fi
fi fi
while [ $# -gt 1 ]; do while [ $# -gt 1 ]; do
echo -n "$1" case "$app:$1" in
ip6tables:--icmp-type) echo -n "--icmpv6-type" ;;
ip6tables:icmp|ip6tables:ICMP) echo -n "icmpv6" ;;
iptables:--icmpv6-type) echo -n "--icmp-type" ;;
iptables:icmpv6) echo -n "icmp" ;;
*:}|*:{) shift; continue ;;
*) echo -n "$1" ;;
esac
echo -ne "\0" echo -ne "\0"
shift shift
done | xargs -0 ${FW_TRACE:+-t} \ done | xargs -0 ${FW_TRACE:+-t} \
@ -180,3 +187,24 @@ fw_get_port_range() {
fi fi
} }
fw_get_family_mode() {
local hint="$1"
local zone="$2"
local mode="$3"
local ipv4 ipv6
[ -n "$FW_ZONES4$FW_ZONES6" ] && {
list_contains FW_ZONES4 $zone && ipv4=1 || ipv4=0
list_contains FW_ZONES6 $zone && ipv6=1 || ipv6=0
} || {
ipv4=$(uci_get_state firewall core ${zone}_ipv4 0)
ipv6=$(uci_get_state firewall core ${zone}_ipv6 0)
}
case "$hint:$ipv4:$ipv6" in
*4:1:*|*:1:0) echo 4 ;;
*6:*:1|*:0:1) echo 6 ;;
*) echo $mode ;;
esac
}