Created
August 14, 2020 07:40
-
-
Save samson4649/413d6419bb872143d23dc85ded070c04 to your computer and use it in GitHub Desktop.
Bash hotspot creation script - has some bugs but i use internally when needed.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
if (( $(id -u) != 0 )); then | |
echo "Non root user detected - need to run with root privileges. Exiting..." | |
exit 99 | |
fi | |
### start functions | |
function _clean(){ | |
graceful_exit 5 | |
rm "${ERR_FIFO}" "${LOG_DIR}" -r &>/dev/null | |
exec 2>&- | |
exec 3<&- | |
} | |
function _out(){ | |
echo "$@" | |
} | |
function _debug(){ | |
[[ "${DEBUG,,}" == "true" ]] && _out "[DEBUG] $@" | |
} | |
function _info(){ | |
_out "[INFO] $@" | |
} | |
function _warn(){ | |
_out "[WARN] $@" | |
} | |
function _error(){ | |
_out "[ERROR] $@" | |
} | |
function print_err(){ | |
echo -e "\n\n!!! Error Dump !!!\n" | |
sleep 1 | |
cat <$ERR_FIFO | |
echo -e "\n!!! End Dump !!!\n" | |
exit 99 | |
} | |
function _pause(){ | |
sleep 0.5 | |
} | |
graceful_exit() { | |
echo "Exit requested..." | |
_debug "closing ${HS_INTERFACE}" | |
iw dev ${HS_INTERFACE} del | |
_debug "bringing OG wifi interface back online" | |
ip l set up dev wlan0 | |
_pause | |
local timeout=${1:-4} | |
local list="" | |
for c in $(ps -o pid= --ppid $$); do | |
# request children shutdown | |
kill -0 ${c} 2>/dev/null && kill -TERM ${c} && list="$list $c" || true | |
done | |
if [ -n "$list" ]; then | |
# schedule hard kill after timeout | |
(sleep ${timeout}; kill -9 ${list} 2>/dev/null || true) & | |
local killer=${!} | |
wait ${list} 2>/dev/null || true | |
# children exited gracfully - cancel timer | |
sleep 0.5 && kill -9 ${killer} 2>/dev/null && list="" || true | |
fi | |
[ -z "$list" ] && echo "Exit Gracefully (0)" && exit 0 || echo "Dirty Exit (1)" && exit 1 | |
} | |
### end functions | |
## trap exit | |
trap exit INT TERM ERR | |
trap _clean EXIT | |
# make fifo for stderr hiding | |
ERR_FIFO=/tmp/hotspot_setup.stderr | |
exec 3<>$ERR_FIFO | |
exec 2>&1 | |
DEBUG=true | |
LOG_DIR=$(mktemp -d) | |
declare -a PIDS | |
# interface bindings | |
SRC_DEVICE=phy0 | |
HS_INTERFACE=hotspot0 | |
BR_INTERFACES=() | |
USE_BRIDGE="" | |
# check that the interface supports ap mode | |
if ! iw phy | head -n +$(iw phy | grep -n 'Band 1:' | cut -d':' -f1) | tail -n +$(iw phy | grep -n 'Supported interface modes:' | cut -d':' -f1) | grep -E '^[[:space:]]*\* AP$' &>/dev/null ; then | |
echo "no interface that is compatible with AP mode found. Exiting..." | |
exit 99 | |
fi | |
# check if the user wants a bridge wrapped on the interface | |
if [ -z "${USE_BRIDGE}" ]; then | |
read -p "Do you want to bind the interface to a bridge (alternative to routing) ( default: false ): " yn | |
case ${yn,,} in | |
y*) | |
USE_BRIDGE=true | |
;; | |
n*) | |
USE_BRIDGE=false | |
;; | |
*) | |
USE_BRIDGE=false | |
;; | |
esac | |
if [[ "${USE_BRIDGE}" == "true" ]]; then | |
# enter a name for the bridge interface (if no default) | |
if [ -z "${BRIDGE_INTERFACE}" ]; then | |
read -p "Enter an alternate name for the bridge interface ( default: hotspot_br0 ): " BRIDGE_INTERFACE | |
if [ -z "${BRIDGE_INTERFACE}" ]; then | |
BRIDGE_INTERFACE=hotspot_br0 | |
fi | |
fi | |
# interfaces to bridge | |
while read -p "Enter additional interfaces to bind to bridge (leave blank to continue): " INT && [ ! -z "${INT}" ] ; do | |
if ip -o l | sed -E 's/^[0-9]+: ([a-zA-Z0-9-]+):.*$/\1/' | grep ${INT} &>/dev/null; then | |
# interface on host | |
BR_INTERFACES+="${INT}" | |
else | |
# interface not present on host | |
echo "Interface '${INT}' doesnt exist - try again" | |
fi | |
done | |
fi | |
fi | |
echo "Ready to deploy " | |
cat <<EOF | |
Creating hotspot: | |
physical device: ${SRC_DEVICE} | |
interface: ${HS_INTERFACE} | |
using bridge: ${USE_BRIDGE} | |
EOF | |
if [[ "${USE_BRIDGE,,}" == "true" ]]; then | |
cat <<EOF | |
Creating Bridge: | |
interface: ${BRIDGE_INTERFACE} | |
slaves interfaces: ${HS_INTERFACE} ${BR_INTERFACES[@]} | |
EOF | |
fi | |
### actual configuration of interfaces ### | |
# create interface | |
_debug "making secondary wireless interface after disabling primary" | |
ip l set down wlan0 2>&1 >&3 || print_err | |
_pause | |
iw phy ${SRC_DEVICE} interface add ${HS_INTERFACE} type __ap >&3 || print_err | |
_pause | |
_debug "setting to managed mode to get around bug with master mode not being able to set 4addr" | |
iwconfig ${HS_INTERFACE} mode managed | |
_pause | |
_debug "configuring interface to use 4addr settings on wireless" | |
iw dev ${HS_INTERFACE} set 4addr on >&3 || print_err | |
_pause | |
if [[ "${USE_BRIDGE,,}" == "true" ]]; then | |
_debug "adding bridge interface" | |
ip l add ${BRIDGE_INTERFACE} type bridge >&3 || print_err | |
_debug "setting hotspot interface as slave to bridge" | |
ip l set master ${BRIDGE_INTERFACE} ${HS_INTERFACE} >&3 || print_err | |
for INT in ${BR_INTERFACES}; do | |
_debug "setting interface '${INT}' as slave to bridge" | |
ip l set master ${BRIDGE_INTERFACE} ${INT} >&3 || print_err | |
done | |
_debug "bring bridge up" | |
ip l set up ${DRIDGE_INTERFACE} >&3 || print_err | |
fi | |
_debug "compiling configuration file for hostapd" | |
cat <<EOF > hostapd.conf | |
interface=${HS_INTERFACE} | |
driver=nl80211 | |
ssid=${AP_SSID:-cs-2-go} | |
channel=5 | |
hw_mode=g | |
wme_enabled=1 | |
macaddr_acl=0 | |
auth_algs=1 | |
ignore_broadcast_ssid=0 | |
wpa=2 | |
wpa_passphrase=${AP_PASSWORD:-mypassword} | |
wpa_key_mgmt=WPA-PSK | |
wpa_pairwise=TKIP | |
rsn_pairwise=CCMP | |
EOF | |
_debug "Bringing interface ${HS_INTERFACE} up now" | |
ip l set up dev ${HS_INTERFACE} | |
_pause | |
if [[ "${USE_BRIDGE,,}" != "true" ]]; then | |
_debug "Not using bridge therefore starting instance of dhcp server on interface ${HS_INTERFACE}" | |
if [ ! -f /etc/dhcp/dhcpd.conf ]; then | |
_err "not able to find dhcpd configuration in /etc/dhcp/dhcpd.conf - not running dhcp server" | |
else | |
_debug "Using current DHCPd configuration in '/etc/dhcp/dhcpd.conf'" | |
_debug "Setting ip on ${HS_INTERFACE} to match dhcpd configuration" | |
IP_ADDR=$( grep router /etc/dhcp/dhcpd.conf | sed -E 's/^.*[[:space:]](([0-9]{1,3}.?){4});$/\1/') | |
if ! echo "${IP_ADDR}" | grep -E '^([0-9]{1,3}.?){4}$' &>/dev/null; then | |
_err "not able to locate a valid ip for the interface in the dhcpd.conf file - skipping" | |
else | |
ip a add ${IP_ADDR}/24 dev ${HS_INTERFACE} | |
echo "" > /var/lib/dhcp/dhcpd.lease | |
_pause | |
_debug "Starting DHCPd server..." | |
dhcpd -f -cf /etc/dhcp/dhcpd.conf ${HS_INTERFACE} &>"${LOG_DIR}/dhcpd.log" & | |
PIDS+=($!) | |
_pause | |
fi | |
fi | |
fi | |
_debug "Starting hostapd - CTRL+c to exit..." | |
_pause | |
hostapd hostapd.conf &>"${LOG_DIR}/hostapd.log" & | |
PIDS+=($!) | |
_pause | |
tail -vf "${LOG_DIR}"/*.log |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment