Search code examples
cassemblycompilationlow-level

C datatypes size after compilation


The question is as follows: does the C programming language define how the executables produced by compilers should be formatted in terms of data size types? To better explain this, let's assume I compile a C source code file that contains a variable of type int called 'x'. I successfully compile the source code into an executable and run it. During runtime the memory location allocated for 'x' is 4 bytes wide and structured under 2's complement standard.

If I were to run the same compiled executable from a different machine with the same operating system and a compatible CPU, do I have any guarantee that the variable will at all times be 4 bytes wide in the exact same format (meaning the exact same bit footprint)? I know that C has variable data sizes for elementary types and that this only applies to pre-compiled code. But what about post-compiled code? If int translates to assembler DWORD data type on one machine that allocates 32 bits to it, is there any guarantee it will take the form of 32 bits on another? Is DWORD always the same across different CPUs of the same model?

I've always assumed that compilation is just the process of establishing all implementation details and 'setting in stone' the exact size and internal formats of data types in-memory but I would like some confirmation. Also, does this apply to C++ as well?


Solution

  • Below the C level, compilers also abide by some "application binary interface" (abbreviated ABI; not to mistake with API). This is what sets these details in stone. The application binary interface defines the size of types and the representation of integers, among a lot of other things, like how parameters are passed to functions.

    A single platform can support multiple ABIs. For instance, on Windows, you have the native ABI, and you can install Cygwin, which lets you run programs with an ABI closer to the Linux one. However, assuming that two different machines have support for the same ABI, then yes, sharing executables between them is guaranteed to work (assuming the required libraries and such are present) and everything is guaranteed to have a compatible representation.

    This is the same in principle for C++.