On the other hands, there are some "tricks" that someone trying to duplicate that functionality in a higher level language can do, too.
For example, our computers nowadays are much faster and have much more memory. So suppose you have some long, tricky section of assembly code that you know computers some sort of function of a single 32-bit input.
You could simply run that section, in a simulator, with all possible 32-bit inputs and make a table of the results. Then instead of trying to understand what is going on by following the convoluted assembly, your task is to implement the function given by that table. With the function in table form you can do things like look for sections that are linear, or constant, of follow other common patterns.
Hopefully you can get some idea from context in the assembly code what, at a high level, the function is doing, and that should further help you see patterns in the table.
At that point you might as well embed an emulator with a facility to call to/from plain java code. Then you could gradually move things over as needed.
For example, our computers nowadays are much faster and have much more memory. So suppose you have some long, tricky section of assembly code that you know computers some sort of function of a single 32-bit input.
You could simply run that section, in a simulator, with all possible 32-bit inputs and make a table of the results. Then instead of trying to understand what is going on by following the convoluted assembly, your task is to implement the function given by that table. With the function in table form you can do things like look for sections that are linear, or constant, of follow other common patterns.
Hopefully you can get some idea from context in the assembly code what, at a high level, the function is doing, and that should further help you see patterns in the table.