C
Christopher Benson-Manica
Joe Wright said:Please allow me..
Likewise...
#include <stdio.h>
int main(void) {
char *s = "abc";
int *i = (int *)s;
printf("%08x", *i);
printf("%08x\n", *i);
Joe Wright said:Please allow me..
Likewise...
#include <stdio.h>
int main(void) {
char *s = "abc";
int *i = (int *)s;
printf("%08x", *i);
Lew Pitcher said:The answer is that the program is poorly written and invokes behaviour that is
not defined by the C standard. As "undefined behaviour" means that anything
can happen, the output value of 636\261 is just as valid (and just as likely)
as any other output.
Christopher Benson-Manica said:Equally valid, yes, but hardly as likely, unless there are an infinite
number of DS9K implementations to smooth out the spike at 636261
produced by non-evil little endian ASCII implementations.
But there are an infinite number of DS9K implementations. (They're
not required to exist physically, are they?)
Christopher Benson-Manica said:Equally valid, yes, but hardly as likely, unless there are an infinite
number of DS9K implementations to smooth out the spike at 636261
produced by non-evil little endian ASCII implementations.
You could point out all the errors and nonportable assumptions in the code.
But you are not interviewing the interviewer, probably.
He's deciding whether he wants you,
Companies want "team players",
Keith said:6.2.5p9 is what I was thinking of (though I hadn't bothered to look it
up). It guarantees the same representation, but the statement that
The same representation and alignment requirements are meant to
imply interchangeability as arguments to functions, return values
from functions, and members of unions.
is relegated to a footnote; thus my use of the word "almost". I
hadn't been aware of 6.5.2.2p6, which makes the guarantee explicitly
in normative text.
Keith said:For context, here are the relevant lines from the original cruddy
program:
char *s = "abc";
int *i = (int *) s;
It's certainly true that there's no guarantee that the string has any
particular alignment, but I think most implementations do tend to
store strings (and, more generally, arrays) at a stricter alignment
than is required. Doing so can have some performance advantages. For
example, an implementation of memcpy(), or even strcpy(), might use
word moves whenever both the source and the target are suitably
aligned.
It's yet another instance of undefined behavior that's very likely to
work as expected (unfortunately).
[...]pete said:Keith said:Army1987 said:On Wed, 08 Aug 2007 16:18:04 -0700, Keith Thompson wrote: [...]
Also, calling printf with no prototype in scope invokes undefined
behavior (the fix is to add a '#include <stdio.h>' to the top of the
source file). And "%x" is the wrong format for printing an int;
probably 'i' should have been declared as an unsigned int* (the
standard *almost* says that it will work anyway, but it's not
something I'd be comfortable counting on).
For sufficiently large values of "almost". See 6.5.2.2p6, the part
with in n1124.pdf is on the beginning of the next page.
Also see the first sentence of 6.2.5p9.
You were thinking about the fact that *i could be negative?
6.2.5p9 is what I was thinking of (though I hadn't bothered to look it
up). It guarantees the same representation, but the statement that
The same representation and alignment requirements are meant to
imply interchangeability as arguments to functions, return values
from functions, and members of unions.
is relegated to a footnote; thus my use of the word "almost". I
hadn't been aware of 6.5.2.2p6, which makes the guarantee explicitly
in normative text.
The wording of the footnote is wishywashy.
Would the footnote mean something different
if it was written this way?:
The same representation and alignment requirements
imply interchangeability as arguments to functions, return values
from functions, and members of unions.
Keith Thompson said:But there are an infinite number of DS9K implementations. (They're
not required to exist physically, are they?)
Rajeet said:Good day group.
I was asked in an interview to explain the behavior of this program.
void main()
{
char *s = "abc";
int *i = (int *) s;
printf("%x", *i);
}
The question is: why is the output 636261? I don't think I know enough
about C to understand how the conversions between pointer types are
occurring.
Mark said:Euh, interviews are two-way. Do you really want to work for a company
which employs people who don't care about code errors?
Kenneth Brody said:Well, this may be more a case of "we're only coding for one specific
platform, and don't care about portability". (Not that that's
necessarily a good thing, but at least the code becomes "system
specific behavior" rather than "errors". Of course, what happens
when they decided to port to a similar, but 64-bit, platform?)
Answer the interviewer was probably looking for:
The implementation uses 32-bit integers, is little-endian, and
uses the ASCII character set.
How optimistic of you. The answer they were looking for could have been:
Integers are laid out in memory with the least significant byte first.
In other words, not just "this code is running on a little-endian
platform" but "the whole world is little-endian, there is no such
thing as big-endian, and no need for us to use or understand the
descriptive term little-endian because there's no alternative from
which it needs to be distinguished"
use unsigned int rather than int,
I believe it's undefined behavior to cast a char * to an unsigned *
and then dereference it, no less than casting to an int * and then
dereferencing.
I believe it's undefined behavior to cast a char * to an unsigned *
and then dereference it,
Want to reply to this thread or ask your own question?
You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.