Friday, January 29, 2016

Command Line Hardware Hacking 101 - Raspberry Pi controls an LED

While games are fun and all, I wanted to use my Raspberry Pi as more than just a little Linux box. Specifically, I wanted to use it to drive electric circuits. The Hello World of this sort of project is getting the Pi to turn on and off an LED. Fortunately, the kit Shira gave me as a present came with the LEDs, resisitors, and everything else I'd need to accomplish this little experiment.

It took a bit of poking, but I finally found this YouTube video which walked me through the whole process of hooking up an LED to the Pi. It even gave me the few lines of Python code I'd need to get the LED to turn on. Thanks to Murphy's Law, following the instructions exactly yielded a dead circuit. But on a whim I swapped out the red LED with a yellow one, and whooo! It worked!

It was official, I was a hardware hacker!

With that little success in world of hardware, I decided to turn back to the software side of things. As mentioned above, there's a small Python script that drives the above LED. I wondered, could I replicate this from bash? Turns out, I can. In classic Unix style, there's a set of devices files under /sys/class/gpio that I can trivially write to which controls the state of the LED.

In the Python example, I needed to reference GPIO pin 11. However, at the shell level, I needed to access 17. I sort of get why this is, but for now, I'm not dwelling on this. The bottom line is that I needed to run the following code as root to initialize shell access to the LED:

  echo 17 > /sys/class/gpio/export
  echo out > /sys/class/gpio/gpio17/direction

From there, I could turn on and off the LED by echoing 0 or 1 to /sys/class/gpio/gpio17/value. Which is just too cool, if I do say so myself. Once I had this capability in place, I was able to whip up two quick shell scripts. The first is led and it's a shortcut for turning on and off the LED:

#!/bin/bash

GPIO=/sys/class/gpio/gpio17/value

case "$1" in
  on) echo 1 > $GPIO ;;
  off) echo 0 > $GPIO ;;
  *) echo "Usage: `basename $0` {on|off}" ;;
esac

The second is blink which does the same sort of thing, but iterates through durations to turn the LED on and off for:

#!/bin/bash

LED=/sys/class/gpio/gpio17/value

if [ -z "$1" ] ; then
  echo "Usage: `basename $0` on-time off-time ..."
fi

while [ -n "$1" ] ; do
  echo 1 > $LED
  sleep $1 ; shift
  if [ -n "$1" ] ; then
    echo 0 > $LED
    sleep $1 ; shift
  fi
done

echo 0 > $LED

With these commands in place, the command line hacking can begin!

# led on ; sleep 3 ; led off

# while true ; do ./blink 1 1 ; done

# while true ; do ./blink .5 .5 .25 .25 .5 .5 ; done

# while true ; do ./led on ; sleep .25 ; ./led off ; sleep .25 ; done

3 comments:

  1. Now you are now my Bash expert friend. Thank you.

    ReplyDelete
  2. The next logical step is to port your code to FORTH: https://sites.google.com/site/libby8dev/fignition

    ReplyDelete
  3. > Now you are now my Bash expert friend. Thank you.

    I'm not sure about an expert; but it is probably my most frequently used programming language.

    > The next logical step is to port your code to FORTH: https://sites.google.com/site/libby8dev/fignition

    Definitely! The Pi is awesome, but in many respects, it's way too 'big'. It's an entire Linux box. Once I get a feel for it, I'm thinking I'll want to experiment with some smaller hardware - in the FORTH board you pointed to may very well be the way to go. Stay tuned...

    ReplyDelete