Quick Guide für Raspberry Pi: C/C++ mit Geany für Newbies

Atmel, PIC, VEX, Fischertechnik

Moderator: Moderatoren

Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 5399
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Quick Guide für Raspberry Pi: C/C++ mit Geany für Newbies

Beitragvon HaWe » 17. Okt 2015 15:53


DONATE / SPENDE:
Gefällt dir dieses Kompendium und möchtest du dafür einen kleinen Betrag über PAYPAL spenden ?
Dann klicke einfach auf diesen Link -
Gegen eine Spende ab EUR 5,- kannst du dieses gesamte Kompendium auch als WORD.doc erhalten (per Email als .zip):

-> Ja, ich möchte etwas als Anerkennung spenden <-


Ein ganz herzliches Dankeschön! :prima:


Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 5399
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Quick Guide für Raspberry Pi: C/C++ mit Geany für Newbies

Beitragvon HaWe » 17. Okt 2015 15:53

Raspberry Pi mit Arduino über UART verbinden

die RX/TX-Pins der beiden Geräte werden über Kreuz verbunden (d.h. RX mit TX und TX mit RX).
Arduinos, die wie der Raspi ebenfalls 3.3V Level haben, sind z.B. der ZERO und der DUE (der DUE ist meine persönliche 1. Wahl wegen der vielen IOs, trotz Problemen manchmal mit verbugten libs).
5V-Boards brauchen dafür zusätzlich einen Levelshifter oder (viel einfacher) einen Spannungsteiler mit 2 Widerständen.

Schaltplan z.B. für den UNO oder den MEGA etc. (5V),
für den DUE oder ZERO (3.3V) den Arduino-TX-Pin direkt ohne Widerstände mit dem Raspi verbinden:

Bild
Quelle: http://blog.oscarliang.net/raspberry-pi-and-arduino-connected-serial-gpio/

Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 5399
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Re: Raspberry Pi: Quick Guide für Raspberry Pi: C/C++ mit Geany für Dummies (Baustelle)

Beitragvon HaWe » 17. Okt 2015 16:23

Raspberry Pi <-> Arduino UART Kommunikationsprogramm

erster Verbindungstest zwischenRaspi und Arduino, basierend auf meinem Arduino-Arduino-Serial-Comm Programm:
viewtopic.php?f=78&t=8491&start=15#p67476

direkt nach Portieren des Arduino Codes auf Raspi C, offenbar, überraschenderweise: es funktioniert auf Anhieb !... :shock:

funktioniert auch sehr schnell, dabei scheint die Display-Ausgabe auf dem Arduino zu Debug-Zwecken noch am meisten die UART-comm auszubremsen....
Die Arduino Display Ausgabe muss künftig unbedingt als eigener Task per Multitasking (Arduino Due: <Scheduler.h> ) laufen !!

share and enjoy!


für den Raspi:

Code: Alles auswählen


/*
   UART communication
   send/receive byte array (64 bytes)
   *     
   Raspberry Pi  master
   ver 0666nrm2
 
 */
 
// (C) Helmut Wunder (HaWe) 2015
// freie Verwendung für private Zwecke
// für kommerzielle Zwecke nur nach Genehmigung durch den Autor.
// Programming language: gcc C/C++ 
// protected under the friendly Creative Commons Attribution-NonCommercial-ShareAlike 3.0 Unported License
// http://creativecommons.org/licenses/by-nc-sa/3.0/



#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <math.h>
#include <fcntl.h>
#include <string.h>
#include <sys/ioctl.h>
#include <stdint.h>
#include <time.h>
#include <sys/time.h>
#include <errno.h>
#include <pthread.h>


#include <wiringPi.h>
#include <wiringSerial.h>

#define  byte  uint8_t

char   * uart  =  "/dev/ttyAMA0";
int    Serial1;

 




//=====================================================================================
// debug monitor

void displayvalues(char * caption, uint8_t array[]) {
  int cnt;
  char sbuf[128];
 
  sprintf(sbuf, "%s ", caption);
  printf(sbuf); printf("\n");
  for(cnt=0; cnt<8; ++cnt) {
    sprintf(sbuf, "%3d ", array[cnt]);      // print on TFT
    printf(sbuf);
  }   
  printf("\n");
 
}

//=====================================================================================
//=====================================================================================
// serial TCP


const    uint8_t  MSGSIZE=64;
uint8_t  bsync=255;
uint8_t  sendbuf[MSGSIZE];
uint8_t  recvbuf[MSGSIZE];


uint8_t calcchecksum(uint8_t array[]) {
  int32_t  sum=0;
  for(int i=2; i<MSGSIZE; ++i) sum+=(array[i]);
  return (sum & 0x00ff);
}

bool checksumOK(uint8_t array[]){
return (calcchecksum(array)==array[1]);
}

// ================================================================
// addToBuffer and receive function courtesy of chucktodd

