Variablen im Flash (PROGMEM) übergeben

OP #4483491
Lesenswert?
• ▲
▼
Hallo alle miteinander :P

Ich arbeite gerade zum ersten mal mit PROGMEM.
Hier komme ich an einer stelle nicht weiter.

Bild_Fahrrad.c
1
const uint8_t cYCLO_Bitmaps[] PROGMEM=
2
{
3
0b11111111, 0b11111111... //wurde zum Verständnis gekürzt.
4
}
5

6
const uint8_t cYCLO_WidthPixels PROGMEM= 128;
7
const uint8_t cYCLO_HeightPixels PROGMEM= 64;

Bild_Fahrrad.h
1
extern const uint8_t cYCLO_Bitmaps[];
2
extern const uint8_t cYCLO_WidthPixels;
3
extern const uint8_t cYCLO_HeightPixels;

main.c
1
grafik_LCD_bild(0, 0, cYCLO_Bitmaps, cYCLO_WidthPixels, cYCLO_HeightPixels);

grafik_lcd.c
1
void grafik_LCD_bild (uint8_t x, uint8_t y, const uint8_t bitmap[], const uint8_t widthPixels, const uint8_t heightPixels)
2
{
3
lcd_string(dtostrf(pgm_read_byte(&cYCLO_WidthPixels), 3, 0, wert)); //128. Also Richtig.
4
  
5
  lcd_string(dtostrf(pgm_read_byte(&cYCLO_HeightPixels), 3, 0, wert)); //64. Also Richtig.
6

7

8
  lcd_string(dtostrf(pgm_read_byte(&widthPixels), 3, 0, wert)); //ergibt 255. Also falsch.
9
  lcd_string(dtostrf(pgm_read_byte(&heightPixels), 3, 0, wert)); //ergibt 255. Also falsch.
10
}

Wieso kann ich in "grafik_LCD_bild" nicht widthPixels und heightPixels 
auslesen?
Verwende ich im selben Unterprogramm "pgm_read_byte (&bitmap[zahler])" 
kann ich das Array erfolgreich auslesen.

Mir ist bewusst, dass es nicht viel Sinn macht zwei einzelne kleinen 
Variablen im Flash abzulegen. Da sie aber zu "cYCLO_Bitmaps[] PROGMEM" 
gehören hätte ich aber gerne die 2 zugehörigen Variablen ebenfalls im 
Flash.

Was mache ich hier falsch?
#4483618
Lesenswert?
• ▲
▼
@ Matthias Frank (frank91)

>void grafik_LCD_bild (uint8_t x, uint8_t y, const uint8_t bitmap[], const 
>uint8_t widthPixels, const uint8_t heightPixels)


>{
>lcd_string(dtostrf(pgm_read_byte(&cYCLO_WidthPixels), 3, 0, wert)); >//128. Also 
Richtig.

>  lcd_string(dtostrf(pgm_read_byte(&cYCLO_HeightPixels), 3, 0, wert)); >//64. 
Also Richtig.

Direkter Zugriff. Passt.


>  lcd_string(dtostrf(pgm_read_byte(&widthPixels), 3, 0, wert)); //ergibt >255. 
Also falsch.
>  lcd_string(dtostrf(pgm_read_byte(&heightPixels), 3, 0, wert)); //ergibt >255. 
Also falsch.
>}

Geht so nicht. Das muss man anders machen. Entweder mit der Erweiterung 
__flash oder Old school mit PGM_P pointern.

https://www.mikrocontroller.net/articles/AVR-GCC-Tutorial#Flash_mit_flash_und_Embedded-C

progmem Version


main.c
1
grafik_LCD_bild(0, 0, cYCLO_Bitmaps, &cYCLO_WidthPixels, &cYCLO_HeightPixels);


grafik_lcd.c
1
void grafik_LCD_bild (uint8_t x, uint8_t y, PGM_P bitmap, PGM_P widthPixels, PGM_P heightPixels)
2
{
3
  lcd_string(dtostrf(pgm_read_byte(widthPixels), 3, 0, wert));
4
  lcd_string(dtostrf(pgm_read_byte(heightPixels), 3, 0, wert));
5
}

__flash Version


Bild_Fahrrad.c
1
const __flash uint8_t cYCLO_Bitmaps[] PROGMEM=
2
{
3
0b11111111, 0b11111111... //wurde zum Verständnis gekürzt.
4
}
5

