Skip to content

Instantly share code, notes, and snippets.

@dave1707
Created January 3, 2017 19:56
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save dave1707/31a2e7f1bb2a6ea2946e9bb21e54600b to your computer and use it in GitHub Desktop.
Save dave1707/31a2e7f1bb2a6ea2946e9bb21e54600b to your computer and use it in GitHub Desktop.
Lua Bytecode
function convertToByteCode()
aa=3
bb=5
cc=7
dd=aa+bb*cc
end
function setup()
textMode(CORNER)
parameter.boolean("showOps",false)
parameter.boolean("prnt",false)
hString='str="'
hexString=""
charString=""
hexTable={}
opsTable={}
hexDx,hexDy=0,0
opsDx,opsDy=0,0
dump(string.dump(convertToByteCode,true))
createOpsString()
end
function draw()
background(0)
fill(255)
if showOps then
text("Op Instruction Description...",25+opsDx,HEIGHT-25+opsDy)
for a,b in pairs(opsTable) do
text(b,25+opsDx,HEIGHT-a*20-60+opsDy)
end
else
text("Hex dump of the bytecode file",25+hexDx,HEIGHT-25+hexDy)
for a,b in pairs(hexTable) do
text(b,10+hexDx,HEIGHT-a*20-60+hexDy)
end
end
if prnt then
print(table.concat(hexTable))
print(table.concat(opsTable))
prnt=false
end
end
function dump(s)
pos={4,2,6,6,11,6,4,4,3,4,4,4,15}
row=HEIGHT-50
col,off,cnt=0,1,0
opsOffset=47
opsStart=opsOffset+4
varsShown=0
varStart=0
nbrOps=string.byte(s,opsOffset,opsOffset)
for z=1,nbrOps+1 do
pos[z+10]=4
end
varOffset=47+4+nbrOps*4
nbrVars=string.byte(s,varOffset,varOffset)
if nbrVars>0 then
varStart=varOffset+4
pos[#pos+1]=4
end
for z=1,#s do
cnt=cnt+1
col=col+1
v=string.byte(s,z,z)
c=" "..string.char(v).." "
hx=string.format("%02x",v)
hexString=hexString..hx.." "
if v<32 or v>126 then
c=" "
end
charString=charString..c
if cnt>=opsStart and cnt<varOffset then
hString=hString..hx
end
if cnt==varStart then
varsShown=varsShown+1
if varsShown<=nbrVars then
variableSize(cnt,s)
else
table.insert(hexTable,"... File not formatted beyond this point ...\n")
end
end
if pos[off]==nil then
pos[off]=15
end
if col>=pos[off] then
showComments()
table.insert(hexTable,hexString.."\n")
table.insert(hexTable,charString.."\n")
hexString=""
charString=""
col=0
off=off+1
row=row-40
end
end
if hexString~="" then
table.insert(hexTable,hexString.."\n")
table.insert(hexTable,charString.."\n")
end
hString=hString..'"'
loadstring(hString)()
end
function variableSize(c,s)
r0=string.byte(s,c,c)
r1=string.byte(s,c+1,c+1)
if r0==0 then
pos[off]=1
varStart=varStart+1
elseif r0==1 then
pos[off]=2
varStart=varStart+2
elseif r0==3 then
pos[off]=9
varStart=varStart+9
elseif r0==4 then
pos[off]=r1+1
varStart=varStart+r1+1
elseif r0==19 then
pos[off]=9
varStart=varStart+9
end
end
function touched(t)
if t.state==MOVING then
if showOps then
opsDx=opsDx+t.deltaX
opsDy=opsDy+t.deltaY
else
hexDx=hexDx+t.deltaX
hexDy=hexDy+t.deltaY
end
end
end
function createOpsString()
rr="ops={"
for z=1,#str,8 do
rr=rr..'"'
for y=z+6,z,-2 do
rr=rr..string.sub(str,y,y+1)
end
rr=rr..'",'
end
rr=rr.."}"
loadstring(rr)()
createOpsHex()
end
function createOpsHex()
font("Courier")
textMode(CORNER)
for z=1,#ops do
hexBinary(ops[z])
valA=0
for z=8,1,-1 do
if string.sub(strA,z,z)=="1" then
valA=valA+2^(8-z)
end
end
valB=0
for z=9,2,-1 do
if string.sub(strB,z,z)=="1" then
valB=valB+2^(9-z)
end
end
if string.sub(strB,1,1)=="1" then
valB=-valB-1
end
valC=0
for z=9,2,-1 do
if string.sub(strC,z,z)=="1" then
valC=valC+2^(9-z)
end
end
if string.sub(strC,1,1)=="1" then
valC=-valC-1
end
valO=0
for z=6,1,-1 do
if string.sub(strO,z,z)=="1" then
valO=valO+2^(6-z)
end
end
valsBx=0
for z=18,2,-1 do
if string.sub(strsBx,z,z)=="1" then
valsBx=valsBx+2^(18-z)
end
end
valsBx=131070-valsBx
if string.sub(strsBx,1,1)=="1" then
valsBx=valsBx-131071
end
valBx=0
for z=18,2,-1 do
if string.sub(strBx,z,z)=="1" then
valBx=valBx+2^(18-z)
end
end
opCodes(valO,valA,valB,valC,valsBx,valBx)
end
end
function opCodes(op,a,b,c,sBx,Bx)
local str="op code missing "..op
if op==0 then
str=string.format("%2d MOVE R(%d) = R(%d)",op,a,b)
elseif op==1 then
str=string.format("%2d LOADK R(%d) = Kst(%d)",op,a,Bx)
elseif op==2 then
str=string.format("%2d LOADKX R(%d) = Kst(extra arg)",op,a)
elseif op==3 then
str=string.format("%2d LOADBOOL R(%d) = (Bool)%d; if (%d) pc++",op,a,b,c)
elseif op==4 then
str=string.format("%2d LOADNIL R(%d),R(%d+1), ..., R(%d+%d) = nil",op,a,a,a,b)
elseif op==5 then
str=string.format("%2d GETUPVAL R(%d) = UpValue[%d]",op,a,b)
elseif op==6 then
str=string.format("%2d GETTABUP R(%d) = UpValue[%d][%d]",op,a,b,c)
elseif op==7 then
str=string.format("%2d GETTABLE R(%d) = R(%d)[RK(%d)]",op,a,b,c)
elseif op==8 then
str=string.format("%2d SETTABUP UpValue[%d][RK(%d)] = RK(%d)",op,a,b,c)
elseif op==9 then
str=string.format("%2d SETUPVAL UpValue[%d] = R(%d)",op,b,a)
elseif op==10 then
str=string.format("%2d SETTABLE R(%d)[RK(%d)] = RK(%d)",op,a,b,c)
elseif op==11 then
str=string.format("%2d NEWTABLE R(%d) = {} (size=%d,%d)",op,a,b,c)
elseif op==12 then
str=string.format("%2d SELF R(%d+1) = R(%d); R(%d)=R(%d)[RK(%d)]",op,a,b,a,b,c)
elseif op==13 then
str=string.format("%2d ADD R(%d) = RK(%d) + RK(%d)",op,a,b,c)
elseif op==14 then
str=string.format("%2d SUB R(%d) = RK(%d) - RK(%d)",op,a,b,c)
elseif op==15 then
str=string.format("%2d MUL R(%d) = RK(%d) * RK(%d)",op,a,b,c)
elseif op==16 then
str=string.format("%2d MOD R(%d) = RK(%d) %% RK(%d)",op,a,b,c)
elseif op==17 then
str=string.format("%2d POW R(%d) = RK(%d) ^ RK(%d)",op,a,b,c)
elseif op==18 then
str=string.format("%2d DIV R(%d) = RK(%d) / RK(%d)",op,a,b,c)
elseif op==19 then
str=string.format("%2d IDIV R(%d) = RK(%d) // RK(%d)",op,a,b,c)
elseif op==20 then
str=string.format("%2d BAND R(%d) = RK(%d) & RK(%d)",op,a,b,c)
elseif op==21 then
str=string.format("%2d BOR R(%d) = RK(%d) | RK(%d)",op,a,b,c)
elseif op==22 then
str=string.format("%2d BXOR R(%d) = R(%d) ~ R(%d)",op,a,b,c)
elseif op==23 then
str=string.format("%2d SHL R(%d) = RK(%d) << RK(%d)",op,a,b,c)
elseif op==24 then
str=string.format("%2d SHR R(%d) = R(%d) >> R(%d)",op,a,b,c)
elseif op==25 then
str=string.format("%2d UNM R(%d) = -R(%d)",op,a,b)
elseif op==26 then
str=string.format("%2d BNOT R(%d) = ~R(%d)",op,a,b)
elseif op==27 then
str=string.format("%2d NOT R(%d) = not R(%d)",op,a,b)
elseif op==28 then
str=string.format("%2d LEN R(%d) = length of R(%d)",op,a,b)
elseif op==29 then
str=string.format("%2d CONCAT R(%d) = R(%d)..R(%d)",op,a,b,c)
elseif op==30 then
str=string.format("%2d JMP pc += %d",op,sBx)
elseif op==31 then
str=string.format("%2d EQ if ((RK(%d) == RK(%d)) ~= %d then pc++ ",op,b,c,a)
elseif op==32 then
str=string.format("%2d LT if ((RK(%d) < RK(%d)) ~= %d then pc++ ",op,b,c,a)
elseif op==33 then
str=string.format("%2d LE if ((RK(%d) <= RK(%d)) ~= %d then pc++ ",op,b,c,a)
elseif op==34 then
str=string.format("%2d TEST if not (R(%d) <=> %d) then pc++",op,a,c)
elseif op==35 then
str=string.format("%2d TESTSET if (R(%d) <=> %d) then R(%d) =R(%d) else pc++",op,b,c,a,b)
elseif op==36 then
str=string.format("%2d CALL R(%d), ..., R(%d+%d-2)=R(%d)(R(%d+1), ..., R(%d+%d-1))",op,a,a,c,a,a,a,b)
elseif op==37 then
str=string.format("%2d TAILCALL return R(%d)(R(%d+1), ..., R(%d+%d-1))",op,a,a,a,b)
elseif op==38 then
str=string.format("%2d RETURN R(%d), ..., R(%d+%d-2)",op,a,a,b)
elseif op==39 then
str=string.format("%2d FORLOOP R(%d) += R(%d+2) if R(%d) <?= R(%d+1) then {pc+=%d; R(%d+3)=R(%d)}",op,a,a,a,a,sBx,a,a)
elseif op==40 then
str=string.format("%2d FORPREP R(%d) -= R(%d+2) pc+=%d",op,a,a,sBx)
elseif op==41 then
str=string.format("%2d TFORCALL R(%d+3), ..., R(%d+2+%d) = R(%d)(R(%d+1)R(+d+2))",op,a,a,c,a,a,a)
elseif op==42 then
str=string.format("%2d TFORLOOP if R(%d+1) ~= nil then {R(%d) = R(%d+1); pc += %d}",op,a,a,a,sBx)
elseif op==43 then
str=string.format("%2d SETLIST R(%d)[(%d-1) * FPF+i] = R(%d+i) 1<=i<=%d",op,a,c,a,b)
elseif op==44 then
str=string.format("%2d CLOSURE R(%d) = closure(KPROTO[%d])",op,a,Bx)
end
table.insert(opsTable,str.."\n")
end
function hexBinary(num)
local tab={["0"]="0000",["1"]="0001",["2"]="0010",["3"]="0011",
["4"]="0100",["5"]="0101",["6"]="0110",["7"]="0111",
["8"]="1000",["9"]="1001",["a"]="1010",["b"]="1011",
["c"]="1100",["d"]="1101",["e"]="1110",["f"]="1111"}
local str=""
local cnt=0
for z=1,#num do
s=string.sub(num,z,z)
str=str..tab[s]
end
local str1=""
local str2=""
for z=1,#str do
cnt=cnt+1
s=string.sub(str,z,z)
str1=str1..s
str2=str2..s
if cnt==9 then
strB=str1
str1=""
elseif cnt==18 then
strC=str1
strsBx=str2
strBx=str
str1=""
elseif cnt==26 then
strA=str1
str1=""
elseif cnt==32 then
strO=str1
end
end
end
function showComments()
if off==1 then
hexString=hexString.." File signature"
elseif off==2 then
hexString=hexString.." (x.) Lua version"
elseif off==7 then
hexString=hexString.." Beginning line number of function used"
elseif off==8 then
hexString=hexString.." Ending line number of function used"
elseif off==9 then
hexString=hexString.." ..x Number of registers used"
elseif off==10 then
hexString=hexString.." Number of Op code lines"
elseif cnt>47 and off==nbrOps+11 then
hexString=hexString.." Number of Variable or Constant lines"
end
end
@srijan-paul
Copy link

Hey there, I randomly came across this script while looking for a way to convert Lua code to bytecode, Am I supposed to include this and call it from my script ? I'm kind of confused on the usage.

@dave1707
Copy link
Author

dave1707 commented Sep 30, 2020 via email

@LucianoRodriguez0764
Copy link

I've multiple Worms3D Scripts in .lub extension. I know that if i want to see the configs of that missions, I need to decompile them into .lua files. Do you know how to do it?

Example of the code I want to see from the .lub file

bronzetime � pB� zD� ÀyD�� silvertime � �A� goldtime � à@�� id1 � �� id2 �� id3 ��

@dave1707
Copy link
Author

Luk0764 I’m not sure what that code looks like or what a .lub file is for. The above program was just meant to convert small lines of code just to see what the byte code looked like. If you look at the above program in the first function “convertToByteCode”, it just takes a few lines of lua code and converts that to byte code. It doesn’t take a .lua file and convert it. So I don’t think this program will do anything for you. The above program was written on my iPad using the app Codea from the Apple App Store. Codea uses the Lua language.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment