[PD] Sensors GPIO Raspberry Pi Pd

Martin Peach martin.peach at sympatico.ca
Mon Apr 29 17:38:33 CEST 2013


Here's a patch to display data from two D6T sensors on the same I2C bus. 
The clock line is switched using a 4051 analog multiplexer. The control 
line is GPIO_17 of the Pi connected to A of the 4051 (B, C and Inhibit 
are at 0V). 10k resistors to 3.3V are on each sensor's clock line at X0 
and X1 of the 4051 (I2C clock connects to X). Because the code accesses 
the GPIO file system it needs to be run as root. I have two different 
sensors so the code reads two different packet lengths. Just a proof of 
concept, there could be up to 8 identical sensors on the same bus with 
this setup.

Martin

On 2013-04-25 20:04, Julian Brooks wrote:
> Just spotted this:
> https://github.com/kadamski/i2c-gpio-param
> Could be useful
>
>
> On 25 April 2013 15:54, Martin Peach <martin.peach at sympatico.ca
> <mailto:martin.peach at sympatico.ca>> wrote:
>
>     On 2013-04-25 10:37, Julian Brooks wrote:
>
>         'Nother 2 dumb questions:
>         What's the difference between the ones that have
>         spider/centipede type
>         legs and the straight ones (which would be best to get).
>
>
>     The PDIP package is what you want, not the SOIC. The only difference
>     is size. DIP packages are human-friendly, surface mount is for robots.
>
>
>         And also are you attaching the MC14051 to any type of
>         board/adaptor or
>         just soldering straight on to the pins?
>
>
>     I have it in a breadboard right now, to make it more permanent I
>     would solder a socket to a prototyping board then (after verifying
>     the connections) plug the chip into the socket. Soldering to the
>     pins makes it difficult to replace the IC, and risks damaging it
>     with the heat if you're not good at soldering quickly and to the
>     point. A CD4051 would also work, it's basically the same circuit.
>
>     Martin
>
>
>

