Forum: Mikrocontroller und Digitale Elektronik Arduino: Möchte erhaltene Daten über Serialport im Arduino Flashspeicher schreiben und auslesen


von p. p. (intergo)


Lesenswert?

Hallo, habe ein kleines Problem und zwar:

Habe mir eine GUI geschrieben womit ich über die Serielle Schnittstelle 
vom Arduino Daten empfange und zu ihm senden kann.
Das fdunktioniert auch soweit.
Das problem ist, ich sende ja kommandos als String an dem Arduino und 
dieses sollen in einem Array gespeichert werden und dann den Array in 
den Flashspeicher speichern, und später sollen diese wieder ausgelesen 
werden und auf Abruf an die GUI übertragen werden, doch es klappt leider 
nicht.
Versuche es Studenlang, aber es geht nicht. Bitt um Hilfe.
Hier ist mein COde:
1
/*Code zum Empfangen und Senden von Daten über Serialport (GUI<-> Arduino) */
2
#include <avr/pgmspace.h> 
3
/*prog_char string_0[] PROGMEM = "hallo";
4
prog_char string_1[] PROGMEM = "luigi wie geht es dir";
5
6
7
PROGMEM const char *string_table[] =
8
{
9
  string_0,
10
  string_1
11
};*/
12
char Word[30];
13
14
15
//Globale Variablen
16
/*----------Varaiblen fürs Senden---------------------------------------*/
17
int ist_senden= 1; //Falls Arduino an GUI sendet
18
const int ledPin1= 22;  //Mit Digital PIN 22 verbundene Led  (senden)-(rote led)
19
/*----------------------------------------------------------------------*/
20
21
/*----------Variablen fürs Empfangen------------------------------------*/
22
const int ledPin2= 23; //MIt Digital PIN 23 verbundene Led (empfangen)-(gelbe led)
23
int ist_receive=2; //Falls Arduino von GUI empfangen soll
24
char myChar;
25
int i;
26
27
int k;
28
//prog_uchar signMessage[]  PROGMEM={};
29
30
/*----------------------------------------------------------------------*/
31
/*-----------Auswahlvariable für Swtich-Case----------------------------*/
32
int inByte=0; //Variable wo das Empfangene abgespeichert wird(als Byte)
33
/*----------------------------------------------------------------------*/
34
35
/*----------- Hier beginnt das Programm---------------------------------*/
36
37
void setup()
38
{
39
  Serial.begin(9600); //Serialport öffnen mit baudrate 9600
40
  pinMode(ledPin1, OUTPUT); //ledPin1(senden LED), wird als Output gesetzt
41
  pinMode(ledPin2, OUTPUT); //ledPin2 (empf. LED), wird als Output gesetzt
42
  
43
}
44
45
46
void loop()
47
{
48
  if (Serial.available() > 0) //Prüfen , ob mindestens ein Zeichen im Port vorhanden ist (Hier prüfe ich , ob senden oder EMpfangen)
49
  {
50
    inByte = Serial.read(); //lese zeichen au und speichere in chr vom typ char
51
     
52
  
53
  switch (inByte){
54
55
    /*Senden der Daten von Arduino zur GUI*/    
56
    case 1: 
57
              
58
              blink_receive();
59
              
60
                myChar= pgm_read_byte_near(signMessage + k);
61
                //strcpy_P(buffer, (char*)pgm_read_word(&(signMessage[i])));
62
                Serial.print(myChar);
63
                Serial.write(13); //carriage return linefeed
64
                delay(500);
65
              
66
              blink_receive();
67
              
68
              
69
              break; //beende case 1
70
    
71
    /* Von GUI empfangen*/          
72
    case 2:
73
              if (Serial.available() > 0)
74
              {
75
               Word[i] = Serial.read();
76
                
77
                prog_uchar signMessage[]  PROGMEM = {Word[i]};
78
               
79
                
80
              } 
81
                blink_receive();
82
               
83
               break;
84
              
85
     
86
     
87
     //falls keine 1 oder 2
88
    
89
    /*default:
90
    
91
            if (Serial.available() > 0) //Prüfen , ob mindestens ein Zeichen im Port vorhanden ist (Hier prüfe ich , ob senden oder EMpfangen)
92
            {
93
    
94
              chr = Serial.read(); //lese zeichen au und speichere in chr vom typ char
95
              wahl = int(chr); //Umwandeln in lesbares
96
            }
97
            
98
            
99
           } */
100
           
101
}
102
}
103
}
104
105
106
/*---------------------funktion für das Blinken beim senden an GUI----------------------*/
107
/*---------------------Blink funktion 0,5sek an und 0,5sek aus--------------------------*/
108
109
/*Rote LED*/
110
111
void blink_send()
112
{
113
  
114
  digitalWrite(ledPin1, HIGH); //leuchtet
115
  delay(500); //leuchtet 0,5 sek
116
  digitalWrite(ledPin1, LOW); //aus
117
  delay(500);
118
  
119
}
120
/*-------------------------------------------------------------------------------------*/
121
122
123
/*----------Funktion die in Case 2 aufegrufen wird, damit LED blinkt-------------------*/
124
125
/*gelbe LED*/
126
127
void blink_receive()
128
{
129
  digitalWrite(ledPin2, HIGH); //leuchtet
130
  delay(500); // 0,5sek an
131
  digitalWrite(ledPin2,LOW); //aus
132
  delay(500); //0,5sek aus
133
  
134
}  
135
 
