Hallo,
es sieht nicht so gut aus. Anbei meine aktuellen Testcodes, wo 240 Bytes hin und zurück geschickt und verglichen werden.
MEGA:
Code:
// Wire Slave Receiver
// by Nicholas Zambetti <http://www.zambetti.com>
// Demonstrates use of the Wire library
// Receives data as an I2C/TWI slave device
// Refer to the "Wire Master Writer" example for use with this
// Created 29 March 2006
// This example code is in the public domain.
#include <Wire.h>
#define REGSIZE 240
byte rspeicher[REGSIZE];
byte wspeicher[REGSIZE];
byte puffer[32];
byte Register=1;
byte rdblock=0;
byte wrblock=0;
byte pos=0;
byte fertig=0;
long dg=0;
long timeout=0;
void setup() {
Wire.begin(4); // join I2C bus with address #8
Wire.onReceive(receiveEvent); // register event
Wire.onRequest(requestEvent); // register event
Serial.begin(57600); // start serial for output
Serial.println();
Serial.println("Starte I2C-Test");
}
void loop() {
byte i=0;
delay(100);
timeout++;
if (timeout==90){
timeout=0;
Wire.begin(4);
Serial.println("TimeOut!");
dg=0;
}
if (fertig !=0){
fertig=0;
timeout=0;
dg++;
Serial.println(dg);
for (i=0;i<REGSIZE;i++){
wspeicher[i]=rspeicher[i];
/* Serial.print(rspeicher[i]);
Serial.print (" ");*/
}
// Serial.println();
}
}
// function that executes whenever data is received from master
// this function is registered as an event, see setup()
void receiveEvent(int howMany) {
byte x=0;
if(howMany == 2){
rdblock = Wire.read();
if (rdblock<=240){
rspeicher[rdblock]=Wire.read();
}
if (rdblock==REGSIZE-1){
fertig=1;
}
}else{
if (howMany == 1){
x=Wire.read();
if (x >=10 && x <=250){
wrblock=x-10;
/* Serial.print("Lesebyte: ");
Serial.println(wrblock);*/
}
}else{
Serial.print ("Anzahl Daten: ");
Serial.println(howMany);
while (0 < Wire.available()) { //überflüssiges lesen
x=Wire.read();
}
}
}
}
// function that executes whenever data is requested by master
// this function is registered as an event, see setup()
void requestEvent() {
//Wire.write(speicher[Register],1);
puffer[0]=wrblock;
puffer[1]=wspeicher[puffer[0]];
Wire.write(puffer,2);
/* Serial.print("Sendebyte: ");
Serial.println(puffer[0]);
/* Serial.print(", Wert: ");
Serial.println(puffer[1]);*/
}
Raspi HW:
Code:
// GCC -Wall -pthread -o /var/scripte/i2cmaster01 /var/scripte/i2cmaster01.c -lpigpio -lrt
// /var/scripte/i2cmaster01
//I2C mit pipgio
//peterfido
//V0.0.2
#include <signal.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <pigpio.h>
#define ADDRESS 0x04
#define MSGSIZE 240
char empfdata[MSGSIZE]; //
char senddata[MSGSIZE];
char commando[32];
int handle=0;
int handles=-1;
unsigned int laenge=0;
volatile sig_atomic_t done = 0;
void term(int signum)
{
done = 1;
/*
int res=0;
int dl=0;
if (handles >= 0){
for (dl=0;dl<handles;dl++){
res=i2cClose(dl);
printf("%d geschlossen: %d\n",dl, res);
}
}
gpioTerminate();
printf( "\nSIGINT wurde augeloest - Programm wird beendet\n" );
exit( 1 );*/
}
void schreiben() {
int res=0;
// int i=0;
int wrblock=0;
int Fehler=0;
for (wrblock=0;wrblock<MSGSIZE;wrblock++){
commando[0]=wrblock;
commando[1]=senddata[wrblock];
res=i2cWriteDevice(handle,commando,2);
if (res!=0){
printf("S I2C-Fehler: %d, Block: %d\n", res,wrblock);
Fehler++;
/* wrblock--;
usleep(15000);
if (Fehler==10){
break;
}*/
break;
}
usleep(15000);
}
/* printf("Gesendet:\n");
for(i=0;i<MSGSIZE;i++){
printf("%d ",senddata[i]);
}
printf("\n");
*/
}
void lesen() {
int res=0;
// int i=0;
int rdblock=0;
int Fehler=0;
for (rdblock=0;rdblock<MSGSIZE;rdblock++){
commando[0]=rdblock+10;
res=i2cWriteDevice(handle,commando,1);
if (res==0){
usleep(1000);
res=i2cReadDevice(handle,commando,2);
if (res==2){
// printf("Empfangene Daten: %d, Block: %d\n",res,rdblock);
if (rdblock==commando[0]){
empfdata[rdblock]=commando[1];
}
}else{
printf("E Fehler beim Blockeinlesen: %d, Block: %d\n", res,rdblock);
Fehler++;
rdblock--;
usleep(15000);
if (Fehler==10){
break;
}
break;
}
}else{
printf("E Fehler beim Leseblock schreiben %d, Block: %d\n", res,rdblock);
break;
}
}
/*
printf("Empfangen:\n");
for(i=0;i<MSGSIZE;i++){
printf("%d ",empfdata[i]);
}
printf("\n");
*/
}
int vergleichen()
{
unsigned int i=0;
int ret=0;
for (i=0;i<MSGSIZE;i++){
if (empfdata[i]!=senddata[i]){
ret=-1;
break;
}
}
return ret;
}
int main(int argc, char **argv)
{
int res=0;
int i=0;
long dg=1;
long maxdg=0;
unsigned int Fehler=0;
struct sigaction action;
memset(&action, 0, sizeof(struct sigaction));
action.sa_handler = term;
sigaction(SIGINT, &action, NULL);
sigaction(SIGTERM, &action, NULL);
if (gpioInitialise() < 0)
{
printf("Fehler beim Initialisieren von gpio!");
gpioTerminate();
}else{
handle=i2cOpen(1,ADDRESS,0);
if(handle>=0){
handles ++;
printf("\n\n\nStarte I2C-Test (%d)\n\n",handle);
while (!done)
{
srand(time(NULL));
for(i=0;i<MSGSIZE;i++){
senddata[i]=rand() % 255;
}
schreiben();
usleep(100000);
lesen();
usleep(100000);
if (vergleichen()==0){
printf("Daten OK %ld (%ld)\n",dg,maxdg);
Fehler=0;
dg++;
}else{
printf("***************************** Daten fehlerhaft %ld *****************************\n",dg);
Fehler++;
dg=0;
if (dg>maxdg){
maxdg=dg;
}
sleep(1);
if (Fehler==100){
break;
}
}
}
}else{
printf("E Fehler beim Oeffnen: %d\n", handle);
}
}
res=i2cClose(handle);
if (res!=0){
printf("E Fehler beim Schliessen: %d\n", res);
}else{
handles--;
printf("E Schliessen OK %d\n",handle);
}
gpioTerminate();
return 0;
}
Raspi BitBang:
Code:
// GCC -Wall -pthread -o /var/scripte/bbi2cmaster /var/scripte/bbi2cmaster.c -lpigpio -lrt
// /var/scripte/bbi2cmaster
//I2C mit pipgio
//peterfido
//V0.0.2
#include <signal.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <pigpio.h>
#define SDA 2
#define SCL 3
#define TAKT 100000
#define PAUSEN 5000
#define ADDRESS 0x04
#define MSGSIZE 240
char empfdata[MSGSIZE]; //
char senddata[MSGSIZE];
char commando[64];
char puffer[12];
unsigned int laenge=0;
volatile sig_atomic_t done = 0;
void term(int signum)
{
done = 1;
}
int I2CResetBus(void)
{
char i;
int res=0;
if(gpioRead(SDA) && gpioRead(SCL)) {
return 0;
}
gpioSetMode(SCL, PI_INPUT);
gpioSetMode(SDA, PI_INPUT);
gpioSetPullUpDown(SDA, PI_PUD_UP); // Sets SDA pull-up.
gpioSetPullUpDown(SCL, PI_PUD_UP); // Sets SDA pull-up.
usleep(50);
if(!gpioRead(SCL)) {
return -1; /* SCL wird extern auf Low gehalten, nix zu machen */
}
for(i = 0; i<9; i++) {
gpioSetMode(SCL, PI_OUTPUT);
gpioWrite(SCL, 0);
usleep(50);
gpioSetMode(SCL, PI_INPUT);
gpioSetPullUpDown(SCL, PI_PUD_UP); // Sets SDA pull-up.
usleep(50);
if(gpioRead(SDA)) {
break; /* SDA ist high STOP */
}
} /* for */
if(!gpioRead(SDA)) {
return -1;
}
commando[0]= 3; //stop
commando[1]= 0; // Fertig
res=bbI2CZip(SDA,commando,2,NULL,0);
if (res!=0){
printf("Fehler beim Reset!\n");
}
if(gpioRead(SDA) && gpioRead(SCL)){
return 0;
}else{
return -1;
}
}
void schreiben() {
int res=0;
// int i=0;
int wrblock=0;
int Fehler=0;
for (wrblock=0;wrblock<MSGSIZE;wrblock++){
commando[0]= 4; //'Adresse setzen ankündigen
commando[1]= ADDRESS; //'Adresse übergeben
commando[2]= 2; //start
commando[3]= 7; //'Bytes senden
commando[4]= 2; //'Anzahl
commando[5]= wrblock; //Block
commando[6]= senddata[wrblock]; //Wert
commando[7]= 3; //stop
commando[8]= 0; //keine weiteren Parameter
res=I2CResetBus();
res=bbI2CZip(SDA,commando,9,NULL,0);
res=I2CResetBus();
if (res!=0){
printf("S I2C-Fehler: %d, Block: %d\n", res,wrblock);
Fehler++;
wrblock--;
usleep(PAUSEN*3);
if (Fehler==10){
break;
}
}
usleep(PAUSEN);
}
/*
printf("Gesendet:\n");
for(i=0;i<MSGSIZE;i++){
printf("%d ",senddata[i]);
}
printf("\n");
*/
}
void lesen() {
int res=0;
// int i=0;
int rdblock=0;
int Fehler=0;
for (rdblock=0;rdblock<MSGSIZE;rdblock++){
commando[0]= 4; //'Adresse setzen ankündigen
commando[1]= 4; //'Adresse übergeben
commando[2]= 2; //start
commando[3]= 7; //'Bytes senden
commando[4]= 1; //'Anzahl
commando[5]= rdblock+10; //Byte
commando[6]= 2; //start
commando[7]= 6; //Bytes lesen
commando[8]= 2; //Anzahl
commando[9]= 3; //stop
commando[10]= 0; //keine weiteren Parameter
res=I2CResetBus();
res=bbI2CZip(SDA,commando,11,puffer,12);
res=I2CResetBus();
if (res==0){
if (puffer[0]==rdblock){
empfdata[rdblock]=puffer[1];
Fehler=0;
}else{
printf("E Falsche Blocknummer. Erwartet: %d, bekommen: %d, Wert: %d\n",rdblock,puffer[0],puffer[1]);
Fehler++;
rdblock--;
if (Fehler==10){
break;
}
}
}else{
printf("E Fehler beim Blockeinlesen. Block: %d\n",rdblock);
Fehler++;
rdblock--;
if (Fehler==10){
break;
}
}
usleep(PAUSEN);
}
printf("Empfangen:\n");
/* for(i=0;i<MSGSIZE;i++){
printf("%d ",empfdata[i]);
}
printf("\n");
*/
}
int vergleichen()
{
unsigned int i=0;
int ret=0;
for (i=0;i<MSGSIZE;i++){
if (empfdata[i]!=senddata[i]){
ret=-1;
break;
}
}
return ret;
}
int main(int argc, char **argv)
{
int res=0;
int i=0;
long dg=1;
long maxdg=0;
unsigned int Fehler=0;
struct sigaction action;
memset(&action, 0, sizeof(struct sigaction));
action.sa_handler = term;
sigaction(SIGINT, &action, NULL);
sigaction(SIGTERM, &action, NULL);
if (gpioInitialise() < 0)
{
printf("Fehler beim Initialisieren von gpio!");
gpioTerminate();
}else{
res=bbI2COpen(SDA,SCL,TAKT);
res=res+gpioSetMode(SDA, PI_INPUT); // Set SDA as input.
res=res+gpioSetMode(SCL, PI_INPUT); // Set SDA as input.
res=res+gpioSetPullUpDown(SDA, PI_PUD_UP); // Sets SDA pull-up.
res=res+gpioSetPullUpDown(SCL, PI_PUD_UP); // Sets SDA pull-up.
if(res==0){
printf("\n\n\nStarte I2C-Test\n\n");
while (!done)
{
srand(time(NULL));
for(i=0;i<MSGSIZE;i++){
senddata[i]=rand() % 255;
}
schreiben();
usleep(5000);
lesen();
usleep(5000);
if (vergleichen()==0){
printf("Daten OK %ld (%ld)\n",dg,maxdg);
Fehler=0;
dg++;
}else{
printf("***************************** Daten fehlerhaft %ld *****************************\n",dg);
Fehler++;
dg=0;
if (dg>maxdg){
maxdg=dg;
}
sleep(1);
if (Fehler==100){
break;
}
}
}
}else{
printf("E Fehler beim Oeffnen\n");
}
}
res=bbI2CClose(SDA);
if (res!=0){
printf("E Fehler beim Schliessen: %d\n", res);
}else{
printf("E Schliessen OK\n");
}
gpioTerminate();
return 0;
}
Mein Fazit:
Ich bleibe bei UART.
Lesezeichen