[squeak-dev] Bit operators (was: Is anyone else running a 64-bit image on a regular basis?)

Bert Freudenberg bert at freudenbergs.de
Mon Sep 8 16:28:59 UTC 2014


On 08.09.2014, at 16:45, David Corking <lists at dcorking.com> wrote:
> Bert Freudenberg wrote:
> 
>>> Indeed. Not just C though.
>>> In JavaScript I discovered that (42 << 32) == 42.
> 
> Thanks Bert.
> 
> Also confirmed on Google Chrome 36.0 (V8 3.26) and Node v0.10.
> 
> Right shift is the same (42 >> 32) == 42.
> And (42 >> 35) == 5

It's in the ECMAScript standard. At least it's the same everywhere.

> Did you have to work around it when designing SqueakJS ?

Yes: https://github.com/bertfreudenberg/SqueakJS/commit/6d694d0733

> My guess is
> not: I guess that the SqueakJS VM is a purely 32 bit machine, and that
> this behaviour won't affect Smalltalk programs.

The VM needs to provide the bitShift primitive for SmallIntegers. That is, it needs to return a correct result if that fits into a SmallInt, and fail otherwise (it could also generate a LargeInt, but doesn't have to).

In Squeak, the single "bitShift:" methods shifts both left and right depending on the argument's sign, whereas in most other languages, you cannot shift by a negative amount. So there is one thing to watch out when implementing a VM.

I'm not really sure what happens in C, but in JS you get this nicety when shifting by a negative number:

	16 << -8 == 268435456

So the VM needs to handle negative shifts separately anyway, and in JS it needs to special-case shifts larger than 31, too.

> Have fun!
> David
> 
> p.s.
> 
> I wonder if this is a restriction imposed by the language standard, or
> is merely a side effect of a common implementation choice. The MDN
> reference page says "Bitwise operators treat their operands as a
> sequence of 32 bits".  Which, with hindsight, leaves shifts of more
> than 31 bits undefined.
> https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Bitwise_Operators

They're well defined, they just operate on 32 bit signed values:

	1<<31 == -2147483648

That is, the result of shifts and bitwise operators is always done in 32 bits. But there's no direct way to detect overflow (even though other JS integer operations are accurate to 53 bits [because there are no actual integers]).

> However, my naive reading of this paragraph of the ECMAScript 5
> standard suggests that wrapping around a bit shift is just plain
> wrong, and that it should yield 0 or fail (until a 64 bit Javascript
> standard is written)
> http://www.ecma-international.org/ecma-262/5.1/#sec-11.7

Marvel at 11.7.1 step 7:

	• Let shiftCount be the result of masking out all but the least significant 5 bits of rnum, that is, compute rnum & 0x1F.

- Bert -



-------------- next part --------------
A non-text attachment was scrubbed...
Name: smime.p7s
Type: application/pkcs7-signature
Size: 4142 bytes
Desc: not available
Url : http://lists.squeakfoundation.org/pipermail/squeak-dev/attachments/20140908/b8d440cf/smime.bin


More information about the Squeak-dev mailing list