[Date Prev][Date Next][Thread Prev][Thread Next]
[Date Index]
[Thread Index]
- Subject: LuaJIT - loop conditional code generation
- From: Jani Piitulainen <jani.piitulainen+ll@...>
- Date: Wed, 29 Feb 2012 19:45:30 +0200
Is there a way to stop simple conditionals in a loop from jumping out of a compiled trace?
"bit.band" with one argument is used here to tell LuaJIT result is a 32-bit integer, it's compiled to nothing. It can sometimes be useful reducing unnecessary double <-> int conversions (like cvtsi2sd & cvtsd2si).
for i=1, 1000000, 1 do
if band(i, 7)==0 then
c = band(c + 1)
end
if band(i, 7)==3 then
c = band(c - 1)
end
a = band(a + c)
end
Using LuaJIT git head x64. The generated code is very similar for x86.
ebx = i, ebp = a, eax = c
->LOOP:
394cffd0 mov r15d, ebx
394cffd3 and r15d, +0x07
394cffd7 jz 0x394c0028 ->6 -- this jumps out of the JITted trace, right? why not jnz to "cmp r15d, +0x03" here + add eax, 1?
394cffdd cmp r15d, +0x03
394cffe1 jz 0x394c002c ->7
394cffe7 add ebp, eax
394cffe9 add ebx, +0x01
394cffec cmp ebx, 0x000f4240
394cfff2 jle 0x394cffd0 ->LOOP
Full code:
local bit = require("bit");
local band=bit.band;
function test()
local a=band(0)
local c=band(1)
for i=1, 1000000, 1 do
if band(i, 7)==0 then
c = band(c + 1)
end
c = band(c - 1)
end
-- changing conditions into following form produces effectively identical x64 code
-- c = band(c + (band(i, 7)==0 and 1 or 0))
-- c = band(c - (band(i, 7)==3 and 1 or 0))
a = band(a + c)
end
return a,c
end
for j=1, 10, 1 do
print(test())
end
Thanks,
Jani Piitulainen