http://tobba.pw/disasm.php
Put in any code and it will compile and disassemble it, for optimization or educational purposes (actually do whatever the hell you want)
Note that it only supports ~120 opcodes right now, most ones used only in one place like the ones for the built-in icon procs are not supported at this time
Current problems:
* Switch statements dont always decode properly, and the whole thing sometimes dies in a fire on them
* Globals come out with their number instead of their name (need to write code to handle the defvar table)
* Above also applies for certain proc calls
ID:1304890
![]() Jun 27 2013, 2:14 pm
|
|
Flame Sage wrote:
Just as a general warning: That's an extremely infantile and redundant warning considering this is a legitimately useful resource, and also the likelihood this guy made a disassembler to steal yur speshul codez is just about nil. |
Interesting:
proc/add(x, y) |
proc/Add(a, b) Even more interesting stuff. Using the . operator is much faster than creating your own variable, and using the return statement directly is even slightly faster. |
I'm gonna have to add some code that decodes the defvars structures and such, then I can nicely list the variable and argument names for each function
And then I need to make it store a proper indexable list of defvars without it becoming a mess I should also restructure the whole way it handles opcodes to be much more flexible, which would make writing the IL recompiler simpler later on |
Doohl wrote:
> proc/Add(a, b) Even more interesting stuff. Using the . operator is much faster than creating your own variable, and using the return statement directly is even slightly faster. Yep, so this means if you need to manipulate a single variable in a proc, you should always use ., and if you need to only return a value with no manipulation, use return. |
or just do what you think makes the most readable code because an extra instruction isn't a big deal
|
Giacomand wrote:
or just do what you think makes the most readable code because an extra instruction isn't a big deal I would very much go for this. The tool provided is very interesting, and may (as the OP notes) be useful for understanding what is produced, which may help tweaking optimisation on heavy algorithms you cannot replace for whatever reason, but this stuff certainly ain't top priority for the majority of your codebase. |
Most of my code problems are figuring out how to do something many many times in a single tick because the VM seems to be slow at calculating a lot of trig at once. So this is definitely helpful in those situations...
The majority of byond won't benefit from this because most people have very basic problems. |
If you're using any math functions, note that:
/proc/a() It was mostly meant for some debugging purposes of my own, but it had some nice uses figuring out what is going on internally and generally an insight in how weird BYOND is in a lot of places |
That kind of behaviour is normal for many optimising compilers. "5*5" is an easy expression to evaluate - to optimise out abs(5) requires proving some things about abs() (no side-effects, for example), and frankly that's a pain.
More complicated optimising compilers tend to do things like special-case simple mathematical functions applied to constants, but sometimes they get that wrong and weird things happen in edge cases. Basically, not optimising out abs(5) is the correct decision for a project on DM's scale. Maybe if they were the visual studio compiler team it wouldn't be. But they don't have those resources and the potential benefit is minor. Also: That's an extremely infantile and redundant warning considering this is a legitimately useful resource, and also the likelihood this guy made a disassembler to steal yur speshul codez is just about nil. Agreed. |
abs(5) is actually pretty much no different than -5 operation wise with how the bytecode works right now
It actually does optimise that now because of some work Lummox JR did |
FIREking wrote:
Most of my code problems are figuring out how to do something many many times in a single tick because the VM seems to be slow at calculating a lot of trig at once. So this is definitely helpful in those situations... So very true. 99% of this community is not at the point where they would ever care about this or even understand when and why they should. |
I think Stephen's ultimate point is that complex, does not equate into useful.
Everyone programs differently, despite being given the same tools. Albert Einstein said it best to sum it all up-- "If you don't understand a subject enough to explain it simply, you don't understand it very well at all." I personally believe that. It's nice to have a tool like this at your disposal-- but it's usefulness is really just dependent upon "how" you code your games. |
atom/wtf/Del() Double ret? Bug or i'm don't understand something? |
Weird stuff
//////////////////////////////////// |
Double ret is because return compiles right down to ret/retval, theres also always a ret inserted by the compiler, so if you type return at the end you end up with two rets
|
O_o Dear god, I was right!
Thanks Tobba! I've been writing my own VM for the last two days. I'm doing it with no experience in writing VMs, and I just started writing without doing any research. I'm actually pretty impressed with how close my solution is to Dan's, given that he produced that after being taught how to do VMs, and I produced something similar with pure inductive reasoning. One thing that absolutely baffles me, is why they are using opcodes for built-in procs. It would make more sense to me to store a C pointer to the function, then essentially post-compile, jam the internal function call pointers into a lookup table. Then you make an opcode for INSTRUCTION_INTERNAL_CALL and slap that bad boy in there. That way, the opcode looks something like this: push [arg1]..[argX] push [argcount] push [memaddr] icall For any function overriding a built-in function, you just set up the proc index list to skip any values that have a memaddr pointer to an icall. That way, you can find out what ..() is simply by subtracting 1 from the reference index then accessing proc_refs[ref-1] |
I wouldn't input any DM code in here you don't want to get stolen, any input into someone else's server could have the potential to get logged.