RTV forum PL | NewsGroups PL

Jak wyświetlać stringi powyżej 64KB w ATmega128 przy użyciu printf_P?

ATmega128 i stringi w pamieci programu

NOWY TEMAT

elektroda NewsGroups Forum Index - Elektronika Polska - Jak wyświetlać stringi powyżej 64KB w ATmega128 przy użyciu printf_P?

Adam Dybkowski
Guest

Thu May 06, 2004 10:30 pm   



Pisze sobie jak zwykle:

printf_P (PSTR ("Hejho\r\n"));

a tu nagle stringi przestają się wypisywać. :-o

Po bliższej analizie okazuje się, że przekroczyłem magiczną granicę 64KB
kodu i stringi umieszczone w górnej połówce pamięci programu się nie
wypisują. Problem w tym, że do funkcji printf_P przekazywany jest tylko
16-bitowy adres stringu, do tego wewnątrz zagrzebanego vfprintf kolejne
literki pobierane są z pamięci programu przy pomocy makra PRG_RDB
(tożsamego z pgm_read_byte_near, które nie umie sięgać powyżej 64KB).

Macie jakieś błyskotliwe rozwiązanie tego problemu? Niby normalnie
stringi leżą na początku programu, za wektorami przerwań. Ale w
bootloaderze wszystko jest już wysoko (od 0x1e000), a i tam chciałbym
korzystać z dobrodziejstw funkcji printf_P, nie zaśmiecając przy tym
pamięci danych (czyli nie zwykły printf).

--
Adam Dybkowski
adybkows@amwaw.edu.pl
http://www.amwaw.edu.pl/~adybkows/

Marcin Kubiak
Guest

Fri May 07, 2004 6:53 am   



Użytkownik "Adam Dybkowski" <adybkows@amwaw.edu.pl> napisał w wiadomości
Quote:
Pisze sobie jak zwykle:

printf_P (PSTR ("Hejho\r\n"));

a tu nagle stringi przestają się wypisywać. :-o

Po bliższej analizie okazuje się, że przekroczyłem magiczną granicę 64KB
kodu i stringi umieszczone w górnej połówce pamięci programu się nie
wypisują. Problem w tym, że do funkcji printf_P przekazywany jest tylko
16-bitowy adres stringu,

Witam. Niestety nie znam C, ale z tego co mi sie wydaje nie mam mozliwosc
zadresowania w Atmega128 niczego powyzej FFFFh. Jest tak poniewaz pamiec ma
ogranizacje 16bit wiec ralanie masz 64k slow i adresujesz słowo adresem
16bit. Jest tak we wszystkich AVRach.

--
Pozdrawiam
Marcin Kubiak

Marcin Kubiak
Guest

Fri May 07, 2004 7:02 am   



Użytkownik "Marcin Kubiak" napisał w wiadomości
Quote:

Użytkownik "Adam Dybkowski" <adybkows@amwaw.edu.pl> napisał w wiadomości
Pisze sobie jak zwykle:

printf_P (PSTR ("Hejho\r\n"));

a tu nagle stringi przestają się wypisywać. :-o

Po bliższej analizie okazuje się, że przekroczyłem magiczną granicę 64KB
kodu i stringi umieszczone w górnej połówce pamięci programu się nie
wypisują. Problem w tym, że do funkcji printf_P przekazywany jest tylko
16-bitowy adres stringu,

Witam. Niestety nie znam C, ale z tego co mi sie wydaje nie mam mozliwosc
zadresowania w Atmega128 niczego powyzej FFFFh. Jest tak poniewaz pamiec
ma
ogranizacje 16bit wiec ralanie masz 64k slow i adresujesz słowo adresem
16bit. Jest tak we wszystkich AVRach.

Przepraszam pomylilem sie. Przez ELPM mozna adresowac pojedyncze bajtyw
pamieci programu. Nie wiem natomiast czemu kompilator C sobie z tym nie
radzi.
--
Pozdrawiam
Marcin Kubiak

Milosz Skowyra
Guest

Fri May 07, 2004 12:57 pm   



Adam Dybkowski wrote:

Quote:
Po bliższej analizie okazuje się, że przekroczyłem magiczną granicę 64KB
kodu i stringi umieszczone w górnej połówce pamięci programu się nie
wypisują. Problem w tym, że do funkcji printf_P przekazywany jest tylko
16-bitowy adres stringu, do tego wewnątrz zagrzebanego vfprintf kolejne
literki pobierane są z pamięci programu przy pomocy makra PRG_RDB
(tożsamego z pgm_read_byte_near, które nie umie sięgać powyżej 64KB).

Afair jezeli uzywa LPM to nie dostaniesz sie do drugiej polowki pamieci.
Zeby dostac sie ponad 64KB, musi uzywac ELPM i bitu RAMPZ. A nie da sie
go zmusic do uzywania pgm_read_byte_far. W GCC zdefiniowany w pgmspace.h
??

#ifdef RAMPZ

/** \ingroup avr_pgmspace
\def pgm_read_byte_far(address_long)
Read a byte from the program space with a 32-bit (far) address.

\note The address is a byte address.
The address is in the program space. */

#define pgm_read_byte_far(address_long) __ELPM((unsigned
long)(address_long))

/** \ingroup avr_pgmspace
\def pgm_read_word_far(address_long)
Read a word from the program space with a 32-bit (far) address.

\note The address is a byte address.
The address is in the program space. */

#define pgm_read_word_far(address_long) __ELPM_word((unsigned
long)(address_long))



--
Regards. Przy odpowiedzi usun "." przed "net" z adresu!!!
|-----------------------------------------------------|
| Milosz Skowyra GSM Mobile +48 600 95 35 72 |
| miloszek@fido.net.org.pl 2:484/2.47 on fidonet |
|-----------------------------------------------------|

Adam Dybkowski
Guest

Fri May 07, 2004 9:56 pm   



Milosz Skowyra wrote:

Quote:
Po bliższej analizie okazuje się, że przekroczyłem magiczną granicę 64KB
kodu i stringi umieszczone w górnej połówce pamięci programu się nie
wypisują. Problem w tym, że do funkcji printf_P przekazywany jest tylko
16-bitowy adres stringu, do tego wewnątrz zagrzebanego vfprintf kolejne
literki pobierane są z pamięci programu przy pomocy makra PRG_RDB
(tożsamego z pgm_read_byte_near, które nie umie sięgać powyżej 64KB).

Afair jezeli uzywa LPM to nie dostaniesz sie do drugiej polowki pamieci.
Zeby dostac sie ponad 64KB, musi uzywac ELPM i bitu RAMPZ. A nie da sie
go zmusic do uzywania pgm_read_byte_far. W GCC zdefiniowany w pgmspace.h

We wlasnym kodzie to zaden problem. Ale zeby dzialala zwykla funkcja
printf_P, to by chyba wymagalo zmian w bibliotece libc (a dokladniej w
funkcji vfprintf) i przekompilowania jej. Ma ktos prostsze pomysly?

--
Adam Dybkowski
adybkows@amwaw.edu.pl
http://www.amwaw.edu.pl/~adybkows/

Zbych
Guest

Fri May 07, 2004 10:13 pm   



Pewnego dnia Adam Dybkowski przemówił ludzkim głosem:
Quote:
Ma ktos prostsze pomysly?

Nie znam gcc, ale może dane, przed linkowaniem są umieszczane w jakimś
bloku danych typu .text i może da się w jakiś sposób skłonić linkier do
umieszczenia tego bloku przed granicą 32k słowa ?

--
*Warning*: Dates in Calendar are closer than they appear.

### /mail: bzb<at>poczta<dot>onet<dot>pl/ ###

Adam Dybkowski
Guest

Sat May 08, 2004 12:17 am   



Zbych wrote:

Quote:
Ma ktos prostsze pomysly?

Nie znam gcc, ale może dane, przed linkowaniem są umieszczane w jakimś
bloku danych typu .text i może da się w jakiś sposób skłonić linkier do
umieszczenia tego bloku przed granicą 32k słowa ?

W standardowym skrypcie linkera wlasnie tak jest - dane umieszczane w
pamieci programu (sekcja AFAIR ".progmem") leza na poczatku pamieci, tuz
za wektorami przerwan. I wszystko jest OK (jezeli nie przekroczymy 64KB
tej sekcji).

