Hi,

I use very frequently the wireless to connect to different nets and I
have a script for personal use which probably (??) could be useful for
some of you. At least some of the misc people I know asked me to post
this here.

I also have seen/read a lot of critics to obsd for not having a couple
of tools for doing such things. I hope this helps obsd a bit (???).

In any case, I hope I don't overwhelm your inbox with unwished spam. I
am sure that a lot of you have already done something similar...

This script is thought to help you find the different available
connections (named "beams" for historical reasons) where you happen to
be when you execute it. It will display them in the following order:

1- "Public" connections (i.e. without wep key)
2- "Secured" connections (i.e. with wep)

They are also shown in order according to the strength of the signal
and then you're prompted to choose the number of the beam you wish to
connect to. Of course, if a wep password is required, you will be
asked for it. Afterwards it'll connect to it.

Please note that you will have to modify the script to

a- select your IFACE (in my case iwi0)
b- select your LANG (in my case "catala", but "english" is also available)

ah, so... author? Let's say... an "anonymous donor to the public domain" ;)

A big thank you to everybody and in this occasion especially to Damien
for his great work.

Cheers,

Pau

--------------------------------------------------------

#!/bin/sh
#
#
# wifiprobe ver 0.1
#
# Copyright (c) 2007 anonymous donor to the public domain
#
# BSD license and disclaimers apply.
#
# Do not change to zsh;  it will break. There are subtle differences.
#
# This script should be installed with execute permissions, and
# be invoked by name.
#
# Developed under and for OpenBSD 4.1  9/2007
#
#-------------------------------------------------------------------------
#
#  helper functions
#
#-------------------------------------------------------------------------

function parseit
{
   local therest

   shift 1
   beamname=$1
   shift 1
   therest=$*
   IFS=" "
   set $therest
   shift 4
   sigstrength=$1
   shift 1
}


function readprobe
{
#
# this was not as easy to write as it looks
#
   local Foo

   while read Foo
   do
      IFS=" "
      if  echo $Foo | grep -q \"  ; then
         IFS="\""
      fi
      parseit $Foo
      beam[nbeam]=${beamname}
      strength[nbeam]=${sigstrength%dB}
#      printf "%4d\t%-32s\t%s\t%s\n" $nbeam "${beam[$nbeam]}"
$sigstrength ${strength[nbeam]}
      nbeam=$(($nbeam+1))
   done
}

function sortandprint
{
   typeset tempnm
   typeset tempst
   typeset -i i
   typeset -i j
   typeset -i inc
   typeset -i n
   typeset -i s

   s=$1
   n=$2
# s is offset in arrays where sort starts
# n is number of items to sort
# In other words, sort elements $s to $s + $n
#
# Implement a Shell sort.  In ksh.  Painful.  All the write-only jive-notation
# of perl, none of the functionality.
#

   if [ $n -eq 0 ]; then
      echo $MSG9
      return
   fi

   inc=$(($n/2))
   while [ $inc -gt 0 ]
   do
      i=$inc
      while [ $i -lt $n ]
      do
         j=$i
         tempst=${strength[$(($i+$s))]}
         tempnm=${beam[$(($i+$s))]}
#
# to change the sense of the sort, change the second test.
# use -lt for biggest first, -gt for smallest first.
#
         while [[ $j -ge $inc  && ${strength[$(($j+$s-$inc))]} -lt $tempst ]]
         do
            strength[$(($j+$s))]=${strength[$(($j+$s-$inc))]}
            beam[$(($j+$s))]=${beam[$(($j+$s-$inc))]}
            j=$(($j-$inc))
         done
         strength[$(($j+$s))]=$tempst
         beam[$(($j+$s))]=$tempnm
         i=$(($i+1))
      done

      if [ $inc -eq 2 ]; then
         inc=1
      else
         inc=$(($inc/2))
      fi
   done

   i=$s
   while [ $i -lt $(($n+$s)) ]
   do
      printf "%4d   %-32s\t%3d dB\n" $(($i+1)) "${beam[$i]}" ${strength[$i]}
      i=$(($i+1))
   done
}


cleanup ()
{
   if [ -t 0 -a -t 1 ]; then
      stty sane
   fi
   rm -f ${TMPPROBE}
   exit
}

#-------------------------------------------------------------------------
#
# "main" part of the script
#
#-------------------------------------------------------------------------

LANG="catala"
progname=`basename $0`

if [ X$LANG = X"english" ]; then

   MSG1="$progname:  Wireless access selection for device:"
   MSG2="Available public beams"
   MSG3="Available secured beams"
   MSG4="$progname: no wireless beams found"
   MSG5="choice out of range"
   MSG6="try again"
   MSG7="public access beam selected"
   MSG8="$progname: not interactive and no public beams"
   MSG9="none probed"
   MSG10="usage: $progname [interface_name]"
   CHOOSEPROMPT="Select beam> "
   PASSPROMPT="Password for"

