I wish ANSI-C sizeof (void) == 1 (was Re: preprocessing subterfuge) 
Author Message
 I wish ANSI-C sizeof (void) == 1 (was Re: preprocessing subterfuge)


Quote:

>>Gnu C with -Wall -ansi -pedantic has a pretty tight sphincter.
>May be, but it still insists on assigining a size of 1 (one) to the type void,
>which according to the parts of the standards I have seen, is an incomplete type.
>Thus you get a warning:
>void.c:3: warning: sizeof applied to a void type

When I first heard of GNU C's deviation from the standard with the sizeof type
'void', I thought it was a bad idea; but now I hope ANSI will standardise it
next time around. void * is the natural type to use when you're considering a
pointer to a chunk of memory that can hold any arbitrary type; in the Unix
kernel for instance it seems a natural replacement for caddr_t. And any time
I need to do arithmetic on one, it's always in terms of bytes - it would be
great to be able to not have to cast to char * every time you need to do
arithmetic on one, which seems to happen quite a lot in stuff like device
drivers.

Any comments?

Graham
--
Graham Stoney                    | "a Perl script is correct if it's halfway
Flip Dibner fan club, "Hi Flip!" |  readable and gets the job done before your
Ph: +61 2 805-2909  Fax: -2929   |  boss fires you." L. Wall & R. Schwartz



Mon, 30 Jan 1995 12:13:16 GMT  
 I wish ANSI-C sizeof (void) == 1 (was Re: preprocessing subterfuge)

|>
|> When I first heard of GNU C's deviation from the standard with the sizeof type
|> 'void', I thought it was a bad idea; but now I hope ANSI will standardise it
|> next time around. void * is the natural type to use when you're considering a
|> pointer to a chunk of memory that can hold any arbitrary type; in the Unix
|> kernel for instance it seems a natural replacement for caddr_t. And any time
|> I need to do arithmetic on one, it's always in terms of bytes - it would be
   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
If you need to do arithmetic on one, then the variable should not be declared
as "void *" in the first place. That type is for pointing to objects whose
size you don't know. If you know you're going to be dealing with arrays of
bytes, then declare it as "[unsigned] char *".

-Chris

|> great to be able to not have to cast to char * every time you need to do
|> arithmetic on one, which seems to happen quite a lot in stuff like device
|> drivers.
|>
|> Any comments?
|>
|> Graham
|> --
|> Graham Stoney                    | "a Perl script is correct if it's halfway
|> Flip Dibner fan club, "Hi Flip!" |  readable and gets the job done before your
|> Ph: +61 2 805-2909  Fax: -2929   |  boss fires you." L. Wall & R. Schwartz

--
==================
Chris Volpe
G.E. Corporate R&D



Wed, 01 Feb 1995 03:51:32 GMT  
 I wish ANSI-C sizeof (void) == 1 (was Re: preprocessing subterfuge)
]
] When I first heard of GNU C's deviation from the standard with the sizeof type
] 'void', I thought it was a bad idea; but now I hope ANSI will standardise it
] next time around. void * is the natural type to use when you're considering a
] pointer to a chunk of memory that can hold any arbitrary type;

    Yes, that's the problem: it's a chunk of memory, not necessarily a
chunk of char's.  Even though sizeof(char) may be 1 by definition, that
doesn't mean it's a natural unit of memory on every machine.  As chips
come along with more bits-per-computation, a pointer to a char may
become useless (and inefficient) outside the context of a character
string.

] kernel for instance it seems a natural replacement for caddr_t. And any time
] I need to do arithmetic on one, it's always in terms of bytes

    Sorry to start the byte fight again, but the meaning of a byte is
very tenuous, and can't be the basis for a universal pointer, as "void
*" is meant to be.

    To paraphrase someone (Ritchie?), if you want a pointer to char, you
know where to find it.

                                           -- Bill K.

Bill Kaufman,          | "Hush my darling / Be still my darling /
Corporate Lackey       |  The lion's on the phone,..."



Wed, 01 Feb 1995 12:25:33 GMT  
 I wish ANSI-C sizeof (void) == 1 (was Re: preprocessing subterfuge)

Quote:

>|>                   void * is the natural type to use when you're considering a
>|> pointer to a chunk of memory that can hold any arbitrary type; in the Unix
>|> kernel for instance it seems a natural replacement for caddr_t. And any time
>|> I need to do arithmetic on one, it's always in terms of bytes - it would be
>   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
>If you need to do arithmetic on one, then the variable should not be declared
>as "void *" in the first place. That type is for pointing to objects whose
>size you don't know. If you know you're going to be dealing with arrays of
>bytes, then declare it as "[unsigned] char *".