bool addToBuffer( uint8_t buf[], uint8_t *cnt, uint16_t timeout){
bool inSync = *cnt>0;
unsigned long start=millis();
while((*cnt<MSGSIZE)&&(millis()-start<timeout)){
  if( serialDataAvail( Serial1 ) ) { // grab new char, test for sync char, if so start adding to buffer
    buf[*cnt] = (uint8_t)serialGetchar( Serial1 );
    if(inSync) *cnt += 1; 
    else{
     if(buf[*cnt]==0xFF){
       inSync = true;
       *cnt +=1;
       }
     }
    }
  }
return (*cnt==MSGSIZE);
}


//=====================================================================================

bool receive(uint8_t * buf, uint16_t timeout, uint8_t *cnt){ // by passing cnt in and out,
// i can timeout and still save a partial buffer, so a resync costs less (less data lost)

bool inSync=false;
unsigned long start=millis();
uint8_t * p;  // pointer into buf for reSync operation
bool done=false;

do{
  done = addToBuffer(buf,cnt,timeout); // if this return false, a timeout has occured, and the while will exit.
  if(done){                         // do checksumOK test of buffer;
    done=checksumOK(buf);
    if(!done){                      // checksumOK failed, scan buffer for next sync char
       p = (uint8_t*)memchr((buf+1),0xff,(MSGSIZE-1));   
       
       
       if(p){ // found next sync char, shift buffer content, refill buffer
         *cnt = MSGSIZE -(p-buf); // count of characters to salvage from this failure
         memcpy(buf,p,*cnt); //cnt is now where the next character from Serial is stored!
         }
       else *cnt=0; // whole buffer is garbage
       }
    }
   
  } while(!done&&(millis()-start<timeout));

return done; // if done then buf[] contains a sendbufid buffer, else a timeout occurred
}

//=====================================================================================


void loop()
{
  char     sbuf[128],  resOK;   
  static   uint8_t cnt=0;
  uint8_t  cbuf[MSGSIZE], chk;

 
  //   send to slave
 
  //Serial.println();
  sendbuf[0]=bsync;
  sendbuf[1]=calcchecksum(sendbuf);
 
  for(uint8_t i=0; i<MSGSIZE; i++) {                     // 
     serialPutchar( Serial1, sendbuf[i]);                // Send values to the slave       
  }       
  //serialFlush( Serial1 );                              // clear output buffer
 
  sprintf(sbuf, "send : %4d %4d     ", sendbuf[4], sendbuf[6]);
  printf(sbuf);

 
  //     Receive from slave

  memset(cbuf, 0, sizeof(cbuf));
   
  resOK = receive ( cbuf, 10000,&cnt);
 
  if( resOK ) {                         //  receive ok?
     cnt=0;

     memcpy(recvbuf, cbuf, sizeof(cbuf));
     
     // debug
     sprintf(sbuf, "received: %4d %4d    \n ", recvbuf[4], recvbuf[6]);
     printf(sbuf);
 
      memset(sendbuf, 0, sizeof(sendbuf));    // clear send buf
     // debug: test values to send back! 
      sendbuf[4]=recvbuf[4]+10;                      // change [4] to send back
      sendbuf[6]=recvbuf[6]+20;                      // change [6] to send back
       
       
  }
 
}


//=====================================================================================

 
int main() {
    unsigned long timesav;
    char  sbuf[128];

     
    printf("initializing..."); printf("\n");
   
    // UART Serial com port
    Serial1 = serialOpen (uart, 115200); // for Arduino code compatibility reasons
   
    while(1) { loop(); }
   
    serialClose( Serial1);
   

    exit(0);
}





for the Arduino Due:

Code: Alles auswählen

/*       
       UART communication
       send/receive byte array (64 bytes)
       
       Arduino slave
       ( Arduino Due + Mega;  for small AVR use SoftwareSerial ! )     
       ver 0666nas2
       
 */

 
// (C) Helmut Wunder (HaWe) 2015
// freie Verwendung für private Zwecke
// für kommerzielle Zwecke nur nach Genehmigung durch den Autor.
// Programming language: Arduino Sketch C/C++ (IDE 1.6.1 - 1.6.5)
// protected under the friendly Creative Commons Attribution-NonCommercial-ShareAlike 3.0 Unported License
// http://creativecommons.org/licenses/by-nc-sa/3.0/


 

//=====================================================================================

const    uint8_t  MSGSIZE=64;
uint8_t  bsync=255;
uint8_t  sendbuf[MSGSIZE];
uint8_t  recvbuf[MSGSIZE];


//=====================================================================================

const uint32_t UARTclock = 115200;

//=====================================================================================

void displayvalues(char * caption, uint8_t array[]) {
  int cnt;
  char sbuf[128];
 
  sprintf(sbuf, "%s ", caption); 
  Serial.println(sbuf);
  for(cnt=0; cnt<8; ++cnt) {
    if(cnt%8==0) Serial.println();
    sprintf(sbuf, "%3d ", array[cnt]);      // print on TFT
    Serial.print(sbuf);                      // Print sendbufue to the Serial Monitor
  }   
  Serial.println();
 
}


//=====================================================================================
// serial transmission

