mikrocontroller.net

Forum: Compiler & IDEs Array in AVR Studio GCC mit variabler Länge


Autor: Philipp (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo alle zusammen,

ich bin gerade dabei einen AT90CAN128 auf dem STK500/501 mit AVR Studio 
4.18 und WIN Avr 4.3.3 zu programmieren. Ist nicht das erste Programm 
das ich für einen Atmel µP schreibe, allerdings das erste für einen 
AT90, was ja aber eigentlich keinen unterschied macht (außer Register 
und Co.).
Mein Problem ist, dass ich zu beginn des Programms ein Array aufbauen, 
dessen Länge pro Programmdurchlauf verschiedene Werte hat. Die Länge 
wird nicht zur Laufzeit geändert, sondern ist konstant während des 
Ablaufes. Wird das Programm unterbrochen, kann es allerdings sein, dass 
das Array deleted wird und mit einer neuen länge wieder aufgebaut. Sieht 
dann im Code so aus:
//START
#include "common.h"
#include "interrupt.h"
#include "inttypes.h"
#include "io.h"
#include "math.h"
#include "stdint.h"
#include "stdio.h"
#include "stdlib.h"
#include "string.h"

...

int main(void)
{
...

//Berechnung der Array-Laenge
int var_laenge = var_Drehzahl / var_steigung;
//               (int)          (int)

volatile double sinoid[var_laenge];
...
}

Später im Code werden die Werte aus dem Array dann zu Erzeugung einer 
PWM genutzt...sollen sie zumindest.

Das Problem ist, dass egal bei welchem Optimierer, entweder das Array 
die Länge 1 bekommt oder ich die Fehlermeldung in der Watch bekomme: 
"Location not valid".
Nur und Ausschließlich wenn ich es mit einer festen Länge aufbaue, 
bekomme ich keinen Fehler. Das klaut aber Speicherplatz ohne Ende. Hat 
einer eine Idee woran es liegen kann???

Autor: Karl Heinz (kbuchegg) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Philipp schrieb:
> Hallo alle zusammen,
>
> ich bin gerade dabei einen AT90CAN128 auf dem STK500/501 mit AVR Studio
> 4.18 und WIN Avr 4.3.3 zu programmieren. Ist nicht das erste Programm
> das ich für einen Atmel µP schreibe, allerdings das erste für einen
> AT90, was ja aber eigentlich keinen unterschied macht (außer Register
> und Co.).
> Mein Problem ist, dass ich zu beginn des Programms ein Array aufbauen,
> dessen Länge pro Programmdurchlauf verschiedene Werte hat. Die Länge
> wird nicht zur Laufzeit geändert, sondern ist konstant während des
> Ablaufes. Wird das Programm unterbrochen, kann es allerdings sein, dass
> das Array deleted wird und mit einer neuen länge wieder aufgebaut.

Definiere das Array mit der maximalen Größe, die sich im Speicher gerade 
noch ausgeht, lass es dabei bewenden und benutze nur den Teil den du 
brauchst.
Achtung: Vom verfügbaren SRAM musst du noch einen Anteil für lokale 
Variablen bzw. den Stack abziehen. Aber was dann noch übrig bleibt, 
kannst du alles in das Array buttern.

> Nur und Ausschließlich wenn ich es mit einer festen Länge aufbaue,
> bekomme ich keinen Fehler. Das klaut aber Speicherplatz ohne Ende.

Speicherplatz, der ansonsten Brach liegen würde und für nichts gut ist.


Du baust ein Parkhaus auch nicht um, nur weil am Dienstag nicht mehr als 
20 Autos parken wollen.

Autor: Karl Heinz (kbuchegg) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Du musst bei der µC Programmierung anders denken als bei der 
PC-Programmierung.
Du musst dein Programm für den Worst-Case auslegen. Wenn dann Speicher 
nicht benutzt wird, weil er in diesem einen Programlauf nicht gebraucht 
wird, ist es auch gut. Es stört niemanden, wenn du von einem 100 
Einträge Array momentan nur 20 benutzt. Davon profitiert keiner, weil 
dein Programm das einzige was läuft. Wenn du aber die 100 brauchst, dann 
hast du sie auch.
Schlimmer wäre es umgekehrt: Wenn du mehr Speicher verbrauchen würdest 
als du hast.

Autor: Oliver (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Philipp schrieb:
> Nur und Ausschließlich wenn ich es mit einer festen Länge aufbaue,
> bekomme ich keinen Fehler.

Das liegt nicht an dem gezeigten Code-Auschnitt. Der ist soweit in 
Ordnung.

Oliver

Autor: Philipp (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Danke für die schnellen Antworten. Ja, habe zwar irgendwann mal bei 
"Programmierung für embedded Systeme" gehört, dass es unelegant ist aber 
naja... =) werde es wohl so machen!

Autor: Klaus Wachtler (mfgkw)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Der avr-gcc akzeptiert in diesem Fall diese beiden Versionen:
  int var_Drehzahl = 1000;
  int var_steigung = 100;
  //Berechnung der Array-Laenge
  int var_laenge = var_Drehzahl / var_steigung;
  {
    volatile double *sinoid = (double*)alloca( var_laenge*sizeof(double) );
    sinoid[0] = 1.0;
    sinoid[9] = 1.0;
  }
  int var_Drehzahl = 1000;
  int var_steigung = 100;
  //Berechnung der Array-Laenge
  int var_laenge = var_Drehzahl / var_steigung;
  {
    volatile double sinoid[var_laenge];
    sinoid[0] = 1.0;
    sinoid[9] = 1.0;
  }

Für die erste ist #include <alloca.h> nötig.

In beiden Fällen landet das Feld auf dem Stack und wird
automatisch bei Blockende aufgeräumt.
Die üblichen Heapprobleme bei kleinen Rechnern schlagen also
hier nicht zu.
Solange die Feldlänge im Rahmen bleibt, sehe ich da auch
nichts unelegantes daran.

Wieso includest du eigentlich alle Header mit "" ?
Gelinde gesagt ungewöhnlich...

Autor: Philipp (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ähm....gute Frage...damit ich nicht durcheinander komme, wenn ich sehe, 
dass include kleiner sein soll als der Header under der Header wiederum 
größer als der Kommentar?! :D Gewohnheitssache, ist aber doch seit c90 
eh egal, oder habe ich da was verpasst?

Autor: Klaus Wachtler (mfgkw)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Keine Ahnung.
Was sollte sich mit C90 bzgl. <> und "" geändert haben?

Autor: Philipp (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
war es nicht so, das bis c90 <> immer die standartlibs aufgerufen wurden 
und mit "" die im eingenen projekt ordner? da ich zu den menschen 
gehöre, die der meinung sind, benutzte header gehören in den projekt 
ordner (weitergabe von programmen, keine default installationen, 
eigenbrödlerei...), kann ich sie ja lokal aufrufen. oder sehe ich da 
einen unterschied nicht?

Autor: Jörg Wunsch (dl8dtl) (Moderator) Benutzerseite
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Philipp schrieb:
> war es nicht so, das bis c90 <> immer die standartlibs aufgerufen wurden
> und mit "" die im eingenen projekt ordner?

Das ist auch in C99 so geblieben.  Genauer gesagt, bei "" beginnt
die Suchreihenfolge im aktuellen Verzeichnis, geht danach aber
bei den mit -I genannten Verzeichnissen weiter, abschließend werden
die Systemverzeichnisse durchsucht.

> da ich zu den menschen
> gehöre, die der meinung sind, benutzte header gehören in den projekt
> ordner (weitergabe von programmen, keine default installationen,
> eigenbrödlerei...), kann ich sie ja lokal aufrufen. oder sehe ich da
> einen unterschied nicht?

Dann musst du aber auch alle Bibliotheksdateien der Standard-
bibliothek mit kopieren, denn die Header sind nur ein kleiner Teil
der Bibliothek, und die Systemheader müssen nun mal zur Bibliothek
passen (bzw. zum Compiler, manche Header stammen von diesem).  Du
wirst dann auch nicht umhin kommen, dem Compiler die neue Lage der
Bibliotheksverzeichnisse mit -B-Optionen mitzuteilen.

Alles in allem eine reichlich umständliche Vorgehensweise, finde ich.

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.