136
/*-------------------------------------------------------------------------------------*/

Würde mich über eure Hilfe freuen.
Danke

von Wusel D. (stefanfrings_de)


Lesenswert?

> prog_uchar signMessage[]  PROGMEM = {Word[i]};

Das geht nicht. Du hast hier innerhalb der loop Funktion eine lokale 
Variable deklariert. Lokale Variablen liegen IMMER im Stack, also im 
RAM. Die Schlüsselwörter prog und PROGMEM (doppelt gemoppelt) 
widersprechen dem.

Weiterhin hat das Array signMessage[] keine definierte Größe. Ich 
schätze, der Compiler macht daraus ein Array mit Größe 0, also nix.

Die Syntax {...} bei der Zuweisung zu einem Array erfordert meines 
wissens nach einen konstanten Ausdruck.

Um auf die Daten im Programmspeicher zuzugreifen, braucht man besondere 
Assembler Befehle, die in der AVR C Library netterweise in Funktionen 
gekapselt wurden. Sie sind hier dokumentiert: 
http://www.nongnu.org/avr-libc/user-manual/group__avr__pgmspace.html

Aber das bringt Dich so nicht weiter, denn der Programmspeicher ist 
read-only.

Du solltest Die Daten im EEPROM ablegen. Auch dafür gibt es eine 
Library: 
http://www.nongnu.org/avr-libc/user-manual/group__avr__eeprom.html

Beachte, dass dass EEPROM im Gegensatz zu RAM nur begrenzt oft 
beschreibbar ist.

von p. p. (intergo)


Lesenswert?

HI ja problem is, dass mit dem strings im EEPROM klappt icht so wie ich 
es mir vorstelle.

