Hallo zusammen,
ich bin dabei eine einfache Kommunikation zwischen einem Arduino
(Adafruit WICED) und einem Beaglebone mit einem Ubuntu aufzubauen. Es
soll eine mehr oder weniger Realtime fähige Regelung entstehen. Der
Arduino soll dabei lediglich einige Sensorwerte einlesen (nimmt etwas 60
us Laufzeit in Anspruch), diese verrechnen und sie als eine
Integerzahl/Chararray über einen UART an den Beaglebone senden. Mit dem
BBB soll ausschließlich gelesen werden. Also nur 2 Leitungen. SIGNAL/GND
Der Testcode für den Arduino besteht aus dem Senden einer Zahl von
1-32000, die sich jede Millisekunde erhöhrt. D.h. nach etwa 32 sec
beginnt der uC von vorne die Daten zu übertragen. Dient mit der
Überprüfung ob ich wirklich die aktuellen Daten des uCs bekomme.
1 | int test = 1;
|
2 |
|
3 | void setup()
|
4 | {
|
5 | Serial.begin(115200);
|
6 | while (!Serial)
|
7 | {
|
8 | delay(1);
|
9 | }
|
10 | }
|
11 |
|
12 | void loop()
|
13 | Serial.println(test);
|
14 | test++;
|
15 | if(test >= 32000){
|
16 | test = 1;
|
17 | }
|
18 | delayMicroseconds(1000);
|
19 | }
|
Auf dem Beaglebone Black möchte ich diese nun Einlesen. Wollte dieses
mit der libserial machen. Ich wollte dieses eigentlich direkt über
termios machen und habe mich angefangen dort einzulesen. Bin aber auf
dem Weg an libserial hängengeblieben.
1 | #include <stdio.h>
|
2 | #include <time.h>
|
3 | #include <iostream>
|
4 | #include <SerialStream.h>
|
5 |
|
6 | using namespace std;
|
7 | using namespace LibSerial;
|
8 |
|
9 | const int LOOP_UPDATE = 1;
|
10 |
|
11 | int main()
|
12 | {
|
13 | double time_counter = 0;
|
14 | clock_t this_time = clock();
|
15 | clock_t last_time = this_time;
|
16 |
|
17 |
|
18 | const int buffersize = 8;
|
19 | char input_buffer[buffersize];
|
20 | string tmpBuffer = "";
|
21 |
|
22 | LibSerial::SerialStream serial_uart_1;
|
23 | serial_uart_1.SetBaudRate(SerialStreamBuf::BAUD_115200);
|
24 | serial_uart_1.SetCharSize(SerialStreamBuf::CHAR_SIZE_8);
|
25 | serial_uart_1.SetParity(SerialStreamBuf::PARITY_NONE);
|
26 | serial_uart_1.SetFlowControl(SerialStreamBuf::FLOW_CONTROL_NONE);
|
27 | serial_uart_1.SetNumOfStopBits(1);
|
28 |
|
29 | serial_uart_1.Open("/dev/ttyACM0"); //Test auf dem Computer über USB
|
30 |
|
31 | while (1)
|
32 | {
|
33 | this_time = clock();
|
34 | time_counter += (double)(this_time - last_time);
|
35 | last_time = this_time;
|
36 |
|
37 | /*Auslesen des UARTS mit 10 Samples per sec*/
|
38 | if(time_counter > (double)(LOOP_UPDATE * CLOCKS_PER_SEC/10))
|
39 | {
|
40 | time_counter -= (double)(LOOP_UPDATE * CLOCKS_PER_SEC/10);
|
41 | serial_uart_1.read(input_buffer, buffersize);
|
42 | tmpBuffer = string(input_buffer);
|
43 | cout << tmpBuffer;
|
44 | }
|
45 | }
|
46 |
|
47 | serial_uart_1.Close();
|
48 | return(0);
|
49 | }
|
Ich habe mit UART noch nicht gearbeitet und denke, dass ich noch einige
grundlegende Verständnisprobleme damit habe. Ich habe mir das
folgendermaßen vorgestellt:
Ich sende alle 200 us die Daten (z.B. als Hex bei max (int)32000 wäre
man mit 2 Bytes fertig). Auf dem Beaglebone wollte ich dann in der Loop
etwa im 1 ms Zyklus die Daten einfach direkt dem Stream entnehmen. Der
UART Port fängt an zu empfangen wartet auf den Startbit und überträgt
die 2 Bytes und wäre damit fertig. So war meine Vorstellung.
Bei meinem Code lese ich jedoch nur den Buffer aus d.h. in jeder Loop
auf dem Beaglebone spring er nur einen digit hoch. Heißt für mich, dass
der uC den Buffer befüllt und der BBB sich mit dem "veralteten" Daten
beschäftigt. "Der uC läuft dem BBB einfach weg". Bei 0.1 s Looptime im
Test müsste ich jedoch Wertänderungen in 100ern sehen. Dazu kommen noch
die gelegentlichen Lücken.
Bedeutet für mich, dass der uC schon seine Arbeit richtig verrichtet ich
auf der BBB Seite jedoch den Buffer flute und mich mit dem Abarbeiten
dieser Daten beschäftige, obwohl schon lange neue Daten vom uC
bereitliegen müssten. Ich weiß nicht genau wo ich genau anfangen soll
den Fehler zu suchen.
Könnte mir jemand diesbezüglich Tipps geben, wo meine gedanklichen
Fehler liegen?
Viele Grüße
Dieter