Lua BitOp 提供5.1和5.2版本位操作运算 (跨平台C语言实现 说明部分1)

来源:互联网 发布:中学生预防网络诈骗 编辑:程序博客网 时间:2024/06/07 13:50
BitOp作为The LuaJIT Project中的一个子项目。
Lua BitOp is a C extension module for Lua 5.1/5.2 which adds bitwise operations on numbers.
Features 特点:
支持的位运算符:
Supported functions: bit.tobit, bit.tohex, bit.bnot, bit.band, bit.bor, bit.bxor, bit.lshift, bit.rshift, bit.arshift, bit.rol, bit.ror, bit.bswap
16位 32位 64位操作平台
Consistent semantics across 16, 32 and 64 bit platforms.
支持LUA Number的类型
Supports different lua_Number types: either IEEE 754 doubles, int32_t or int64_t.
运行的操作系统
Runs on Linux, *BSD, Mac OS X, Windows and probably anything else you can find.
Compatible with the built-in bitwise operations in LuaJIT 2.0.
It's as fast as you can get with the standard Lua/C API.



BitOp
Lua uses only a single number type which can be redefined at compile-time.
By default this is a double, i.e. a floating-point number with 53 bits of precision.
Operations in the range of 32 bit numbers (and beyond) are exact.
There is no loss of precision, so there is no need to add an extra integer number type.
Modern desktop and server CPUs have fast floating-point hardware — FP arithmetic is nearly the same speed as integer arithmetic.
Any differences vanish under the overhead of the Lua interpreter itself.
Even today, many embedded systems lack support for fast FP operations.
These systems benefit from compiling Lua with an integer number type (with 32 bits or more).
The different possible number types and the use of FP numbers cause some problems when defining bitwise operations on Lua numbers.
The following sections define the operational semantics and try to explain the rationale behind them.
LUA语言仅仅使用一种数字类型。并且可以在编译前重新定义。
默认情况下,LUA使用Double类型作为LUA Number的实现。Double类型有53位精度。
操作32位范围内的数字是精确的。所有,没有必须增加额外的整数类型。
现在桌面和服务器CPU都有很快操作float-point硬件。Float-point 速度和整数计算速度相当。
甚至在今天,许多嵌入式系统缺少对float-pointer类型支持。这些操作系统使用整数作为Lua Number来受益。
但是,使用Float-Point作为Lua Number类型导致位操作问题。
Input and Output Ranges
1、
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.
位操作符不能直接在Float-Point类型上面使用或者Float-Point类型的二进制上面使用。
在使用Float-Point或者Float-Point二进制时,必须把他们转换换成整数。位操作完成后再转换成Float-Point.
2、
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.
使用32位整数可以跨所有操作系统。
3、
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.
float类型提供24位精度。float不太适合作为位运算。同时,LUA BitOp不使用float作为Lua Number的实现。
4、
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.
位操作运算符把位模式看做无符号类型。(在右移动时,符号位没有被忽略)
5、
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).
LUA Number类型必须是有符号类型同时被限制至少32位。如果重新定位LUA Number作为无符号类型将不能跨平台。
所有位运算必须被定义为返回值为至少32位有符号类型。
6、
Hexadecimal literals are treated as unsigned numbers by the Lua parser before converting them to the Lua number type.
This means they can be out of the range of signed 32 bit integers if the Lua number type has a greater range.
E.g. 0xffffffff has a value of 4294967295 in the default installation, but may be -1 on embedded systems.
当LUA解析16进制常量时,数值在被转换成Lua Number前被认为无符号类型。
这就意味着返回值可能是超过32位有符号的范围。例如:0xffffffff默认情况下位2^32,但是在嵌入式系统中可能为-1;
7、
It's highly desirable that hex literals are treated uniformly across systems when used in bitwise operations.
All bit operations accept arguments in the signed or the unsigned 32 bit range (and more, see below).
Numbers with the same underlying bit pattern are treated the same by all operations.
16进制在所有平台上使用位操作时必须被统一。所有位操作符文必须接受32位有符号类型或无符号类型。
LUA Number类型的所有位操作必须被统一对待。


Modular Arithmetic
Arithmetic operations on n-bit integers are usually based on the rules of  modular arithmetic modulo 2n.
Numbers wrap around when the mathematical result of operations is outside their defined range.
This simplifies hardware implementations and some algorithms actually require this behavior (like many cryptographic functions).
E.g. for 32 bit integers the following holds: 0xffffffff + 1 = 0

Arithmetic modulo 232 is trivially available if the Lua number type is a 32 bit integer.
Otherwise normalization steps must be inserted.
Modular arithmetic should work the same across all platforms as far as possible:
1、
For the default number type of double, arguments can be in the range of ±2^51 and still be safely normalized across all platforms by taking their least-significant 32 bits.
The limit is derived from the way doubles are converted to integers.
2、
?The function bit.tobit can be used to explicitly normalize numbers to implement modular addition or subtraction.
E.g. bit.tobit(0xffffffff + 1) returns 0 on all platforms.
3、?The limit on the argument range implies that modular multiplication is usually restricted to multiplying already normalized numbers with small constants. FP numbers are limited to 53 bits of precision, anyway.
 E.g. (2^30+1)2 does not return an odd number when computed with doubles.
 
Restricted and Undefined Behavior
The following rules are intended to give a precise and useful definition (for the programmer).
yet give the implementation (interpreter and compiler) the maximum flexibility and the freedom to apply advanced optimizations.
It's strongly advised not to rely on undefined or implementation-defined behavior.
下面规则主要为了用户可以确定精度和用户行为。同时解释器和编译器也没有提供实现。这样用户可以拥有最大化的自由去提高优化。
All kinds of floating-point numbers are acceptable to the bitwise operations.
None of them cause an error, but some may invoke undefined behavior:
1、-0 is treated the same as +0 on input and is never returned as a result.
2、Passing ±Inf, NaN or numbers outside the range of ±251 as input yields an undefined result.
3、Non-integral numbers may be rounded or truncated in an implementation-defined way.
This means the result could differ between different BitOp versions, different Lua VMs, on different platforms or even between interpreted vs. compiled code
所有的Float-Point类型都可以接受位操作运算。但是伪操作运算不会引起操作,但是位操作运算的结果是不确定的。
1、-0和+0都可以作为参数,但是不能作为返回值。
2、解析 ±Inf, NaN 时超过2^51位返回结果将是未定义的。

Avoid passing fractional numbers to bitwise functions. Use math.floor() or math.ceil() to get defined behavior.
当为了避免位操作法时Float-Point类型时,可以通过math.floor() or math.ceil() 来获取整数部分来实现定义的行为。


0 0
原创粉丝点击