bitwise.lua 9.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363
  1. -- $Id: testes/bitwise.lua $
  2. -- See Copyright Notice in file lua.h
  3. print("testing bitwise operations")
  4. require "bwcoercion"
  5. local numbits = string.packsize('j') * 8
  6. assert(~0 == -1)
  7. assert((1 << (numbits - 1)) == math.mininteger)
  8. -- basic tests for bitwise operators;
  9. -- use variables to avoid constant folding
  10. local a, b, c, d
  11. a = 0xFFFFFFFFFFFFFFFF
  12. assert(a == -1 and a & -1 == a and a & 35 == 35)
  13. a = 0xF0F0F0F0F0F0F0F0
  14. assert(a | -1 == -1)
  15. assert(a ~ a == 0 and a ~ 0 == a and a ~ ~a == -1)
  16. assert(a >> 4 == ~a)
  17. a = 0xF0; b = 0xCC; c = 0xAA; d = 0xFD
  18. assert(a | b ~ c & d == 0xF4)
  19. a = 0xF0.0; b = 0xCC.0; c = "0xAA.0"; d = "0xFD.0"
  20. assert(a | b ~ c & d == 0xF4)
  21. a = 0xF0000000; b = 0xCC000000;
  22. c = 0xAA000000; d = 0xFD000000
  23. assert(a | b ~ c & d == 0xF4000000)
  24. assert(~~a == a and ~a == -1 ~ a and -d == ~d + 1)
  25. a = a << 32
  26. b = b << 32
  27. c = c << 32
  28. d = d << 32
  29. assert(a | b ~ c & d == 0xF4000000 << 32)
  30. assert(~~a == a and ~a == -1 ~ a and -d == ~d + 1)
  31. do -- constant folding
  32. local code = string.format("return -1 >> %d", math.maxinteger)
  33. assert(load(code)() == 0)
  34. local code = string.format("return -1 >> %d", math.mininteger)
  35. assert(load(code)() == 0)
  36. local code = string.format("return -1 << %d", math.maxinteger)
  37. assert(load(code)() == 0)
  38. local code = string.format("return -1 << %d", math.mininteger)
  39. assert(load(code)() == 0)
  40. end
  41. assert(-1 >> 1 == (1 << (numbits - 1)) - 1 and 1 << 31 == 0x80000000)
  42. assert(-1 >> (numbits - 1) == 1)
  43. assert(-1 >> numbits == 0 and
  44. -1 >> -numbits == 0 and
  45. -1 << numbits == 0 and
  46. -1 << -numbits == 0)
  47. assert(1 >> math.mininteger == 0)
  48. assert(1 >> math.maxinteger == 0)
  49. assert(1 << math.mininteger == 0)
  50. assert(1 << math.maxinteger == 0)
  51. assert((2^30 - 1) << 2^30 == 0)
  52. assert((2^30 - 1) >> 2^30 == 0)
  53. assert(1 >> -3 == 1 << 3 and 1000 >> 5 == 1000 << -5)
  54. -- coercion from strings to integers
  55. assert("0xffffffffffffffff" | 0 == -1)
  56. assert("0xfffffffffffffffe" & "-1" == -2)
  57. assert(" \t-0xfffffffffffffffe\n\t" & "-1" == 2)
  58. assert(" \n -45 \t " >> " -2 " == -45 * 4)
  59. assert("1234.0" << "5.0" == 1234 * 32)
  60. assert("0xffff.0" ~ "0xAAAA" == 0x5555)
  61. assert(~"0x0.000p4" == -1)
  62. assert(("7" .. 3) << 1 == 146)
  63. assert(0xffffffff >> (1 .. "9") == 0x1fff)
  64. assert(10 | (1 .. "9") == 27)
  65. do
  66. local st, msg = pcall(function () return 4 & "a" end)
  67. assert(string.find(msg, "'band'"))
  68. local st, msg = pcall(function () return ~"a" end)
  69. assert(string.find(msg, "'bnot'"))
  70. end
  71. -- out of range number
  72. assert(not pcall(function () return "0xffffffffffffffff.0" | 0 end))
  73. -- embedded zeros
  74. assert(not pcall(function () return "0xffffffffffffffff\0" | 0 end))
  75. print'+'
  76. package.preload.bit32 = function () --{
  77. -- no built-in 'bit32' library: implement it using bitwise operators
  78. local bit = {}
  79. function bit.bnot (a)
  80. return ~a & 0xFFFFFFFF
  81. end
  82. --
  83. -- in all vararg functions, avoid creating 'arg' table when there are
  84. -- only 2 (or less) parameters, as 2 parameters is the common case
  85. --
  86. function bit.band (x, y, z, ...)
  87. if not z then
  88. return ((x or -1) & (y or -1)) & 0xFFFFFFFF
  89. else
  90. local arg = {...}
  91. local res = x & y & z
  92. for i = 1, #arg do res = res & arg[i] end
  93. return res & 0xFFFFFFFF
  94. end
  95. end
  96. function bit.bor (x, y, z, ...)
  97. if not z then
  98. return ((x or 0) | (y or 0)) & 0xFFFFFFFF
  99. else
  100. local arg = {...}
  101. local res = x | y | z
  102. for i = 1, #arg do res = res | arg[i] end
  103. return res & 0xFFFFFFFF
  104. end
  105. end
  106. function bit.bxor (x, y, z, ...)
  107. if not z then
  108. return ((x or 0) ~ (y or 0)) & 0xFFFFFFFF
  109. else
  110. local arg = {...}
  111. local res = x ~ y ~ z
  112. for i = 1, #arg do res = res ~ arg[i] end
  113. return res & 0xFFFFFFFF
  114. end
  115. end
  116. function bit.btest (...)
  117. return bit.band(...) ~= 0
  118. end
  119. function bit.lshift (a, b)
  120. return ((a & 0xFFFFFFFF) << b) & 0xFFFFFFFF
  121. end
  122. function bit.rshift (a, b)
  123. return ((a & 0xFFFFFFFF) >> b) & 0xFFFFFFFF
  124. end
  125. function bit.arshift (a, b)
  126. a = a & 0xFFFFFFFF
  127. if b <= 0 or (a & 0x80000000) == 0 then
  128. return (a >> b) & 0xFFFFFFFF
  129. else
  130. return ((a >> b) | ~(0xFFFFFFFF >> b)) & 0xFFFFFFFF
  131. end
  132. end
  133. function bit.lrotate (a ,b)
  134. b = b & 31
  135. a = a & 0xFFFFFFFF
  136. a = (a << b) | (a >> (32 - b))
  137. return a & 0xFFFFFFFF
  138. end
  139. function bit.rrotate (a, b)
  140. return bit.lrotate(a, -b)
  141. end
  142. local function checkfield (f, w)
  143. w = w or 1
  144. assert(f >= 0, "field cannot be negative")
  145. assert(w > 0, "width must be positive")
  146. assert(f + w <= 32, "trying to access non-existent bits")
  147. return f, ~(-1 << w)
  148. end
  149. function bit.extract (a, f, w)
  150. local f, mask = checkfield(f, w)
  151. return (a >> f) & mask
  152. end
  153. function bit.replace (a, v, f, w)
  154. local f, mask = checkfield(f, w)
  155. v = v & mask
  156. a = (a & ~(mask << f)) | (v << f)
  157. return a & 0xFFFFFFFF
  158. end
  159. return bit
  160. end --}
  161. print("testing bitwise library")
  162. local bit32 = require'bit32'
  163. assert(bit32.band() == bit32.bnot(0))
  164. assert(bit32.btest() == true)
  165. assert(bit32.bor() == 0)
  166. assert(bit32.bxor() == 0)
  167. assert(bit32.band() == bit32.band(0xffffffff))
  168. assert(bit32.band(1,2) == 0)
  169. -- out-of-range numbers
  170. assert(bit32.band(-1) == 0xffffffff)
  171. assert(bit32.band((1 << 33) - 1) == 0xffffffff)
  172. assert(bit32.band(-(1 << 33) - 1) == 0xffffffff)
  173. assert(bit32.band((1 << 33) + 1) == 1)
  174. assert(bit32.band(-(1 << 33) + 1) == 1)
  175. assert(bit32.band(-(1 << 40)) == 0)
  176. assert(bit32.band(1 << 40) == 0)
  177. assert(bit32.band(-(1 << 40) - 2) == 0xfffffffe)
  178. assert(bit32.band((1 << 40) - 4) == 0xfffffffc)
  179. assert(bit32.lrotate(0, -1) == 0)
  180. assert(bit32.lrotate(0, 7) == 0)
  181. assert(bit32.lrotate(0x12345678, 0) == 0x12345678)
  182. assert(bit32.lrotate(0x12345678, 32) == 0x12345678)
  183. assert(bit32.lrotate(0x12345678, 4) == 0x23456781)
  184. assert(bit32.rrotate(0x12345678, -4) == 0x23456781)
  185. assert(bit32.lrotate(0x12345678, -8) == 0x78123456)
  186. assert(bit32.rrotate(0x12345678, 8) == 0x78123456)
  187. assert(bit32.lrotate(0xaaaaaaaa, 2) == 0xaaaaaaaa)
  188. assert(bit32.lrotate(0xaaaaaaaa, -2) == 0xaaaaaaaa)
  189. for i = -50, 50 do
  190. assert(bit32.lrotate(0x89abcdef, i) == bit32.lrotate(0x89abcdef, i%32))
  191. end
  192. assert(bit32.lshift(0x12345678, 4) == 0x23456780)
  193. assert(bit32.lshift(0x12345678, 8) == 0x34567800)
  194. assert(bit32.lshift(0x12345678, -4) == 0x01234567)
  195. assert(bit32.lshift(0x12345678, -8) == 0x00123456)
  196. assert(bit32.lshift(0x12345678, 32) == 0)
  197. assert(bit32.lshift(0x12345678, -32) == 0)
  198. assert(bit32.rshift(0x12345678, 4) == 0x01234567)
  199. assert(bit32.rshift(0x12345678, 8) == 0x00123456)
  200. assert(bit32.rshift(0x12345678, 32) == 0)
  201. assert(bit32.rshift(0x12345678, -32) == 0)
  202. assert(bit32.arshift(0x12345678, 0) == 0x12345678)
  203. assert(bit32.arshift(0x12345678, 1) == 0x12345678 // 2)
  204. assert(bit32.arshift(0x12345678, -1) == 0x12345678 * 2)
  205. assert(bit32.arshift(-1, 1) == 0xffffffff)
  206. assert(bit32.arshift(-1, 24) == 0xffffffff)
  207. assert(bit32.arshift(-1, 32) == 0xffffffff)
  208. assert(bit32.arshift(-1, -1) == bit32.band(-1 * 2, 0xffffffff))
  209. assert(0x12345678 << 4 == 0x123456780)
  210. assert(0x12345678 << 8 == 0x1234567800)
  211. assert(0x12345678 << -4 == 0x01234567)
  212. assert(0x12345678 << -8 == 0x00123456)
  213. assert(0x12345678 << 32 == 0x1234567800000000)
  214. assert(0x12345678 << -32 == 0)
  215. assert(0x12345678 >> 4 == 0x01234567)
  216. assert(0x12345678 >> 8 == 0x00123456)
  217. assert(0x12345678 >> 32 == 0)
  218. assert(0x12345678 >> -32 == 0x1234567800000000)
  219. print("+")
  220. -- some special cases
  221. local c = {0, 1, 2, 3, 10, 0x80000000, 0xaaaaaaaa, 0x55555555,
  222. 0xffffffff, 0x7fffffff}
  223. for _, b in pairs(c) do
  224. assert(bit32.band(b) == b)
  225. assert(bit32.band(b, b) == b)
  226. assert(bit32.band(b, b, b, b) == b)
  227. assert(bit32.btest(b, b) == (b ~= 0))
  228. assert(bit32.band(b, b, b) == b)
  229. assert(bit32.band(b, b, b, ~b) == 0)
  230. assert(bit32.btest(b, b, b) == (b ~= 0))
  231. assert(bit32.band(b, bit32.bnot(b)) == 0)
  232. assert(bit32.bor(b, bit32.bnot(b)) == bit32.bnot(0))
  233. assert(bit32.bor(b) == b)
  234. assert(bit32.bor(b, b) == b)
  235. assert(bit32.bor(b, b, b) == b)
  236. assert(bit32.bor(b, b, 0, ~b) == 0xffffffff)
  237. assert(bit32.bxor(b) == b)
  238. assert(bit32.bxor(b, b) == 0)
  239. assert(bit32.bxor(b, b, b) == b)
  240. assert(bit32.bxor(b, b, b, b) == 0)
  241. assert(bit32.bxor(b, 0) == b)
  242. assert(bit32.bnot(b) ~= b)
  243. assert(bit32.bnot(bit32.bnot(b)) == b)
  244. assert(bit32.bnot(b) == (1 << 32) - 1 - b)
  245. assert(bit32.lrotate(b, 32) == b)
  246. assert(bit32.rrotate(b, 32) == b)
  247. assert(bit32.lshift(bit32.lshift(b, -4), 4) == bit32.band(b, bit32.bnot(0xf)))
  248. assert(bit32.rshift(bit32.rshift(b, 4), -4) == bit32.band(b, bit32.bnot(0xf)))
  249. end
  250. -- for this test, use at most 24 bits (mantissa of a single float)
  251. c = {0, 1, 2, 3, 10, 0x800000, 0xaaaaaa, 0x555555, 0xffffff, 0x7fffff}
  252. for _, b in pairs(c) do
  253. for i = -40, 40 do
  254. local x = bit32.lshift(b, i)
  255. local y = math.floor(math.fmod(b * 2.0^i, 2.0^32))
  256. assert(math.fmod(x - y, 2.0^32) == 0)
  257. end
  258. end
  259. assert(not pcall(bit32.band, {}))
  260. assert(not pcall(bit32.bnot, "a"))
  261. assert(not pcall(bit32.lshift, 45))
  262. assert(not pcall(bit32.lshift, 45, print))
  263. assert(not pcall(bit32.rshift, 45, print))
  264. print("+")
  265. -- testing extract/replace
  266. assert(bit32.extract(0x12345678, 0, 4) == 8)
  267. assert(bit32.extract(0x12345678, 4, 4) == 7)
  268. assert(bit32.extract(0xa0001111, 28, 4) == 0xa)
  269. assert(bit32.extract(0xa0001111, 31, 1) == 1)
  270. assert(bit32.extract(0x50000111, 31, 1) == 0)
  271. assert(bit32.extract(0xf2345679, 0, 32) == 0xf2345679)
  272. assert(not pcall(bit32.extract, 0, -1))
  273. assert(not pcall(bit32.extract, 0, 32))
  274. assert(not pcall(bit32.extract, 0, 0, 33))
  275. assert(not pcall(bit32.extract, 0, 31, 2))
  276. assert(bit32.replace(0x12345678, 5, 28, 4) == 0x52345678)
  277. assert(bit32.replace(0x12345678, 0x87654321, 0, 32) == 0x87654321)
  278. assert(bit32.replace(0, 1, 2) == 2^2)
  279. assert(bit32.replace(0, -1, 4) == 2^4)
  280. assert(bit32.replace(-1, 0, 31) == (1 << 31) - 1)
  281. assert(bit32.replace(-1, 0, 1, 2) == (1 << 32) - 7)
  282. -- testing conversion of floats
  283. assert(bit32.bor(3.0) == 3)
  284. assert(bit32.bor(-4.0) == 0xfffffffc)
  285. -- large floats and large-enough integers?
  286. if 2.0^50 < 2.0^50 + 1.0 and 2.0^50 < (-1 >> 1) then
  287. assert(bit32.bor(2.0^32 - 5.0) == 0xfffffffb)
  288. assert(bit32.bor(-2.0^32 - 6.0) == 0xfffffffa)
  289. assert(bit32.bor(2.0^48 - 5.0) == 0xfffffffb)
  290. assert(bit32.bor(-2.0^48 - 6.0) == 0xfffffffa)
  291. end
  292. print'OK'