uint8_t calcchecksum(uint8_t array[]) {
  int32_t  sum=0;
  for(int i=2; i<MSGSIZE; ++i) sum+=(array[i]);
  return (sum & 0x00ff);
}

#define  checksumOK(array)  (calcchecksum(array)==array[1])


// ================================================================
// addToBuffer and receive function courtesy of chucktodd

bool addToBuffer( uint8_t buf[], uint8_t *cnt, uint16_t timeout){
bool inSync = *cnt>0;
unsigned long start=millis();
while((*cnt<MSGSIZE)&&(millis()-start<timeout)){
  if(Serial1.available()){ // grab new char, test for sync char, if so start adding to buffer
    buf[*cnt] = (uint8_t)Serial1.read();
    if(inSync) *cnt += 1; 
    else{
     if(buf[*cnt]==0xFF){
       inSync = true;
       *cnt +=1;
       }
     }
    }
  }
return (*cnt==MSGSIZE);
}


//=====================================================================================

bool receive(uint8_t * buf, uint16_t timeout, uint8_t *cnt){ // by passing cnt in and out,
// i can timeout and still save a partial buffer, so a resync costs less (less data lost)

bool inSync=false;
unsigned long start=millis();
uint8_t * p;  // pointer into buf for reSync operation
bool done=false;

do{
  done = addToBuffer(buf,cnt,timeout); // if this return false, a timeout has occured, and the while will exit.
  if(done){ // do checksumOK test of buffer;
    done=checksumOK(buf);
    if(!done){// checksumOK failed, scan buffer for next sync char
       p = (uint8_t*)memchr((buf+1),0xff,(MSGSIZE-1));
       
       
       if(p){ // found next sync char, shift buffer content, refill buffer
         *cnt = MSGSIZE -(p-buf); // count of characters to salvage from this failure
         memcpy(buf,p,*cnt); //cnt is now where the next character from Serial is stored!
         }
       else *cnt=0; // whole buffer is garbage
       }
    }
   
  }while(!done&&(millis()-start<timeout));

return done; // if done then buf[] contains a sendbufid buffer, else a timeout occurred
}

//=====================================================================================
//=====================================================================================

void loop()
{
  char     sbuf[128],  resOK;   
  static   uint8_t cnt=0;
  uint8_t  cbuf[MSGSIZE], chk;
 

  //     Receive from master

  memset(cbuf, 0, sizeof(cbuf));
   
  resOK = receive ( cbuf, 10000,&cnt);
 
  if( resOK ) {                                      //    receive ok?
    cnt=0;

    //displayvalues(60, "Received...:", cbuf);
         
     memcpy(recvbuf, cbuf, sizeof(cbuf));
     
     memset(sendbuf, 0, sizeof(sendbuf));     
     // debug: test values to send back! 
      sendbuf[4]=recvbuf[4]+1;                      // change [4] to send back
      sendbuf[6]=recvbuf[6]+1;                      // change [6] to send back 

  }


 
  //   send to master
 
  //Serial.println();
  sendbuf[0]=bsync;
  sendbuf[1]=calcchecksum(sendbuf);
  for(uint8_t i=0; i<MSGSIZE; i++) {       
     Serial1.write(sendbuf[i]);                      // Send values to the master       
  }       
  //Serial1.flush();                                 // clear output buffer
  //displayvalues(20, "Transmitted...: ", sendbuf);
  sprintf(sbuf, "recieve: %4d %4d     send: %4d %4d", recvbuf[4], recvbuf[6], sendbuf[4], sendbuf[6]);
  Serial.println(sbuf);
 
}


//=====================================================================================



void setup() {
   char sbuf[128];   
   int32_t  i=0;

               
   // Serial
   Serial.begin(115200);   // USB terminal
 
   Serial1.begin(UARTclock);                    // RX-TX UART
   while(Serial1.available())  Serial1.read();  // clear output buffer
   
   sprintf(sbuf, "setup(): done.");
   Serial.println(); Serial.println(sbuf);   
 
   sprintf(sbuf, "Rx slave, BAUD= %ld", UARTclock );;

}

//=====================================================================================


Raspi+Due.jpg

Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 5399
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Re: Raspberry Pi: Quick Guide für Raspberry Pi: C/C++ mit Geany für Dummies (Baustelle)

Beitragvon HaWe » 17. Okt 2015 16:23


DONATE / SPENDE:
Gefällt dir dieses Kompendium und möchtest du dafür einen kleinen Betrag über PAYPAL spenden ?
Dann klicke einfach auf diesen Link -
Gegen eine Spende ab EUR 5,- kannst du dieses gesamte Kompendium auch als WORD.doc erhalten (per Email als .zip):

-> Ja, ich möchte etwas als Anerkennung spenden <-


Ein ganz herzliches Dankeschön! :prima:


Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 5399
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Quick Guide für Raspberry Pi: C/C++ mit Geany für Dummies (Baustelle)

Beitragvon HaWe » 20. Okt 2015 15:28


Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 5399
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Quick Guide für Raspberry Pi: C/C++ mit Geany für Dummies (Baustelle)

Beitragvon HaWe » 20. Okt 2015 15:28

