question about cast

G

Garma

Richard Heathfield said:
int main(void)

{

You can't assign to a value, only to an object. (int)y is a value, not an
object. You should get a diagnostic. Turn up your warning level.


int main(void)

{

Same reason the first one shouldn't. You can't assign to a value, only to an
object. (double)y is a value, not an object.

--
Richard Heathfield : (e-mail address removed)
"Usenet is a strange place." - Dennis M Ritchie, 29 July 1999.
C FAQ: http://www.eskimo.com/~scs/C-faq/top.html
K&R answers, C books, etc: http://users.powernet.co.uk/eton

My question may not be related to OP much.
What is an object that is different from value in CO?
Could you elaborate further on "You can't assign to a value, only to an
object."
Thanks!
 
H

Horst Kraemer

[snippage]
double x;
double *y;
(int) y = x;

Your compiler uses some extension to the C language.

This much is reasonably clear (the other "likely" possibility is that
his compiler is simply broken :) ).
In C the first assignment may be written as

*(int*)&y = x;

Note that one popular compiler that adds a "cast as lvalue" rule,
the GNU C Compiler (gcc), defines cast-as-lvalue *very* differently.
The assignment to (int)y is not equivalent to the above, but rather
to the (syntactically valid but semantically dodgy) ANSI/ISO C code:

(int)(y = (double *)(int)&x)

Apparently it doesn't act according the definition:

For this file

double x=1;
double *y=0;

void f(void)
{
(int)y=x;
}


gcc 3.2 (mingw) produces this output


.file "foo.c"
.globl _x
.data
.align 8
_x:
.long 0
.long 1072693248
.globl _y
.align 4
_y:
.long 0
.text
.align 2
.globl _f
.def _f; .scl 2; .type 32; .endef
_f:
pushl %ebp
movl %esp, %ebp
subl $4, %esp
fldl _x ## load double from _x
fnstcw -2(%ebp)
movw -2(%ebp), %ax
movb $12, %ah
movw %ax, -4(%ebp)
fldcw -4(%ebp)
fistpl _y ## store int to _y
fldcw -2(%ebp)
leave
ret


which converts the double value in &x to int and stores it to &y and
is semantically equivalent to

*(int*)&y = x;

Regards
Horst
 
K

Keith Thompson

Garma said:
My question may not be related to OP much.
What is an object that is different from value in CO?
Could you elaborate further on "You can't assign to a value, only to an
object."

(Is "CO" a typo for "C"?)

An object is a variable (more or less; the C standard rarely uses the
term "variable", and an object needn't be modifiable). An object is a
container; the thing it contains is a value.

For example:

int x;
x = 42; /* ok: x is an object */
42 = x; /* illegal: 42 is a value, so you can't assign to it */
(x + 1) = 43; /* illegal: x + 1 is a value, so you can't assign to it */

Look up "lvalue" in your C textbook.
 
C

Chris Torek

Apparently it doesn't ...

Sorry, I goofed -- I added an "&" that was not in the original
code, of which this is a version:
double x=1;
double *y=0;

void f(void)
{
(int)y=x;
}

Since y has type "double *", the "GCC meaning" is:

(int)(y = (double *)(int)x)

If you compile this:
*(int*)&y = x;

you do indeed get the same machine code, because "int", "int *",
and "double *" all have the same size and format on the x86; and
of course the last quoted C code line above has the same meaning
as:

*(int *)&y = (int)x;

Converting x to int requires code that changes the representation
-- this is the fldl/fistpl instruction pair (the control word store
and reload, fnstcw and fldcw, are red herrings) -- but converting
the resulting "int" to "double *" requires no code on the (32-bit)
Intel (it does require code on IA-64 and the like). This hides
the difference between "then convert int to double *" vs "now just
assign". If you have access to a 64-bit machine, gcc should generate
different code for these two cases (i.e., the two casts then assign
to y, vs the one cast or automatic conversion to assign to *(int *)&y).

(You will also get warnings about converting from 32-bit integers
to 64-bit pointers, where that occurs.)
 
R

Richard Bos

The return type of main has nothing to do with the problem I'm talking
about.

You do not know that. Undefined is undefined.
My question is: is it possible to cast a pointer to a double ?

And the obvious answer is "no". As you'd already observed yourself.
I think it does not make more sense to cast a pointer to int than casting
a pointer to double ...

The Standard Committee thought differently, and so do I.

To every address in memory, you can at least assign _some_ kind of index
number. That index number might not make sense in the context of any
other program running on the same computer, or indeed when interpreted
as any other kind of pointer than the original, but it is, at least,
possible, and might in principle be useful to someone doing a very
low-level, system-specific job.
Transforming an address in memory to a floating-point number, however,
does not make sense at all, not even in Gnuck. How, to begin with, would
you map them?

Richard
 
R

Richard Bos

Horst Kraemer said:
Your compiler uses some extension to the C language. It allows
(int)y=x because sizeof(int)==sizeof y on this platform and it refuses
(double)y=x because sizeof(double)>sizeof y on this platform.

This does not explain why we _can_ assign longs to ints and vice versa.

Richard
 
H

Horst Kraemer

Sorry, I goofed -- I added an "&" that was not in the original
code, of which this is a version:


Since y has type "double *", the "GCC meaning" is:

(int)(y = (double *)(int)x)

OK, the fog clears up. Thanks for your input.
 
D

Dan Pop

In said:
about. My question is: is it possible to cast a pointer to a double ?

No, the language does not define such a conversion.
I think it does not make more sense to cast a pointer to int than casting
a pointer to double ...

You're dead wrong. On most implementations using linear addressing,
pointers contain memory addresses which are integers and converting
a pointer to an integer is a run time no-op. Such conversions are often
useful, e.g. when you need to check if a pointer is correctly aligned.

OTOH, converting an address to a floating point type doesn't have much
meaning or use. It's still possible, though, just not directly:
(double)(unsigned long)pointer.

Dan
 
I

Irrwahn Grausewitz

Trollsdale said:
Yacine wrote:

Sorry about your encounters with our "indigenous trolls".
After awhile you'll begin to recognize them and ignore them.

Whoever bell'd that cat did a good job.
 

Ask a Question

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.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,744
Messages
2,569,483
Members
44,903
Latest member
orderPeak8CBDGummies

Latest Threads

Top