#!/bin/bash # BUG DA RISOLVERE/FEATURE DA AGGIUNGERE IN QUESTA VERSIONE # # 1) problema del calcolo della velocità della rete dopo l'aggiornamento forzato # (trovare il numero di secondi passati...) # (a volte dà una velocità negativa, ed in genere sembra essere un po' più # alta di quello che dovrebbe essere) # progname=dwm_bar version=0.4 author=mt # scegliere opportunamente l'interfaccia di rete interf_eth=eth0 interf_wlan=wlan0 # server audio/alsa acard=0 acontrol="Master" pcontrol="PCM" # variabili globali ed impostazioni di default declare -i nseccycle=10 declare -i outercyclestep=3 declare -i nsec=$nseccycle declare -i outercycle=0 declare -i result=0 declare -i batt_full declare -i batt_perc declare -i cputot_new=0 declare -i cputot_old=0 declare -i lcdbr_cur declare -i lcdbr_max declare -i nettransfrate_old=0 declare -i ram_tot declare -i received_new_eth=0 declare -i received_new_wlan=0 #declare -i received_old_eth=0 #declare -i received_old_wlan=0 declare -i swap_tot declare -i temp declare -i t_old=0 declare -i transf_eth=0 declare -i transf_wlan=0 declare -i transfrate_eth_old=0 declare -i transfrate_wlan_old=0 declare -i transmit_new_eth=0 declare -i transmit_new_wlan=0 #declare -i transmit_old_eth=0 #declare -i transmit_old_wlan=0 declare -i wait_status=0 declare check_batt=false declare check_lcd=false declare check_temp=false declare col_batt declare col_cpu declare col_lvg declare col_ram declare col_temp declare col_vol declare col_volpcm declare show_batt=false declare show_lcd=false declare show_sec=false declare vol declare volpcm declare tpu="°C" declare colors=false declare loop=true declare root=true declare stdout=false declare show_pcm=true declare utf8=false # trova i file di informazioni sullo stato della batteria: battfile=`find /proc/acpi/battery/BAT?/state | head -n 1` battinfo=`find /proc/acpi/battery/BAT?/info | head -n 1` lcdbrfile="/proc/acpi/video/VGA/LCD/brightness" # trova il percorso completo del comando xsetroot xset=`which xsetroot 2> /dev/null` sens=`which sensors 2> /dev/null` # altre info non mutabili user=$USERNAME host=`hostname -s 2> /dev/null` # oppure uname -n [[ "$host" = "" || "$host" = "localhost" ]] && host=`hostname` batt_full=`cat "$battinfo" | awk '/full\ capacity:/ {print $4}'` ram_tot=`cat /proc/meminfo | awk '/MemTotal:/ {print $2}'` swap_tot=`cat /proc/meminfo | awk '/SwapTotal:/ {print $2}'` lcdbr_max=`head -n 1 "$lcdbrfile" | awk '{print $NF}'` lcdbr_max=$((lcdbr_max/10)) actype=`amixer -c $acard sget $acontrol | grep "channels:" | awk '{print $3}'` pctype=`amixer -c $acard sget $pcontrol | grep "channels:" | awk '{print $3}'` printhelp() { echo "$progname [Options]" echo "Options:" echo " -h|--help: print this message and exit" echo " -v|--version: print version number and exit" echo " -1: only one run (for testing purpose)" echo " -c: use special sequence characters for colors" echo " -n : number of seconds between outputs (min 1, max 90, default: 10)" echo " -N : number of cycles for updating all infos (min 1, max 100, default: 3)" echo " -o: print (also) to standard output" echo " -t: don't use xsetroot (only testing, useful with option -o)" echo " -u: use UTF-8 encoding (default is ISO-8859-1)" echo echo "Signals:" echo " 1) [SIGHUP] : force updating info and output" echo " 3) [SIGQUIT]: force exit from the infinite-loop" echo return } # funzione per il conteggio dei byte ricevuti/trasmessi #byte_count(){ # # interface="$1" # # mode="$2" # while read line; do # if [[ $line == ${interface}:* ]]; then # [[ "$mode" == "r" ]] && { echo $line | awk -F':' '{print $2}' | awk '{print $1}'; } # [[ "$mode" == "t" ]] && { echo $line | awk '{print $9}'; } # fi # done < /proc/net/dev #} force_exit(){ exit 0 } force_output(){ outercycle=0 output outercycle=1 nsec=0 } output(){ local -i res=0 update if $stdout; then echo -e "$stext" fi if $root; then $xset -name "`echo -e "$stext"`" res=$? fi return $res } queue_update_request(){ # qualcosa non va... [[ $wait_status -eq 1 ]] && echo "$progname: warning! Update request ignorated!" >&2 && return wait_status=1 sleep 1 force_output wait_status=0 } update(){ local -i batt_charge local -i cpuidle local -i cputot local -i cpu_perc local -i nettransfrate local -i ram_free local -i ram_perc local -i swap_free local -i swap_perc local -i t_now local -i t_diff local show_eth=false local show_swap=false local show_wlan=false local datetime min=`date "+%-M"` sec=`date "+%-S"` t_now=$((min*60+sec)) t_diff=$((t_now-t_old)) [[ $t_diff -lt 0 ]] && t_diff=$((t_diff+3600)) t_old=$t_now if [[ $outercycle -eq 0 ]]; then # update also less variable infos if $check_batt; then batt_charge=`cat "$battfile" | awk '/remaining\ capacity:/ {print $3}'` batt_perc=$(($batt_charge*100/$batt_full)) if [[ $batt_perc -lt 100 ]]; then show_batt=true batt_state=`cat "$battfile" | awk '/charging state:/ {print $3}'` [[ "$batt_state" == "charging" ]] && col_batt=$col_red || col_batt=$col_blu else show_batt=false col_batt=$col_norm fi fi if $check_lcd; then lcdbr_cur=`cat "$lcdbrfile" | awk '/current:/ {print $2}'` lcdbr_cur=$((lcdbr_cur/10)) [[ $lcdbr_cur -ne $lcdbr_max ]] && show_lcd=true || show_lcd=false fi if $check_temp; then temp=`sensors 2> /dev/null | grep Core | head -n 1 | awk -F: '{print $2}' | awk '{print $1}' | cut -b 2-3` if [[ $temp -lt 40 ]]; then col_temp=$col_norm elif [[ $temp -lt 45 ]]; then col_temp=$col_blu else col_temp=$col_red fi fi vol=`amixer -c $acard sget $acontrol | grep "$actype.*:" | awk -F: '{print $2}' | awk '{print $3}' | tr -d '[]\n'` volstat=`amixer -c $acard sget $acontrol | grep "$actype.*:" | awk -F: '{print $2}' | awk '{print $NF}'` volpcm=`amixer -c $acard sget $pcontrol | grep "$pctype.*:" | head -n 1 | awk -F: '{print $2}' | awk '{print $3}' | tr -d '[]\n'` [[ "$volstat" == "[on]" ]] && col_vol="$col_norm" || col_vol="$col_green" [[ "$volpcm" == "100%" ]] && show_pcm=false || show_pcm=true fi # and now update all other infos lvg=`cat /proc/loadavg | awk '{print $1}'` # come confrontare variabili reali? if [[ "`echo $lvg | cut -b 1`" != "0" ]]; then col_lvg=$col_red else col_lvg=$col_norm fi cpu_line=`head -n 1 /proc/stat` cpuidle_new=`echo $cpu_line | awk '{print $5}'` # idle clocks cputot_new=`echo $cpu_line | awk '{print $2+$3+$4+$5+$6+$7+$8}'` # $9 and $10 are usually 0 cpuidle=$((cpuidle_new-cpuidle_old)) cputot=$((cputot_new-cputot_old)) cpuidle_old=$cpuidle_new cputot_old=$cputot_new [[ $cputot -lt 1 ]] && cputot=1 cpu_perc=$(((cputot-cpuidle)*100/cputot)) if [[ $cpu_perc -lt 20 ]]; then col_cpu=$col_norm elif [[ $cpu_perc -lt 60 ]]; then col_cpu=$col_blu else col_cpu=$col_red fi ram_free=`cat /proc/meminfo | awk '/MemFree:/ {print $2}'` ram_perc=$(((ram_tot-ram_free)*100/ram_tot)) if [[ $ram_perc -lt 20 ]]; then col_ram=$col_norm elif [[ $ram_perc -lt 60 ]]; then col_ram=$col_blu else col_ram=$col_red fi if $check_swap; then swap_free=`cat /proc/meminfo | awk '/SwapFree:/ {print $2}'` swap_perc=$(((swap_tot-swap_free)*100/swap_tot)) [[ $swap_perc -gt 0 ]] && show_swap=true || show_swap=false if [[ $swap_perc -lt 10 ]]; then col_swap=$col_norm elif [[ $swap_perc -lt 30 ]]; then col_swap=$col_blu else col_swap=$col_red fi fi while read line; do if [[ $line == ${interf_eth}:* ]]; then received_new_eth=`echo $line | awk -F':' '{print $2}' | awk '{print $1}'` transmit_new_eth=`echo $line | awk '{print $9}'` elif [[ $line == ${interf_wlan}:* ]]; then received_new_wlan=`echo $line | awk -F':' '{print $2}' | awk '{print $1}'` transmit_new_wlan=`echo $line | awk '{print $9}'` fi done < /proc/net/dev transf_eth=$((received_new_eth+transmit_new_eth)) transf_wlan=$((received_new_wlan+transmit_new_wlan)) # msec=$((nsec*1000+1)) # nettransfrate=$((1000*(received_new+transmit_new-received_old-transmit_old)/msec)) # Oss: bisognerebbe dividere per tdiff (o nsec), ma può essere zero... # se le chiamate a force_update sono molto ravvicinate tra di loro # (anche se non dovrebbero, ma mi sa che non funzia...) # per cui faccio un controllo if [[ $transf_eth -gt 0 ]]; then #nettransfrate=$(((received_new+transmit_new-received_old-transmit_old)/nseccycle)) #[[ $nsec -gt 0 ]] && nettransfrate=$(((received_new+transmit_new-received_old-transmit_old)/nsec)) || nettransfrate=$nettransfrate_old # [[ $nsec -eq 0 ]] && [[ $t_diff -eq 0 ]] && transfrate_eth=$transfrate_eth_old || transfrate_eth=$(((transf_eth-transf_eth_old)/t_diff)) else transfrate_eth=0 fi if [[ $transf_wlan -gt 0 ]]; then [[ $t_diff -eq 0 ]] && transfrate_wlan=$transfrate_wlan_old || transfrate_wlan=$(((transf_wlan-transf_wlan_old)/t_diff)) else transfrate_wlan=0 fi transf_eth_old=$transf_eth transf_wlan_old=$transf_wlan if [[ $transfrate_eth -gt 0 || $transfrate_eth_old -gt 0 ]]; then show_eth=true if [[ $transfrate_eth -gt 1024 ]]; then eth_krate=`echo "scale=2; $transfrate_eth/1024" | bc` eth="$eth_krate kiB/s" else eth="$transfrate_eth B/s" fi else show_eth=false # da ripensare: solo se si scollega la rete non deve essere mostrata... # cmq dovrebbe funzionare anche così fi if [[ $transfrate_wlan -gt 0 || $transfrate_wlan_old -gt 0 ]]; then show_wlan=true if [[ $transfrate_wlan -gt 1024 ]]; then wlan_krate=`echo "scale=2; $transfrate_wlan/1024" | bc` wlan="$wlan_krate kiB/s" else wlan="$transfrate_wlan B/s" fi else show_wlan=false fi transfrate_eth_old=$transfrate_eth transfrate_wlan_old=$transfrate_wlan $show_sec && datetime=`date "+%a %-d %b %H:%M:%S"` || datetime=`date "+%a %-d %b %H:%M"` stext="$user@${host} [VM $col_vol$vol$col_norm|" $show_pcm && stext="${stext}VP $col_volpcm$volpcm$col_norm|" $show_batt && stext="${stext}BA $col_batt$batt_perc%$col_norm|" $show_lcd && stext="${stext}BR $lcdbr_cur/$lcdbr_max|" $check_temp && stext="${stext}TP $col_temp$temp$tpu$col_norm|" stext="${stext}LA $col_lvg$lvg$col_norm|CP $col_cpu$cpu_perc$col_norm%|RA $col_ram$ram_perc$col_norm%" $show_swap && stext="${stext}|SW $swap_perc%" $show_eth && stext="${stext}|ET $net" # || stext="${stext}]" $show_wlan && stext="${stext}|WI $wlan]" || stext="${stext}]" stext="${stext} $col_blu$datetime$col_norm" } # real start trap force_exit 2 trap force_exit 3 trap force_exit 6 trap queue_update_request 1 trap force_output 10 trap force_output 22 (echo $LANG | grep -q -i 'utf8') && utf8=true # controllo opzioni date da linea di comando while [ "$1" != "" ]; do case $1 in "-h"|"--help") printhelp exit 0 ;; "-v"|"--version") echo "$progname: version $version (by $author)" exit 0 ;; "-1") loop=false ;; "-c") colors=true ;; "-N") shift outercyclestep=$1 if [ $outercyclestep -le 0 || $outercyclestep -gt 100 ]; then echo "$progname: error! Option -N \nTry $0 --help for more help" >&2 exit 2 fi ;; "-n") shift nseccycle=$1 if [[ $nseccycle -le 0 || $nseccycle -gt 90 ]]; then echo "$progname: error! Option -n \nTry $0 --help for more help" >&2 exit 2 fi nsec=$nseccycle ;; "-o") stdout=true ;; "-t") root=false show_sec=true ;; "-u") utf8=true ;; *) echo "$progname: error in the options!" >&2 exit 2 ;; esac shift done if $root && [[ "$xset" == "" ]]; then echo "$progname: error! Command xsetroot not found!" >&2 exit 2 fi [[ -f "$battinfo" && -f "$battfile" ]] && check_batt=true [[ -f "$lcdbrfile" ]] && check_lcd=true [[ "$sens" == "" ]] || check_temp=true $utf8 && tpu="°C" if $colors; then col_norm="\x01" col_sel="\x02" col_urg="\x03" col_err="\x04" col_blu="\x05" col_red="\x06" col_green="\x07" else col_norm="" col_sel="" col_urg="" col_err="" col_blu="" col_red="" col_green="" fi while [[ $result -eq 0 ]]; do if [[ $nsec -eq $nseccycle ]]; then [[ $outercycle -eq $outercyclestep ]] && outercycle=0 output result=$? outercycle=$((outercycle+1)) nsec=0 fi $loop || break #sleep $nseccycle sleep 1 nsec=$((nsec+1)) done exit $result