X-Git-Url: https://git.archive.openwrt.org/?p=openwrt.git;a=blobdiff_plain;f=package%2Fnetwork%2Fipv6%2Fipv6-support%2Ffiles%2Fsupport.sh;h=01efb9ed7c492656bc8bcca6728f5e415d891edb;hp=37173781a45b22f00fc03ff8484012307e320d02;hb=517ebc0869b32f6be00a98d81f9fc4074a5103fa;hpb=83ef4411d0f72fc6f137b189173d99ad0769cbef diff --git a/package/network/ipv6/ipv6-support/files/support.sh b/package/network/ipv6/ipv6-support/files/support.sh index 37173781a4..01efb9ed7c 100644 --- a/package/network/ipv6/ipv6-support/files/support.sh +++ b/package/network/ipv6/ipv6-support/files/support.sh @@ -5,13 +5,13 @@ . /lib/functions/network.sh config_load network6 - +local NAT="ip6tables -t nat" conf_get() { local __return="$1" local __device="$2" local __option="$3" - local __value=$(cat "/proc/sys/net/ipv6/conf/$device/$option") + local __value=$(cat "/proc/sys/net/ipv6/conf/$__device/$__option") eval "$__return=$__value" } @@ -67,10 +67,52 @@ resolve_network() { } +setup_masquerading() { + local cmd="$1" + local chain="network6_masquerade_$2" + local device="$3" + + $NAT -D POSTROUTING -j "$chain" 2>/dev/null && { + $NAT -F "$chain" 2>/dev/null + $NAT -X "$chain" 2>/dev/null + } + + [ "$cmd" != "stop" ] && { + $NAT -N "$chain" + $NAT -A "$chain" -o "$device" -j MASQUERADE + $NAT -A POSTROUTING -j "$chain" + } +} + + +setup_npt_chain() { + local cmd="$1" + local network="$2" + local chain="network6_npt_$network" + + [ "$cmd" != "start" ] && { + $NAT -D POSTROUTING -j "$chain" 2>/dev/null && { + $NAT -D PREROUTING -j "$chain" 2>/dev/null + $NAT -F "$chain" 2>/dev/null + $NAT -X "$chain" 2>/dev/null + } + } + + [ "$cmd" != "stop" ] && { + $NAT -N "$chain" 2>/dev/null && { + $NAT -A PREROUTING -j "$chain" + $NAT -A POSTROUTING -j "$chain" + } + } +} + + announce_prefix() { local prefix="$1" local network="$2" - local cmd="$3" + local device="$3" + local cmd="$4" + local type="$5" local addr=$(echo "$prefix" | cut -d/ -f1) local rem=$(echo "$prefix" | cut -d/ -f2) @@ -84,11 +126,50 @@ announce_prefix() { valid=$(echo "$rem" | cut -d, -f3) } - local msg='{"network": "'"$network"'", "prefix": "'"$addr"'", "length": '"$length" - [ -n "$valid" ] && msg="$msg"', "valid": '"$valid"', "preferred": '"$prefer" - [ -z "$cmd" ] && cmd=newprefix - - ubus call 6distributed "$cmd" "$msg}" + # Get prefix configuration + local ula="" + local prefix_action="" + config_get ula global ula_prefix + config_get prefix_action "$network" prefix_action + [ -z "$prefix_action" ] && prefix_action="distribute" + + # Always announce the ULA when doing NPT + [ "$prefix" == "$ula" -a "$prefix_action" == "npt" ] && prefix_action="distribute" + + [ "$prefix_action" == "distribute" -o "$prefix_action" == "npt" ] && { + local msg='{"network": "'"$network"'", "prefix": "'"$addr"'", "length": '"$length" + [ -n "$valid" ] && msg="$msg"', "valid": '"$valid"', "preferred": '"$prefer" + [ -z "$cmd" ] && cmd=newprefix + + [ "$prefix_action" == "npt" ] && msg="$msg"', "npt": 1' + [ "$type" == "secondary" ] && msg="$msg"', "secondary": 1' + + # Detect MTU + local mtu + conf_get mtu "$device" mtu + msg="$msg"', "mtu": '"$mtu" + + ubus call 6distributed "$cmd" "$msg}" + } + + [ "$prefix_action" == "npt" ] && { + local chain="network6_npt_$network" + local ula_addr=$(echo "$ula" | cut -d/ -f1) + local ula_rem=$(echo "$ula" | cut -d/ -f2) + local ula_length=$(echo "$ula_rem" | cut -d, -f1) + local device="" + + network_get_device device "$network" + [ "$length" -lt "$ula_length" ] && length="$ula_length" + [ "$cmd" == "delprefix" ] && cmd="-D $chain" || cmd="-A $chain" + + local in="-i $device -d $addr/$length -j NETMAP --to $ula_addr/$ula_length" + local out="-o $device -s $ula_addr/$ula_length -j NETMAP --to $addr/$length" + + setup_npt_chain start "$network" + $NAT $cmd $in + $NAT $cmd $out + } } @@ -98,8 +179,17 @@ disable_router() { # Notify the address distribution daemon ubus call 6distributed deliface '{"network": "'"$network"'"}' - # Disable advertisement daemon - stop_service /usr/sbin/6relayd "/var/run/ipv6-router-$network.pid" + + # Start RD & DHCPv6 service + local router_service + config_get router_service global router_service + + if [ "$router_service" == "dnsmasq" ]; then + rm -f "/var/etc/dnsmasq.d/ipv6-router-$network.conf" + /etc/init.d/dnsmasq restart + else + stop_service /usr/sbin/6relayd "/var/run/ipv6-router-$network.pid" + fi } @@ -216,6 +306,26 @@ restart_relay() { } +setup_prefix_fallback() { + local cmd="$1" + local network="$2" + local device="$3" + + stop_relay "$network" + restart_relay "$network" + + setup_masquerading stop "$network" + + [ "$cmd" != "stop" ] && { + local fallback="" + config_get fallback "$network" prefix_fallback + + [ "$fallback" == "relay" ] && restart_relay "$network" fallback + [ "$fallback" == "masquerade" ] && setup_masquerading start "$network" "$device" + } +} + + restart_master_relay() { local network="$1" local mode="$2" @@ -248,30 +358,25 @@ disable_interface() { # Disable distribution disable_router "$network" - # Disable relay + # Disable any active relays, masquerading rules and NPT rules stop_relay "$network" + setup_masquerading stop "$network" + setup_npt_chain stop "$network" # Disable DHCPv6 client if enabled, state script will take care stop_service /usr/sbin/odhcp6c "/var/run/ipv6-dhcpv6-$network.pid" } -enable_static() { +enable_ula_prefix() { local network="$1" - local device="$2" - - # Enable global forwarding - local global_forward - conf_get global_forward all forwarding - [ "$global_forward" != "1" ] && conf_set all forwarding 1 - - # Configure device - conf_set "$device" accept_ra 1 - conf_set "$device" forwarding 1 + local ula="$2" + local device="$3" + [ -z "$ula" ] && ula="global" # ULA-integration local ula_prefix="" - config_get ula_prefix "$network" ula_prefix + config_get ula_prefix "$ula" ula_prefix # ULA auto configuration (first init) [ "$ula_prefix" == "auto" ] && { @@ -289,15 +394,36 @@ enable_static() { ula_prefix="fd$r1:$r2:$r3::/48" # Save prefix so it will be preserved across reboots - uci_set network6 "$network" ula_prefix "$ula_prefix" + config_set "$ula" ula_prefix "$ula_prefix" + uci_set network6 "$ula" ula_prefix "$ula_prefix" uci_commit network6 } # Announce ULA - [ -n "$ula_prefix" ] && announce_prefix $ula_prefix $network + [ -n "$ula_prefix" ] && announce_prefix "$ula_prefix" "$network" "$device" newprefix secondary +} + + +enable_static() { + local network="$1" + local device="$2" + + # Enable global forwarding + local global_forward + conf_get global_forward all forwarding + [ "$global_forward" != "1" ] && conf_set all forwarding 1 + + # Configure device + conf_set "$device" accept_ra 1 + conf_set "$device" forwarding 1 + + # Enable ULA + enable_ula_prefix "$network" global "$device" + # Compatibility (deprecated) + enable_ula_prefix "$network" "$network" "$device" # Announce all static prefixes - config_list_foreach "$network" static_prefix announce_prefix $network + config_list_foreach "$network" static_prefix announce_prefix "$network" "$device" # start relay if there are forced relay members restart_relay "$network" @@ -315,16 +441,26 @@ enable_router() { [ "$length" -ne "0" ] && ubus call 6distributed newiface '{"network": "'"$network"'", "iface": "'"$device"'", "length": '"$length"'}' # Start RD & DHCPv6 service - local pid="/var/run/ipv6-router-$network.pid" - - # Start server - start_service "/usr/sbin/6relayd -S . $device" "$pid" + local router_service + config_get router_service global router_service + + if [ "$router_service" == "dnsmasq" ]; then + local dnsmasq_opts + config_get dnsmasq_opts "$network" dnsmasq_opts + [ -z "$dnsmasq_opts" ] && dnsmasq_opts="ra-names,24h" + + local conf="/var/etc/dnsmasq.d/ipv6-router-$network.conf" + mkdir -p $(dirname $conf) + echo "dhcp-range=::00ff,::ffff,constructor:$device,$dnsmasq_opts" > $conf + echo "enable-ra" >> $conf + /etc/init.d/dnsmasq restart + else + local pid="/var/run/ipv6-router-$network.pid" + start_service "/usr/sbin/6relayd -S . $device" "$pid" + fi # Try relaying if necessary restart_master_relay "$network" - - # start relay if there are forced relay members - restart_relay "$network" } @@ -378,7 +514,7 @@ enable_6to4() { local prefix="" network_get_ipaddr6 prefix "$network" - announce_prefix "$prefix/$prefixlen" "$network" + announce_prefix "$prefix/$prefixlen" "$network" "$device" } @@ -387,14 +523,16 @@ enable_interface() local network="$1" local device="$2" local mode="" + config_get mode "$network" mode + [ -n "$mode" -a "$mode" != "none" ] || return # Compatibility with old mode names [ "$mode" == "downstream" ] && mode=router [ "$mode" == "upstream" ] && mode=dhcpv6 # Run mode startup code - [ "$mode" == "dhcpv6" -o "$mode" == "static" ] && enable_static "$network" "$device" + enable_static "$network" "$device" [ "$mode" == "dhcpv6" ] && enable_dhcpv6 "$network" "$device" [ "$mode" == "router" ] && enable_router "$network" "$device" [ "$mode" == "6to4" -o "$mode" == "6rd" ] && enable_6to4 "$network" "$device" "$mode"