-------------- next part --------------
#N canvas 2 0 1015 665 10;
#X obj 34 21 unpack 1 2 3 4 5 6 7 8 9;
#X obj 34 -51 netreceive 33333 1;
#X floatatom 34 147 5 0 0 0 - - -;
#X floatatom 74 147 5 0 0 0 - - -;
#X floatatom 114 147 5 0 0 0 - - -;
#X floatatom 154 147 5 0 0 0 - - -;
#X floatatom 194 147 5 0 0 0 - - -;
#X floatatom 234 147 5 0 0 0 - - -;
#X floatatom 274 147 5 0 0 0 - - -;
#X floatatom 314 147 5 0 0 0 - - -;
#X floatatom 354 146 5 0 0 0 - - -;
#X obj 57 215 vsl 15 128 0 500 0 0 empty empty empty 0 -9 0 10 -260097
-1 -1 6756 1;
#X obj 77 215 vsl 15 128 0 500 0 0 empty empty empty 0 -9 0 10 -4034
-1 -1 6782 1;
#X obj 97 215 vsl 15 128 0 500 0 0 empty empty empty 0 -9 0 10 -4034
-1 -1 6731 1;
#X obj 117 215 vsl 15 128 0 500 0 0 empty empty empty 0 -9 0 10 -4034
-1 -1 6350 1;
#X obj 137 215 vsl 15 128 0 500 0 0 empty empty empty 0 -9 0 10 -4034
-1 -1 6502 1;
#X obj 157 215 vsl 15 128 0 500 0 0 empty empty empty 0 -9 0 10 -4034
-1 -1 6604 1;
#X obj 177 215 vsl 15 128 0 500 0 0 empty empty empty 0 -9 0 10 -4034
-1 -1 6756 1;
#X obj 197 215 vsl 15 128 0 500 0 0 empty empty empty 0 -9 0 10 -4034
-1 -1 7188 1;
#X obj 217 215 vsl 15 128 0 500 0 0 empty empty empty 0 -9 0 10 -4034
-1 -1 7137 1;
#X obj 34 -11 route d6t8l d6t44l;
#X obj 462 6 unpack 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17;
#X floatatom 416 41 5 0 0 0 - - -;
#X floatatom 479 201 5 0 0 0 - - -;
#X floatatom 602 201 5 0 0 0 - - -;
#X floatatom 719 201 5 0 0 0 - - -;
#X floatatom 843 201 5 0 0 0 - - -;
#X floatatom 480 269 5 0 0 0 - - -;
#X floatatom 601 269 5 0 0 0 - - -;
#X floatatom 720 269 5 0 0 0 - - -;
#X floatatom 842 269 5 0 0 0 - - -;
#X floatatom 482 336 5 0 0 0 - - -;
#X floatatom 603 336 5 0 0 0 - - -;
#X floatatom 723 336 5 0 0 0 - - -;
#X floatatom 846 336 5 0 0 0 - - -;
#X floatatom 483 407 5 0 0 0 - - -;
#X floatatom 601 407 5 0 0 0 - - -;
#X floatatom 723 407 5 0 0 0 - - -;
#X floatatom 847 407 5 0 0 0 - - -;
#X obj 274 198 cnv 15 24 24 empty p01_rcv empty 20 12 0 14 -211168
-262144 0;
#X obj 304 198 cnv 15 24 24 empty p02_rcv empty 20 12 0 14 -174112
-262144 0;
#X obj 334 198 cnv 15 24 24 empty p03_rcv empty 20 12 0 14 -170016
-262144 0;
#X obj 364 198 cnv 15 24 24 empty p04_rcv empty 20 12 0 14 -182368
-262144 0;
#X obj 274 228 cnv 15 24 24 empty p05_rcv empty 20 12 0 14 -137025
-262144 0;
#X obj 304 228 cnv 15 24 24 empty p06_rcv empty 20 12 0 14 -174112
-262144 0;
#X obj 334 228 cnv 15 24 24 empty p07_rcv empty 20 12 0 14 -194720
-262144 0;
#X obj 364 228 cnv 15 24 24 empty p08_rcv empty 20 12 0 14 -202912
-262144 0;
#X obj 274 258 cnv 15 24 24 empty p09_rcv empty 20 12 0 14 -132865
-262144 0;
#X obj 304 258 cnv 15 24 24 empty p10_rcv empty 20 12 0 14 -198816
-262144 0;
#X obj 334 258 cnv 15 24 24 empty p11_rcv empty 20 12 0 14 -256480
-262144 0;
#X obj 364 258 cnv 15 24 24 empty p12_rcv empty 20 12 0 14 -260960
-262144 0;
#X obj 274 288 cnv 15 24 24 empty p13_rcv empty 20 12 0 14 -149377
-262144 0;
#X obj 304 288 cnv 15 24 24 empty p14_rcv empty 20 12 0 14 -231776
-262144 0;
#X obj 334 288 cnv 15 24 24 empty p15_rcv empty 20 12 0 14 -260576
-262144 0;
#X obj 364 288 cnv 15 24 24 empty p16_rcv empty 20 12 0 14 -260640
-262144 0;
#X msg 406 231 \; p01_rcv color \$1 0;
#X msg 526 231 \; p02_rcv color \$1 0;
#X msg 646 231 \; p03_rcv color \$1 0;
#X msg 766 231 \; p04_rcv color \$1 0;
#X msg 406 300 \; p05_rcv color \$1 0;
#X msg 526 300 \; p06_rcv color \$1 0;
#X msg 646 300 \; p07_rcv color \$1 0;
#X msg 766 300 \; p08_rcv color \$1 0;
#X msg 406 371 \; p09_rcv color \$1 0;
#X msg 526 371 \; p10_rcv color \$1 0;
#X msg 646 371 \; p11_rcv color \$1 0;
#X msg 766 371 \; p12_rcv color \$1 0;
#X msg 406 440 \; p13_rcv color \$1 0;
#X msg 526 440 \; p14_rcv color \$1 0;
#X msg 646 440 \; p15_rcv color \$1 0;
#X msg 766 440 \; p16_rcv color \$1 0;
#X obj 247 170 cnv 15 24 24 empty p00_rcv empty 20 12 0 14 -223520
-262144 0;
#X msg 462 66 \; p00_rcv color \$1 0;
#X text 59 161 Martin Peach 2013_04_27;
#X obj 462 38 temp2rgb;
#X obj 406 201 temp2rgb;
#X obj 406 269 temp2rgb;
#X obj 406 336 temp2rgb;
#X obj 406 407 temp2rgb;
#X obj 526 201 temp2rgb;
#X obj 526 269 temp2rgb;
#X obj 526 336 temp2rgb;
#X obj 526 407 temp2rgb;
#X obj 646 407 temp2rgb;
#X obj 646 336 temp2rgb;
#X obj 646 269 temp2rgb;
#X obj 646 201 temp2rgb;
#X obj 766 201 temp2rgb;
#X obj 766 269 temp2rgb;
#X obj 766 336 temp2rgb;
#X obj 766 407 temp2rgb;
#X obj 63 353 cnv 15 24 24 empty p20_rcv empty 20 12 0 14 -202912 -262144
0;
#X obj 93 382 cnv 15 24 24 empty p21_rcv empty 20 12 0 14 -207072 -262144
0;
#X obj 123 382 cnv 15 24 24 empty p22_rcv empty 20 12 0 14 -198816
-262144 0;
#X obj 153 382 cnv 15 24 24 empty p23_rcv empty 20 12 0 14 -153473
-262144 0;
#X obj 183 382 cnv 15 24 24 empty p24_rcv empty 20 12 0 14 -174112
-262144 0;
#X obj 213 382 cnv 15 24 24 empty p25_rcv empty 20 12 0 14 -186464
-262144 0;
#X obj 243 382 cnv 15 24 24 empty p26_rcv empty 20 12 0 14 -202912
-262144 0;
#X obj 273 382 cnv 15 24 24 empty p27_rcv empty 20 12 0 14 -256480
-262144 0;
#X obj 303 382 cnv 15 24 24 empty p28_rcv empty 20 12 0 14 -248224
-262144 0;
#X obj -99 63 temp2rgb;
#X msg -99 93 \; p20_rcv color \$1 0;
#X obj -99 133 temp2rgb;
#X obj -99 203 temp2rgb;
#X obj -99 273 temp2rgb;
#X obj -99 343 temp2rgb;
#X obj -99 413 temp2rgb;
#X msg -99 163 \; p21_rcv color \$1 0;
#X msg -99 233 \; p22_rcv color \$1 0;
#X msg -99 303 \; p23_rcv color \$1 0;
#X msg -99 373 \; p24_rcv color \$1 0;
#X msg -99 443 \; p25_rcv color \$1 0;
#X obj -99 483 temp2rgb;
#X obj -99 553 temp2rgb;
#X obj -99 623 temp2rgb;
#X msg -99 513 \; p26_rcv color \$1 0;
#X msg -99 583 \; p27_rcv color \$1 0;
#X msg -99 653 \; p28_rcv color \$1 0;
#X connect 0 0 2 0;
#X connect 0 0 100 0;
#X connect 0 1 3 0;
#X connect 0 1 102 0;
#X connect 0 2 4 0;
#X connect 0 2 103 0;
#X connect 0 3 5 0;
#X connect 0 3 104 0;
#X connect 0 4 6 0;
#X connect 0 4 105 0;
#X connect 0 5 7 0;
#X connect 0 5 106 0;
#X connect 0 6 8 0;
#X connect 0 6 112 0;
#X connect 0 7 9 0;
#X connect 0 7 113 0;
#X connect 0 8 10 0;
#X connect 0 8 114 0;
#X connect 1 0 20 0;
#X connect 2 0 11 0;
#X connect 3 0 12 0;
#X connect 4 0 13 0;
#X connect 5 0 14 0;
#X connect 6 0 15 0;
#X connect 7 0 16 0;
#X connect 8 0 17 0;
#X connect 9 0 18 0;
#X connect 10 0 19 0;
#X connect 20 0 0 0;
#X connect 20 1 21 0;
#X connect 21 0 22 0;
#X connect 21 0 74 0;
#X connect 21 1 23 0;
#X connect 21 1 75 0;
#X connect 21 2 24 0;
#X connect 21 2 79 0;
#X connect 21 3 25 0;
#X connect 21 3 86 0;
#X connect 21 4 26 0;
#X connect 21 4 87 0;
#X connect 21 5 27 0;
#X connect 21 5 76 0;
#X connect 21 6 28 0;
#X connect 21 6 80 0;
#X connect 21 7 29 0;
#X connect 21 7 85 0;
#X connect 21 8 30 0;
#X connect 21 8 88 0;
#X connect 21 9 31 0;
#X connect 21 9 77 0;
#X connect 21 10 32 0;
#X connect 21 10 81 0;
#X connect 21 11 33 0;
#X connect 21 11 84 0;
#X connect 21 12 34 0;
#X connect 21 12 89 0;
#X connect 21 13 35 0;
#X connect 21 13 78 0;
#X connect 21 14 36 0;
#X connect 21 14 82 0;
#X connect 21 15 37 0;
#X connect 21 15 83 0;
#X connect 21 16 38 0;
#X connect 21 16 90 0;
#X connect 74 0 72 0;
#X connect 75 0 55 0;
#X connect 76 0 59 0;
#X connect 77 0 63 0;
#X connect 78 0 67 0;
#X connect 79 0 56 0;
#X connect 80 0 60 0;
#X connect 81 0 64 0;
#X connect 82 0 68 0;
#X connect 83 0 69 0;
#X connect 84 0 65 0;
#X connect 85 0 61 0;
#X connect 86 0 57 0;
#X connect 87 0 58 0;
#X connect 88 0 62 0;
#X connect 89 0 66 0;
#X connect 90 0 70 0;
#X connect 100 0 101 0;
#X connect 102 0 107 0;
#X connect 103 0 108 0;
#X connect 104 0 109 0;
#X connect 105 0 110 0;
#X connect 106 0 111 0;
#X connect 112 0 115 0;
#X connect 113 0 116 0;
#X connect 114 0 117 0;
-------------- next part --------------
#N canvas 811 136 338 485 10;
#X obj 51 18 inlet;
#X text 71 238 red;
#X text 160 237 green;
#X text 239 280 blue;
#X obj 212 308 +;
#X obj 51 222 * -65536;
#X obj 227 264 * -1;
#X obj 197 416 - 1;
#X obj 197 454 outlet;
#X obj 197 385 + 0;
#X obj 143 222 * -256;
#X obj 51 49 t f f f;
#X obj 51 168 i;
#X obj 227 215 i;
#X obj 227 191 * 1.5;
#X msg 215 140 255;
#X obj 215 116 t b f;
#X obj 227 167 -;
#X obj 143 179 clip 0 255;
#X obj 143 139 - 128;
#X obj 51 119 - 200;
#X obj 51 194 clip 0 255;
#X obj 215 66 clip 255;
#X obj 51 143 * 3;
#X connect 0 0 11 0;
#X connect 4 0 9 1;
#X connect 5 0 9 0;
#X connect 6 0 4 1;
#X connect 7 0 8 0;
#X connect 9 0 7 0;
#X connect 10 0 4 0;
#X connect 11 0 20 0;
#X connect 11 1 19 0;
#X connect 11 2 22 0;
#X connect 12 0 21 0;
#X connect 13 0 6 0;
#X connect 14 0 13 0;
#X connect 15 0 17 0;
#X connect 16 0 15 0;
#X connect 16 1 17 1;
#X connect 17 0 14 0;
#X connect 18 0 10 0;
#X connect 19 0 18 0;
#X connect 20 0 23 0;
#X connect 21 0 5 0;
#X connect 22 0 16 0;
#X connect 23 0 12 0;
-------------- next part --------------
/* d6t_reader.c is a program that reads from omron d6t IR sensors using the raspberry pi i2c bus */
/* It sends sensor packets in a form readable by a pure-data [netreceive] object. */
// based on elinux.org/interfacing_with_I2C_Devices
// Martin Peach 20130416
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <linux/i2c.h>
#include <linux/i2c-dev.h>
#include <unistd.h>
#include <sys/ioctl.h>
#include <sys/types.h>
//#include <sys/stat.h>
#include <fcntl.h>
#include <arpa/inet.h>
#include <netinet/in.h>
#include <sys/socket.h>
#include <signal.h>
// Set a Pd [netreceive] to listen on this PORT
#define PORT 33333
// Pd is running on this machine IP
#define IP "192.168.2.15" 
//#define IP "127.0.0.1"
// The SENSOR_PACKET_SIZE is 35 for D6T44L, 19 for D6T8L
#define D6T44L_SENSOR_PACKET_SIZE 35
#define D6T8L_SENSOR_PACKET_SIZE 19
// PD_SELECTOR is the first item in the message sent to netrecceive
#define D6T44L_PD_SELECTOR "d6t44l"
#define D6T8L_PD_SELECTOR "d6t8l"
// SENSOR_SELECT_PIN connects to A of a 4051 multiplexer to select X0 or X1 output for the i2c clock.
// GPIO_17 is rPi GPIO_GEN_0, pin 11 on the P1 header.
#define SENSOR_SELECT_PIN 17
// calc_crc and D6T_checkPEC are from Omron's crc code from the DST-44L/DST-8L Thermal Sensor Whitepaper
unsigned char calc_crc (unsigned char data);
int D6T_checkPEC (unsigned char *buf, int pPEC);

