Home Explore Blog CI



neovim

4th chunk of `runtime/doc/lua-bit.txt`
a4e7152c66b0f90251075c61b99b52d9bf78d1cbe9f1decf0000000100000fa0
 = rshift(j, 5)
          p[jx] = band(p[jx], rol(-2, j))
        end
      end
    end

    io.write(string.format("Found %d primes up to %d\n", count, m))
<
Lua BitOp is quite fast. This program runs in less than 90 milliseconds on a 3
GHz CPU with a standard Lua installation, but performs more than a million
calls to bitwise functions. If you're looking for even more speed, check out
|lua-luajit|.

------------------------------------------------------------------------------
Caveats                                                      *lua-bit-caveats*

Signed Results ~

Returning signed numbers from bitwise operations may be surprising to
programmers coming from other programming languages which have both signed and
unsigned types. But as long as you treat the results of bitwise operations
uniformly everywhere, this shouldn't cause any problems.

Preferably format results with `bit.tohex` if you want a reliable unsigned
string representation. Avoid the `"%x"` or `"%u"` formats for `string.format`. They
fail on some architectures for negative numbers and can return more than 8 hex
digits on others.

You may also want to avoid the default number to string coercion, since this
is a signed conversion. The coercion is used for string concatenation and all
standard library functions which accept string arguments (such as `print()` or
`io.write()`).

Conditionals ~

If you're transcribing some code from C/C++, watch out for bit operations in
conditionals. In C/C++ any non-zero value is implicitly considered as `true`.
E.g. this C code: >c
    if (x & 3) ...
<
must not be turned into this Lua code: >lua
    if band(x, 3) then ... -- wrong!
<
In Lua all objects except `nil` and `false` are considered `true`. This
includes all numbers. An explicit comparison against zero is required in this
case: >lua
    if band(x, 3) ~= 0 then ... -- correct!

Comparing Against Hex Literals ~

Comparing the results of bitwise operations (signed numbers) against hex
literals (unsigned numbers) needs some additional care. The following
conditional expression may or may not work right, depending on the platform
you run it on: >lua
    bit.bor(x, 1) == 0xffffffff
<
E.g. it's never true on a Lua installation with the default number type. Some
simple solutions:

    Never use hex literals larger than 0x7fffffff in comparisons: >lua
        bit.bor(x, 1) == -1
<
    Or convert them with bit.tobit() before comparing: >lua
        bit.bor(x, 1) == bit.tobit(0xffffffff)
<
    Or use a generic workaround with bit.bxor(): >lua
        bit.bxor(bit.bor(x, 1), 0xffffffff) == 0
<
    Or use a case-specific workaround: >lua
        bit.rshift(x, 1) == 0x7fffffff
<
==============================================================================
OPERATIONAL SEMANTICS AND RATIONALE                        *lua-bit-semantics*


Input and Output Ranges ~
                                                          *lua-bit-io-ranges*

Bitwise operations cannot sensibly be applied to FP numbers (or their
underlying bit patterns). They must be converted to integers before operating
on them and then back to FP numbers.

It's desirable to define semantics that work the same across all platforms.
This dictates that all operations are based on the common denominator of 32
bit integers. The `float` type provides only 24 bits of precision. This makes it
unsuitable for use in bitwise operations. Lua BitOp refuses to compile against
a Lua installation with this number type.

Bit operations only deal with the underlying bit patterns and generally ignore
signedness (except for arithmetic right-shift). They are commonly displayed
and treated like unsigned numbers, though.

But the Lua number type must be signed and may be limited to 32 bits. Defining
the result type as an unsigned number would not be cross-platform safe. All
bit operations are thus defined to return results in the range of signed 32
bit numbers (converted to the Lua number type).

                                      

Title: Lua BitOp: Caveats, Signed Results, Conditionals, and Operational Semantics
Summary
This section discusses potential pitfalls and considerations when using Lua BitOp, including the implications of signed results, the need for explicit comparisons in conditionals (unlike C/C++), and issues when comparing against hexadecimal literals. It also explains the operational semantics and rationale behind Lua BitOp, emphasizing the use of 32-bit integers for cross-platform compatibility and the decision to return signed 32-bit numbers as results.