-#!/bin/bash
-
-#########################################################################
-# This program is free software: you can redistribute it and/or modify #
-# it under the terms of the version 3 of the GNU General Public License #
-# as published by the Free Software Foundation. #
-# #
-# This program is distributed in the hope that it will be useful, but #
-# WITHOUT ANY WARRANTY; without even the implied warranty of #
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU #
-# General Public License for more details. #
-# #
-# You should have received a copy of the GNU General Public License #
-# along with this program. If not, see <http://www.gnu.org/licenses/>. #
-# #
-# Written by and Copyright (C) Francois Fleuret #
-# Contact <francois@fleuret.org> for comments & bug reports #
-#########################################################################
-
-INTERFACE=${WIFI_INTERFACE}
-
-[[ ${INTERFACE} ]] || INTERFACE=wlan0
-
-MTU=512
-
-SCAN_OUTPUT=$(mktemp /tmp/scanresult.XXXXXX)
-SHOW_CLOSED=0
-
-######################################################################
-
-VT_CURSOR_OFF=$'\033[?25l'
-VT_CURSOR_ON=$'\033[?25h'
-
-VT_RESET=$'\033[0m'
-VT_BOLD=$'\033[1m'
-VT_UNDERLINE=$'\033[4m'
-VT_BLINK=$'\033[5m'
-
-VT_BLACK_FG=$'\033[30m'
-VT_RED_FG=$'\033[31m'
-VT_GREEN_FG=$'\033[32m'
-VT_YELLOW_FG=$'\033[33m'
-VT_BLUE_FG=$'\033[34m'
-VT_MAGENTA_FG=$'\033[35m'
-VT_CYAN_FG=$'\033[36m'
-VT_WHITE_FG=$'\033[37m'
-
-VT_BLACK_BG=$'\033[40m'
-VT_RED_BG=$'\033[41m'
-VT_GREEN_BG=$'\033[42m'
-VT_YELLOW_BG=$'\033[43m'
-VT_BLUE_BG=$'\033[44m'
-VT_MAGENTA_BG=$'\033[45m'
-VT_CYAN_BG=$'\033[46m'
-VT_WHITE_BG=$'\033[47m'
-
-######################################################################
-
-function cleanup-before-quit () {
- echo ${VT_CURSOR_ON}
- stty "$stty_state"
- rm -f ${SCAN_OUTPUT}
- if [[ "${interface_was_up}" == "" ]]; then
- echo "The interface was down."
- ifconfig ${INTERFACE} down
- fi
-}
-
-function sigint-handler () {
- cleanup-before-quit
- echo "Interrupted"
- exit 0
-}
-
-function scan () {
- echo
- echo " Scanning ..."
- iwconfig ${INTERFACE} ap off essid ""
- iwlist ${INTERFACE} scan | \
- sed -e "s/^[\t ]*//" | grep ^"Cell\|ESSID\|Quality\|Encryption" | \
- sed \
- -e "s/Cell [0-9]* - Address: \([0-9]*\)/AP,\1/" \
- -e "s/^ *ESSID:\\\"\([^\\\"]*\)\\\".*$/ESSID,\1/" \
- -e "s/Quality=\([0-9]*\).*$/QUALITY,\1/" \
- -e "s/Encryption key:/ENCRYPTION,/" | \
- awk 'BEGIN { FS="," }
- {
- if($1 == "ESSID") { essid=$2 }
- else if($1 == "AP") { ap=$2 }
- else if($1 == "QUALITY") { quality=$2; }
- else if($1 == "ENCRYPTION") {
- if($2 == "off") {
- open=" "
- printf("%d,%s,%s,%s\n",quality,open,essid,ap);
- } else {
- if('${SHOW_CLOSED}') {
- open="(closed)"
- printf("%d,%s,%s,%s\n",quality,open,essid,ap);
- }
- }
- }
- }' | \
- sort -rn > ${SCAN_OUTPUT}
-
- number_of_aps=$(wc -l ${SCAN_OUTPUT} | awk '{print $1}')
-
- chmod a+rw ${SCAN_OUTPUT}
-}
-
-function redisplay () {
- clear
-
- echo
- echo -n " ${VT_UNDERLINE}Hotspot selection${VT_RESET}"
- if [[ $SHOW_CLOSED == 0 ]]; then
- echo " (show only open networks)"
- else
- echo
- fi
- echo
- echo " [s,r] scan [m] switch the free-only view and scan [q] quit"
- echo " [e] select essid + dhcp [a] selects essid/ap + dhcp [k] kill dhcp and quit"
- echo
-
- for i in $(ifconfig -s | grep -E -v ^lo\|Iface\|wmaster | awk '{print $1}'); do
- echo " Warning: $i is up"
- done
- echo
-
- if [[ ${number_of_aps} == "0" ]]; then
- echo " ${VT_RED_FG}${VT_BOLD}No access point detected.${VT_RESET}"
- else
-
- awk < ${SCAN_OUTPUT} 'BEGIN { nb=1; FS="," }
- {
- if(nb == '$current_ap') {
- printf(" =>");
- } else {
- printf(" ");
- }
- if($2 == "(closed)") {
- printf("'${VT_RED_FG}'");
- printf("% 3s %s \"%s\" %s'${VT_RESET}'\n", $1, $2, $3, $4);
- } else {
- printf("'${VT_GREEN_FG}'");
- printf("% 3s %s \"%s\" %s'${VT_RESET}'\n", $1, $2, $3, $4);
- }
- nb=nb+1;
- }'
- fi
-}
-
-function get-selected-essid-ap () {
- cat ${SCAN_OUTPUT} | \
- awk 'BEGIN { nb=1; FS="," }
- {
- if(nb == '$current_ap') {
- printf("%s,%s\n", $3, $4);
- }
- nb=nb+1;
- }'
-}
-
-function kill-dhcp () {
- PID=$(pidof dhclient)
- if [[ ${PID} ]]; then
- echo "Killing dhclient"
- dhclient -x ${INTERFACE}
- fi
-}
-
-######################################################################
-
-function process-key () {
-
- case $1 in
- e) # Selects essid + dhcp
- SELECTED=$(get-selected-essid-ap)
- ESSID=$(echo ${SELECTED} | cut -f 1 -d,)
- echo "Running DHCP on ${INTERFACE} for ESSID \"${ESSID}\"."
- iwconfig ${INTERFACE} ap auto essid "${ESSID}"
- kill-dhcp
- echo
- dhclient ${INTERFACE}
- # if [[ $? == 0 ]]; then
- # iwconfig ${INTERFACE} > ~/.hotspot-ap
- # fi
- ifconfig ${INTERFACE} mtu ${MTU}
- interface_was_up=1
- cont=0
- ;;
-
- "return"|a) # Selects essid/ap + dhcp
- SELECTED=$(get-selected-essid-ap)
- ESSID=$(echo ${SELECTED} | cut -f 1 -d,)
- AP=$(echo ${SELECTED} | cut -f 2 -d,)
- echo "Running DHCP on ${INTERFACE} for ESSID \"${ESSID}\" and AP ${AP}."
- iwconfig ${INTERFACE} ap ${AP} essid "${ESSID}"
- kill-dhcp
- echo
- dhclient ${INTERFACE}
- # if [[ $? == 0 ]]; then
- # iwconfig ${INTERFACE} > ~/.hotspot-ap
- # fi
- ifconfig ${INTERFACE} mtu ${MTU}
- interface_was_up=1
- cont=0
- ;;
-
- k) # kill dhcp
- echo "Killing DHCP and bringing down ${INTERFACE}."
- kill-dhcp
- ifconfig ${INTERFACE} down
- cont=0
- ;;
-
- r|s) # re-scanning the access points
- scan
- redisplay
- ;;
-
- m) # Switching the mode to show the protected spots
- SHOW_CLOSED=$((1-SHOW_CLOSED))
- scan
- redisplay
- ;;
-
- "down"|n)
- current_ap=$((current_ap+1))
- if [[ $current_ap -gt $number_of_aps ]]; then
- current_ap=$number_of_aps
- fi
- redisplay
- ;;
-
- "up"|p)
- current_ap=$((current_ap-1))
- if [[ $current_ap -lt 1 ]]; then
- current_ap=1
- fi
- redisplay
- ;;
-
- "esc-esc"|q)
- echo " Quit."
- cont=0
- ;;
-
- *)
- ;;
- esac
-}
-
-######################################################################
-## The main
-
-if [[ $1 == "-k" ]]; then
- echo "Killing DHCP and bringing down ${INTERFACE}."
- kill-dhcp
- ifconfig ${INTERFACE} down
- exit 1
-fi
-
-trap cleanup-before-quit EXIT
-
-stty_state=$(stty -g)
-
-trap sigint-handler SIGHUP SIGINT SIGQUIT SIGABRT SIGTERM
-
-stty -echo -icrnl -icanon -xcase min 1 time 0
-
-echo ${VT_CURSOR_OFF}
-
-current_ap=1
-cont=1
-current_keymap=default
-
-interface_was_up=$(ifconfig | grep ${INTERFACE})
-
-ifconfig ${INTERFACE} up
-
-scan
-
-redisplay
-
-while [[ ${cont} == 1 ]]; do
-
- CHAR=$(dd bs=1 count=1 2>/dev/null)
-
- case ${current_keymap} in
- default) ##################################################
- case ${CHAR} in
-
- [a-z])
- process-key ${CHAR}
- ;;
-
- "\r")
- process-key "return"
- ;;
-
- "\ e")
- process-key "down"
- ;;
-
- "\10")
- process-key "up"
- ;;
-
- "\e") #$'\033'")
- current_keymap=escape
- ;;
-
- *)
- ;;
- esac
- ;;
-
- escape) ##################################################
- case ${CHAR} in
- "$'\033'")
- process-key "esc-esc"
- ;;
- "[")
- current_keymap=cursor
- ;;
- *)
- current_keymap=default
- ;;
- esac
- ;;
-
- cursor) ##################################################
-
- current_keymap=default
-
- case ${CHAR} in
- A)
- process-key "up"
- ;;
- B)
- process-key "down"
- ;;
- *)
- ;;
- esac
- ;;
-
- *)
- echo "Unknown keymap. This is an internal and weird bug."
- cont=0
- ;;
- esac
-
-done