test edit

Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 5399
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Re:Quick Guide für Raspberry Pi: C/C++ mit Geany für Dummies (Baustelle)

Beitragvon HaWe » 4. Nov 2015 11:59

Platzhalter

Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 5399
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Quick Guide für Raspberry Pi: C/C++ mit Geany für Dummies

Beitragvon HaWe » 4. Nov 2015 11:59

Nutzung von USB, zum Verbinden über USB-Schnittstellen:

Nachdem beide Geräte (Raspi und Arduino) USB-Schnittstellen besitzen, und USB auch nur ein serielles Protokoll ist, kann man beide Geräte auch direkt über ihre USB-Buchsen verbinden. Die Ardino-USB-Buchse ist immer schon mit UART0 (RX0/TX0 auf pins 0+1) verbunden, beim Raspi muss man die genaue Adresse des Ports, mit dem der Arduino verbunden ist, erst noch herausfinden.

bisher wird auf dem Raspi dies als GPIO-Schnittstellen-Adresse verwendet (BCM 14+15):
/dev/ttyAMA0.

Um den Namen des Raspi-USB-Ports herauszufinden, an dem der Arduino angeschlossen ist, lässt man den erst mal ab und öffnet eine Linux Konsole.
Dann steckt man den Arduino ein und tippt in der Konsole

Code: Alles auswählen

dmesg | tail

Da kommt dann u.a.
new full-speed USB device ...
...
cdc_acm ...: ttyACM0: USB ACM device
usbcore: registered new interface driver cdc_acm

Will heißen, der Arduino hängt per USB an einem virtuellen UART mit dem Namen:
/dev/ttyACM0

Dies ist die neue serielle Adresse auf dem Raspi.

Am Arduino ist der serielle Port dann automatisch
Serial (RX0/TX0)
über den USB-Stecker, mit dem man ansonsten mit dem PC verbindet zum Programmieren oder für das Serielle Terminal Window.



Soll dagegen das Raspi-USB-Kabel direkt mit einem Arduino-UART-Pin verbunden werden, braucht man einen gesonderten USB-UART-Adapter:


f) Nutzung von USB-ch341 uart converter:

ch341_57.JPG


http://www.ebay.de/itm/USB-Seriell-TTL-LVTTL-Adapter-Converter-fur-z-B-Arduino-inkl-Kabel-/301883482496

Jumper für Arduino DUE auf 3.3V ändern !!!

Diesen Adapter einfach in die USB-Buchse einstecken, dann lassen sich die RX/TX Pins mit einem anderen seriellen Gerät (UART-Sensor oder Arduino Serial) verbinden.
Eingabe im Terminal:

Code: Alles auswählen

dmesg | tail

Da kommt dann u.a.
usb 1-1.3: new USB device found, idvendor=...
...
USB serial support registered cor ch341 -uart
ch341 1-1.3:1.0: ch341 uart converter detected
ch341 1-1.3:1.0: ch341 uart converter now attached to ttyUSB0

Will heißen, der ch341-UART-Konverter hängt an einem virtuellen UART mit dem Namen:
/dev/ttyUSB0


(Danke an Mxt (Roboternetz-Forum) und Marco Niesen ! )

Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 5399
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Quick Guide für Raspberry Pi: C/C++ mit Geany für Dummies

Beitragvon HaWe » 4. Nov 2015 11:59

test edit

Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 5399
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Quick Guide für Raspberry Pi: C/C++ mit Geany für Dummies (Baustelle)

Beitragvon HaWe » 4. Nov 2015 12:00

Raspberry Pi: I2C Schnittstelle (Pi B+ und Pi 2)

Lit.:
http://www.raspberry-pi-geek.de/Magazin ... -Pi-Teil-1

a) Übersicht:

Die Pins für I2C liegen auf dem Raspi auf den folgenden GPIOs:

Code: Alles auswählen

i2c-1:
phys.
3     SDA.1   wiringPi 8  (BCM 2)
5     SCL.1   wiringPi 9  (BCM 3)

i2c-0
phys.
27    SDA.0   wiringPi 30 (BCM 0)
28    SCL.0   wiringPi 31 (BCM 1)


RPi_GPIO_pinout.png


Links:
http://www.netzmafia.de/skripten/hardware/RasPi/RasPi_I2C.html
http://blog.retep.org/2014/02/15/connecting-an-arduino-to-a-raspberry-pi-using-i2c/
http://blog.oscarliang.net/raspberry-pi-arduino-connected-i2c/


b) Den RasPi für I2C vorbereiten

(abweichend von der Vorschrift in den Links: keine Blacklist, kein manuelles Patchen einer boot-config-Datei für i2c-1 etc.):

Code: Alles auswählen

sudo raspi-config

Code: Alles auswählen

=> (9)  Advanced Options
=> (A7) I2C
=> I2C Modul enablen: <Ja>
=> beim Booten automatisch laden: <OK>

Trotzdem wird dann zwar i2c-1, aber nicht i2c-0 geladen. Dazu ist dann doch wieder mal ein extra Schritt nötig:

Code: Alles auswählen

