Ti posto il mio codice volentieri, ma prendilo con le pinze perchè non sono per niente esperto (anzi ogni commento è ben accetto!)
Come detto altrove il mio setup consiste in 4 moduli con ATtiny85 che aspettano di essere interrogati dal Master (per ora un Arduino Mega, per debug) e rispondono con la lettura di 2 pin analogici. Gli ATtiny85 non hanno Seriale HW, quindi utilizzo la Newsoftserial modificata (Grazie Leo..).
Il Mega per ora legge soltanto i dati in arrivo controllandone la qualità.
Non ho avuto tempo di provarlo bene, sto aspettando di rientrare a casa, ma ad una prima prova funzionava.
Cmq, Master su Arduino Mega:
int EN_PIN = 4;
int LED_PIN = 13;
int ind = 0;
char buf[8];
int dati[4][2];
void setup() {
pinMode(EN_PIN, OUTPUT);
Serial.begin(9600);
Serial1.begin(9600);
Serial.println("iniziamo!");
pinMode (LED_PIN, OUTPUT);
digitalWrite(EN_PIN, LOW);
}
void loop() {
// inviare req(address '1' to '4', richiesta '5' to '8')
req('1','5');
delay(100);
req('2','5');
delay(100);
req('3','5');
delay(100);
req('4','5');
delay(1000);
}
void req(char addr, char reqType) {
// Invia richiesta:
digitalWrite(EN_PIN, HIGH);
delay(10);
Serial1.write(2);
Serial1.write(addr);
Serial1.write(reqType);
Serial1.write(addr+reqType);
Serial1.write(3);
Serial.println("dati inviati..");
digitalWrite(EN_PIN, LOW);
// Lettura risposta:
if (Serial1.available()>0) {
Serial.println("La seriale c'e'..");
if (Serial1.read()==2) {
Serial.println("ricevuto 2");
for (int i=0; i<8; i++) {
buf[i] = Serial1.read();
}
ind = buf[0];
if (ind == addr) {
int sommaBytes = 0;
for (int k=0;k<5;k++) {
sommaBytes = sommaBytes + byte(buf[k]);
}
byte checksum = (buf[6] << 8 | buf[5]); //////////// prima era: int checksum = (buf[6] << 8 | buf[5]);
//////////// ma se buf[6] inizia per 1 checksum diventa negativo, e la comparazione con sommaBytes ritorna False.
if ((buf[7]==3)&&(sommaBytes==checksum)) {
Serial.println("Checksum and ETX ok!");
ind = ind-48;
Serial.print("Indirizzo : ");
Serial.println(ind);
Serial.println("SUM ok!");
Serial.println("ETX ok!");
Serial.print("Motore : ");
Serial.println(ind);
dati[ind][0] = (byte(buf[2]) << 8 | byte(buf[1]));
dati[ind][1] = (byte(buf[4]) << 8 | byte(buf[3]));
Serial.print(" Cella1 : ");
Serial.println(dati[ind][0]);
Serial.print(" Cella2 : ");
Serial.println(dati[ind][1]);
}
}
}
}
}
e Slave su ATtiny85:
#include <NewSoftSerial.h>
#include <icrmacros.h>
NewSoftSerial mySer (2, 0);
int EN_PIN = 1;
//int LED_PIN = 0;
int cella1 = 1012;
int cella2 = 1003;
char addr = '1';
int reqType;
char buf[4];
void setup() {
pinMode(EN_PIN, OUTPUT);
mySer.begin(9600);
//pinMode (LED_PIN, OUTPUT);
digitalWrite(EN_PIN, LOW);
}
void loop() {
while (mySer.available()==0) {
}
delay(10);
if (mySer.read()==2) {
for (int i=0; i<4; i++) {
buf[i] = mySer.read();
}
int ind = buf[0];
if (ind == addr) {
reqType = buf[1];
if ((buf[3]==3)&&(buf[0]+buf[1]==buf[2])) {
if (reqType == '5') {
invia();
}
}
}
}
}
void invia() {
digitalWrite(EN_PIN, HIGH);
delay(1);
mySer.write(2);
mySer.write(addr);
mySer.write(lowByte(cella1));
mySer.write(highByte(cella1));
mySer.write(lowByte(cella2));
mySer.write(highByte(cella2));
int checksum = (addr+lowByte(cella1)+highByte(cella1)+lowByte(cella2)+highByte(cella2));
mySer.write(lowByte(checksum));
mySer.write(highByte(checksum));
mySer.write(3);
digitalWrite(EN_PIN, LOW);
}
EDIT: lo scrivo solo se a qualcuno viene in mente di prendere spunto da questo codice, che c'è un piccolo errore nel Master. l'ho corretto e ho segnato il punto.
in più i delay sono da regolare a seconda della velocità di trasmissione. Quindi il codice così com'è non è affidabile al 100%.
Davide.