LinuxQuestions.org
Download your favorite Linux distribution at LQ ISO.
Home Forums Tutorials Articles Register
Go Back   LinuxQuestions.org > Forums > Linux Forums > Linux - Distributions > Slackware > Slackware - ARM
User Name
Password
Slackware - ARM This forum is for the discussion of Slackware ARM.

Notices


Reply
  Search this Thread
Old 01-12-2016, 06:52 AM   #31
louigi600
Member
 
Registered: Dec 2013
Location: Italy
Distribution: Slackware
Posts: 635

Original Poster
Blog Entries: 20

Rep: Reputation: 81

The buttons need to connected across +3.3V and gpio22,23,24,25,27
while the leds need to be connected between +3.3V and gpio4,7,8,17,18 like this 3.3V o---|>|---o GPIO so that the gpio sinks the current (and is inverted so that when value is 1 output is 0v).

To use it first execute it with "start" parameter, then execute it with "monitor &"
status,report and find were mainly used for debugging. but may still be handy.
When you press a button the corresponding led goes on as soon as the script catches the button press and remains on until the action has been taken.
If there's nothing in the port led stays on for 2 seconds to prevent bounce .... if there's something that is not a network I don't know what would happen for sure but I assume that it should do the same as if nothing is plugged in the port.
If you do not actually unplug the nic in the usb port you can press it again to reenable the device (restart AP for example) once the led goes back off.

Have fun.

Code:
#!/bin/bash 
NAME=$(basename $0)
#This array maps the kernel gpio port, their direction, the pi's gpio pin and 
#the inverter status
#GPIO04 is iset to output, is connected to pin 7 and is inverted 
#hence "4:OUT:7:1" 
GPIO_PINS=(4:out:7:1 7:out:26:1 8:out:24:1 17:out:11:1 18:out:12:1 22:in:15:0 23:in:16:0 24:in:18:0 25:in:22:0 27:in:13:0)

#Actions array for when input pin is detected high (same order as the input pins set in GPIO_PINS
#so button connected to gpio22 does shutdown and so on
ACTIONS=("do_shutdown" "usb_toggle 1 2" "usb_toggle 1 3" "usb_toggle 1 4" "usb_toggle 1 5")