int gpio_init(int gpio_number, int direction);
int gpio_write(int gpio_number, int value);
int gpio_free(int gpio_number);

void  sigint_handler(int sig);

/* non-zero direction is output */
#define GPIO_IN 0
#define GPIO_OUT 1
// Executes when the user presses Ctrl+C. Frees up GPIO pins

void sigint_handler(int sig)
{
    gpio_free(SENSOR_SELECT_PIN);
    exit (sig);
}

int gpio_init(int gpio_number, int direction)
{
    FILE    *fp;
    //create a variable to store whether we are sending a '1' or a '0'
    char    set_value[4];
    char    path[128];
    //Using sysfs we need to write "38" to /sys/class/gpio/export
    //This will create the folder /sys/class/gpio/gpio38
    // use fopen instead of open because we don't want buffering
    if ((fp = fopen("/sys/class/gpio/export", "ab")) == NULL)
    {
        printf("Cannot open export file.\n");
        return(1);
    }
    //Set pointer to beginning of the file (is this necessary?)
    rewind(fp);
    //Write our value of "38" to the file
    sprintf(set_value,"%d", gpio_number);
    fwrite(&set_value, sizeof(char), strlen(set_value), fp);
    fclose(fp);

    printf("...export file accessed, new pin now accessible\n");

    //Open the pin's sysfs file in binary for reading and writing, store file pointer in fp
    sprintf(path, "/sys/class/gpio/gpio%d/direction", gpio_number);
    if ((fp = fopen(path, "rb+")) == NULL)
    {
        printf("Cannot open direction file.\n");
        return(2);
    }
    //Set pointer to beginning of the file
    rewind(fp);
    //Write our value of "out" to the file
    if (direction) strcpy(set_value,"out");
    else strcpy(set_value,"in");
    fwrite(&set_value, sizeof(char), strlen(set_value), fp);
    fclose(fp);
    printf("...direction set to %sput\n", (direction)?"out":"in");
    return 0;
}