6
const __flash uint8_t cYCLO_WidthPixels PROGMEM= 128;
7
const __flash uint8_t cYCLO_HeightPixels PROGMEM= 64;

Bild_Fahrrad.h
1
extern const __flash uint8_t cYCLO_Bitmaps[];
2
extern const __flash uint8_t cYCLO_WidthPixels;
3
extern const __flash uint8_t cYCLO_HeightPixels;


main.c
1
grafik_LCD_bild(0, 0, cYCLO_Bitmaps, cYCLO_WidthPixels, cYCLO_HeightPixels);


grafik_lcd.c
1
void grafik_LCD_bild (uint8_t x, uint8_t y, const __flash uint8_t *bitmap, uint8_t widthPixels, uint8_t heightPixels)
2
{
3
  lcd_string(dtostrf(widthPixels), 3, 0, wert));
4
  lcd_string(dtostrf(heightPixels), 3, 0, wert));
5
}
#4483637
Lesenswert?
• ▲
▼
Hier nochmal korrigiert.


__flash Version


Bild_Fahrrad.c
1
const __flash uint8_t cYCLO_Bitmaps[]=
2
{
3
0b11111111, 0b11111111... //wurde zum Verständnis gekürzt.
4
}
5

6
const __flash uint8_t cYCLO_WidthPixels = 128;
7
const __flash uint8_t cYCLO_HeightPixels = 64;

Bild_Fahrrad.h
1
extern const __flash uint8_t cYCLO_Bitmaps[];
2
extern const __flash uint8_t cYCLO_WidthPixels;
3
extern const __flash uint8_t cYCLO_HeightPixels;


main.c
1
grafik_LCD_bild(0, 0, cYCLO_Bitmaps, cYCLO_WidthPixels, cYCLO_HeightPixels);


grafik_lcd.c
1
void grafik_LCD_bild (uint8_t x, uint8_t y, const __flash uint8_t *bitmap, uint8_t widthPixels, uint8_t heightPixels)
2
{
3
  lcd_string(dtostrf(widthPixels), 3, 0, wert));
4
  lcd_string(dtostrf(heightPixels), 3, 0, wert));
5
  lcd_string(dtostrf(bitmap[0]), 3, 0, wert));
6
}
OP #4483671
Lesenswert?
• ▲
▼
Ich hab das mit dem flash jetzt ausprobiert, weil ich dann das 
pgm_read_byte nicht mehr benötige und es das ganze übersichtlicher 
macht.

Das ganze hat dank deiner Hilfe sofort funktioniert :P
Danke :-D

Bei:
1
void grafik_LCD_bild (uint8_t x, uint8_t y, const __flash uint8_t *bitmap, uint8_t widthPixels, uint8_t heightPixels)

hast du das __flash nur bei dem Array mit angegeben. Brauche ich das bei 
widthPixels und heightPixels nicht?
#4483743
Lesenswert?
• ▲
▼
@ Matthias Frank (frank91)

>Bei:

>void grafik_LCD_bild (uint8_t x, uint8_t y, const __flash uint8_t *bitmap, 
>uint8_t widthPixels, uint8_t heightPixels)

>hast du das __flash nur bei dem Array mit angegeben. Brauche ich das bei
>widthPixels und heightPixels nicht?

Nein, weil beim Funktionsaufruf die __flash Variablen gelesen und als 
normale Parameter übergeben werden. Die Arbeit des Flash-Zugriffs 
geschieht dort. Beim Pointer ist das anders, dort muss ja auch innerhalb 
der Funktion bekannt sein, dass es kein normaler Pointer ist sondern ein 
__flash Pointer.

Antwort schreiben

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.

Formatierung
  • [c]C-Code[/c]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] – Link zu einem Artikel
  • Verweis auf einen anderen Beitrag: Rechtsklick auf dessen Beitrags-ID (#8078628), „Adresse kopieren“, in den Text einfügen

Mehr zur Formatierung

Längeren Sourcecode als Anhang, nicht in den Text. JPG nur für Fotos und Scans; Zeichnungen und Screenshots als PNG oder GIF. Siehe Bildformate.

Schon registriert? Anmelden

Wird nicht angezeigt. Wir schicken dir einen Link; sobald du damit bestätigst, erscheint dein Beitrag.

Mit dem Abschicken legst du einen kostenlosen Account an und erkennst die Nutzungsbedingungen und die Datenschutzerklärung an.