Path: utzoo!utgpu!water!watmath!clyde!cbosgd!ucbvax!hoptoad!gnu From: gnu@hoptoad.uucp (John Gilmore) Newsgroups: comp.lang.c Subject: Re: what C needs -- packed structures Message-ID: <3816@hoptoad.uucp> Date: 11 Jan 88 07:12:49 GMT References: <8801071842.AA04669@decwrl.dec.com> <2083@chinet.UUCP> Organization: Nebula Consultants in San Francisco Lines: 62 dag@chinet.UUCP (Daniel A. Glasser) wrote: > Take the following bit of C code: > struct yerks { > char y_foo; > int *y_fie; > char y_poo; > }; > struct yerks *w; > int i; > i = *w->y_fie; > The assignment, on a PDP-11, takes code to the effect of the following: > [five instructions] > Now, assume that you are on a 68000 -- > [nine instructions -- not optimal either] > Okay, that not seem too painful? > No, packed structures do not belong in the standard... > C is supposed to be an efficient > language. If you really need packed structures, and want them portable, > code them directly with macros and unions. To me this looks like an argument *for* packed structures. Is the author proposing that if we want to access data defined by an outside constraint, we should write assembly language routines? I would rather have the C compiler figure out the difference between the PDP-11 assembler sequence and the 68000 sequence, thank you. Or how is he proposing that we write "portable" definitions using macros and unions, which are just as dependent as structs on compiler alignment, word size, etc? What ends up happening is that a C struct is defined which works on the current compiler; this gradually gets hacked with #ifdef's to work on various compilers as needed, but it still has to depend on individual compilers' ideas of alignment constraints, since the C language allows the compiler to add padding between members or bitfields with impunity. I had to write and maintain a lot of code like this which accessed device registers on the Sun CPU board, or control block layouts in memory that were shared with Ethernet chips or disk controllers or whatever. It was all heavily compiler dependent and I'm sure it broke when ported to the Sun-4, but we didn't have any better tools in C for this. What we need is a portable way to tell the compiler, "don't add any padding -- just lay down the bits like I tell you." You could precede a structure declaration with "#pragma packed", which would require the structure definition to declare all its fields as bitfields (not allowing the element sizes to default) and to declare each field either signed or unsigned (not allowing the signedness to default). The resulting structure would contain exactly those bitfields, laid down end-to-end in big-endian order, without regard to any alignment considerations. This would still not resolve floating point formats, or ones' complement versus twos' complement signed integers, but the rest of the "binary data description problem" (including the #ifdef BIG_ENDIAN / LITTLE_ENDIAN hassle) would be solved. This is too unformed an idea for this C standard, but if some people implement it, like it, and it doesn't have hidden problems, maybe for the next one. -- {pyramid,ptsfa,amdahl,sun,ihnp4}!hoptoad!gnu gnu@toad.com I forsee a day when there are two kinds of C compilers: standard ones and useful ones ... just like Pascal and Fortran. Are we making progress yet? -- ASC:GUTHERY%slb-test.csnet