Search code examples
c64-bitx86-64bit-shiftstdint

Left-shifting an uint64_t zeroes out most significant dword


The title sums it up: left-shifting an uint64_t doesn't output the expected value, and I'd like to know why. What I get is the expected result with its 4 most significant bytes zeroed out. I'm using an x86_64 CPU (Intel i7 3770k), on Debian Jessie 64bit. This is a test program that reproduces the same behavior.

#include <stdio.h>
#include <stdint.h>

int main(int argc, char * * argv)
{
    uint64_t var = 0xDEFEC8ED;

    printf("%016x\n", var << 24);

    return 0;
}

OUTPUT 00defec8ed000000 // expected 00000000ed000000 // obtained


Solution

  • It is uint64_t and you need a different type for the printf

    #include <stdio.h>
    #include <stdint.h>
    
    int main(int argc, char * * argv)
    {
        uint64_t var = 0xDEFEC8ED;
    
        printf("%016llx\n", (unsigned long long)(var << 24));
    
        return 0;
    }
    

    Which is not fully correct because there are special macros for printing those types since C99:

    #include <stdio.h>
    #include <stdint.h>
    #include <inttypes.h>
    
    int main(int argc, char * * argv)
    {
        uint64_t var = 0xDEFEC8ED;
    
        printf("%016" PRIX64 "\n", var << 24);
    
        return 0;
    }
    

    But you may or may not have them.