odhcp6c: add source routing support
[openwrt/svn-archive/archive.git] / package / network / ipv6 / odhcp6c / files / dhcpv6.script
index 859ae1b7454521b7d14e73acc45619d4b1a73435..1d5f521e45f1ee228ea545caf1f08bead4c571e7 100755 (executable)
@@ -3,40 +3,19 @@
 . /lib/functions.sh
 . /lib/netifd/netifd-proto.sh
 
-ipv6_conf() {
-       echo "$3" > "/proc/sys/net/ipv6/conf/$1/$2"
-}
-
-# RFC 6204 requires us to block forwarding until address acquisition is complete
-ipv6_block_forwarding() {
-       ip6tables "-$2" forwarding_rule -o "$1" -j REJECT --reject-with no-route 2>/dev/null
-}
-
-prepare_interface() {
-       local device="$1"
-
-       ipv6_block_forwarding "$device" A
-
-       ipv6_conf "$device" accept_ra 2
-       ipv6_conf "$device" forwarding 2
-
-       # Send RS
-       [ -x /usr/sbin/6relayd ] && /usr/sbin/6relayd -s "$device"
-}
-
-cleanup_interface() {
-       local device="$1"
-       ipv6_conf "$device" accept_ra 1
-       ipv6_conf "$device" forwarding 1
-       ipv6_block_forwarding "$device" D
-}
-
 setup_interface () {
        local device="$1"
-       ipv6_block_forwarding "$device" D
-
        proto_init_update "*" 1
 
+       # Merge RA-DNS
+       for radns in $RA_DNS; do
+               local duplicate=0
+               for dns in $RDNSS; do
+                       [ "$radns" = "$dns" ] && duplicate=1
+               done
+               [ "$duplicate" = 0 ] && RDNSS="$RDNSS $radns"
+       done
+
        for dns in $RDNSS; do
                proto_add_dns_server "$dns"
        done
@@ -49,8 +28,69 @@ setup_interface () {
                proto_add_ipv6_prefix "$prefix"
        done
 
+       [ -n "$USERPREFIX" ] && proto_add_ipv6_prefix "$USERPREFIX"
+
+       # Merge addresses
+       for entry in $RA_ADDRESSES; do
+               local duplicate=0
+               local addr="${entry%%/*}"
+               for dentry in $ADDRESSES; do
+                       local daddr="${dentry%%/*}"
+                       [ "$addr" = "$daddr" ] && duplicate=1
+               done
+               [ "$duplicate" = "0" ] && ADDRESSES="$ADDRESSES $entry"
+       done
+
+       for entry in $ADDRESSES; do
+               local addr="${entry%%/*}"
+               entry="${entry#*/}"
+               local mask="${entry%%,*}"
+               entry="${entry#*,}"
+               local preferred="${entry%%,*}"
+               entry="${entry#*,}"
+               local valid="${entry%%,*}"
+
+               proto_add_ipv6_address "$addr" "$mask" "$preferred" "$valid" 1
+       done
+
+       for entry in $RA_ROUTES; do
+               local addr="${entry%%/*}"
+               entry="${entry#*/}"
+               local mask="${entry%%,*}"
+               entry="${entry#*,}"
+               local gw="${entry%%,*}"
+               entry="${entry#*,}"
+               local valid="${entry%%,*}"
+               entry="${entry#*,}"
+               local metric="${entry%%,*}"
+
+               if [ -z "$SOURCE_ROUTING" -o -z "$gw" ]; then
+                       proto_add_ipv6_route "$addr" "$mask" "$gw" "$metric" "$valid"
+               else
+                       proto_add_ipv6_route "$addr" "$mask" "$gw" "$metric" "$valid" "::/128"
+                       for prefix in $PREFIXES; do
+                               local paddr="${prefix%%,*}"
+                               proto_add_ipv6_route "$addr" "$mask" "$gw" "$metric" "$valid" "$paddr"
+                       done
+               fi
+       done
+
        proto_send_update "$INTERFACE"
 
+       if [ -n "$AFTR_IP " -a -n "$IFACE_DSLITE" ]; then
+uci -q batch <<-EOF >/dev/null
+set network.$IFACE_DSLITE.proto=dslite
+set network.$IFACE_DSLITE.auto=0
+set network.$IFACE_DSLITE.peeraddr=$AFTR_IP
+set network.$IFACE_DSLITE.tunlink=$INTERFACE
+commit network
+EOF
+
+               ifdown "$IFACE_DSLITE"
+               /etc/init.d/network reload
+               ifup "$IFACE_DSLITE"
+       fi
+
        # TODO: $SNTP_IP $SIP_IP $SNTP_FQDN $SIP_DOMAIN
 }
 
@@ -60,16 +100,14 @@ teardown_interface() {
 }
 
 case "$2" in
-       started)
-               prepare_interface "$1"
-       ;;
-       stopped)
-               cleanup_interface "$1"
+       bound)
+               teardown_interface "$1"
+               setup_interface "$1"
        ;;
-       informed|bound|updated|rebound)
+       informed|updated|rebound|ra-updated)
                setup_interface "$1"
        ;;
-       unbound|timeout)
+       started|stopped|unbound)
                teardown_interface "$1"
        ;;
 esac