Das mit dem Schreibeen und Auslesen des Flashspeichers geht nur, wenn 
ich festgelegte Strings dort eintragen möchte
Hier der code:
1
/*Code zum Empfangen und Senden von Daten über Serialport (GUI<-> Arduino) */
2
#include <avr/pgmspace.h> 
3
char message;
4
int i;
5
6
7
prog_char string_0[] PROGMEM = "hallo";
8
prog_char string_1[] PROGMEM = "test wie geht es dir";
9
10
11
PROGMEM const char *string_table[] =
12
{
13
  string_0,
14
  string_1
15
};
16
char buffer[30];
17
18
19
//Globale Variablen
20
/*----------Varaiblen fürs Senden---------------------------------------*/
21
int ist_senden= 1; //Falls Arduino an GUI sendet
22
const int ledPin1= 22;  //Mit Digital PIN 22 verbundene Led  (senden)-(rote led)
23
/*----------------------------------------------------------------------*/
24
25
/*----------Variablen fürs Empfangen------------------------------------*/
26
const int ledPin2= 23; //MIt Digital PIN 23 verbundene Led (empfangen)-(gelbe led)
27
int ist_receive=2; //Falls Arduino von GUI empfangen soll
28
29
30
31
/*----------------------------------------------------------------------*/
32
/*-----------Auswahlvariable für Swtich-Case----------------------------*/
33
int inByte=0; //Variable wo das Empfangene abgespeichert wird(als Byte)
34
/*----------------------------------------------------------------------*/
35
36
/*----------- Hier beginnt das Programm---------------------------------*/
37
38
void setup()
39
{
40
  Serial.begin(9600); //Serialport öffnen mit baudrate 9600
41
  pinMode(ledPin1, OUTPUT); //ledPin1(senden LED), wird als Output gesetzt
42
  pinMode(ledPin2, OUTPUT); //ledPin2 (empf. LED), wird als Output gesetzt
43
  
44
}
45
46
47
void loop()
48
{
49
  if (Serial.available() > 0) //Prüfen , ob mindestens ein Zeichen im Port vorhanden ist (Hier prüfe ich , ob senden oder EMpfangen)
50
  {
51
    inByte = Serial.read(); //lese zeichen au und speichere in chr vom typ char
52
     
53
  
54
  switch (inByte){
55
56
    /*Senden der Daten von Arduino zur GUI*/    
57
    case 1: 
58
              
59
              blink_receive();
60
              for (int i=0; i<3; i++)
61
              {
62
                strcpy_P(buffer, (char*)pgm_read_word(&(string_table[i])));
63
                Serial.write( buffer);
64
                Serial.write(13);
65
                delay(500);
66
              }
67
              blink_receive();
68
              
69
                
70
                
71
                
72
             
73
              
74
              break; //beende case 1
75
    
76
    /* Von GUI empfangen*/          
77
    case 2:
78
              if (Serial.available() > 0)
79
              {
80
                
81
              } 
82
                blink_receive();
83
               
84
               break;
85
              
86
     
87
     
88
     //falls keine 1 oder 2
89
    
90
    /*default:
91
    
92
            if (Serial.available() > 0) //Prüfen , ob mindestens ein Zeichen im Port vorhanden ist (Hier prüfe ich , ob senden oder EMpfangen)
93
            {
94
    
95
              chr = Serial.read(); //lese zeichen au und speichere in chr vom typ char
96
              wahl = int(chr); //Umwandeln in lesbares
97
            }
98
            
99
            
100
           } */
101
           
102
}
103
}
104
}
105
106
107
/*---------------------funktion für das Blinken beim senden an GUI----------------------*/
108
/*---------------------Blink funktion 0,5sek an und 0,5sek aus--------------------------*/
109
110
/*Rote LED*/
111
112
void blink_send()
113
{
114
  
115
  digitalWrite(ledPin1, HIGH); //leuchtet
116
  delay(500); //leuchtet 0,5 sek
117
  digitalWrite(ledPin1, LOW); //aus
118
  delay(500);
119
  
120
}
121
/*-------------------------------------------------------------------------------------*/
122
123
124
/*----------Funktion die in Case 2 aufegrufen wird, damit LED blinkt-------------------*/
125
126
/*gelbe LED*/
127
128
void blink_receive()
129
{
130
  digitalWrite(ledPin2, HIGH); //leuchtet
131
  delay(500); // 0,5sek an
132
  digitalWrite(ledPin2,LOW); //aus
133
  delay(500); //0,5sek aus
134
  
135
}  
136
 
137
/*-------------------------------------------------------------------------------------*/


Komme einfach nicht weiter

von PittyJ (Gast)


Lesenswert?

Auf dem Ethernet-Shield ist auch ein SD-Kartenslot.
Mit der SD-Bibliothek kann man darauf zugreifen. So kann ganz einfach 
langfristig gespeichert werden.

von p. p. (intergo)


Lesenswert?

hmm ok.
Und über EEPROM wäre es auch gut, aber ich bekomme es nicht hin es 
auszulesen bzw reinzuspeichern.

Häng da fest

von PittyJ (Gast)


Lesenswert?

Die Eprom-Funktion werden in der Referenz beschrieben.
 http://arduino.cc/en/Reference/EEPROM
Was geht denn da nicht?

von p. p. (intergo)


Lesenswert?

bekomme es von der Syntax nicht hin, dass ich über die for schleife 
werte auslese über serialport und diese, eins nach den anderen in den 
eeprom speichere

von PittyJ (Gast)


Lesenswert?


von p. p. (intergo)


Lesenswert?

Ne esist nicht so, dass ich kein C kann.
Ich kann es nicht umsetzen, da ich den Wald vor lauter bäume niht mehr 
sehe.

Jetzt geht es teilweise , aber bekomme nur einen Wert aus dem eeprom 
ausgelesen, die darauffolgenden garnicht mehr.
Könnt ihr vllt einen blick drauf werfen?

