1

I'm implementing a library, that uses many bit tricks under the hood. One of the requirements is for the signed integer right shift to be arithmetic.

Whether the "right-bit-shift on negative signed integer" fills the empty left side with zeroes or ones is implementation-defined - but how can I check which one it is during compilation?

One of my ideas was:

static_assert( ((int32_t{-1}) >> 31) == -1, "");
static_assert( ((int64_t{-1}) >> 63) == -1, "");

But can I be sure, that this operation will be performed the same way both during compile time and runtime? Is there any better way to check that?

Kaznov
  • 1,035
  • 10
  • 17
  • The behaviour is defined by the C++20 standard to be arithmetic, filling with ones - but I need an answer working for previous standards too. – Kaznov Aug 29 '21 at 20:41
  • There are several similar questions. [This one](https://stackoverflow.com/questions/5123314/compile-time-checking-if-right-shift-is-arithmetic-on-signed-types) is pretty close, although I'm not sure about some of the suggestions in the answers. – 1201ProgramAlarm Aug 29 '21 at 21:56

1 Answers1

0

This is exactly what static assert is meant for, so your first idea is probably the best one. I believe that static_assert() should make certain that it will work during runtime too, but if you want to do a runtime check to be certain, assert() works the same way but do the check during runtime, I would just put it at the start of your main function to only do the check once.

Suggestion: I would actually add an error message into the static_assert like static_assert( ((int32_t{-1}) >> 31) == -1, "int32_t Right Shift Is Not Arithmetic"); so if you ever compile for a different implementation of right shift you know what the error is.

kjhayes
  • 143
  • 7