Отличительной чертой математики со знаком / без знака является то, что при сдвиге номера со знаком вправо копируется самый старший бит. Когда вы сдвигаете число без знака, новые биты равны 0.
#define HIGH_BIT(n) ((n) & (1 << sizeof(n) * CHAR_BITS - 1))
#define IS_SIGNED(n) (HIGH_BIT(n) ? HIGH_BIT(n >> 1) != 0 : HIGH_BIT(~n >> 1) != 0
Таким образом, этот макрос использует условное выражение, чтобы определить, установлен ли старший бит числа. Если это не так, макрос устанавливает его путем побитового отрицания числа. Мы не можем сделать арифметическое отрицание, потому что -0 == 0. Затем мы сдвигаемся вправо на 1 бит и проверяем, произошло ли расширение знака.
Это предполагает арифметику дополнения 2, но обычно это безопасное предположение.