Hier der Code:
1
/*Code zum Empfangen und Senden von Daten über Serialport (GUI<-> Arduino) */
2
3
//Globale Variablen
4
/*----------Varaiblen fürs Senden---------------------------------------*/
5
int ist_senden= 1; //Falls Arduino an GUI sendet
6
const int ledPin1= 22;  //Mit Digital PIN 22 verbundene Led  (senden)-(rote led)
7
/*----------------------------------------------------------------------*/
8
9
/*----------Variablen fürs Empfangen------------------------------------*/
10
const int ledPin2= 23; //MIt Digital PIN 23 verbundene Led (empfangen)-(gelbe led)
11
int ist_receive=2; //Falls Arduino von GUI empfangen soll
12
13
#include <EEPROM.h>
14
15
char chr;
16
int addr=0; //inizialadresse EEPROM -> 4kbyte -> 4096byte , also von 0-4093
17
char valEE;
18
19
/*----------------------------------------------------------------------*/
20
/*-----------Auswahlvariable für Swtich-Case----------------------------*/
21
int inByte=0; //Variable wo das Empfangene abgespeichert wird(als Byte)
22
/*----------------------------------------------------------------------*/
23
24
/*----------- Hier beginnt das Programm---------------------------------*/
25
26
27
28
void setup()
29
{
30
  Serial.begin(9600); //Serialport öffnen mit baudrate 9600
31
  pinMode(ledPin1, OUTPUT); //ledPin1(senden LED), wird als Output gesetzt
32
  pinMode(ledPin2, OUTPUT); //ledPin2 (empf. LED), wird als Output gesetzt
33
  
34
}
35
36
37
void loop()
38
{
39
  if (Serial.available() > 0) //Prüfen , ob mindestens ein Zeichen im Port vorhanden ist (Hier prüfe ich , ob senden oder EMpfangen)
40
  {
41
    inByte = Serial.read(); //lese zeichen au und speichere in chr vom typ char
42
     
43
  
44
  switch (inByte){
45
46
    /*Senden der Daten von Arduino zur GUI*/    
47
    case 1: 
48
    
49
              blink_send();
50
              /*Serial.write("Hallo, ich bin dein Arduino");
51
              Serial.write(13); //Carriage return, damit man in GUI untereinander eingetragen hat(Formatierung)
52
              delay(1500); //warte 1,5sek
53
              blink_send();
54
              Serial.write("Ich habe vor genau 1,5 sek hallo gesagt.");
55
              Serial.write(13);
56
              delay(1000); //warte 1 sek
57
              blink_send();
58
              Serial.write("Jetzt geht es von vorne los....");
59
              Serial.write(13);
60
              //delay(10); */
61
              
62
              valEE=EEPROM.read(addr);
63
              Serial.println(valEE);
64
              
65
             
66
              
67
              break; //beende case 1
68
    
69
    /* Von GUI empfangen*/          
70
    case 2:
71
              if (Serial.available() > 0)
72
              {
73
                chr=Serial.read();
74
                EEPROM.write(addr, chr);
75
                addr=addr+1;
76
                if(addr=4096) addr=0;
77
                
78
                
79
              } 
80
                blink_receive();
81
               
82
               break;
83
              
84
     
85
     
86
     //falls keine 1 oder 2
87
    
88
    /*default:
89
    
90
            if (Serial.available() > 0) //Prüfen , ob mindestens ein Zeichen im Port vorhanden ist (Hier prüfe ich , ob senden oder EMpfangen)
91
            {
92
    
93
              chr = Serial.read(); //lese zeichen au und speichere in chr vom typ char
94
              wahl = int(chr); //Umwandeln in lesbares
95
            }
96
            
97
            
98
           } */
99
           
100
}
101
}
102
}
103
104
105
/*---------------------funktion für das Blinken beim senden an GUI----------------------*/
106
/*---------------------Blink funktion 0,5sek an und 0,5sek aus--------------------------*/
107
108
/*Rote LED*/
109
110
void blink_send()
111
{
112
  
113
  digitalWrite(ledPin1, HIGH); //leuchtet
114
  delay(500); //leuchtet 0,5 sek
115
  digitalWrite(ledPin1, LOW); //aus
116
  delay(500);
117
  
118
}
119
/*-------------------------------------------------------------------------------------*/
120
121
122
/*----------Funktion die in Case 2 aufegrufen wird, damit LED blinkt-------------------*/
123
124
/*gelbe LED*/
125
126
void blink_receive()
127
{
128
  digitalWrite(ledPin2, HIGH); //leuchtet
129
  delay(500); // 0,5sek an
130
  digitalWrite(ledPin2,LOW); //aus
131
  delay(500); //0,5sek aus
132
  
133
}  
134
 
135
/*-------------------------------------------------------------------------------------*/

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.