I compiled this code using Visual Studio 2010 (cl.exe /W4
) as a C file:
int main( int argc, char *argv[] )
{
unsigned __int64 a = 0x00000000
Use this to avoid the sign extension:
unsigned __int64 a = 0x00000000FFFFFFFFLL;
Note the L on the end. Without this it is interpreted as a 32-bit signed number (-1) and then cast.
Converting a pointer to/from an integer is implementation defined.
Here is how gcc does it, i.e. it sign extends if the integer type is larger than the pointer type(this'll happen regardless of the integer being signed or unsigned, just because that's how gcc decided to implement it).
Presumably msvc behaves similar. Edit, the closest thing I can find on MSDN is this/this, suggesting that converting 32 bit pointers to 64 bit also sign extends.
Integer constants (e.g, 0x00000000FFFFFFFF
) are signed integers by default, and hence may experience sign extension when assigned to a 64-bit variable. Try replacing the value on line 3 with:
0x00000000FFFFFFFFULL
From the C99 standard (§6.3.2.3/6):
Any pointer type may be converted to an integer type. Except as previously specified, the result is implementation-defined. If the result cannot be represented in the integer type, the behavior is undefined. The result need not be in the range of values of any integer type.
So you'll need to find your compiler's documentation that talks about that.