Tutorial: Interrupt-Driven Event-Counter on the Raspberry Pi

From dftwiki3
Revision as of 19:28, 23 July 2013 by Thiebaut (talk | contribs) (Compilation)
Jump to: navigation, search

--D. Thiebaut (talk) 19:57, 23 July 2013 (EDT)


This page is under construction. Its purpose is to illustrate how to implement a user-level interrupt in C on a Raspberry Pi to count events. You may want to start with the very first tutorial of this series, here.


Page under construction!
UnderConstruction.jpg


Getting the Environment Ready

Install the WiringPi Library

  • Get the WiringPi library from drogon.net
  • Follow the directions on the Web site to download to the Pi. In my case the Pi is connected to my Mac through an ethernet cable, so I downloaded the tgz archive from https://git.drogon.net/?p=wiringPi;a=summary and sftp it over to the pi. I renamed the actual library to wiring.tgz, which is easier to type than its actual name.
sftp pi@169.254.0.2
sftp> pwd 
Remote working directory: /home/pi
sftp> put wiring.tgz
Uploading wiring.tgz to /home/pi/wiring.tgz
wiring.tgz                                                                            100%  108KB 107.8KB/s   00:00    
sftp> quit
  • Connect to the RPI and build the library
 tar -xzvf wiring.tgz 
 cd wiringPi-cbf6d64/
 ./build 
wiringPi Build script
=====================


WiringPi Library
make: Warning: File `Makefile' has modification time 1.4e+07 s in the future
[UnInstall]
[Compile] wiringPi.c
[Compile] wiringSerial.c
...
[Compile] drc.c
[Link (Dynamic)]
[Install Headers]
[Install Dynamic Lib] 
make: warning:  Clock skew detected.  Your build may be incomplete.

WiringPi Devices Library
make: Warning: File `Makefile' has modification time 1.4e+07 s in the future
[UnInstall]
[Compile] ds1302.c
...
[Link (Dynamic)]
[Install Headers]
[Install Dynamic Lib] 
make: warning:  Clock skew detected.  Your build may be incomplete.

GPIO Utility
make: Warning: File `Makefile' has modification time 1.4e+07 s in the future
[Compile] gpio.c
[Compile] extensions.c
[Compile] readall.c
[Link] 
make: warning:  Clock skew detected.  Your build may be incomplete.
make: Warning: File `Makefile' has modification time 1.4e+07 s in the future
[Install]
make: warning:  Clock skew detected.  Your build may be incomplete.

All Done.

NOTE: This is wiringPi v2, and if you need to use the lcd, Piface,
  Gertboard, MaxDetext, etc. routines then you must change your
  compile scripts to add -lwiringPiDev

  • Add the new library to the libray path, as explained in the INSTALL file of the wiringPi distribution.
 sudo nano /etc/ld.so.conf
and add the following line to it:
  /usr/local/lib
  • Tell the system to configure the libraries:
  sudo ldconfig

Interrupt Service Routine

/*
isr4pi.c
D. Thiebaut
based on isr.c from the WiringPi library, authored by Gordon Henderson
https://github.com/WiringPi/WiringPi/blob/master/examples/isr.c
Compile as follows:

    gcc -o isr4pi isr4pi.c -lwiringPi

 */
#include <stdio.h>
#include <string.h>
#include <errno.h>
#include <stdlib.h>
#include <wiringPi.h>


// What GPIO input are we using?
//This is a wiringPi pin number

#define BUTTON_PIN 0

// globalCounter:
//Global variable to count interrupts
//Should be declared volatile to make sure the compiler doesn't cache it.

static volatile int globalCounter = 0 ;


/*
 * myInterrupt:
 *********************************************************************************
 */

void myInterrupt (void) {
  ++globalCounter ;
}


/*
*********************************************************************************
* main
*********************************************************************************
*/

int main (void) {
  int myCounter = 0 ;

  if (wiringPiSetup () < 0)     {
      fprintf (stderr, "Unable to setup wiringPi: %s\n", strerror (errno)) ;
      return 1 ;
  }

  if ( wiringPiISR (BUTTON_PIN, INT_EDGE_FALLING, &myInterrupt) < 0 ) {
      fprintf (stderr, "Unable to setup ISR: %s\n", strerror (errno)) ;
      return 1 ;
  }


  for (;;) {
      printf ("Waiting ... "); 
      fflush (stdout) ;

      while (myCounter == globalCounter)
         delay (100) ;

      printf(" Done. counter: %5d\n", globalCounter );
      myCounter = globalCounter ;
    }

  return 0 ;
}

Compilation

  • Compile the code above against the WiringPi library as follows:
 gcc -o isr4pi isr4pi.c -lwiringPi