C++Talk.NET Forum Index C++Talk.NET
C++ language newsgroups
 
Archives   FAQFAQ   SearchSearch   MemberlistMemberlist   UsergroupsUsergroups   RegisterRegister 
 ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

Padding in einfachen char-struct
Goto page 1, 2  Next
 
Post new topic   Reply to topic    C++Talk.NET Forum Index -> C++ (German)
View previous topic :: View next topic  
Author Message
Markus Schaaf
Guest





PostPosted: Tue Feb 01, 2005 9:23 am    Post subject: Padding in einfachen char-struct Reply with quote



Ich hätte gerne mal ein paar Kommentare/Erfahrungen zu Folgendem:
Für ein einfaches IO-Protokoll brauche ich Byteströme, die
irgendwie strukturiert sind. Die reine Lehre wäre, zum Schreiben
und Lesen Paare von Funktionen zu benutzen, die intern mit »memcpy«,
Zeigerarithmetik usw. arbeiten. Das wird mir jedoch schnell zu
unübersichtlich und ineffizient. Also mache ich das eher so:

template< unsigned len >
struct String {
unsigned char bytes[len];
};

struct Header {
String<2> preamble;
String<8> sender;
String<8> receiver;

...

Nun die Frage: Soweit ich das bisher beobachten konnte, kommt kein
Compiler auf die Idee, in solche reinen »char«-Strukturen Padding
einzufügen. Allerdings kenne ich auch nicht viele Compiler, und
auch keine exotischen Architekturen (Embedded-Controller wären von
Interesse).

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de
Back to top
kanze@gabi-soft.fr
Guest





PostPosted: Tue Feb 01, 2005 10:14 am    Post subject: Re: Padding in einfachen char-struct Reply with quote



Markus Schaaf wrote:
Quote:
Ich hätte gerne mal ein paar Kommentare/Erfahrungen zu
Folgendem: Für ein einfaches IO-Protokoll brauche ich
Byteströme, die irgendwie strukturiert sind. Die reine Lehre
wäre, zum Schreiben und Lesen Paare von Funktionen zu
benutzen, die intern mit »memcpy«, Zeigerarithmetik usw.
arbeiten. Das wird mir jedoch schnell zu unübersichtlich und
ineffizient. Also mache ich das eher so:

template< unsigned len
struct String {
unsigned char bytes[len];
};

struct Header {
String<2> preamble;
String<8> sender;
String<8> receiver;

...

Nun die Frage: Soweit ich das bisher beobachten konnte, kommt
kein Compiler auf die Idee, in solche reinen »char«-Strukturen
Padding einzufügen. Allerdings kenne ich auch nicht viele
Compiler, und auch keine exotischen Architekturen
(Embedded-Controller wären von Interesse).

Der Compiler darf. Typischerweise würde ich es nur am Ende
erwarten, falls es überhaupt vorkommt.

In der Praxis benutze ich auch so was ähnlich. In meinem Fall
nicht mit templates sondern mit generiertem Code (was sinnvollen
getter und setter erlaubt). Funktionniert's zwar tadellos bei
mir, aber die Portabilität ist hier nicht gefragt.

--
James Kanze GABI Software http://www.gabi-soft.fr
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de

Back to top
Falk Tannhäuser
Guest





PostPosted: Tue Feb 01, 2005 10:39 am    Post subject: Re: Padding in einfachen char-struct Reply with quote



Markus Schaaf wrote:

Quote:
template< unsigned len
struct String {
unsigned char bytes[len];
};

struct Header {
String<2> preamble;
String<8> sender;
String<8> receiver;

...

Nun die Frage: Soweit ich das bisher beobachten konnte, kommt kein
Compiler auf die Idee, in solche reinen »char«-Strukturen Padding
einzufügen. Allerdings kenne ich auch nicht viele Compiler, und
auch keine exotischen Architekturen (Embedded-Controller wären von
Interesse).

powerpc-rtems-g++ --version
powerpc-rtems-g++ (GCC) 3.2.3

Copyright (C) 2002 Free Software Foundation, Inc.
.... (siehe <http://www.rtems.com>)

Weiß nicht, ob der exotisch genug ist - jedenfalls fügt er kein
Padding ein, selbst wenn man 'String<1>'-Member reinpackt.
'short' bzw. 'int'/'long' werden dagegen auf durch 2 bzw. 4
teilbare Adressen gelegt. Compilerspezifische Switches hab
ich jetzt auf die Schnelle nicht angeguckt.

MfG
Falk

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de

Back to top
Thomas Mang
Guest





PostPosted: Tue Feb 01, 2005 11:24 am    Post subject: Re: Padding in einfachen char-struct Reply with quote


<kanze (AT) gabi-soft (DOT) fr> schrieb im Newsbeitrag
news:1107252851.630660.289080 (AT) f14g2000cwb (DOT) googlegroups.com...
Quote:
Markus Schaaf wrote:
Ich hätte gerne mal ein paar Kommentare/Erfahrungen zu
Folgendem: Für ein einfaches IO-Protokoll brauche ich
Byteströme, die irgendwie strukturiert sind. Die reine Lehre
wäre, zum Schreiben und Lesen Paare von Funktionen zu
benutzen, die intern mit »memcpy«, Zeigerarithmetik usw.
arbeiten. Das wird mir jedoch schnell zu unübersichtlich und
ineffizient. Also mache ich das eher so:

template< unsigned len
struct String {
unsigned char bytes[len];
};

struct Header {
String<2> preamble;
String<8> sender;
String<8> receiver;

...

Nun die Frage: Soweit ich das bisher beobachten konnte, kommt
kein Compiler auf die Idee, in solche reinen »char«-Strukturen
Padding einzufügen. Allerdings kenne ich auch nicht viele
Compiler, und auch keine exotischen Architekturen
(Embedded-Controller wären von Interesse).

Der Compiler darf. Typischerweise würde ich es nur am Ende
erwarten, falls es überhaupt vorkommt.


Am Beginn darf er nicht.


Thomas

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de

Back to top
Stefan Reuther
Guest





PostPosted: Tue Feb 01, 2005 6:23 pm    Post subject: Re: Padding in einfachen char-struct Reply with quote

Markus Schaaf wrote:
Quote:
template< unsigned len
struct String {
unsigned char bytes[len];
};

struct Header {
String<2> preamble;
String<8> sender;
String<8> receiver;

Nun die Frage: Soweit ich das bisher beobachten konnte, kommt kein
Compiler auf die Idee, in solche reinen »char«-Strukturen Padding
einzufügen. Allerdings kenne ich auch nicht viele Compiler, und
auch keine exotischen Architekturen (Embedded-Controller wären von
Interesse).

Ich hab es mit allen mir zur Verfügung stehenden Compilern ausprobiert,
inkl. einem für einen DSP von ADI, keiner hat da Padding gemacht.

Ich würde aber auf jeden Fall noch ein assert(sizeof(Header)==1Cool
irgendwo unterbringen.


Stefan

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de

Back to top
Torsten Robitzki
Guest





PostPosted: Tue Feb 01, 2005 6:38 pm    Post subject: Re: Padding in einfachen char-struct Reply with quote

Markus Schaaf wrote:

Quote:
Ich hätte gerne mal ein paar Kommentare/Erfahrungen zu Folgendem:
Für ein einfaches IO-Protokoll brauche ich Byteströme, die
irgendwie strukturiert sind. Die reine Lehre wäre, zum Schreiben
und Lesen Paare von Funktionen zu benutzen, die intern mit »memcpy«,
Zeigerarithmetik usw. arbeiten. Das wird mir jedoch schnell zu
unübersichtlich und ineffizient. Also mache ich das eher so:

template< unsigned len
struct String {
unsigned char bytes[len];
};

struct Header {
String<2> preamble;
String<8> sender;
String<8> receiver;

...

Nun die Frage: Soweit ich das bisher beobachten konnte, kommt kein
Compiler auf die Idee, in solche reinen »char«-Strukturen Padding
einzufügen. Allerdings kenne ich auch nicht viele Compiler, und
auch keine exotischen Architekturen (Embedded-Controller wären von
Interesse).

100_TOR $ cxx/version
Compaq C++ V6.2-048 for OpenVMS Alpha V7.3

legt dort nirgends Padding ein. Durch einen compiletime assert könnte
man ja noch sicher stellen, das es einen Fehler gibt, wenn der code von
einem Compiler übersetzt wird, bei dem sizeof Header != 18 ist. Selbst
wenn es einen Compiler gäbe, der es anders macht, gäbe es sicher auch
irgend welche pragmas und/oder Schalter, um ihm dieses abzugewöhnen.

mfg Torsten

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de

Back to top
Markus Schaaf
Guest





PostPosted: Tue Feb 01, 2005 7:34 pm    Post subject: Re: Padding in einfachen char-struct Reply with quote

Danke allen für die Kommentare. Natürlich ist da ein Compile-
Time-Assert, aber der würde das Problem nur anzeigen, nicht
beheben. Ich will den Code möglichst nicht mehr anfassen müssen,
falls der mal "portiert" werden muß.

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de
Back to top
Mario Schunda
Guest





PostPosted: Tue Feb 01, 2005 10:30 pm    Post subject: Re: Padding in einfachen char-struct Reply with quote

Hallo Markus

So weit mir bekannt ist geht das mit einer
#pragma pack(1) // hier steht wie er packen muss
und endet mit
#pragma pack() // wieder auf compiler default stellen

Sehe dann so aus.

#pragma pack(1)

template< unsigned len >
struct String {
unsigned char bytes[len];
};

struct Header {
        String<2> preamble;
        String<8> sender;
        String<8> receiver;
....

#pragma pack()

Unter dem gcc gibt es da noch die __attribute__ Anweisung.
Wie die genaue Syntax ist weis ich nicht aus dem Kopf.

Mario

PS: Hoffe das pack(x) kennt jeder Compiler.

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de
Back to top
Matthias
Guest





PostPosted: Wed Feb 02, 2005 6:40 am    Post subject: Re: Padding in einfachen char-struct Reply with quote

Markus Schaaf wrote:
Quote:
template< unsigned len
struct String {
unsigned char bytes[len];
};

struct Header {
String<2> preamble;
String<8> sender;
String<8> receiver;

...

Mal ne andere Frage. Warum dieses seltsame String Konstrukt?
Wo liegt der Sinn, für jede neue Länge von Strings eine eigene Klasse
anzulegen?
Was, wenn du hundert Strings hast, die alle unterschiedlich lang sind?
Wilst du dafür 100 Klassen anlegen? Das macht irgendwie keinen Sinn, da
sie sich alle gleich verhalten. Klingt nach ziemlichem Overhead.
--
Regards,
Matthias

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de

Back to top
Roland Frank
Guest





PostPosted: Wed Feb 02, 2005 11:32 am    Post subject: Re: Padding in einfachen char-struct Reply with quote

Markus Schaaf wrote:

Quote:
Danke allen für die Kommentare. Natürlich ist da ein Compile-
Time-Assert, aber der würde das Problem nur anzeigen, nicht
beheben. Ich will den Code möglichst nicht mehr anfassen müssen,
falls der mal "portiert" werden muß.


Tut mir leid, wenn ich hier schlechte Nachrichten überbringen muss:

a) Im Standard ist zwar definiert, dass sizeof(char) == 1 ist,

ABER

b) ist im gleichen Standard völlig offengelassen, welche
Anzahl von bits ein char eigentlich hat.

Mit anderen Worten:

unsigned char test[18];

kann eine Struktur von von 144 bits (char hat 8 bits) oder
auch von 1152 bits sein (char hat 64 bits) und trotzdem
kann in beiden Fällen gelten sizeof(test) == 18.

Der Assert auf die Strukturgröße hilft dir nur wenn der Compiler
beschließt die Struktur zu padden; was er tun darf oder bleiben
lassen kann, je nach Laune.
Im Falle von Padding ist es durchaus möglich, daß der Compiler
dir einen switch (z.B. in Form eines #pragma wie bei vc++)
zur Verfügung stellt um das zu beeinflussen, muss aber nicht.

Wenn du wirklich auch exotische Architekturen in deine
Portierungsüberlegungen einbeziehen willst, dann bleibt dir
nur übrig, dieses Teil im Portierungsguide gut zu dokumentieren :-)

Gruß
Roland

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de

Back to top
Markus Schaaf
Guest





PostPosted: Wed Feb 02, 2005 12:12 pm    Post subject: Re: Padding in einfachen char-struct Reply with quote

"Matthias" <nospam (AT) digitalraid (DOT) com> schrieb:
Quote:
Markus Schaaf wrote:
template< unsigned len
struct String {
unsigned char bytes[len];
};

struct Header {
String<2> preamble;
String<8> sender;
String<8> receiver;

...

Mal ne andere Frage. Warum dieses seltsame String Konstrukt?


Es ist die idiomatische Methode, aus einem Array ein First-Class-Object
zu machen. Was der Dreh- und Angelpunkt bei der ganzen Geschichte ist.

Quote:
Wo liegt der Sinn, für jede neue Länge von Strings eine eigene Klasse
anzulegen?
Was, wenn du hundert Strings hast, die alle unterschiedlich lang sind?
Wilst du dafür 100 Klassen anlegen?

Ich lege gar nichts an. Das macht der Compiler automatisch.

Quote:
Das macht irgendwie keinen Sinn, da
sie sich alle gleich verhalten. Klingt nach ziemlichem Overhead.

Im Gegenteil, es reduziert ihn. Du kannst aber gerne Verbesserungsvorschläge
machen.

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de

Back to top
Markus Schaaf
Guest





PostPosted: Wed Feb 02, 2005 1:05 pm    Post subject: Re: Padding in einfachen char-struct Reply with quote

"Roland Frank" <roland.frank.no-spam (AT) gmx (DOT) info> schrieb:

Quote:
b) ist im gleichen Standard völlig offengelassen, welche
Anzahl von bits ein char eigentlich hat.

Es ist implementation-defined, d.h. jeder Compiler dokumentiert diesen
Wert durch Setzen des Makros »CHAR_BIT« und durch Spezialisierung des
Templates »numeric_limits«. (Darüber hinaus ist die Anzahl der Bits in
einem »char« sowohl für meine Frage als auch für mein Programm völlig
bedeutungslos: Es handelt sich um ein serielles Text-Protokoll. Ob die
einzelnen Zeichen auf dem Draht 7 Bit oder im Speicher 9 haben, ändert
nichts.)

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de

Back to top
Thorsten Nitz
Guest





PostPosted: Wed Feb 02, 2005 6:30 pm    Post subject: Re: Padding in einfachen char-struct Reply with quote

Markus Schaaf schrieb:
Quote:

template< unsigned len
struct String {
unsigned char bytes[len];
};

struct Header {
String<2> preamble;
String<8> sender;
String<8> receiver;

...

Nun die Frage: Soweit ich das bisher beobachten konnte, kommt kein
Compiler auf die Idee, in solche reinen »char«-Strukturen Padding
einzufügen.

Im vergangenen Jahrhundert ist mir mal einer begegnet, der hat
Strukturen stets auf 8 Byte aligned. Da die Member von Header Strukturen
sind, hätte er hinter preamble 6 Byte eingefügt. Irrsinnigerweise hatte
er sogar ein #pragma(pack). Leider weiß ich den Namen und Hersteller
dieses Compilers nicht mehr. Möglicherweise war das im Zusammenhang mit
dem zu Recht vergessenen BEtriebssystem VRTX.

Zeitgenössische Compiler mit solchem Verhalten sind mir nicht bekannt.
Aber man muss immer damit rechnen, dass irgend jemand mit lex und yacc
einen neuen Compiler für eine selbstgestrickte Plattform zusammenbrät
und auf die Menschheit loslässt. Deswegen gibt es ja die Reine Lehre.
Oder man geht das kalkulierte Risiko ein, mal eine Plattform nicht ohne
weiters unterstützen zu können.

Übrigens ist das hier ein klasse Beispiel für boost::static_assert:

boost::static_assert(sizeof(Header)
== sizeof(preamble) + sizeof(sender) + sizeof(receiver));

sagt Dir schon zur Compilezeit, ob gepadded wird.

Tschö, wa!
Thorsten








Allerdings kenne ich auch nicht viele Compiler, und
Quote:
auch keine exotischen Architekturen (Embedded-Controller wären von
Interesse).


--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de

Back to top
Thomas Mang
Guest





PostPosted: Wed Feb 02, 2005 7:46 pm    Post subject: Re: Padding in einfachen char-struct Reply with quote


"Thorsten Nitz" <T.Nitz (AT) epost (DOT) de> schrieb im Newsbeitrag
news:36ckkvF50nr93U1 (AT) individual (DOT) net...
Quote:
Markus Schaaf schrieb:

template< unsigned len
struct String {
unsigned char bytes[len];
};

struct Header {
String<2> preamble;
String<8> sender;
String<8> receiver;

...

Nun die Frage: Soweit ich das bisher beobachten konnte, kommt kein
Compiler auf die Idee, in solche reinen »char«-Strukturen Padding
einzufügen.

Im vergangenen Jahrhundert ist mir mal einer begegnet, der hat
Strukturen stets auf 8 Byte aligned. Da die Member von Header Strukturen
sind, hätte er hinter preamble 6 Byte eingefügt. Irrsinnigerweise hatte
er sogar ein #pragma(pack). Leider weiß ich den Namen und Hersteller
dieses Compilers nicht mehr. Möglicherweise war das im Zusammenhang mit
dem zu Recht vergessenen BEtriebssystem VRTX.

Zeitgenössische Compiler mit solchem Verhalten sind mir nicht bekannt.
Aber man muss immer damit rechnen, dass irgend jemand mit lex und yacc
einen neuen Compiler für eine selbstgestrickte Plattform zusammenbrät
und auf die Menschheit loslässt. Deswegen gibt es ja die Reine Lehre.
Oder man geht das kalkulierte Risiko ein, mal eine Plattform nicht ohne
weiters unterstützen zu können.

Übrigens ist das hier ein klasse Beispiel für boost::static_assert:

boost::static_assert(sizeof(Header)
== sizeof(preamble) + sizeof(sender) + sizeof(receiver));

sagt Dir schon zur Compilezeit, ob gepadded wird.


Das reicht leider nicht. Ich nehme mal an, Markus will die chars in Header
als ein Array ansehen. Das Problem ist, daß z.B. sizeof(String<2>) nicht 2
ergeben muß, weil in String<2> padding bytes drinnen sein können. Damit
verschiebt sich dann logischerweise alles andere dahinter.

Man muß also 2 getrennte asserts machen:

a) sizeof(String<2>) == 2 && sizeof(String<8>) == 8 // am besten in
Header
b) Dein obiges.



Generell kann es sein, daß 3 getrennte arrays in Header besser sind:

struct Header{
char preamble[2];
char sender[8];
char receiver[8];
};

Damit könnte (!) ein blöder Compiler bekehrt werden, und kein padding
zwischen den 3 einfügen, wohingegen einer der generell jede Struktur auf
x-bytes alignt sehr wohl dazwischen was einbaut.
Wie gesagt, alles Konjunktiv, Garantie gibts keine (aber unsicherer dürfte
es meiner Meinung nach nicht geworden sein - eher aber sicherer), und
sizeof(Header) kann selbst dann noch was anderes sein als 18.


Markus: Spricht was dagegen, den Zugriff über Funktionen zu machen?

struct Header
{
enum {preambleSize = 2, signalSize = 8, receiverSize = 8};

char* preamble() {return Chars;}
char* signal() {return preamble() + preambleSize;}
char* receiver() {return signal() + signalSize;}
char Chars[18];
};


Thomas

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de

Back to top
Thomas Mang
Guest





PostPosted: Wed Feb 02, 2005 7:50 pm    Post subject: Re: Padding in einfachen char-struct Reply with quote

Ups, Chars[] soll natürlich so aussehen:


struct Header
{
enum {preambleSize = 2, signalSize = 8, receiverSize = 8};

char* preamble() {return Chars;}
char* signal() {return preamble() + preambleSize;}
char* receiver() {return signal() + signalSize;}

char Chars[preambleSize + signalSize + receiverSize];
};


Thomas

--
de.comp.lang.iso-c++ - Moderation: mailto:voyager+mod (AT) bud (DOT) prima.de
FAQ: http://www.voyager.prima.de/cpp/ mailto:voyager+send-faq (AT) bud (DOT) prima.de
Back to top
Display posts from previous:   
Post new topic   Reply to topic    C++Talk.NET Forum Index -> C++ (German) All times are GMT
Goto page 1, 2  Next
Page 1 of 2

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2006 phpBB Group
SEO toolkit © 2004-2006 webmedic.