Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is there any valid use for a sign-preserving left shift?

There's three basic shifts:

  • Logical left shift: ignores sign bit altogether.
  • Logical right shift: clears sign bit if shift > 0.
  • Arithmetic left shift: same as logical left shift.
  • Arithmetic right shift: retains top bit.

Intel has both sal and shl, but they map to the same opcode and most other architectures seem to only have three mnemonics in the first place.

You could recast the grid in terms of sign-preserving vs not:

  • Logical + arithmetic left shift: not sign-preserving.
  • Logical right shift: not sign-preserving.
  • Arithmetic right shift: sign-preserving.

But this gives rise to a new possibility, a left shift that is sign-preserving. This would have the behavior of retaining the sign bit, but shifting the rest as normal.

And now I have a couple questions:

  1. Is this of any real-world use?
  2. Does any architecture implement this?

Edit: To clarify, what I mean by "sign-preserving" is this, for the example of a left shift of 1 and a bit width of 8:

Not sign-preserving:
S A B C D E F G
 / / / / / / /
A B C D E F G 0

Sign-preserving:
S A B C D E F G
|  / / / / / /
S B C D E F G 0

Hope this helps!


Footnote 1: Fun fact: x86 has a 2nd undocumented opcode for left shifts, e.g. d0 /4 and d0 /6 are both left-shift by 1 of a byte. Sandpile even claims that one is SHL and one is SAL, but the current Intel x86 manuals only document the /4 encoding for both SAL and SHL.

It's unclear if original 8086 was actually designed to use separate opcodes for the 2 names for the same operation, or if the alias opcode has always been undocumented. Whatever the history was, modern x86 no longer documents separate opcodes. (8 instructions share the same leading byte with the /r field distinguishing them: ROL/ROR, RCL/RCR, SHL/SHR, and SAL/SAR. Sticking some other non-shift instruction into the /6 encoding would have cost transistors, and making it fault would probably also have cost more transistors, so it makes sense that original 8086 was designed with a redundant encoding for left shifting, the only question is if/how it was documented historically.)

But this is totally tangential to the actual question: x86's SAL is not the sign-bit-preserving shift being asked about.

like image 613
Isiah Meadows Avatar asked Jun 04 '19 08:06

Isiah Meadows


People also ask

Does Left Shift preserve sign?

No. The sign bit is not preserved -- as the sign bit will be shifted. And if the bit, just right of the sign bit is 1, then the resultant will be negative.

What is an arithmetic shift left?

Arithmetic left shifts are equivalent to multiplication by a (positive, integral) power of the radix (e.g., a multiplication by a power of 2 for binary numbers). Logical left shifts are also equivalent, except multiplication and arithmetic shifts may trigger arithmetic overflow whereas logical shifts do not.

Does C use logical or arithmetic shift?

Many C compilers choose which right shift to perform depending on what type of integer is being shifted; often signed integers are shifted using the arithmetic shift, and unsigned integers are shifted using the logical shift.

What are the differences between arithmetic shift right and shift right operation?

Logical right shift means shifting the bits to the right and MSB(most significant bit) becomes 0. Example: Logical right shift of number 1 0 1 1 0 1 0 1 is 0 1 0 1 1 0 1 0. Arithmetic right shift means shifting the bits to the right and MSB(most significant bit) is same as in the original number.


1 Answers

The Intel 80960 shli instruction behaves this way. The description says, “if the bits shifted out are not the same as the sign bit, an overflow fault is generated. If overflow occurs, the sign of the result is the same as the sign of the src operand.” (The overflow fault can be masked. Even if it is not masked, the destination operand is written with the result.)

like image 174
prl Avatar answered Nov 15 '22 08:11

prl