Big endian kontra little endian, czyli konflikt intere

Witam wszystkich Aktualnie zczytuję z pewnego urządzenia pakiety danych po RSie do ATMegi

128. Dane są binarne i zawierają liczby 8,16 i 32 bitowe. Wszystko by było fajnie, gdyby to urządzenie pracowało w standardzie little-endian, a niestety tak nie jest. Tu mam takie pytanie, czy jest jakaś funkcja(operator), która z automata zamienia kolejność bajtów? Piszę tu, nie na pl.comp.lang.c, ponieważ AVR to 8 bitowiec i takie rzeczy mogą być bardziej specyficzne dla kompilatora avr-gcc. Właściwie funkcja to nie najlepszy pomysł, ale makro było by idealne wklejając wstawkę z assemblera. Przeszukałem google i oprócz informacji, że problem istnieje nie znalazłem właściwie nic. Obecnie robię to w ten sposób: Tworze strukturę danych z polami w odwrotnej kolejności niż w oryginale nadchodzą. Bufor przeznaczony na pakiet wypełniam od końca do początku. W ten sposób po przypisaniu zmiennej wskaźnikowej (typu struktury) adresu ostatniej komórki mogę bez problemu odwoływać się do poszczególnych pól poprzez: zmienna->pole16b; I to działa bez problemu, ale nie wydaje mi się to "estetycznym" rozwiązaniem. Może wyważam już otwarte drzwi? Jak wy do takiego problemu podchodzicie?

Pozdrawiam

Reply to
Krzysztof B.
Loading thread data ...

poczytaj o "pragma pack" - zasadniczo sluzy do ustawiania alignmentu ale niektore kompilatory pozwalaja ustawic w ten sposob endian. (Alignment - kolejny problem przy wysylaniu struktury binarnie - kompilator "zakragla" rozmiary skladnikow do DWORD dodajac puste pola

- np. struktura {BYTE,DWORD} bedzie miec nie 5 a 8 bajtow). GRG

Reply to
abert zielonka

Czasem przydaje mi sie cos takiego do zmiany endianowości dla int:

for (i=0;i<xxx;i++) Buff[i] = dev->data_buffer[ (i ^ 1)];

czy dla long: for (i=0;i<xxx;i++) Buff[i] = dev->data_buffer[ (i ^ 3)];

MiSter

Reply to
Mister

Proponuję zapoznać się z pojęciem unii w języku C. Powinno pomóc. Dane należy wpisać bajtowo, odczytać można w słowie 16 lub 32 bitowym. Pozdrawiam, K.

Reply to
John Smith

Wersja przenośna (bez użycia unii):

unsigned char buf[42]; unsigned int little_int = buf[0]<<8 | buf[1]; unsigned long little_long = buf[0]<<24 | buf[1]<<16 | buf[2]<<8 | buf[3];

Reply to
tbird

ElectronDepot website is not affiliated with any of the manufacturers or service providers discussed here. All logos and trade names are the property of their respective owners.