Forum: Compiler & IDEs RAM - Speicherproblem


von Martin Langbein (Gast)


Lesenswert?

Ich hab ein kleines Programm welches aus einer MMC 512 Bytes in einen
Buffer lesen soll. Aber der Compiler tut die angelegten Variablen im
RAM überschreiben.
Programm:

int main(void){
   USART_Init(51);
   SPIinit();
   MMC_Init();

   char buffer[512]={""};
   unsigned int p=0;<-- Variale ändert sich je nach Bufferinhalt von
                                                              buffer
   readPe1(buffer,&p);

   USART_LongInt_H(p);
}

kann es sein, wenn man am compiler irgendwas falsch eingestellt hat,
dass es dann so komische sachen macht!

von Werner B. (Gast)


Lesenswert?

Da kann der Compiler in 99,99999999999999999999999999999999999% nix
dafür, das ist üblicherweise ein index- oder pointerfehler im
programm.
Oder eventuell geht Dir der Speicher aus (Stack-Overflow). Leg doch
"buffer" und "p" mal als als globale variablen an und sehe nach was
der compiler zum RAMverbrauch sagt.

von Martin Langbein (Gast)


Lesenswert?

hab jetzt variablen global:
Data:        550 bytes (53.7% Full)
(.data + .bss + .noinit)
1K hat der ATmega16
da muss eigendlich noch genug für den stack da sein.
aber mein programm funktioniert nicht mehr(also gar nicht mehr:) )

im listing steht am ende noch dies:

C:\DOKU...KALE~1\Temp/ccgtaaaa.s:23     .bss:00000000 p
C:\DOKU...KALE~1\Temp/ccgtaaaa.s:29     .data:00000000 buffer

C:\DOKU...KALE~1\Temp/ccgtaaaa.s:35     .text:00000000 USART_Init
C:\DOKU...KALE~1\Temp/ccgtaaaa.s:61     .text:00000014 Pause
C:\DOKU...KALE~1\Temp/ccgtaaaa.s:81     .text:0000001e
USART_Transmit
C:\DOKU...KALE~1\Temp/ccgtaaaa.s:98     .text:00000026 USART_Receive

ich nehme an da steht an welcher adresse die variable im ram angelegt
wird?!
aber warum fangen die variablen alle bei 0x00 an??

von Jörg W. (dl8dtl) (Moderator) Benutzerseite


Lesenswert?

> aber warum fangen die variablen alle bei 0x00 an??

Tun sie ja gar nicht, sondern nur zwei von denen, aber die sind
in unterschiedlichen sections (.bss vs. .data).  Der Linker
positioniert diese dann absolut im RAM.  Am besten, du guckst dir
die globale Symboltabelle (.sym) an (und besser nicht das linker
map file .map, das enthält viel zu viel an Infos).

von Werner B. (Gast)


Lesenswert?

@Martin Langbein

<zitat>...mein programm funktioniert nicht mehr...</zitat>

Das deutet doch ganz extrem auf einen Programmfehler hin...

von Martin Langbein (Gast)


Lesenswert?

also wenn ich ehrlich bin dann hoff ich dass es nur ein programmfehler
ist:
ich hau einfach mal kurz mein programm rein:



hab nur die wesentlichen funktionen:
/***************************************************************/
#define PART_ENTRY_ONE  0x1BE
struct tPartitionEntry{
  unsigned char  CurState;
  unsigned char  BegPartHead;
  unsigned int  BegPartSecCyl;
  unsigned char  TypeOfPart;
  unsigned char  EndOfPartHead;
  unsigned int  EndOfPartSecCyl;
  unsigned long  SecMBRFirstSec;
  unsigned long  SecInPart;
};

void readPe1(unsigned char *buffer,struct tPartitionEntry *pe){
  MMC_read_sector(0,buffer);
  pe = (struct tPartitionEntry *)&buffer[PART_ENTRY_ONE];
}


int main(void) {
  unsigned char buffer[512];
  struct tPartitionEntry pe;

  readPe1(buffer,&pe);
  return 0;
}
/*****************************************************************/
Die Funktion MMC_read_sector(0,&buffer[0]); tut auf jeden fall,
die hab ich schon getestet.

Des programm liest 512 Byte in buffer
dann wird ein pointer an die stelle gelegt die ich aus dem puffer lesen
will.

Ich hoffe das hie ein fehler drin is aber ich kann keinen finden.
ich hoffe ihr könnt mir weiter helfen

Gruß Martin

von Jörg W. (dl8dtl) (Moderator) Benutzerseite


Lesenswert?

Du legst eben keinen Pointer dahin, sondern füllst das eine struct
damit aus.  Nicht sehr elegant, und möglicherweise auch nicht das,
was du willst.

Ich würde das eher so schreiben:
1
struct tPartitionEntry * readPe1(unsigned char *buffer){
2
  MMC_read_sector(0,buffer);
3
  return (struct tPartitionEntry *)&buffer[PART_ENTRY_ONE];
4
}
5
6
7
int main(void) {
8
  unsigned char buffer[512];
9
  struct tPartitionEntry *pe;
10
11
  pe = readPe1(buffer);
12
  return 0;
13
}

Allerdings wird der Compiler im Moment den Wert für `pe' gar nicht
erst zuweisen, da der offensichtlich ungenutzt ist.  Mach also besser
noch irgendwas damit, wenn du das Debuggen/Simulieren willst (oder
deklariere die Variable pe vorerst mal `volatile').

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.