Go Down

Topic: Fehler bei zu vielen Strings? (Read 819 times) previous topic - next topic

Snail

Ich habe bei meinem Datenlogger ein komisches Problem (ständiger neustart, oder freeze). Konnte es jedoch schon gut eingrenzen.
Und zwar habe ich viel ausgaben alla   Serial.println("ne menge Text");
wenn ich da ein par Ausgaben wegnehme läuft das Programm wieder fehlerfrei.

Das Programm wird mit ca 22k Byte kompiliert.
Habe das Uno Board (ATmega328)

So ganz versteh ich den Hintergrund nicht. Gibt es vieleicht nur begrenzt Speicherplatz für Strings?

uwefed

#1
Oct 17, 2011, 10:12 pm Last Edit: Oct 18, 2011, 05:05 pm by uwefed Reason: 1
Es gibt begrenzten Speicherplatz (Ram) und basta. Die 2 Kbyte Ram werden vom Kontroller für seine internen Variablen genutzt ( Systemvariablen und Stack) und von allen anderen Variablen des Sketches.
Um Ram zu sparen kannst Du statische variablen ins Flash schreiben mit progmem www.arduino.cc/en/Reference/PROGMEM.
Wenn Du aber ohne Variablen arbeitest und nur
Serial.println("ne menge Text");
schreibst dürfte dies nicht viel Ram verbrauchen. [EDIT] falsche Annahme[/Edit](falls ich falsch liege, bitte korriegiert mich jemand).
Da der Compiler nicht kontrolliert, wieviel RAM gebraucht wird, passiert es, daß wenn mehr Ram benutzt wird als vorhanden ist, Speicherbereiche ungefragt überschrieben werden und alle möglichen Symptome auftreten.
Grüße Uwe

Snail

Hi Uwe
Danke für die Antwort, habe auch gedacht das diese Art keinen RAM Platz verbraucht.
Werde es mal mit progmem Versuchen wenn ich mich da eingelesen habe.

voithian

#3
Oct 18, 2011, 03:29 pm Last Edit: Oct 18, 2011, 03:36 pm by voithian Reason: 1
Hallo,

ich bin mir ziemlich sicher, dass auch bei der Variante mit

Serial.println("ne menge Text");

der String im Datenbereich abgelegt wird, auch wenn dafür keine Variable (mit einem eigenen Namen) existiert. Und Daten landen landen bei einem AVR halt standardmäßig erst einmal im RAM.

Zusätzliche Informationen zum Speichern von Daten im Program Space findet man unter folgendem Link:

http://www.nongnu.org/avr-libc/user-manual/pgmspace.html

Aus diesem Dokument stammen wohl auch die Informationen aus der von Uwe zitierten Arduino-Referenz.

@Snail: Ich würde vorschlagen, den "Monster-String" mit PROGMEM im Programm-Bereich abzulegen, aber dann musst du wohl zur Ausgabe mit Serial.Println() den Monster-String stückchenweise in einen Puffer zurückkopieren und stückchenweise ausgeben, da Serial.println() wahrscheinlich nicht mit dem ge"PROGMEM"ten Speicher direkt umgehen kann.

Und bei der Größe des Puffers solltest du natürlich wiederum nicht zu großzügig sein, denn RAM ist ein kostbar Gut  ;)

Leider hab' ich Moment keine Zeit, es selber auszuprobieren, aber aber wäre nett, wenn du uns mal deine Ergebnisse mitteilen würdest.

Gruß
Wolfgang

Andreas Watterott

Bei Serial.println("ne menge Text") landen die Daten im RAM des AVRs. Um die Daten im Flash abzuspeichern, müssen diese mit PROGMEM oder mit dem Makro PSTR("Mein Text") deklariert werden.
Hier gibt es auch eine Lib. um die Handhabung einfacher zu gestalten: http://arduiniana.org/libraries/flash/

Gruß
Andreas

Snail

So hab alle Serial Ausgaben umgestellt und hier ist mein Ergebnis.


Code: [Select]

println_P(PSTR("viel Text"));

void print_P(char *text)
{
  char c;
  while( c = pgm_read_byte(text) )
  {
    text++;
    Serial.print(c);
  }
}

void println_P(char *text)
{
  print_P(text);
  Serial.println();
}



Hab später auch das hier gefunden. http://arduino.cc/playground/Code/AvailableMemory
Vor umstellung 60Byte frei, danach knappe 700.

Go Up