do_start ()
{ for ((i=0;i<${#GPIO_PINS[*]};i++))
  do
    eval $(echo "GPIO_PIN_DATA=$(echo "(${GPIO_PINS[$i]})" |tr ":" " ")")
    echo ${GPIO_PIN_DATA[0]} > /sys/class/gpio/export
    echo ${GPIO_PIN_DATA[1]} > /sys/class/gpio/gpio${GPIO_PIN_DATA[0]}/direction
    sleep 0.2
    [ ${GPIO_PIN_DATA[3]} -ne 0 ] && echo ${GPIO_PIN_DATA[3]} > /sys/class/gpio/gpio${GPIO_PIN_DATA[0]}/active_low
    [ "${GPIO_PIN_DATA[1]}" = "out" ] && echo 0 > /sys/class/gpio/gpio${GPIO_PIN_DATA[0]}/value
  done
}

do_stop ()
{ MYPID=$$
  PIDS=$(ps -eo pid,cmd |grep -wvE "grep|$MYPID" |grep -w "rc.gpio monitor" |awk '{print $1}')
  [ "$PIDS" != "" ] && kill -9 $PIDS
  for ((i=0;i<${#GPIO_PINS[*]};i++))
  do
    eval $(echo "GPIO_PIN_DATA=$(echo "(${GPIO_PINS[$i]})" |tr ":" " ")")
    echo ${GPIO_PIN_DATA[0]} > /sys/class/gpio/unexport
  done
}

show_status ()
{ for ((i=0;i<${#GPIO_PINS[*]};i++))
  do
    eval $(echo "GPIO_PIN_DATA=$(echo "(${GPIO_PINS[$i]})" |tr ":" " ")")
    echo -n "/sys/class/gpio/gpio${GPIO_PIN_DATA[0]}: "
    echo -n "direction: $(cat /sys/class/gpio/gpio${GPIO_PIN_DATA[0]}/direction) "
    echo -n "pin#: ${GPIO_PIN_DATA[2]} "
    echo -n "invert: $(cat /sys/class/gpio/gpio${GPIO_PIN_DATA[0]}/active_low) "
    echo "value: $(cat /sys/class/gpio/gpio${GPIO_PIN_DATA[0]}/value)"
  done
}

show_report ()
{ echo "Reporting all the gpio pinns status ... "
  for PIN in $(find /sys/class/gpio  -type l -maxdepth 1 -name "gpio[0-9]*")
  do
    echo "${PIN}: direction: $(cat $PIN/direction) value: $(cat $PIN/value)"
  done
}

#takes as input bus number and port and outputs the NIC's name
find_nic ()
{ #/sys/bus/usb/devices/usb<bus number>/<bus number>-<root port>/<bus number>-<root port>.<port>
  #/sys/bus/usb/devices/<bus number>-<root port>.<port>
  SYSBP=/sys/bus/usb/devices
  SYSNICDIR=$(find -H $SYSBP/${1}-1.${2}:* -type d -name net 2>/dev/null)
  [ "$SYSNICDIR" != "" ] && NIC=$(ls --indicator-style=none  $SYSNICDIR) || return
  echo $NIC
}

usb_toggle ()
{ STIME=$(date +s)
  GPIOPIN=$(echo ${GPIO_PINS[$(($2 - 1))]} |awk -F: '{print $1}')
  echo 1 > /sys/class/gpio/gpio$GPIOPIN/value
  NIC=$(find_nic $1 $2)
  [ "$NIC" = "" -o ! -f /etc/rc.d/network/$NIC ] && return
  if [ $(ifconfig $NIC |head -1 |grep -wc UP) -ge 1 ]
  then
    echo "stopping $NIC"
    /etc/rc.d/network/$NIC stop >/dev/null 2>&1
  else
    echo "starting $NIC"
    /etc/rc.d/network/$NIC start >/dev/null 2>&1
  fi
  sleep $(( 5 - $(date +%s) + $STIME )) >/dev/null 2>&1
  echo 0 > /sys/class/gpio/gpio$GPIOPIN/value
}

do_shutdown ()
{ GPIOPIN=$(echo ${GPIO_PINS[0]} |awk -F: '{print $1}')
  echo 1 > /sys/class/gpio/gpio$GPIOPIN/value
  shutdown -h now
}

monitor ()
{ MYPID=$$
  if ps -eo pid,cmd |grep -v grep |grep -wv "$MYPID" |grep -wq "rc.gpio monitor"
  then
    echo "$NAME monitor is already running "
    exit 1
  fi

  j=0
  for ((i=0;i<${#GPIO_PINS[*]};i++))
  do
    eval $(echo "GPIO_PIN_DATA=$(echo "(${GPIO_PINS[$i]})" |tr ":" " ")")
    [ "${GPIO_PIN_DATA[1]}" != "in" ] && continue
    MONITOR_PINS[$j]=${GPIO_PIN_DATA[0]}
    ((j++))
  done
  i=0
  while ((i<=${#MONITOR_PINS[*]}))
  do
    grep -q 1 /sys/class/gpio/gpio${MONITOR_PINS[$i]}/value 2>/dev/null && ${ACTIONS[$i]}
    i=$((++i % ${#MONITOR_PINS[*]}))
    [ $i -eq 0 ] && sleep 0.2
  done
}

case $1 in
  start) do_start;;
  stop) do_stop;;
  status) show_status;;
  report) show_report;;
  monitor) monitor ;;
  find) find_nic $2 $3;;
  *) echo "$NAME <start|stop|report|status|monitor>" ; exit 1;;
esac
http://i246.photobucket.com/albums/g...pshwu4p9x9.jpg

Last edited by louigi600; 01-12-2016 at 07:00 AM.
 
Old 01-13-2016, 05:02 AM   #32
justwantin
Member
 
Registered: Aug 2003
Location: Melbourne, Australia
Distribution: Slackware, Slackwarearm
Posts: 878

Rep: Reputation: 120Reputation: 120
Thanks David!
 
Old 01-13-2016, 12:17 PM   #33
louigi600
Member
 
Registered: Dec 2013
Location: Italy
Distribution: Slackware
Posts: 635

Original Poster
Blog Entries: 20

Rep: Reputation: 81
Forgot to mention: the choice of the input pins was made carefully so that they would all have the same default internal pull up/down status (which is not the case on all the gpio pins) and also be compatible with both Pi1 and Pi2.
If you want to change the pin setup you need to be careful about that.
To my understanding it's possible to reprogram the gpio pin internal pull up/down status (wiringPi does it) ... I just have not figured out how Gordon does that to try replicate it from shell.

If you want to add a usb hub to your Pi1 to have more then just 2 USB ports you need to do a little editing on the script.

If you find the script useful give me a thumbs up please.

Last edited by louigi600; 01-25-2016 at 02:56 AM.
 
Old 10-12-2016, 09:00 AM   #34
louigi600
Member
 
Registered: Dec 2013
Location: Italy
Distribution: Slackware
Posts: 635

Original Poster
Blog Entries: 20

Rep: Reputation: 81
While I was looking into witing some c code to poll the gpio pins status I came across gpio-watch, which does a much better job on monitoring events on input buttons the having a bash script loop and check, and saves me from writing the code myself.

With a combination of gpio-watch and gpio from wiringPI I'm now monitoring 8 buttons on my rPI2 with different actions for each one while still keeping minimal impact on cpu usage.

Last edited by louigi600; 10-18-2016 at 12:11 AM. Reason: fixed the broken link
 
1 members found this post helpful.
Old 10-17-2016, 03:28 PM   #35
justwantin
Member
 
Registered: Aug 2003
Location: Melbourne, Australia
Distribution: Slackware, Slackwarearm
Posts: 878

Rep: Reputation: 120Reputation: 120
@David, thanks for the heads up, nice little bit of C code, ta,

..... but the link is wrong. You have:
Code:
http://log.oddbit.com/2014/07/26/gpiowatch-run-scripts-in-respo/
it should be:
Code:
http://blog.oddbit.com/2014/07/26/gpiowatch-run-scripts-in-respo/
 
1 members found this post helpful.
Old 10-18-2016, 12:11 AM   #36
louigi600
Member
 
Registered: Dec 2013
Location: Italy
Distribution: Slackware
Posts: 635

Original Poster
Blog Entries: 20

Rep: Reputation: 81
Ooops ... clumsy cut and paste ... I'll mend that. Thanks for pointing it out.
 
  


Reply



Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is Off
HTML code is Off



Similar Threads
Thread Thread Starter Forum Replies Last Post
Learning Xlib: Get next Button Press on the display hydraMax Programming 3 01-10-2012 10:14 AM
Turn the power button into a key press? jsteel Linux - General 2 04-21-2011 01:47 AM
i hv to manually press the power button on shutdown after all daemons have been stopp alice_neo Linux - Software 6 09-12-2007 02:55 PM
disable shutdown by press the power button nickraj General 8 03-02-2007 11:16 PM
I want my Controller to output text with button press timrs Linux - Games 9 01-08-2007 06:19 AM

LinuxQuestions.org > Forums > Linux Forums > Linux - Distributions > Slackware > Slackware - ARM

All times are GMT -5. The time now is 05:31 AM.

Main Menu
Advertisement
My LQ
Write for LQ
LinuxQuestions.org is looking for people interested in writing Editorials, Articles, Reviews, and more. If you'd like to contribute content, let us know.
Main Menu
Syndicate
RSS1  Latest Threads
RSS1  LQ News
Twitter: @linuxquestions
Open Source Consulting | Domain Registration