Yes, but I'm _not_ dealing with arrays of bytes. I'm pointing to arbitrary
locations which store as yet unknown types. One example is converting a
pointer in shared memory from one virtual address space to another. Another
is adding the base address of a hardware device to the address at which the
block of address space in which it resides is mapped. You really aren't
dealing with arrays of bytes, just memory addresses; you can't dereference
them, but sometimes you need to add to them.

Graham
--
Graham Stoney                    | "a Perl script is correct if it's halfway
Flip Dibner fan club, "Hi Flip!" |  readable and gets the job done before your
Ph: +61 2 805-2909  Fax: -2929   |  boss fires you." L. Wall & R. Schwartz



Sat, 04 Feb 1995 09:09:45 GMT  
 I wish ANSI-C sizeof (void) == 1 (was Re: preprocessing subterfuge)

Quote:
>>> void * is the natural type to use when you're considering a
>>> pointer to a chunk of memory that can hold any arbitrary type ...
>>> And any time I need to do arithmetic on one, it's always in terms
>>> of bytes ...
>> If you need to do arithmetic on one, then the variable should not be
>> declared as "void *" in the first place. That type is for pointing to
>> objects whose size you don't know. ...
> Yes, but I'm _not_ dealing with arrays of bytes. I'm pointing to arbitrary
> locations which store as yet unknown types.

The last two quoted posters are both correct.  In ANSI C, it is specified
that character types occupy one byte and that any object (i.e. a single
declared variable, or the result of a single call to malloc()) is made up
of bytes which can be (sorry, Steve) addressed linearly.  If you really
have to do operations of the type just described, then you ARE viewing the
object as an array of bytes, and char * (or unsigned char *, etc.) is the
right type to use.  If you find this unpleasant, consider "typedef char byte".

Void * points with the same precision as char *, but is appropriate when you
will be treating the object of unknown type as a WHOLE rather than as an
array of bytes.  This is why it has ITS special properties: it can be freely
converted without a cast to and from any other object pointer type, but you
can't do address arithmetic on it.
--
Mark Brader                     "You can't [compare] computer memory and recall
SoftQuad Inc., Toronto           with human memory and recall.  It's comparing

This article is in the public domain.



Sat, 04 Feb 1995 22:48:33 GMT  
 I wish ANSI-C sizeof (void) == 1 (was Re: preprocessing subterfuge)

|> >If you need to do arithmetic on one, then the variable should not be declared
|> >as "void *" in the first place. That type is for pointing to objects whose
|> >size you don't know. If you know you're going to be dealing with arrays of
|> >bytes, then declare it as "[unsigned] char *".
|>
|> Yes, but I'm _not_ dealing with arrays of bytes. I'm pointing to arbitrary
|> locations which store as yet unknown types. One example is converting a
|> pointer in shared memory from one virtual address space to another. Another
|> is adding the base address of a hardware device to the address at which the
|> block of address space in which it resides is mapped. You really aren't
|> dealing with arrays of bytes, just memory addresses; you can't dereference
|> them, but sometimes you need to add to them.

When you do such operations, you are treating the block of memory as an
array of bytes. A shared memory segment is an array of bytes. When you
convert between virtual address spaces, you are subtracting the start
address of the segment from the pointer in question. Thus, you are
doing pointer arithmetic on that big char array returned by shmat(2),
regardless of what structure-pointer-type you are going to convert the
pointer to later.

There's no need to make (void *) behave like (char *). If you want
a (char *), you know where to find it.

|>
|> Graham
|> --
|> Graham Stoney                    | "a Perl script is correct if it's halfway
|> Flip Dibner fan club, "Hi Flip!" |  readable and gets the job done before your
|> Ph: +61 2 805-2909  Fax: -2929   |  boss fires you." L. Wall & R. Schwartz

--
==================
Chris Volpe
G.E. Corporate R&D



Mon, 06 Feb 1995 06:33:20 GMT  
 
 [ 6 post ] 

 Relevant Pages 

1. relation between sizeof(void*), sizeof(int)

2. sizeof(void*) versus sizeof(foo*)

3. Is void main(void) ANSI standard??

4. Wish there was getch() in ANSI C

5. ANSI C and comment preprocessing

6. ANSI C -- preprocessing

7. Problem with sizeof of a struct void pointer

8. void *, ptr arithmetic and sizeof()

9. sizeof void*

10. sizeof(void) ??

11. from void (void*) to void (_cdecl*) (void*)

12. Question about sizeof (*(void *))

 

 
Powered by phpBB® Forum Software