update script to have stages

This commit is contained in:
Nico Schottelius 2020-06-14 00:07:47 +02:00
parent 8dfb2c95e6
commit 4ca2a762fd

View file

@ -2,18 +2,28 @@
# 2020-06-13, Nico Schottelius
# See https://ungleich.ch/u/products/viirb-ipv6-box/
if [ $# -ne 4 ]; then
echo "$0 interface viirb-id your-dot-cdist"
if [ $# -lt 4 ]; then
echo "$0 interface viirb-id your-dot-cdist [stages]"
echo " interface to add the config ip address to"
echo " viirb-id: number in decimal format"
echo " your-dot-cdist: path to YOUR ungleich-dot-cdist repo"
echo " owner-mail-reference: How to identify the owner"
echo " stages: define which stages to execute"
echo ""
echo " stage1: setup your host, check connection to VIIRB"
echo " stage2: flash latest openwrt onto the VIIRB"
echo " stage3: configure the vpn endpoint"
echo " stage4: configure the VIIRB with wireguard + settings"
echo " stage5: Verify VIIRB on VPN, cleanup VIIRB"
echo ""
echo "Example to configure viirb02:"
echo "$0 wlan0 2 ~/vcs/ungleich-dot-cdist 'Nico Schottelius, nico.schottelius@ungleich.ch, Ticket 2342'"
echo "$0 wlan0 2 ~/vcs/ungleich-dot-cdist 'Nico Schottelius, nico.schottelius@ungleich.ch, Ticket 2342' '1 3 4'"
exit 1
fi
echo "FIXME: missing IPv6 announcements on LAN"
set -x
set -x
@ -22,6 +32,12 @@ id=$1; shift
dot_cdist=$1; shift
owner=$1; shift
if [ $# -ge 1 ]; then
stages=$1; shift
else
stages="1 2 3 4 5"
fi
hex_id=$(printf "%0.2x\n" "$id")
viirb_hostname=viirb${hex_id}
@ -37,12 +53,14 @@ my_wifi_ip=${my_prefix}:7ea::42
version=19.07.3
filename=openwrt-${version}-ramips-mt76x8-vocore2-squashfs-sysupgrade.bin
# root password
root_password=$(pwgen -1 32)
# IP address for setting it up initially
viirb_ip=192.168.61.1
# wireguard
private_key=$(wg genkey)
private_key=EL76tScnk84v8TGSSD3tPDhUjjYVPrfmNMBE3zbuRXg=
public_key=$(echo $private_key | wg pubkey)
vpn_endpoint_host=vpn-2a0ae5c1300.ungleich.ch
@ -50,12 +68,81 @@ vpn_endpoint_pubkey=ft68G2RID7gZ6PXjFCSCOdJ9yspRg+tUw0YrNK9cTxE=
# cdist
dot_cdist_files=${dot_cdist}/type/__ungleich_wireguard/files
peerfile=${dot_cdist_files}/${vpn_endpoint_host}.peer${hex_id}
peerfilename=${vpn_endpoint_host}.peer${hex_id}
peerfile=${dot_cdist_files}/${peerfilename}
vpnconfig=${dot_cdist_files}/${vpn_endpoint_host}
# Configure VPN server / update cdist
echo Updating VPNserver
cat <<EOF > ${peerfile}
################################################################################
# Stage 1: test / connect to the new VIIRB
#
# We delete so that we can run idempotent
stage1()
{
sudo ip addr del 192.168.61.2/24 dev "$dev" 2>/dev/null || true
sudo ip addr add 192.168.61.2/24 dev "$dev"
# don't care about other/old known_host entries
ssh-keygen -R ${viirb_ip}
ping -c2 ${viirb_ip}
if [ $? -ne 0 ]; then
echo "Cannot reach any VIIRB - exiting"
exit 1
fi
cat ~/.ssh/id_rsa.pub | ssh root@${viirb_ip} "cat > /etc/dropbear/authorized_keys"
}
################################################################################
# Get latest OpenWRT & flash it
stage2()
{
# Don't re-download if we already have it
wget -c http://downloads.openwrt.org/releases/${version}/targets/ramips/mt76x8/${filename}
scp ${filename} root@${viirb_ip}:/tmp
ssh root@${viirb_ip} "sysupgrade /tmp/*.bin"
# It still pings for some time - wait for the reboot to happen
echo "Waiting for VIIRB to disappear"
sleep 15
wait=0
found=""
while [ $wait -lt 180 ]; do
ping -c1 ${viirb_ip} >/dev/null
if [ $? -eq 0 ]; then
found=yes
# wait for ssh to come up
sleep 10
break
fi
sleep 1
wait=$((wait+1))
done
if [ ! "$found" ]; then
echo "Did not find updated viirb - debug / restart it"
exit 1
fi
}
################################################################################
# Stage 3: prepare VPN endpoint
#
stage3()
{
# Configure VPN server / update cdist
echo Updating VPNserver
cat <<EOF > ${peerfile}
# ${viirb_hostname} ${owner}
[Peer]
PublicKey = ${public_key}
@ -63,28 +150,32 @@ AllowedIPs = ${my_network}
EOF
# Generate real config
cat ${dot_cdist_files}/${vpn_endpoint_host}.* > ${vpnconfig}
cd ${dot_cdist_files}
git add ${vpn_endpoint_host}
git commit -m "[vpn] Updated config for peer ${viirb_hostname} ${my_network}"
git pull
git push
# Generate real config
cat ${dot_cdist_files}/${vpn_endpoint_host}.* > ${vpnconfig}
cd ${dot_cdist_files}
git add ${vpn_endpoint_host} ${peerfilename}
git commit -m "[vpn] Updated config for peer ${viirb_hostname} ${my_network}"
git pull
git push
cdist config -vv -j8 ${vpn_endpoint_host} -c ${dot_cdist}
cdist config -vv -j8 ${vpn_endpoint_host} -c ${dot_cdist}
}
exit 0
################################################################################
# Stage 4: configure the VIIRB
#
stage4()
{
# System
cat <<EOF | ssh -t "root@${viirb_ip}"
cat <<EOF | ssh -t "root@${viirb_ip}"
set -x
# Setup lan to also retrieve an ip address via dhcp
# This stays in the final setup
uci set network.lanv4=interface
uci set network.lanv4.proto='dhcp'
uci set network.lanv4.ifname='br-lan'
uci set network.lan.proto='dhcp'
uci delete network.lan.ipaddr
uci delete network.lan.netmask
# This is temporary
uci set network.lanv4temp=interface
@ -98,10 +189,10 @@ uci commit network
# update the sources
opkg update
opkg install wireguard
# DNS upstream over VPN gives DNS64
#uci set dhcp.@dnsmasq[0].server='2a0a:e5c0:a::a' '2a0a:e5c0:2:a::a'
# install wireguard + gui
opkg install wireguard
opkg install luci-app-wireguard
# wifi ip address
uci set network.wifi=interface
@ -117,6 +208,9 @@ uci set wireless.radio0.htmode='HT40'
uci set wireless.radio0.country='CH'
uci set wireless.radio0.channel='6'
# Ensure it is not disabled
uci delete wireless.radio0.disabled
uci set wireless.default_radio0=wifi-iface
uci set wireless.default_radio0.device='radio0'
uci set wireless.default_radio0.mode='ap'
@ -139,11 +233,14 @@ uci set network.wg0.private_key='${private_key}'
uci set network.wg0.listen_port='51820'
uci set network.wg0.addresses='${my_wireguard_ip}/64'
uci add network wireguard_wg0
if ! uci get network.@wireguard_wg0[0]; then
uci add network wireguard_wg0
fi
uci set network.@wireguard_wg0[0]=wireguard_wg0
uci set network.@wireguard_wg0[0].persistent_keepalive='25'
uci set network.@wireguard_wg0[0].public_key='${vpn_endpoint_pubkey}'
uci set network.@wireguard_wg0[0].description='ungleich IPv6VPN.ch'
uci set network.@wireguard_wg0[0].description='IPv6VPN.ch by ungleich'
uci set network.@wireguard_wg0[0].allowed_ips='::/0'
uci set network.@wireguard_wg0[0].endpoint_host='${vpn_endpoint_host}'
uci set network.@wireguard_wg0[0].endpoint_port='51820'
@ -155,59 +252,102 @@ uci commit
# Firewall configuration
# Remove temporary IP
if ! uci show firewall | grep "name='Allow-SSH'"; then
uci add firewall rule
uci set firewall.@rule[-1].name='Allow-SSH'
uci set firewall.@rule[-1].src='wan'
uci set firewall.@rule[-1].dest='lan'
uci set firewall.@rule[-1].proto='tcp'
uci set firewall.@rule[-1].dest_port='22'
uci set firewall.@rule[-1].target='ACCEPT'
fi
if ! uci show firewall | grep "name='Allow-HTTPS'"; then
uci add firewall rule
uci set firewall.@rule[-1].name='Allow-HTTPS'
uci set firewall.@rule[-1].src='wan'
uci set firewall.@rule[-1].dest='lan'
uci set firewall.@rule[-1].proto='tcp'
uci set firewall.@rule[-1].dest_port='443'
uci set firewall.@rule[-1].target='ACCEPT'
fi
if ! uci show firewall | grep "name='Allow-HTTP'"; then
uci add firewall rule
uci set firewall.@rule[-1].name='Allow-HTTP'
uci set firewall.@rule[-1].src='wan'
uci set firewall.@rule[-1].dest='lan'
uci set firewall.@rule[-1].proto='tcp'
uci set firewall.@rule[-1].dest_port='80'
uci set firewall.@rule[-1].target='ACCEPT'
fi
# Add interfaces to the right network zone
uci set firewall.@zone[0].network='lan lanv4 wifi'
uci set firewall.@zone[1].network='wg0'
uci commit firewall
# Reboot
# Ensure VPN works
# Remove our ssh keys!
#
reboot
EOF
}
exit 0
################################################################################
# Stage 5: Verify the VIIRB via VPN
#
stage5()
{
# Wait for the VIIRB to come back, but on the VPN address
wait=0
found=""
# We delete so that we can run idempotent
sudo ip addr del 192.168.61.2/24 dev "$dev" 2>/dev/null || true
sudo ip addr add 192.168.61.2/24 dev "$dev"
while [ $wait -lt 180 ]; do
ping -c1 ${my_wireguard_ip} >/dev/null
# don't care about other/old known_host entries
ssh-keygen -R 192.168.61.1
if [ $? -eq 0 ]; then
found=yes
break
fi
sleep 1
wait=$((wait+1))
done
ping -c2 ${viirb_ip}
if [ $? -ne 0 ]; then
echo "Cannot reach any VIIRB - exiting"
exit 1
fi
if [ ! "$found" ]; then
echo "Cannot reach VIIRB via VPN - check manually"
exit 1
fi
set -e
echo "Cleanup process."
echo "Set the root password when prompted to: ${root_password}"
# VPN works, remove artefacts, set correct DNS servers that support DNS64
cat <<EOF | ssh -t "root@${viirb_ip}"
# DNS upstream over VPN gives DNS64
uci delete dhcp.@dnsmasq[0].server
uci add_list dhcp.@dnsmasq[0].server='2a0a:e5c0:0:a::a'
uci add_list dhcp.@dnsmasq[0].server='2a0a:e5c0:2:a::a'
# Don't re-download if we already have it
wget -c http://downloads.openwrt.org/releases/${version}/targets/ramips/mt76x8/${filename}
scp ${filename} root@${viirb_ip}:/tmp
ssh root@${viirb_ip} "sysupgrade /tmp/*.bin"
# Remove temporary IP
uci delete network.lanv4temp
wait=0
found=""
uci commit
while [ $wait -lt 180 ]; do
ping -c1 ${viirb_ip} >/dev/null
# Remove our ssh keys
rm -f /etc/dropbear/authorized_keys
if [ $? -eq 0 ]; then
found=yes
# wait for ssh to come up
sleep 10
# Setup root password
printf "${root_password}\n${root_password}\n" | passwd
EOF
echo "Submit to user the root password = ${root_password}"
}
for stage in $(seq 1 5);do
if echo $stages | grep -q $stage; then
eval stage${stage}
fi
done
if [ ! "$found" ]; then
echo "Did not find updated viirb - debug / restart it"
exit 1
fi
exit 0