sudo nano /boot/config.txt
# am Schluss hinzufügen:
dtparam=i2c_vc=on


weitere / optionale settings:

Code: Alles auswählen

#i2c enable
dtparam=i2c_arm=on
#i2c-0 enable
dtparam=i2c_vc=on
#i2c baud rate
dtparam=i2c_arm_baudrate=400000
dtparam=i2c_vc_baudrate=400000
# I2C access without root privileges
SUBSYSTEM="i2c-dev", MODE="0666"


Schießlich Linux i2c-Tools installieren :

Code: Alles auswählen

sudo apt-get update
sudo apt-get install i2c-tools      # I2C-Toolkit fuer die Kommandozeile
sudo apt-get install python-smbus   # optional:  Python-Bibliothek fuer I2C
sudo apt-get install libi2c-dev     # Bibliothek fuer C


Jetzt RPI neu booten. Danach soll man die 2 i2c devices sehen können:

Code: Alles auswählen

pi@raspberrypi ~ $ ls -l /dev/i2c*
crw-rw---T 1 root i2c 89, 0 May 25 11:56 /dev/i2c-0
crw-rw---T 1 root i2c 89, 1 May 25 11:56 /dev/i2c-1


Test: scan the i2c bus:

Code: Alles auswählen

pi@raspberrypi ~ $ i2cdetect -y 1
     0  1  2  3  4  5  6  7  8  9  a  b  c  d  e  f
00:          -- -- -- -- -- -- -- -- -- -- -- -- --
10: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
20: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
30: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
40: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
50: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
60: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
70: -- -- -- -- -- -- -- --

Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 5399
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Quick Guide für Raspberry Pi: C/C++ mit Geany für Dummies (Baustelle)

Beitragvon HaWe » 4. Nov 2015 12:21

c) Den RasPi per I²C mit Arduino verbinden:

Bild
aus: http://blog.oscarliang.net/raspberry-pi ... ected-i2c/
RPI Arduino (Uno/Mega)
--------------------------------------------
GPIO 0 (SDA) <--> Pin A4/20 (SDA)
GPIO 1 (SCL) <--> Pin A5/21 (SCL)
Ground <--> Ground
Keine Level-Konverter nötig, wenn der Raspi master ist, denn er besitzt bereits interne Pullups auf +3,3V !

Nach Verbinden mit Arduino (slave addr=0x04) z.B.:

Code: Alles auswählen

pi@mimas ~ $ i2cdetect -y 1
     0  1  2  3  4  5  6  7  8  9  a  b  c  d  e  f
00:          -- 04 -- -- -- -- -- -- -- -- -- -- --
10: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
20: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
30: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
40: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
50: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
60: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
70: -- -- -- -- -- -- -- --
What you are now seeing is a list of all I2C devices connected. The one you are interested in is 04 which happens to be your arduino.


d) RasPi <-> Arduino I²C-Kommunikationsprogramm:

:-pc: funktioniert momentan nur mit Arduino DUE (ARM), nicht mit MEGA (AVR)
(Clock Stretching Fehler? eingebaute Pullups beim Mega?)
:-pc:

Testcode Raspi I2C Master:

Code: Alles auswählen

//  Raspberry Pi Master code to send/receive byte arrays
//  to an Arduino as an I2C slave
//
//  ver. 0.002a


#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <wiringPi.h>
#include <wiringPiI2C.h>

#include <errno.h>
#include <string.h>

#define MSGSIZE 30


unsigned char  calcchecksum( unsigned char array[]) {   
  int32_t  sum=0;
  for(int i=2; i<MSGSIZE; ++i) sum+=(array[i]);
  return (sum & 0x00ff);
}



int main (void)
{
   
  int fd, i ;
  unsigned char test=0;
  unsigned char data [MSGSIZE] ;

  if ((fd = wiringPiI2CSetup (0x04) ) < 0)
  {
    fprintf (stderr, "Can't open RTC: %s\n", strerror (errno)) ;
    exit (EXIT_FAILURE) ;
  }


  for (;;)
  {
    memset(data, 0, sizeof(data) );
    data[0]=  0xff;    // init for transmission error check
    read (fd, data, MSGSIZE) ;
    if( data[1] != calcchecksum( data )  ) {
         // handle transmission error !
    }   
    else {
       printf ("  read:  ");
       for (i = 0 ; i < 7 ; ++i)
          printf ("  %3d", data [i]) ;
       //printf ("\n") ;
       delay(10) ;
     
       memset(data, 0, sizeof(data) );
       data[5]=  test++;
       data[0]=  0xff;
       data[MSGSIZE-1]= 0x04;
       data[1] = calcchecksum( data );
       
       write(fd, data, MSGSIZE) ;
       printf ("   write: ");
       for (i = 0 ; i < 7; ++i)
         printf ("  %3d", data [i]) ;
       printf ("\n\n") ;
       delay(10) ;     
    }
  }

  return 0 ;
}


Testcode Arduino i2c Slave:

Code: Alles auswählen

//  Arduino code to send/receive byte arrays
//  Arduino as an I2C slave
//
//  ver. 0.002


