notcake / glib

[Deprecated] OOP Lua library for Garry's Mod.
GNU General Public License v3.0
19 stars 7 forks source link

Implement LuaJIT 2.1.0 new instructions in decompiler #7

Open ExtReMLapin opened 4 years ago

ExtReMLapin commented 4 years ago

New instructions are

SpiralP commented 4 years ago

I'm hitting this by trying to print functions with the 2 arg for loop

for _ in next, {} do end

 SpiralP@self: function() for _ in next,{} do end end

    glib/lua/decompiler/functionbytecodereader.lua:629: attempt to index local 'variable' (a nil value)
         1: DecompilePass1 (self = { GLib.Lua.FunctionBytecodeReader: 0x01e6de905a00 }) [glib/lua/decompiler/functionbytecodereader.lua: 629]
         2: Decompile (self = { GLib.Lua.FunctionBytecodeReader: 0x01e6de905a00 }) [glib/lua/decompiler/functionbytecodereader.lua: 444]
         3: ToString (self = { GLib.Lua.FunctionBytecodeReader: 0x01e6de905a00 }) [glib/lua/decompiler/functionbytecodereader.lua: 335]
         4: ToString (self = { GLib.Lua.BytecodeReader: 0x01e6e3073298 }) [glib/lua/decompiler/bytecodereader.lua: 113]
         5: Print (self = GCompute.GLua.Printing.FunctionPrinter, printer = { GCompute.GLua.Printing.Printer: 0x01e6fdafe218 }, coloredTextSink = { GCompute.Pipe: 0x01e6df53f160 }, obj = function (), printingOptions = 1, alignmentController = { GCompute.GLua.Printing.AlignmentController: 0x01e6fdafde18 }, alignmentSink = GCompute.GLua.Printing.NullAlignmentController) [gcompute/glua/printing/functionprinter.lua: 82]
         6: (success = true, function ()) [gcompute/execution/local/gluaexecutioninstance.lua: 163]
         7: Start (self = { GCompute.Execution.GLuaExecutionInstance: 0x01e6e55b7648 }) [gcompute/execution/local/gluaexecutioninstance.lua: 172]
         8: CreateExecutionInstance (self = { GCompute.Execution.GLuaExecutionContext: 0x01e7065a7f58 }, code = "function() for _ in next,{} do end end", sourceId = "@repl_0", instanceOptions = 15, callback = nil) [gcompute/execution/executioncontext.lua: 56]
         9: HandleExecutionInstanceCreationRequest0 (self = { GCompute.Execution.RemoteExecutionContextHost: 0x01e6cafa0ed0 }, connection = { GLib.Net.Connection: 0x01e6e200ec78 }, inBuffer = { GLib.Net.Layer1.PinnedUsermessageInBuffer: 0x01e6dc3fc3f0 }) [gcompute/execution/remote/remoteexecutioncontexthost.lua: 94]
        10: (self = { GCompute.Execution.RemoteExecutionContextHost: 0x01e6cafa0ed0 }, connection = { GLib.Net.Connection: 0x01e6e200ec78 }, inBuffer = { GLib.Net.Layer1.PinnedUsermessageInBuffer: 0x01e6dc3fc3f0 }) [gcompute/```
ExtReMLapin commented 4 years ago

I didn't take the time to get in the luajit code again but referencing the instructions itself isn't hard at all

https://github.com/ExtReMLapin/glib/commits/master

You probably get an error because the olders instructions gets shifted as the new instructions are being inserted between existing ones, not at the end

ExtReMLapin commented 4 years ago

We could go monkey mode and pretend new ins act the same as their "neighbor" (from the commit updated list) but without analyzing the luajit code thats a bit risky

For example you could MAYBE add GETR ins here https://github.com/notcake/glib/blob/bfb3bd19e1651765c9bb36c6de088eb5978a8094/lua/glib/lua/decompiler/functionbytecodereader.lua#L889

notcake commented 4 years ago

The version field in the string.dump() output is 0x01 for 2.0.4 and 0x02 for 2.1.0. The decompiler should be changed to choose which opcode list to use depending on the version field.

notcake commented 4 years ago

Also you didn't make it clear in the OP that it was actually broken rather than producing bad output.

notcake commented 4 years ago

https://github.com/LuaJIT/LuaJIT/commit/73ef845fcaf65937ad63e9cf6b681cb3e61f4504#diff-9d814c5fdcaea6a77da5a688c4488819

ExtReMLapin commented 4 years ago

I didn't make it clear since I had no issue with it, it was a "preventive" issue.

ExtReMLapin commented 4 years ago

The version field in the string.dump() output is 0x01 for 2.0.4 and 0x02 for 2.1.0. The decompiler should be changed to choose which opcode list to use depending on the version field.

I don't see the point of using string.dump as you can already get the luajit version with jit.ver and you can get instructions with jit.util lib as i do here

notcake commented 4 years ago

I don't want to assume the bytecode came from the same LuaJIT environment.

SpiralP commented 4 years ago

Here's another case. I'm finding these by just printing random hooks on my client

SpiralP@self: function() if a ~= b.c then end end

    glib/lua/decompiler/functionbytecodereader.lua:647: attempt to index local 'variable' (a nil value)
         1: DecompilePass1 (self = { GLib.Lua.FunctionBytecodeReader: 0x01d9fc173e28 }) [glib/lua/decompiler/functionbytecodereader.lua: 647]
         2: Decompile (self = { GLib.Lua.FunctionBytecodeReader: 0x01d9fc173e28 }) [glib/lua/decompiler/functionbytecodereader.lua: 444]
ExtReMLapin commented 2 years ago

sir please