Are there any guarantees made by the C language specification that the size of a short will always be double the size of a char?

Viewed 93

From my research, these were the only guarantees that I could find about these built-in integer data types:

  • char will not be smaller than 8 bits
  • short will not be smaller than 16 bits
  • short will not be smaller than char

In practice, according to my experience, short is always double the size of char, but it does not appear that this is a guarantee made by the C language specification. It seems that a scenario such as a 16 bit char and a 16 bit short could still be valid.

This is more of a curiosity question, I realize that if you really need exact widths for your integer data types, you're better off using the stdint.h header.

UPDATE 5/6/2021: I do not believe this question is a duplicate of What platforms have something other than 8-bit char?. I am not asking about the specific size of a char, but rather the ratio between a char and a short, regardless of the actual size of either one. At least for me, many of these answers have enlightened me in a way that the "duplicate" question has not. I hope this also helps others that stumble upon it.

3 Answers

As a few people have already pointed out, the specification makes no guarantees about the "bit widths" of built in types, it's left up to the implementation of the compiler for the given architecture how these are defined.

What's maybe more interesting is how this gets used in practice. In fact there are "current" architectures which have built-in sizes that don't follow the usual 1-2-4-8 conventions. A good example of this (and the one that I have a fair amount of personal experience with) is the Analog Devices SHARC.

From the Wikipedia page:

it knows nothing of 8-bit or 16-bit values since each address is used to point to a whole 32-bit word, not just an octet. It is thus neither little-endian nor big-endian, though a compiler may use either convention if it implements 64-bit data and/or some way to pack multiple 8-bit or 16-bit values into a single 32-bit word. Analog Devices chose to avoid the issue by using a 32-bit char in their C compiler.

A 32-bit character could definitely be called a "pathological" case, but it works just fine for the SHARC, which is widely used in professional and prosumer audio applications. See Universal Audio's Apollo as an example.

In theory, all of char, short, int could have the same size.

Very few implementations are doing that in practice (I cannot name any; I think in the previous century you might have found some)

There is no such guarantee.

The C standard specifies the following values as minimums:

#define CHAR_BIT                         8
#define CHAR_MAX    UCHAR_MAX or SCHAR_MAX
#define CHAR_MIN            0 or SCHAR_MIN
#define INT_MAX                     +32767
#define INT_MIN                     -32767
#define LONG_MAX               +2147483647
#define LONG_MIN               -2147483647
#define LLONG_MAX     +9223372036854775807
#define LLONG_MIN     -9223372036854775807
#define MB_LEN_MAX                       1
#define SCHAR_MAX                     +127
#define SCHAR_MIN                     -127
#define SHRT_MAX                    +32767
#define SHRT_MIN                    -32767
#define UCHAR_MAX                      255
#define USHRT_MAX                    65535
#define UINT_MAX                     65535
#define ULONG_MAX               4294967295
#define ULLONG_MAX    18446744073709551615

So you could have a system where CHAR_BIT is 16 and the max/min values for char match the above minimums for short and the ones for short are unchanged from above, in which case char and short would be the same size.

Related