#include  <Wire.h>

#define  SLAVE_ADDRESS 0x04
#define  MSGSIZE  30
byte     recvarray[MSGSIZE];  // 0=0xff; 1=chksum; ...data...; MSGSIZE-1=SLAVE_ADDRESS
byte     sendarray[MSGSIZE];

volatile int8_t  flag=0;


//=====================================================================================
//=====================================================================================
void setup() {
   int32_t  i=0;

   // Serial terminal window
   i=115200;
   Serial.begin(i);
   Serial.print("Serial started, baud=");
   Serial.println(i);

   // Wire (i2c)
   Wire.begin(SLAVE_ADDRESS);     // start Arduino as a I2C slave, addr=0x04 (7-bit coded)
   
   Wire.onReceive(receiveData );  // event when master array is sent
   Wire.onRequest(sendData );     // event when master requests array to read
   
   memset(sendarray, 0, sizeof(sendarray) );  // init send- and recv arrays
   memset(recvarray, 0, sizeof(recvarray) );   
   
   Serial.print("I2C init: my slave address= ");
   Serial.println(SLAVE_ADDRESS);
   Serial.println("I2C init: done.");
   Serial.println();
   
   Serial.println("setup(): done.");   

}


//=====================================================================================


uint8_t  calcchecksum(uint8_t array[]) {   
  int32_t  sum=0;
  for(int i=2; i<MSGSIZE; ++i) sum+=(array[i]);
  return (sum & 0x00ff);
}

//=====================================================================================

void loop()
{
   char sbuf[128];

   Serial.println(); Serial.println();

   // do something with the received data
   // and then do something to build the sendarray [3]...[MSG_SIZE-2]
   
   if (flag==1) {
       //debug
       sendarray[4] +=1;   
   }

   sendarray[0] = 0xff;                        // 0 = start: 0xff == msg start flag
   sendarray[2] = flag;                        // 2 = send back msg error flag   
   sendarray[MSGSIZE-1] = SLAVE_ADDRESS;       // end of array: ID check     
   
   sendarray[1] = calcchecksum(sendarray);     // 1 = calc new chksum
   flag=0;   
   
   // debug output
   sprintf(sbuf, "Sendarr[4]=%4d,   [5]=%4d,   Recvarr[4]=%4d,  [5]=%4d",
                  sendarray[4], sendarray[5],  recvarray[4],    recvarray[5]) ;
   Serial.println(sbuf);

   delay(1);                                     // short break for the cpu and the bus
}


//=====================================================================================

void receiveData(int byteCount) {
    int32_t i;
    byte val;

    while(Wire.available()<MSGSIZE) ;           // wait for all bytes to complete
    i=0;                                        // init counter var
    while(Wire.available()&& (i<MSGSIZE) )      // read all recv array bytes
    {
      val=Wire.read();
      recvarray[i++]=val;
    }
   
    // check for transmission error
    if(  (recvarray[0]  == 0xff)
      && (recvarray[1]  == calcchecksum(recvarray))
      && (recvarray[MSGSIZE-1] == SLAVE_ADDRESS  ) )
         flag=1;        // data ok
    else
         flag=127;      // data faulty => handle rcv-error => flag =127
}

//=====================================================================================

void sendData(){
  // Wire.write writes data from a slave device in response to a request from a master
  Wire.write(sendarray, MSGSIZE);    // send own byte array back to master..
}

Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 5399
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Re: Quick Guide für Raspberry Pi: C/C++ mit Geany für Dummies (Baustelle)

Beitragvon HaWe » 24. Dez 2015 12:31

Platzhalter...

Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 5399
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Quick Guide für Raspberry Pi: C/C++ mit Geany für Dummies

Beitragvon HaWe » 24. Dez 2015 12:31

i2c Sensoren: Source Code Examples in C/C++ für den Raspi:

(vgl. auch: http://www.robot-electronics.co.uk/htm/ ... amples.htm )

( I2C ) CMPS11 (IMU = 3D-Gyroscope, 3D-Compass, 3D-Accelerometer):
Interface: I2C oder auch UART möglich
I2C Bus speed: STANDARD + FAST-I2C (100-400kHz, getestet)

Bild
cmps11-mode.jpg

http://www.hobbytronics.co.uk/cmps11-tilt-compass
http://www.robot-electronics.co.uk/htm/cmps11i2c.htm

Code: Alles auswählen

/*
 * CMPS11 IMU
 * 3D gyro + 3D compass + 3D accelerometer
 * author: originally by James Henderson for Arduino
 * ported to Raspberry Pi code by HaWe
 * test demo
 * ver 0001a
 *
 */

#include <unistd.h>
#include <errno.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>

#include <wiringPi.h>
#include <wiringPiI2C.h>
 
// CMPS11 IMU
#define CMPS11_ADDR 0x60
int     cmps11;


int main() {
   unsigned char  ver, high_byte, low_byte, angle8;
   signed char    pitch, roll;
   int    angle16;   
   char sbuf[100];
   
   cmps11 = wiringPiI2CSetupInterface("/dev/i2c-1", 0x60);
   ver    =  wiringPiI2CReadReg8 (cmps11, 0) ;   

   sprintf(sbuf, "\n  CMPS11 - fw version: %3d \n\n", ver);    //
   printf(sbuf);
 
   while(1) {
           
     angle8    = wiringPiI2CReadReg8 (cmps11, 1) ;
     high_byte = wiringPiI2CReadReg8 (cmps11, 2) ;
     low_byte  = wiringPiI2CReadReg8 (cmps11, 3) ;
     pitch     = wiringPiI2CReadReg8 (cmps11, 4) ;
     roll      = wiringPiI2CReadReg8 (cmps11, 5 ) ;
     
     angle16 = high_byte;                 // Calculate 16 bit angle
     angle16 <<= 8;
     angle16 += low_byte;
       
     sprintf(sbuf, "roll: %3d ", roll);    // Display roll data
     printf(sbuf);
   
     sprintf(sbuf, "    pitch: %3d ", pitch);      // Display pitch data
     printf(sbuf);
   
     sprintf(sbuf, "    angle full: %d.%d ", angle16/10, angle16%10);     // Display 16 bit angle with decimal place
     printf(sbuf);
 
     sprintf(sbuf, "    angle 8: %3d ", angle8);      // Display 8bit angle
     printf(sbuf);
     printf("\n");
     printf("\n");
     
     delay(100);                           // Short delay before next loop
         
  }

  return (0);
}

Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 5399
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Re: Quick Guide für Raspberry Pi: C/C++ mit Geany für Dummies (Baustelle)

Beitragvon HaWe » 22. Jan 2016 20:07

( I2C ) Real Time Clock RTC DS3231 :

RTC ds3231-real-time-clock.jpg


http://tronixstuff.com/2014/12/01/tutor ... h-arduino/

angelehnt an Arduino Sketch Code: viewtopic.php?f=78&t=8491&start=15#p67456

Code: Alles auswählen

/*
 *
 * RTC DS3231
 *
 * test demo
 * taken from http://tronixstuff.com/2014/12/01/tutorial-using-ds1307-and-ds3231-real-time-clock-modules-with-arduino/
 * ported to Raspberry Pi by HaWe, 2016
 * ver 0001
 *
 */
 
 
#include <string.h>
#include <unistd.h>
#include <errno.h>
#include <stdio.h>
#include <stdint.h>
#include <stdlib.h>
#include <linux/i2c-dev.h>
#include <sys/ioctl.h>
#include <fcntl.h>
#include <unistd.h>

#include <wiringPi.h>
#include <wiringPiI2C.h>

#define  byte  uint8_t
 
// RTC DS3231
#define ADDR_RTCDS3231 0x68
int     frtcds3231;



//=====================================================================================
// Convert normal decimal numbers to binary coded decimal
//=====================================================================================
byte decToBcd(byte val) {  return( (val/10*16) + (val%10) );  }


//=====================================================================================
// Convert binary coded decimal to normal decimal numbers
//=====================================================================================
byte bcdToDec(byte val)  {  return( (val/16*10) + (val%16) ); }


//=====================================================================================




void setDS3231time( byte year, byte month, byte dayOfMonth, byte hour, byte
minute, byte second, byte dayOfWeek)
{
  // sets time and date data to DS3231 
 
  wiringPiI2CWriteReg8(frtcds3231, 0, decToBcd(second));      // set seconds
  wiringPiI2CWriteReg8(frtcds3231, 1, decToBcd(minute));      // set minutes
  wiringPiI2CWriteReg8(frtcds3231, 2, decToBcd(hour));        // set hours
  wiringPiI2CWriteReg8(frtcds3231, 3, decToBcd(dayOfWeek));   // ( 1=Sunday, 7=Saturday)
  wiringPiI2CWriteReg8(frtcds3231, 4, decToBcd(dayOfMonth));  // set dayOfMonth (1 to 31)
  wiringPiI2CWriteReg8(frtcds3231, 5, decToBcd(month));       // set month
  wiringPiI2CWriteReg8(frtcds3231, 6, decToBcd(year));        // set year (0 to 99)
   
}


//=====================================================================================



int main() {
   int  year, month, dayOfMonth, hour, minute, second, dayOfWeek;   
   int i=0, check;
   char sbuf[100];   

   // frtcds3231 = wiringPiI2CSetupInterface( "/dev/i2c-0",  ADDR_RTCDS3231 );     // i2c-0
   frtcds3231 = wiringPiI2CSetupInterface( "/dev/i2c-1",  ADDR_RTCDS3231 );    // i2c-1   
   
   printf(" RTC DS3231 \n");
   printf("Set new Date/Time:   enter 1\n");
   printf("else:   display time\n\n");

   i = getchar();
   
   //debug
   //printf("%d \n", i);
   
   while (i=='1') {
      // get string yy mm dd hh mm ss dw : gets() ?
      printf("yy mm dd hh mm ss dw (DayOfWeek) \n");
      check=scanf("%d %d %d %d %d %d %d", &year, &month, &dayOfMonth,  &hour, &minute, &second, &dayOfWeek);
     
      getchar();
      printf("check=%d\n", check);
     
      if(check==7) {     
       printf("%d \n", year);
       printf("%d \n", month);
       printf("%d \n", dayOfMonth);
       printf("%d \n", hour);
       printf("%d \n", minute);
       printf("%d \n", second);
       printf("%d \n", dayOfWeek);
         setDS3231time( year, month, dayOfMonth, hour, minute, second, dayOfWeek );
      }             
     
      printf(" RTC DS3231 \n");
      printf("Set new Date/Time:   enter 1\n");
      printf("else:   display time\n\n");
      i=0;
      i = getchar();
           
   }
   

 
   while(1) {
     second =     bcdToDec(wiringPiI2CReadReg8 (frtcds3231, 0) & 0x7f );
     minute =     bcdToDec(wiringPiI2CReadReg8 (frtcds3231, 1) );
     hour =       bcdToDec(wiringPiI2CReadReg8 (frtcds3231, 2) & 0x3f );
     dayOfWeek =  bcdToDec(wiringPiI2CReadReg8 (frtcds3231, 3) );
     dayOfMonth = bcdToDec(wiringPiI2CReadReg8 (frtcds3231, 4) );
     month =      bcdToDec(wiringPiI2CReadReg8 (frtcds3231, 5) );
     year =       bcdToDec(wiringPiI2CReadReg8 (frtcds3231, 6) ); 
    -
     sprintf(sbuf, "20%02d/%02d/%02d  %02d:%02d:%02d", year, month, dayOfMonth, hour, minute, second);
     printf(sbuf);
     
     printf(" Day of week %1d: ", dayOfWeek);
     switch(dayOfWeek){
     
     case 1:
       printf("Sunday");
       break;
     case 2:
       printf("Monday");
       break;
     case 3:
       printf("Tuesday");
       break;
     case 4:
       printf("Wednesday");
       break;
     case 5:
       printf("Thursday");
       break;
     case 6:
       printf("Friday");
       break;
     case 7:
       printf("Saturday");
       break;
     }
     printf("\n");      
     
     delay (1000);        
     
          
  }

  return (0);
}
//=====================================================================================
//=====================================================================================


20160807_153100.jpg


Man kann jetzt die RTC zur Synchronisierung der Systemzeit wahlweise mit der Internet- oder der RTC-Zeit verwenden:
http://www.roboternetz.de/community/thr ... post626041

Code: Alles auswählen

if (system("ping -c1 -s1 www.google.com"))
    {
        cout<<"There is no internet connection  \n";
}

Code: Alles auswählen

if (system("ping -c1 -s1 www.google.com"))
    {
        cout<<"There is no internet connection  \n";
}



Einbinden der RTC in den Kernel
(Zeit wird von RTC gelesen, nicht vom Internet Server):

sudo bash
sudo leafpad /etc/rc.local

Code: Alles auswählen

# vor exit:
echo ds3231 0x68 > /sys/class/i2c-adapter/i2c-1/new_device
sudo hwclock -s

#sudo bash beenden mit:
exit

Benutzeravatar
HaWe
Administrator
Administrator
Beiträge: 5399
Registriert: 11. Jan 2006 21:01
Wohnort: ein kleiner Planet in der Nähe von Beteigeuze

Re: Quick Guide für Raspberry Pi: C/C++ mit Geany für Dummies (Baustelle)

Beitragvon HaWe » 22. Jan 2016 20:07

( I2C ) Adafruit TSL2561 Digital Light Sensor :
(Adafruit TSL2561 Digital Luminosity/Lux/Light Sensor)

Bild
https://www.adafruit.com/product/439

Driver Lib: https://github.com/lexruee/tsl2561

Installation:

Code: Alles auswählen

apt-get -install git
# clone  repository:
git clone git://github.com/lexruee/tsl2561.git


Beispielcode, gibt 5 LUX Werte aus:

Code: Alles auswählen

#include "tsl2561.h"
#include <stdlib.h>
#include <stdio.h>
#include <unistd.h>

int main(int argc, char **argv) {
    int address = 0x39;
    char *i2c_device = "/dev/i2c-1";

    void *tsl = tsl2561_init(address, i2c_device);
    tsl2561_enable_autogain(tsl);
    tsl2561_set_integration_time(tsl, TSL2561_INTEGRATION_TIME_13MS);

    if(tsl == NULL){ // check if error is present
        exit(1);
    }

    int c;
    long lux;
    for(c = 0; c < 5; c++){
        lux = tsl2561_lux(tsl);
        printf("lux %lu\n", lux);
        usleep(3 * 1000 * 1000);
    }

    tsl2561_close(tsl);
    i2c_device = NULL;
    return 0;
}



Zurück zu „allgemeine / Nicht-Lego-Robotik und Elektronik“

Wer ist online?

Mitglieder in diesem Forum: 0 Mitglieder und 5 Gäste

Lego Mindstorms EV3, NXT und RCX Forum : Haftungsauschluss