int gpio_write(int gpio_number, int value)
{
    FILE    *fp;
    //create a variable to store whether we are sending a '1' or a '0'
    char    set_value[4];
    char    path[128];

    //SET VALUE
    //Open the LED's sysfs file in binary for reading and writing, store file pointer in fp
    sprintf(path, "/sys/class/gpio/gpio%d/value", gpio_number);
    if ((fp = fopen(path, "rb+")) == NULL)
    {
        printf("Cannot open value file.\n");
        return(3);
    }
    //Set pointer to beginning of the file
    rewind(fp);
    //Write our value of "1" to the file
    sprintf(set_value,"%d", value);
    fwrite(&set_value, sizeof(char), strlen(set_value), fp);
    fclose(fp);
    //printf("...value set to %d...\n", value);

    return 0;
}

int gpio_free(int gpio_number)
{
    FILE    *fp;
    char    set_value[4];
    //Using sysfs we need to write "38" to /sys/class/gpio/unexport
    //This will remove the folder /sys/class/gpio/gpio38
    // use fopen instead of open because we don't want buffering
    if ((fp = fopen("/sys/class/gpio/unexport", "ab")) == NULL)
    {
        printf("Cannot open unexport file.\n");
        return(4);
    }
    //Set pointer to beginning of the file
    rewind(fp);
    //Write our value of "38" to the file
    sprintf(set_value,"%d", gpio_number);
    fwrite(&set_value, sizeof(char), strlen(set_value), fp);
    fclose(fp);

    printf("...unexport file accessed, pin now inaccessible\n");
    return 0;
}

