#!/bin/bash # # script: create_network_ini # # Copyright 2005-2023, Lime Technology # Copyright 2012-2023, Bergware International. # # create initial network.ini file on system start # create system welcome message # update files on DHCP events 'BOUND[6] IPV4LL' # update services listening interfaces / addresses [[ (-z $reason && -z $1) || (-n $reason && ! "BOUND6 IPV4LL" =~ $reason) ]] && exit 0 INI=/var/local/emhttp/network.ini.new CFG=/boot/config/network.cfg declare -A VLANID USE_DHCP IPADDR NETMASK GATEWAY METRIC USE_DHCP6 IPADDR6 NETMASK6 GATEWAY6 PRIVACY6 METRIC6 DESCRIPTION PROTOCOL # run & log functions . /etc/rc.d/rc.runlog mask(){ # convert prefix to netmask set -- $((5-(${1:-0}/8))) 255 255 255 255 $(((255<<(8-(${1:-0}%8)))&255)) 0 0 0 [[ $1 -gt 1 ]] && shift $1 || shift echo $1.$2.$3.$4 } dns() { [[ $1 == 4 ]] && ADDR='(\d{1,3}\.){3}\d+' || ADDR='([0-9a-fA-F]{1,4}::?){1,7}[0-9a-fA-F]*' grep -Po "^nameserver \K$ADDR" /etc/resolv.conf } if [[ -s $CFG ]]; then # import existing settings . <(fromdos <$CFG) else # import default settings IPADDR= NETMASK= GATEWAY= USE_DHCP=yes DHCP_KEEPRESOLV=no BONDING=yes BRIDGING=yes fi # prepare empty file echo -n >$INI # clear update information DATA= # loop thru all defined interfaces (=1 in case of legacy) for ((i=0; i<${SYSNICS:-1}; i++)); do IFACE=${IFNAME[$i]:-eth$i} ETH=${IFACE/#bond/eth} ETH=${ETH/#br/eth} echo "[$ETH]" >>$INI if [[ $i -eq 0 ]]; then # process legacy settings [[ $BRIDGING == yes ]] && BRNICS=eth0 [[ $BONDING == yes ]] && BRNICS=bond0 [[ $BONDING == yes ]] && IFACE=bond0 [[ $BRIDGING == yes ]] && IFACE=br0 [[ $BONDING == yes ]] && BONDNICS=${BONDNICS:-eth0 eth1 eth2 eth3} if [[ ${USE_DHCP:-yes} == yes ]]; then # force DNS setting to automatic if not set DHCP_KEEPRESOLV=${DHCP_KEEPRESOLV:-no} else # force DNS setting to static DHCP_KEEPRESOLV=yes fi if [[ ${USE_DHCP6:-yes} == yes ]]; then # force DNS6 setting to automatic if not set DHCP6_KEEPRESOLV=${DHCP6_KEEPRESOLV:-no} else # force DNS6 setting to static DHCP6_KEEPRESOLV=yes fi echo "DHCP_KEEPRESOLV=\"$DHCP_KEEPRESOLV\"" >>$INI if [[ $DHCP_KEEPRESOLV == no ]]; then # dhcp assigned DNSv4 servers DNS4=$(dns 4) x=1 for SERVER in $DNS4; do echo "DNS_SERVER$x=\"$SERVER\"" >>$INI ((x++)) done else # static assigned DNSv4 servers echo "DNS_SERVER1=\"$DNS_SERVER1\"" >>$INI echo "DNS_SERVER2=\"$DNS_SERVER2\"" >>$INI echo "DNS_SERVER3=\"$DNS_SERVER3\"" >>$INI fi echo "DHCP6_KEEPRESOLV=\"$DHCP6_KEEPRESOLV\"" >>$INI if [[ $DHCP6_KEEPRESOLV == no ]]; then # dhcp assigned DNSv6 servers DNS6=$(dns 6) x=1 for SERVER6 in $DNS6; do echo "DNS6_SERVER$x=\"$SERVER6\"" >>$INI ((x++)) done else # static assigned DNSv6 servers echo "DNS6_SERVER1=\"$DNS6_SERVER1\"" >>$INI echo "DNS6_SERVER2=\"$DNS6_SERVER2\"" >>$INI echo "DNS6_SERVER3=\"$DNS6_SERVER3\"" >>$INI fi fi [[ -n ${BONDNICS[$i]} ]] && echo "BONDING=\"yes\"" >>$INI || echo "BONDING=\"no\"" >>$INI echo "BONDNAME=\"${BONDNAME[$i]:-bond0}\"" >>$INI echo "BONDNICS=\"${BONDNICS[$i]// /,}\"" >>$INI echo "BONDING_MODE=\"${BONDING_MODE[$i]:-1}\"" >>$INI echo "BONDING_MIIMON=\"${BONDING_MIIMON[$i]:-100}\"" >>$INI [[ -n ${BRNICS[$i]} ]] && echo "BRIDGING=\"yes\"" >>$INI || echo "BRIDGING=\"no\"" >>$INI echo "BRNAME=\"${BRNAME[$i]:-br0}\"" >>$INI echo "BRNICS=\"${BRNICS[$i]// /,}\"" >>$INI echo "BRSTP=\"${BRSTP[$i]:-0}\"" >>$INI echo "BRFD=\"${BRFD[$i]:-0}\"" >>$INI echo "DESCRIPTION:0=\"${DESCRIPTION[$i]}\"" >>$INI echo "PROTOCOL:0=\"${PROTOCOL[$i]}\"" >>$INI echo "USE_DHCP:0=\"${USE_DHCP[$i]}\"" >>$INI if [[ ${USE_DHCP[$i]} == yes ]]; then # get dhcp assigned ipv4 address & mask NET=($(ip -br -4 addr show $IFACE|awk '{sub("/"," ",$3);print $3;exit}')) GW=$(ip -4 route show default dev $IFACE|awk '{print $3;exit}') echo "IPADDR:0=\"${NET[0]}\"" >>$INI echo "NETMASK:0=\"$(mask ${NET[1]})\"" >>$INI echo "GATEWAY:0=\"$GW\"" >>$INI echo "METRIC:0=\"${METRIC[$i]}\"" >>$INI DATA="${DATA}${ETH}_I_IPADDR:0=${NET[0]} ${ETH}_S_NETMASK:0=$(mask ${NET[1]}) ${ETH}_I_GATEWAY:0=$GW " if [[ $i -eq 0 && -n $DNS4 ]]; then x=1 for SERVER in $DNS4; do DATA="${DATA}${ETH}_I_DNS-SERVER${x}=$SERVER " ((x++)) done fi else # get static assigned ipv4 address & mask echo "IPADDR:0=\"${IPADDR[$i]}\"" >>$INI echo "NETMASK:0=\"${NETMASK[$i]}\"" >>$INI echo "GATEWAY:0=\"${GATEWAY[$i]}\"" >>$INI echo "METRIC:0=\"${METRIC[$i]}\"" >>$INI fi echo "USE_DHCP6:0=\"${USE_DHCP6[$i]}\"" >>$INI if [[ ${USE_DHCP6[$i]} == yes ]]; then # get auto assigned ipv6 address & prefix NET6=($(ip -br -6 addr show $IFACE scope global|awk '{sub("/"," ",$NF);print $NF;exit}')) GW6=$(ip -6 route show default dev $IFACE|awk '{print $3;exit}') echo "IPADDR6:0=\"${NET6[0]}\"" >>$INI echo "NETMASK6:0=\"${NET6[1]}\"" >>$INI echo "GATEWAY6:0=\"$GW6\"" >>$INI echo "METRIC6:0=\"${METRIC6[$i]}\"" >>$INI echo "PRIVACY6:0=\"${PRIVACY6[$i]}\"" >>$INI DATA="${DATA}${ETH}_I_IPADDR6:0=${NET6[0]} ${ETH}_I_NETMASK6:0=${NET6[1]} ${ETH}_I_GATEWAY6:0=$GW6 " if [[ $i -eq 0 && -n $DNS6 ]]; then x=1 for SERVER6 in $DNS6; do DATA="${DATA}${ETH}_I_DNS6-SERVER${x}=$SERVER6 " ((x++)) done fi else # get static assigned ipv6 address & prefix echo "IPADDR6:0=\"${IPADDR6[$i]}\"" >>$INI echo "NETMASK6:0=\"${NETMASK6[$i]}\"" >>$INI echo "GATEWAY6:0=\"${GATEWAY6[$i]}\"" >>$INI echo "METRIC6:0=\"${METRIC6[$i]}\"" >>$INI echo "PRIVACY6:0=\"\"" >>$INI fi echo "MTU=\"${MTU[$i]}\"" >>$INI if [[ -n ${VLANS[$i]} ]]; then # process VLAN interfaces echo "TYPE=\"trunk\"" >>$INI for ((j=1;j<${VLANS[$i]};j++)); do echo "VLANID:$j=\"${VLANID[$i,$j]}\"" >>$INI echo "DESCRIPTION:$j=\"${DESCRIPTION[$i,$j]}\"" >>$INI echo "PROTOCOL:$j=\"${PROTOCOL[$i,$j]}\"" >>$INI echo "USE_DHCP:$j=\"${USE_DHCP[$i,$j]}\"" >>$INI if [[ ${USE_DHCP[$i,$j]} == yes ]]; then DEV=$IFACE.${VLANID[$i,$j]} # get dhcp assigned ipv4 address & mask NET=($(ip -br -4 addr show $DEV|awk '{sub("/"," ",$3);print $3;exit}')) GW=$(ip -4 route show default dev $DEV|awk '{print $3;exit}') echo "IPADDR:$j=\"${NET[0]}\"" >>$INI echo "NETMASK:$j=\"$(mask ${NET[1]})\"" >>$INI echo "GATEWAY:$j=\"$GW\"" >>$INI echo "METRIC:$j=\"${METRIC[$i,$j]}\"" >>$INI DATA="${DATA}${ETH}_I_IPADDR:$j=${NET[0]} ${ETH}_S_NETMASK:$j=$(mask ${NET[1]}) ${ETH}_I_GATEWAY:$j=$GW " else # get static assigned ipv4 address & mask echo "IPADDR:$j=\"${IPADDR[$i,$j]}\"" >>$INI echo "NETMASK:$j=\"${NETMASK[$i,$j]}\"" >>$INI echo "GATEWAY:$j=\"${GATEWAY[$i,$j]}\"" >>$INI echo "METRIC:$j=\"${METRIC[$i,$j]}\"" >>$INI fi echo "USE_DHCP6:$j=\"${USE_DHCP6[$i,$j]}\"" >>$INI if [[ ${USE_DHCP6[$i,$j]} == yes ]]; then DEV=$IFACE.${VLANID[$i,$j]} # get auto assigned ipv6 address & prefix NET6=($(ip -br -6 addr show $DEV scope global|awk '{sub("/"," ",$NF);print $NF;exit}')) GW6=$(ip -6 route show default dev $DEV|awk '{print $3;exit}') echo "IPADDR6:$j=\"${NET6[0]}\"" >>$INI echo "NETMASK6:$j=\"${NET6[1]}\"" >>$INI echo "GATEWAY6:$j=\"$GW6\"" >>$INI echo "METRIC6:$j=\"${METRIC6[$i,$j]}\"" >>$INI echo "PRIVACY6:$j=\"${PRIVACY6[$i,$j]}\"" >>$INI DATA="${DATA}${ETH}_I_IPADDR6:$j=${NET6[0]} ${ETH}_I_NETMASK6:$j=${NET6[1]} ${ETH}_I_GATEWAY6:$j=$GW6 " else # get static assigned ipv6 address & prefix echo "IPADDR6:$j=\"${IPADDR6[$i,$j]}\"" >>$INI echo "NETMASK6:$j=\"${NETMASK6[$i,$j]}\"" >>$INI echo "GATEWAY6:$j=\"${GATEWAY6[$i,$j]}\"" >>$INI echo "METRIC6:$j=\"${METRIC6[$i,$j]}\"" >>$INI echo "PRIVACY6:$j=\"\"" >>$INI fi done else # interface without VLANs echo "TYPE=\"access\"" >>$INI fi done # atomically update file mv $INI ${INI%.*} log "interface=${interface:-$1}, reason=$reason, protocol=$protocol" # delayed execution /usr/local/emhttp/webGui/scripts/update_services 30 # send update information if [[ -n $DATA && -e /var/run/nginx.socket ]]; then curl -sfd "$DATA" --unix-socket /var/run/nginx.socket http://localhost/pub/dhcp?buffer_length=1 >/dev/null 2>&1 fi # generate our welcome text (management interface only) if [[ -z $interface || "eth0 br0 bond0" =~ $interface ]]; then . /etc/unraid-version echo -e "Unraid Server OS version: $version" >/etc/issue # find management interface [[ -e /sys/class/net/bond0 ]] && dev=bond0 || dev=eth0 [[ -e /sys/class/net/br0 ]] && dev=br0 IPv4=$(ip -br -4 addr show $dev scope global|awk '{print $3;exit}') IPv6=$(ip -br -6 addr show $dev scope global|awk '{print $NF;exit}') # show current IP assignment [[ -n $IPv4 ]] && echo " IPv4 address: ${IPv4%/*}" >>/etc/issue || echo " IPv4 address: not set" >>/etc/issue [[ -n $IPv6 ]] && echo " IPv6 address: ${IPv6%/*}" >>/etc/issue || echo " IPv6 address: not set" >>/etc/issue echo >>/etc/issue fi exit 0