Ale w bootloaderze, ktory caly musi sie zmiescic na koncu pamieci,
wszystko zaczyna sie od wysokiego adresu (np. 0x1e000). Wtedy wysoko
musi lezec i kod programu, i te nieszczesne stale lokowane w pamieci
programu.

BTW: Obilo mi sie o oczy, ze znaczna czesc biblioteki libc-avr pisal
Polak. Moze warto do niego napisac z prosba o niezbedne poprawki w
funkcji vfprintf?

--
Adam Dybkowski
adybkows@amwaw.edu.pl
http://www.amwaw.edu.pl/~adybkows/

Jurek Szczesiul
Guest

Sat May 08, 2004 6:28 am   



Sat, 08 May 2004 00:56:13 +0200, na pl.misc.elektronika, Adam Dybkowski
napisał(a):

Quote:
We wlasnym kodzie to zaden problem. Ale zeby dzialala zwykla funkcja
printf_P, to by chyba wymagalo zmian w bibliotece libc (a dokladniej w
funkcji vfprintf) i przekompilowania jej. Ma ktos prostsze pomysly?

Tam juz jest taki mechanizm - vprintf wystepuje w kilku wersjach (
podstawowa - w glownej libm.a , rozszerzona dla float i minimalna dla
niewielkich kostek ) . Wersje zamienna lokujemy wylaczajac vsprintf z
linkowania opcja -u i dolaczajac odpowiednia dodatkowa biblioteke. Ale
napisac nastepna wersje dla odwolan far juz trzeba samemu.

--
Pozdrowienia
Jurek Szczesiul

Zbych
Guest

Sat May 08, 2004 8:26 am   



Pewnego dnia Adam Dybkowski przemówił ludzkim głosem:

Quote:
Ale w bootloaderze, ktory caly musi sie zmiescic na koncu pamieci,
wszystko zaczyna sie od wysokiego adresu (np. 0x1e000). Wtedy wysoko
musi lezec i kod programu, i te nieszczesne stale lokowane w pamieci
programu.

To w końcu piszesz bootloader, który siedzi na końcu pamięci, czy
"zwykły" program, który przekroczył 64kB ?
Bo jeśli zwykły program, to najprostszym obejściem problemu
(przynajmniej tak mi się wydaje) jest wymuszenie umieszczania stałych
poniżej granicy 64KB.

Quote:
BTW: Obilo mi sie o oczy, ze znaczna czesc biblioteki libc-avr pisal
Polak. Moze warto do niego napisac z prosba o niezbedne poprawki w
funkcji vfprintf?

Artur Lipowski, ale najprościej byłoby zadać pytanie na liście
mailingowej avr-libc-dev:
http://mail.nongnu.org/mailman/listinfo/avr-libc-dev

--
*Warning*: Dates in Calendar are closer than they appear.

### /mail: bzb<at>poczta<dot>onet<dot>pl/ ###

Adam Dybkowski
Guest

Sat May 08, 2004 8:12 pm   



Zbych wrote:

Quote:
Ale w bootloaderze, ktory caly musi sie zmiescic na koncu pamieci,
wszystko zaczyna sie od wysokiego adresu (np. 0x1e000). Wtedy wysoko
musi lezec i kod programu, i te nieszczesne stale lokowane w pamieci
programu.

To w końcu piszesz bootloader, który siedzi na końcu pamięci, czy
"zwykły" program, który przekroczył 64kB ?

Bootloadera nie pisze sie tylko z samej radosci pisania, obok powstaje
reszta programu. Smile A problem ze stringami odczytywanymi z pamieci
programu objawil sie u mnie wlasnie w bootloaderze.

--
Adam Dybkowski
adybkows@amwaw.edu.pl
http://www.amwaw.edu.pl/~adybkows/

elektroda NewsGroups Forum Index - Elektronika Polska - Jak wyświetlać stringi powyżej 64KB w ATmega128 przy użyciu printf_P?

NOWY TEMAT

Regulamin - Zasady uzytkowania Polityka prywatnosci Kontakt RTV map News map