unsigned char calc_crc (unsigned char data)
{
  int           index;
  unsigned char temp;

  for (index = 0; index < 8; index++)
  {
    temp = data;
    data <<= 1;
    if (temp & 0x80) data ^= 0x07;
  }
  return data;
}

int D6T_checkPEC (unsigned char *buf, int pPEC)
{
  unsigned char crc = 0;
  int           i;

  //crc = calc_crc( 0x14 );
  //crc = calc_crc( 0x4C ^ crc );
  crc = calc_crc( 0x15 ^ crc );
  for ( i = 0; i < pPEC; i++)
  {
    crc = calc_crc(buf[i] ^ crc);
    //    if (crc == buf[pPEC]) printf("MATCH at %d\n", i);
  }
  printf("D6T_checkPEC says 0x%02X\n", crc);
  return (crc == buf[pPEC]);
}

int main (int argc, char **argv)
{
  int 							        i2c_file;
  char 							        filename[32];
  int                       addr = 0x0A;
  unsigned char             inbuf[63];
  unsigned char             outbuf;
  char                      netbuf[256];
  const char                *buffer;
  int                       i, j, s;
  int                       initialized = 0;
  int							          sensor = 0; // which one
  int                       bufsize = D6T44L_SENSOR_PACKET_SIZE; // read packet size for the current sensor
  struct sockaddr_in        sock;

  // initialize the GPIO pin(s) to select the sensor via a multiplexer on its clock line
  // GPIO_17 == GPIO_GEN0 on the pi == pin 11 on connector P1
  i = gpio_init(SENSOR_SELECT_PIN, GPIO_OUT); // make pin an output
  if (0 != i)
  {
	    printf ("Unable to init GPIO %d (%d)\n", SENSOR_SELECT_PIN, i);
	    sigint_handler ( EXIT_FAILURE );
  }
  // select sensor in channel 0
  i = gpio_write(SENSOR_SELECT_PIN, sensor&0x01); // output low
  if (0 != i)
  {
	    printf ("Unable to write GPIO %d (%d)\n", SENSOR_SELECT_PIN, i);
	    sigint_handler ( EXIT_FAILURE );
  }
  // Assign a handler to free the GPIO pin on Ctrl+C.
  signal (SIGINT, (__sighandler_t)sigint_handler);

  // set up a socket to send UDP datagrams through
  if (( s = socket( AF_INET, SOCK_DGRAM, IPPROTO_UDP )) < 0)
  {
    printf ("Unable to create socket (%d)\n", errno);
    buffer = strerror(errno);
    printf(">> %s <<\n", buffer);
    sigint_handler ( EXIT_FAILURE );
  }
  memset (( char *) &sock, 0 , sizeof(sock) ); // clear the sock struct
  sock.sin_family = AF_INET;
  sock.sin_port = htons ( PORT );
  if ( inet_aton( IP, &sock.sin_addr ) == 0 )
  {
    printf ( "Unable to make address from %s\n", IP );
    sigint_handler ( EXIT_FAILURE );
  }
  // The Omron sensor streams data after being initialized so we only need to write it once
  if ( argc > 1 ) initialized = atoi(argv[1]);
  printf("%s: initialized:%d\n", argv[0], initialized);
  // Open the I2C connection
  sprintf(filename, "/dev/i2c-1");
  if ((i2c_file = open(filename, O_RDWR)) < 0)
  {
    printf ("Failed to open the bus. (%d)\n", errno);
    sigint_handler (EXIT_FAILURE);
  }
  // set the slave address
  if (ioctl(i2c_file, I2C_SLAVE, addr) < 0)
  {
    printf ("Failed to acquire bus access and/or talk to slave. (%d)\n", errno);
    sigint_handler (EXIT_FAILURE);
  }
  // start reading packets
  do
  {
    // read the first sensor, a D6T44L
    sensor = 0;
    bufsize = D6T44L_SENSOR_PACKET_SIZE; // packet size for sensor 0
    i = gpio_write(SENSOR_SELECT_PIN, sensor&0x01); // select sensor in channel 0
    if (0 != i)
    {
      printf ("Unable to write GPIO %d (%d)\n", SENSOR_SELECT_PIN, i);
      sigint_handler ( EXIT_FAILURE );
    }
    do // read packets until we get one with no errors
    {
    	// clear the inbuf first
    	for ( i = 0; i < bufsize; ++i) inbuf[i] = 0;

    	// we only need to write the command once.
    	// After that the sensor will return data
    	// any time it is read.
    	if ( !initialized )
    	{
        outbuf = 0x4C; // the command
    		if (write( i2c_file, &outbuf, 1 ) != 1)
    		{
    			printf("Write failed (%d)\n", errno);
    			buffer = strerror(errno);
    			printf(">> %s <<\n", buffer);
    			sigint_handler (EXIT_FAILURE);
    		}
    		//initialized = 1; // only set after all sensors are intialized
    	}
    	// read a packet
    	if (read (i2c_file, inbuf, bufsize) != bufsize)
    	{
    		printf("Read failed (%d)\n", errno);
    		buffer = strerror(errno);
    		printf(">> %s <<\n", buffer);
    	}
    } while (!D6T_checkPEC (inbuf, bufsize-1));
    // print the result
    for (i = 0; i < bufsize-1; i += 2)
    {
      printf("%d ", inbuf[i]+(inbuf[i+1]<<8));
    }
    printf("<0x%02X>\n", inbuf[bufsize-1]);
    // send the result to Pd
    j = sprintf (netbuf, D6T44L_PD_SELECTOR);
    for (i = 0; i < bufsize-1; i += 2)
    {
      j += sprintf(&netbuf[j], " %d", inbuf[i] + (inbuf[i+1]<<8));
    }
    j += sprintf(&netbuf[j], "\n"); // CR NOT semicolon for Pd's [netreceive]
    if (sendto ( s, netbuf, j, 0, (const struct sockaddr *)&sock, sizeof(sock)) < 0 )
    {
      printf ("sendto error (%d)\n", errno);
      buffer = strerror (errno);
      printf (">> %s <<\n", buffer);
    }
    printf("%s\n", netbuf);

    usleep (200000); // wait 200ms

    // read second sensor, a D6T8L
    sensor = 1;
    bufsize = D6T8L_SENSOR_PACKET_SIZE; // sensor 1 is D6T8L
    i = gpio_write(SENSOR_SELECT_PIN, sensor&0x01); // select sensor in channel 1
    if (0 != i)
    {
      printf ("Unable to write GPIO %d (%d)\n", SENSOR_SELECT_PIN, i);
      sigint_handler ( EXIT_FAILURE );
    }
    do
    {

      // clear the inbuf first
      for ( i = 0; i < D6T8L_SENSOR_PACKET_SIZE; ++i) inbuf[i] = 0;

      outbuf = 0x4C; // the command
      // we only need to write the command once.
      // After that the sensor will return data
      // any time it is read.
      if (! initialized)
      {
        if (write( i2c_file, &outbuf, 1 ) != 1)
        {
          printf("Write failed (%d)\n", errno);
          buffer = strerror(errno);
          printf(">> %s <<\n", buffer);
          sigint_handler (EXIT_FAILURE);
        }
        initialized = 1;
      }
      if (read (i2c_file, inbuf, D6T8L_SENSOR_PACKET_SIZE) != D6T8L_SENSOR_PACKET_SIZE)
      {
        printf("Read failed (%d)\n", errno);
        buffer = strerror(errno);
        printf(">> %s <<\n", buffer);
      }
    } while (!D6T_checkPEC (inbuf, D6T8L_SENSOR_PACKET_SIZE-1));
    // print to console
    for (i = 0; i < D6T8L_SENSOR_PACKET_SIZE-1; i += 2)
    {
      printf("%d ", inbuf[i]+(inbuf[i+1]<<8));
    }
    printf("<0x%02X>\n", inbuf[bufsize-1]);
    // send to Pd
    j = sprintf (netbuf, D6T8L_PD_SELECTOR);
    for (i = 0; i < D6T8L_SENSOR_PACKET_SIZE-1; i += 2)
    {
      j += sprintf(&netbuf[j], " %d", inbuf[i] + (inbuf[i+1]<<8));
    }
    j += sprintf(&netbuf[j], "\n"); // CR NOT semicolon for Pd's [netreceive]
    if (sendto ( s, netbuf, j, 0, (const struct sockaddr *)&sock, sizeof(sock)) < 0 )
    {
      printf ("sendto error (%d)\n", errno);
      buffer = strerror (errno);
      printf (">> %s <<\n", buffer);
    }
    printf("%s\n", netbuf);
    // sensors are supposed to update about every 400ms
    usleep (200000); // wait 200ms
  } while (1);
  close(i2c_file);
  return EXIT_SUCCESS;
}
 


More information about the Pd-list mailing list