elif [ X$LANG = X"catala" ] ; then

   MSG1="$progname: Dispositu de xarxa sense fil:"
   MSG2="Xarxes obertes disponibles"
   MSG3="Xarxes tancades detectades"
   MSG4="$progname: No hi ha cap xarxa disponible"
   MSG5="La xarxa que has triat no es troba en la llista"
   MSG6="mira de fer-ho una altra vegada..."
   MSG7="Has triat una xarxa oberta"
   MSG8="$progname: No interactiu, i no hi ha d'obertes"
   MSG9="no n'has avaluat cap"
   MSG10="Com fer-ho servir: $progname [nom_dispositiu]"
   CHOOSEPROMPT="Tria la xarxa> "
   PASSPROMPT="Mot de pas per a"
fi

IFACE=iwi0
if [ $# -gt 0 ]; then
   IFACE=$1
   shift 1
   if [ $# -gt 0 ]; then
      echo Extra arguments: $@ 1>&2
      echo $MSG10 1>&2
      exit 1
   fi
fi

TMPPROBE=`mktemp -t ${IFACE}.XXXXXXXX`

# only half-hearted efforts to rm this file are made.


testing=false
#testing=true
if [ X$testing = Xtrue ]; then
# hacks for development use by author
#   exho="echo dummy command: "
#   PROBECMD="cat /home/mass/play/weasel"
#   SUDO=""
#   SUDO="Pseudo-SUDO"
else
   exho=""
   SUDO="sudo"
   PROBECMD="${SUDO} ifconfig -M ${IFACE}"
fi

trap cleanup EXIT INT PIPE

typeset -i nbeam=0
typeset -i private=0

# one can get more clever than this, one might involve PAGER
# one might involve LESS
# not this one, though

if [ -t 0 -a -t 1 ]; then
   mypager=more
else
   mypager=cat
fi

# generate a menu
# Do this even for batch use, to log results during, say, boot/rc
#
# if this script is used in another script and output is not
# wanted, then invoke it with >/dev/null and perhaps 2>/dev/null
# That is the True Path
#
# The parsing done by the sed/grep pipe is not robust at all.
# It is possible that a recipe for bouillabaise might pass muster
# as output sufficiently parseable to attempt to configure a device
# later on.  The "correct" way to do this job is with a compiled
# program, modelled on ifconfig, that gathers this information from
# ioctl(2) calls on the device.  (see routines getinfo() et al in
# the sources for ifconfig.)  Parsing output not intended for
# human reading is a path to later madness.  This script is twice
# as long as it might be, if the need to parse and later accomodate
# device "nwids" with embedded blanks did not exist.
#

echo $MSG1 ${IFACE}
echo
echo $MSG2
echo "-----------------------------------------------------------------"
eval $PROBECMD | sed "s/^[[:space:]]*//g" | grep ^nwid | grep -v
privacy > ${TMPPROBE}
readprobe < ${TMPPROBE}

sortandprint 0 $nbeam  > ${TMPPROBE}
eval ${mypager} ${TMPPROBE}

# for obscure reasons of scoping, do not "simplify" the preceding
# two lines by discarding the temp file and putting readprobe on the
# end of the pipe.
#
# Put no function in a pipe (wrecks scope)
#
# the dividing point between public and private:

private=${nbeam}

echo
echo $MSG3
echo "-----------------------------------------------------------------"
eval $PROBECMD | sed "s/^[[:space:]]*//g" | grep ^nwid | grep privacy
>${TMPPROBE}
readprobe < ${TMPPROBE}

sortandprint $private $(($nbeam-$private)) > ${TMPPROBE}
eval ${mypager} ${TMPPROBE}

# the "if" establishes whether stdin and stdout are ttys.
# This is not flawless, of course, but tends to guess whether
# an operator is present.
# It would be better if a variable asserting batchness were present
# on the command line or in the environment.

typeset -i choice=-1

if [ $nbeam -eq 0 ] ; then
   echo $MSG4 1>&2
   cleanup
fi

if [ -t 0 -a -t 1 ]; then
   while [ 0 ]
   do
      read choice?"$CHOOSEPROMPT"
      if [ $choice -eq 0 ] ; then
         break
      elif [ $choice -gt $nbeam ] ; then
         echo $MSG5 $choice
         echo $MSG6
      else
         break
      fi
   done

   if [ $choice -eq 0 ] ; then
      cleanup
   fi

#
# decrement choice to accommodate zero-based arrays
#
   choice=$(($choice-1))
   if [ $choice -ge $private ] ; then
      stty -echo
      read pass?"$PASSPROMPT ${beam[$choice]}> "
      stty echo
      echo
#        this leaks the password to stdout when exho=echo.  Big deal?
      eval ${exho} ${SUDO} ifconfig ${IFACE} nwid \"${beam[$choice]}\" \
    nwkey \"${pass}\"
   else
      echo $MSG7 ${beam[$choice]}
      eval ${exho} ${SUDO} ifconfig ${IFACE} nwid \"${beam[$choice]}\" \
    -nwkey down
   fi
else   # non-interactive: configure the first (strongest) public beam
   if [ $private -eq 0 ] ; then
      echo $MSG8 1>&2
      cleanup
   else
      choice=1
      eval ${exho} ${SUDO} ifconfig ${IFACE} nwid \"${beam[$choice]}\" \
    -nwkey down 1>&2
   fi
fi

eval ${exho} ${SUDO} dhclient ${IFACE}

cleanup

Reply via email to