In article <bg**********@reader-00.news.insnet.cw.net>
"Ned" <no****@spam.com> wrote:
# char *foo(int idx)
# {
# switch (idx)
# {
# case 0:return "Hello";
# case 1:return "Goodbye";
# }
# return "world";
# }
# Im just wondering about stacks. Was this memory allocated on the stack
(It is not really clear what "this" memory is supposed to refer to,
although as it turns out, the most obvious guess -- the memory
holding the text of the string literals -- is what Ned meant.)
In article <vj************@corp.supernews.com>
Derk Gwen <de******@HotPOP.com> writes:String literals are allocated statickally. This code is the same as
char *foo(int idx) {
static char A[] = "Hello";
static char B[] = "Goodbye";
static char C[] = "world";
switch (idx) {
case 0: return A;
case 1: return B;
}
return C;
}
It is indeed "the same" with respect to storage duration. It is,
however, different in some other respects:
- The original version has three anonymous arrays, rather than
three named arrays. The new version has named arrays (A, B,
and C) whose names are visible inside foo(). This change is
unlikely to matter.
- The anonymous arrays in the original may or may not (at the
compiler's discretion) be placed in read-only memory. If so,
this has much the same effect as if the named arrays were "static
const char A[]" and so on. The *type* of the anonymous arrays
is "array N of char" but the storage itself *may* be read-only.
C does this rather bizarre thing mainly for historical reasons
("const" did not exist before C89). This change might well
matter, because it means that:
char *p = foo(n);
p[i] = new_value;
is invalid in the original, but valid in the replacement.
- Finally, the contents of the anonymous arrays in the original
may or may not (again at the compiler's discretion) be shared
with other string literals, while the contents of the named
arrays in the replacement are certainly not shared. Again, this
change might well matter. Given the replacement code, and a
(valid) assignment to p[i] as in the second difference above,
a later call to the replacement foo() will return the modified
string, but no other strings in the program will be modified.
On the other hand, if the compiler chooses not to place string
literals in read-only memory, yet *does* share string literals,
then something like the code below might produce the output
shown below (although technically the effect is undefined):
char *p = foo(0);
p[0] = 'J';
printf("I expect Jello here: %s\n", p);
printf("And here we print %s\n", "Hello");
[output]
I expect Jello here: Jello
And here we print Jello
In short, using an actual explicit array (of type "char [N]") has
the fundamentally different property of being a known, separate,
well-behaved ordinary array, which you can modify with predictable
behavior. Using the anonymous array (of type char [N]) produced
by a string literal gives you an array that *may* be read-only and
*may* share storage with other string literals in the program.
The storage duration is the same, but the accessibility and uniqueness
may change. As long as you do not attempt to overwrite string
literals -- in effect, treating them as arrays of "const char" --
this will not matter. In that respect, it would be nice if string
literals had type "const char [N]", but since "const" is rather
broken in C, and did not exist before 1989, they cannot have such
a type.
--
In-Real-Life: Chris Torek, Wind River Systems (BSD engineering)
Salt Lake City, UT, USA (40°39.22'N, 111°50.29'W) +1 801 277 2603
email: forget about it
http://67.40.109.61/torek/index.html (for the moment)
Reading email is like searching for food in the garbage, thanks to spammers.