T
Thomas G. Marshall
Arthur J. O'Dwyer said:The official C99 specification is copyright ISO and distributed by
various national member bodies as well as by ISO itself. Someone
(ANSI?) sells it in PDF form for $18. Google.
The N869 draft standard (a preliminary version) is publicly
available. Official distributions of the C90 standard are
apparently no longer available, but neither is it free. Which is a
pity.
Returns from malloc(), yes. Those other things you mentioned, C has
no conception of them. You get "regions of data storage" in C by
allocating them, either with object definitions (register, automatic,
and static objects) or with calls to malloc, calloc or realloc
(dynamic objects). That's it, as far as standard C is concerned.
How is malloc() itself written then when it needs to coordinate throughout
the heap? Can it be called C?
If not then we have a problem: I want to quiz someone on their knowledge of
what a C program will do, not on what's called defined behavior in the spec.
It occurred to me while driving today one of the reasons why the C
specification might want to be hands off of incrementing an address that
happens to be 0. It is conceivable to me that the C spec. would have to
account for machines where the address 0 is of particular meaning, and that
even loading an address register with the value can cause a maskable
interrupt. (not accessing the what's at the location 0 in any way, just the
address itself).
Furthermore, they would have to also account for regions of address space
that is not memory mapped, nor handled by the address translator.
Many implementations will let you write whatever you like, wherever
you like, as long as you call a magic function first, or put a magic
value in a pointer, or whatever, but all that falls under "undefined
behavior" (or "implementation-defined behavior") in the Standard, and
is never portable.
To answer your other post, and to give a slightly more sophisticated
"quiz" (since I'm feeling nice today, no, null pointers never point
to objects according to the Standard (that's part of the definition of
"null pointer"; consider --- how else would you make "if (p != NULL)"
useful, if NULL could be a valid address too?).
That was the trouble. The malloc's never return that. You have to be
careful on that machine.
And no quiz on C
should assume *implicitly* that the quizzee thinks sizeof(long)==4.
It's established by me in the begining, as I posted. I've been on machines
where the size of byte, short, and long are the same 32 bits, and sizeof()
each of them is 1.
A portable "quiz":
#include <stdio.h>
int main()
{
char arr[100][2];
char *p = arr[1];
char *q = arr[5];
int alpha = &arr[5] - &arr[1];
int beta = q - p;
int gamma = sizeof **arr;
printf("%d %d %d\n", alpha, beta, gamma);
return 0;
}
-Arthur
No good for my purposes. I'm looking for something very concise and
specific, and the ensuing conversation, part of which can be the C99
dictates about how it'll work on compilers, but is undefined by the spec.
WHOA. Please take a look at N869 3.18:
3.18
1 undefined behavior
behavior, upon use of a nonportable or erroneous program construct, of
erroneous data, or of indeterminately valued objects, for which this
International Standard *imposes no requirements*
2 NOTE Possible undefined behavior ranges from ignoring the situation
completely with unpredictable results, to behaving during translation or
program execution in a documented manner characteristic of the environment
(with or without the issuance of a diagnostic message), to terminating a
translation or execution (with the issuance of a diagnostic message).
3 EXAMPLE An example of undefined behavior is the behavior on integer
overflow.
When 3.18 #1 says that undefined behavior can be behavior for which this
standard imposes no requirements, is that suggesting that there are no
requirements for that issue. That null pointer incrementing is simply free
of requirements?
PLEASE do not freak out on me with ire. It does no good in this ng to do
so. I'm trying to dig through what is what.
I'm crossing this over to comp.lang.c so they can beat this up as well. For
those in c.l.c, the initiating concern is over the following interview
question of mine:
What does the following C snippet produce on a
"normal 32 bit system". That is, 32 bit longs, byte
addressable 32 bit address space, etc., etc. A
sparcstation 1 for example IIRC---no tricks, nothing
hidden. If there's a typo, I'm sorry, I'm typing this quickly.
long *a = 0;
long *b = 0;
a++;
b++; b++;
printf ("%d %d %d\n", a, b, (b-a));
Forget the newbies. 99% of the senior candidates rattle off:
4 8 4
(I'll add for the purists that a byte here is an octet.)
The goal of this question was to show that the answer would be:
4 8 1
but really to discuss pointer issues.
One of the big complaints here is that I'm being told that the C
specification does not allow me to increment a null pointer. Nor can I
subtract pointers that do not point within the same object (or 1 past an
array).
I'm going to repost this under something more concise if there's lackluster
response---it's getting unweildy.