diff --git a/scripts/private-network b/scripts/private-network index 8a3c5c0..5b7c8be 100755 --- a/scripts/private-network +++ b/scripts/private-network @@ -6,9 +6,9 @@ set -e case "$1" in - --wait) - WAIT=1 - ;; + --wait) + WAIT=1 + ;; esac IFNAME=$1 @@ -24,109 +24,109 @@ MACADDR=$4 [ "$WAIT" ] && { while ! grep -q ^1$ /sys/class/net/$CONTAINER_IFNAME/carrier 2>/dev/null - do sleep 1 + do sleep 1 done exit 0 } [ "$IPADDR" ] || { - echo "Syntax:" - echo "pipework [-i containerinterface] /[@default_gateway] [macaddr]" - echo "pipework [-i containerinterface] dhcp [macaddr]" - echo "pipework --wait" - exit 1 + echo "Syntax:" + echo "pipework [-i containerinterface] /[@default_gateway] [macaddr]" + echo "pipework [-i containerinterface] dhcp [macaddr]" + echo "pipework --wait" + exit 1 } # First step: determine type of first argument (bridge, physical interface...) if [ -d /sys/class/net/$IFNAME ] then - if [ -d /sys/class/net/$IFNAME/bridge ] - then - IFTYPE=bridge - BRTYPE=linux - elif $(which ovs-vsctl >/dev/null) && $(ovs-vsctl list-br|grep -q ^$IFNAME$) - then - IFTYPE=bridge - BRTYPE=openvswitch - else IFTYPE=phys - fi + if [ -d /sys/class/net/$IFNAME/bridge ] + then + IFTYPE=bridge + BRTYPE=linux + elif $(which ovs-vsctl >/dev/null) && $(ovs-vsctl list-br|grep -q ^$IFNAME$) + then + IFTYPE=bridge + BRTYPE=openvswitch + else IFTYPE=phys + fi else - case "$IFNAME" in - br*) - IFTYPE=bridge - BRTYPE=linux - ;; - *) - echo "I do not know how to setup interface $IFNAME." - exit 1 - ;; - esac + case "$IFNAME" in + br*) + IFTYPE=bridge + BRTYPE=linux + ;; + *) + echo "I do not know how to setup interface $IFNAME." + exit 1 + ;; + esac fi -# Second step: find the guest (for now, we only support LXC containers) +# Second step: find the guest while read dev mnt fstype options dump fsck do - [ "$fstype" != "cgroup" ] && continue - echo $options | grep -qw devices || continue - CGROUPMNT=$mnt + [ "$fstype" != "cgroup" ] && continue + echo $options | grep -qw devices || continue + CGROUPMNT=$mnt done < /proc/mounts [ "$CGROUPMNT" ] || { - echo "Could not locate cgroup mount point." - exit 1 + echo "Could not locate cgroup mount point." + exit 1 } # Try to find a cgroup matching exactly the provided name. N=$(find "$CGROUPMNT" -name "$GUESTNAME" | wc -l) case "$N" in - 0) - echo "Container $GUESTNAME not found." - exit 1 - ;; - 1) - true - ;; - *) - echo "Found more than one container matching $GUESTNAME." - exit 1 - ;; + 0) + echo "Container $GUESTNAME not found." + exit 1 + ;; + 1) + true + ;; + *) + echo "Found more than one container matching $GUESTNAME." + exit 1 + ;; esac if [ "$IPADDR" = "dhcp" ] then - # Check for first available dhcp client - DHCP_CLIENT_LIST="udhcpc dhcpcd dhclient" - for CLIENT in $DHCP_CLIENT_LIST; do - which $CLIENT >/dev/null && { - DHCP_CLIENT=$CLIENT - break - } - done - [ -z $DHCP_CLIENT ] && { - echo "You asked for DHCP; but no DHCP client could be found." - exit 1 + # Check for first available dhcp client + DHCP_CLIENT_LIST="udhcpc dhcpcd dhclient" + for CLIENT in $DHCP_CLIENT_LIST; do + which $CLIENT >/dev/null && { + DHCP_CLIENT=$CLIENT + break } + done + [ -z $DHCP_CLIENT ] && { + echo "You asked for DHCP; but no DHCP client could be found." + exit 1 + } else - # Check if a subnet mask was provided. - echo $IPADDR | grep -q / || { - echo "The IP address should include a netmask." - echo "Maybe you meant $IPADDR/24 ?" - exit 1 - } - # Check if a gateway address was provided. - if echo $IPADDR | grep -q @ - then - GATEWAY=$(echo $IPADDR | cut -d@ -f2) - IPADDR=$(echo $IPADDR | cut -d@ -f1) - else - GATEWAY= - fi + # Check if a subnet mask was provided. + echo $IPADDR | grep -q / || { + echo "The IP address should include a netmask." + echo "Maybe you meant $IPADDR/24 ?" + exit 1 + } + # Check if a gateway address was provided. + if echo $IPADDR | grep -q @ + then + GATEWAY=$(echo $IPADDR | cut -d@ -f2) + IPADDR=$(echo $IPADDR | cut -d@ -f1) + else + GATEWAY= + fi fi NSPID=$(head -n 1 $(find "$CGROUPMNT" -name "$GUESTNAME" | head -n 1)/tasks) [ "$NSPID" ] || { - echo "Could not find a process inside container $GUESTNAME." - exit 1 + echo "Could not find a process inside container $GUESTNAME." + exit 1 } [ ! -d /var/run/netns ] && mkdir -p /var/run/netns @@ -136,31 +136,31 @@ ln -s /proc/$NSPID/ns/net /var/run/netns/$NSPID # Check if we need to create a bridge. [ $IFTYPE = bridge ] && [ ! -d /sys/class/net/$IFNAME ] && { - (ip link set $IFNAME type bridge > /dev/null 2>&1) || (brctl addbr $IFNAME) - ip link set $IFNAME up + (ip link set $IFNAME type bridge > /dev/null 2>&1) || (brctl addbr $IFNAME) + ip link set $IFNAME up } # If it's a bridge, we need to create a veth pair [ $IFTYPE = bridge ] && { - LOCAL_IFNAME=pl$NSPID$CONTAINER_IFNAME - GUEST_IFNAME=pg$NSPID$CONTAINER_IFNAME - ip link add name $LOCAL_IFNAME type veth peer name $GUEST_IFNAME - case "$BRTYPE" in - linux) - (ip link set $LOCAL_IFNAME master $IFNAME > /dev/null 2>&1) || (brctl addif $IFNAME $LOCAL_IFNAME) - ;; - openvswitch) - ovs-vsctl add-port $IFNAME $LOCAL_IFNAME - ;; - esac - ip link set $LOCAL_IFNAME up + LOCAL_IFNAME=pl$NSPID$CONTAINER_IFNAME + GUEST_IFNAME=pg$NSPID$CONTAINER_IFNAME + ip link add name $LOCAL_IFNAME type veth peer name $GUEST_IFNAME + case "$BRTYPE" in + linux) + (ip link set $LOCAL_IFNAME master $IFNAME > /dev/null 2>&1) || (brctl addif $IFNAME $LOCAL_IFNAME) + ;; + openvswitch) + ovs-vsctl add-port $IFNAME $LOCAL_IFNAME + ;; + esac + ip link set $LOCAL_IFNAME up } # If it's a physical interface, create a macvlan subinterface [ $IFTYPE = phys ] && { - GUEST_IFNAME=ph$NSPID$CONTAINER_IFNAME - ip link add link $IFNAME dev $GUEST_IFNAME type macvlan mode bridge - ip link set $IFNAME up + GUEST_IFNAME=ph$NSPID$CONTAINER_IFNAME + ip link add link $IFNAME dev $GUEST_IFNAME type macvlan mode bridge + ip link set $IFNAME up } ip link set $GUEST_IFNAME netns $NSPID @@ -168,26 +168,26 @@ ip netns exec $NSPID ip link set $GUEST_IFNAME name $CONTAINER_IFNAME [ "$MACADDR" ] && ip netns exec $NSPID ip link set $CONTAINER_IFNAME address $MACADDR if [ "$IPADDR" = "dhcp" ] then - [ $DHCP_CLIENT = "udhcpc" ] && ip netns exec $NSPID $DHCP_CLIENT -qi $CONTAINER_IFNAME - [ $DHCP_CLIENT = "dhclient" ] && ip netns exec $NSPID $DHCP_CLIENT $CONTAINER_IFNAME - [ $DHCP_CLIENT = "dhcpcd" ] && ip netns exec $NSPID $DHCP_CLIENT -q $CONTAINER_IFNAME + [ $DHCP_CLIENT = "udhcpc" ] && ip netns exec $NSPID $DHCP_CLIENT -qi $CONTAINER_IFNAME + [ $DHCP_CLIENT = "dhclient" ] && ip netns exec $NSPID $DHCP_CLIENT $CONTAINER_IFNAME + [ $DHCP_CLIENT = "dhcpcd" ] && ip netns exec $NSPID $DHCP_CLIENT -q $CONTAINER_IFNAME else - ip netns exec $NSPID ip addr add $IPADDR dev $CONTAINER_IFNAME - [ "$GATEWAY" ] && { - ip netns exec $NSPID ip route delete default >/dev/null 2>&1 && true - } - ip netns exec $NSPID ip link set $CONTAINER_IFNAME up - [ "$GATEWAY" ] && { - ip netns exec $NSPID ip route replace default via $GATEWAY - } + ip netns exec $NSPID ip addr add $IPADDR dev $CONTAINER_IFNAME + [ "$GATEWAY" ] && { + ip netns exec $NSPID ip route delete default >/dev/null 2>&1 && true + } + ip netns exec $NSPID ip link set $CONTAINER_IFNAME up + [ "$GATEWAY" ] && { + ip netns exec $NSPID ip route replace default via $GATEWAY + } fi # Give our ARP neighbors a nudge about the new interface if which arping > /dev/null 2>&1 then - IPADDR=$(echo $IPADDR | cut -d/ -f1) - ip netns exec $NSPID arping -c 1 -A -I $CONTAINER_IFNAME $IPADDR > /dev/null 2>&1 + IPADDR=$(echo $IPADDR | cut -d/ -f1) + ip netns exec $NSPID arping -c 1 -A -I $CONTAINER_IFNAME $IPADDR > /dev/null 2>&1 else - echo "Warning: arping not found; interface may not be immediately reachable" + echo "Warning: arping not found; interface may not be immediately reachable" fi exit 0