I have a nice fully functioning module (wrtten using tcl/cpp) it works fine.
I want to use ramdebugger to debug scripts using that module
When I enter
load mylib.so
command1_from_lib xx
command2_from lib yy
If (say) command2 returns an error then ramdebugger dies
[paul#paul-es5 ramdebugger7.7.1]$ ./ramdebugger
alloc: invalid block: 0x999c058: 0 0
Aborted
It dies here in libtcl / ResetObjResult
if ((objResultPtr->bytes != NULL)
&& (objResultPtr->bytes != tclEmptyStringRep)) {
ckfree((char *) objResultPtr->bytes);
}
My suspicion is there is confusion over the global tclEmptyStringRep. I think the starkitted(?) ramdebugger has one and the dynamically loaded libtcl has a different one - the bytes pointer should logically be pointing to an empty string but the value there does not match what gdb shows for the global
I am a tcl noob and need any help I can get. Alternatively a suggestion for a different debugger would work
edit: fixed
Use tclStub to defer the link between the extension and the tcl runtime.
This sounds very much like a bug to me, as opposed to a question which this site can answer. You should contact the ramdebugger people to see if they can help.
However, for general Tcl debugging you could also see if the tools produced by ActiveState help; IIRC you can get a free trial to see if they can make any headway. (Myself, I'm of the put-lots-of-printf-calls in school of debugging, so I'm nobody's poster child.)
Related
when I reverse the binary with IDA gui, all the functions get decompiled without a problem.
but when I am running an automatic script on ida without gui, there is always the same function, that refuses to be decompiled. (when I am openning the same IDB that the automation script worked on, the function get decompiled without a problem)
I am using bip. and using BipFunc.can_decompile to check if a function can get decompiled.
EDIT:
according to an answer bellow, I have tried to add the following:
if not func.can_decompile:
print(f"can't decompile function 0x{func.ea:04x}, trying again")
decomp_all()
if not func.can_decompile:
print(f"can't decompile function 0x{func.ea:04x}, trying again")
decomp_all_twice_cacheclear()
if not func.can_decompile:
print(f"can't decompile function 0x{func.ea:04x}, skipping...")
return
sadly it did not work, I get all 3 prints every time, even on different binaries
it seems to be fixed on IDA Pro 7.6
There is several reason you can get an error on the decompilation from IDA. If it works on some case and other it does not it is probably because of the call analysis. When decompiling a function IDA will try to gather information on the function called by this one and in some case fail to get those information which will make the decompilation fail. But once that function has been decompiled, the information fetched by IDA will be updated, and so the decompilation of the caller function might now work. So basically it means you have to decompile the function in an order, which is a pain, for fixing that the simplest way is to just decompile everything twice, but it can take quite some time if you do it on "big" binaries.
I though I put that in the Bip repository somewhere but I can't find it, so here is a small plugin/code which should allows to do that:
from bip import *
class DecompileAll(BipPlugin):
"""
Plugin for decompiling all the function in the binary.
"""
#menu("Bip/DecompileAll/", "Invalidate hexrays caches")
def clear_hxcCache(self):
HxCFunc.invalidate_all_caches()
#menu("Bip/DecompileAll/", "Decompile all func")
def decomp_all(self):
count = 0
for f in HxCFunc.iter_all():
count += 1
print("0x{:X} functions decompiled".format(count))
#menu("Bip/DecompileAll/", "Decompile twice with cache clear")
def decomp_all_twice_cacheclear(self):
HxCFunc.invalidate_all_caches()
self.decomp_all()
self.decomp_all()
Just for information the basic reason for decompilation error, is that it is not able to make a correct translation of some piece of code because it does not understand the assembly, this is typically true if there is a problem during the analysis and the code is not correctly detected (also happens a lot if you are dealing with obfuscation). You can typically view this case by an error telling you "failed analysis at ADDR" in the IDAPython console, and then look at the problem. Probably not your case but might still help.
Glad to hear you are using bip. So about the BipFunc.can_decompile function: like indicated in the documentation (https://synacktiv.github.io/bip/build/html/base/func.html#bip.base.BipFunction.can_decompile) it will just try to decompile the function and see if an error occurs. The code is pretty straight forward (https://github.com/synacktiv/bip/blob/master/bip/base/func.py#L372), this is mostly written for being done while using one-liner, its the same thing as catching the exception when trying to decompile.
Warning: as the reference types proposal isn't complete yet, this code will not run without toggling flags or setting in order to enable executing experimental code.
If you are on Google Chrome or a Chromium browser, you will need to enable the following flag:
chrome://flags/#enable-experimental-webassembly-features
I had set up a simple handwritten Wasm module for personal use. I could've easily written it in JavaScript, but it was easier and made more sense to use Wasm, and since it was a simple, personal script, I wouldn't care if other people couldn't run it.
I had compiled it using wabt's wat2wasm.
The Wasm module was intended to be fed the entire globalThis object to import from.
From there, it took four TypedArray constructors: Uint8Array, Uint16Array, Uint32Array, and BigUint64Array.
Take note: no code was executed prior to the Wasm, thus there cannot be any interference.
Later, I had realized that that the Wasm wasn't working as intended at all, my math was correct, but the variables were wrong.
I had narrowed my problem down to just this:
;; global -> global variable
(import "globalThis" "Uint8Array" (global $Uint8Array externref))
(import "globalThis" "Uint16Array" (global $Uint16Array externref))
(import "globalThis" "Uint32Array" (global $Uint32Array externref))
(import "globalThis" "BigUint64Array" (global $BigUint64Array externref))
;; func -> function
(import "console" "log" (func $console::log (param externref)))
(start $_start)
(func $_start
global.get $Uint8Array
call $console::log
global.get $Uint16Array
call $console::log
global.get $Uint32Array
call $console::log
global.get $BigUint64Array
call $console::log
)
This Wasm was instantiated like so:
WebAssembly.instantiateStreaming(
fetch(
"test.wasm", {
mode : "same-origin",
credentials : "omit",
cache : "no-store",
redirect : "error",
referrer : "no-referrer"
}
), globalThis
).catch( console.error );
The interesting problem is that the logs all say the same thing: Uint8Array.
I was dumbfounded. This has to be literally impossible. The JavaScript file itself was not cached, the WebAssembly was being fetched with "no-cache," the web page itself wasn't cached.
Then I thought, because I was using XHTML, maybe it didn't happen in HTML files. It did there too.
I tried converting the Wasm file to a TypedArray and just using WebAssembly.instantiate, suddenly, it worked flawlessly.
At this point the server must be serving the wrong file, because the further I go, the more this seems like nonsense.
I almost want to say that this is a Chromium browser or V8 runtime error, but I need to narrow it down a bit more before I blindly attempt to present this as a bug.
I have set up two different versions of the same code, on Repl.it, and on CodeSandBox.io, so that hopefully someone can try running it themself, to confirm the bug, and maybe attempt to debug where I went wrong.
(Could this be a problem with Repl.it's server?)
This was a compiler bug fixed by Chromium in
https://chromium-review.googlesource.com/c/v8/v8/+/2551100.
This was the response that I had gotten from one of the developers:
This is indeed a timing issue that has been fixed in https://chromium-review.googlesource.com/c/v8/v8/+/2551100. The problem happens when there are only imported globals, and compilation of the WebAssembly functions finishes before the stream actually finishes. In this case, the offset calculation happens after the compiler uses the offsets, and therefore produces incorrect code.
A workaround is to define one global that is not imported, as this causes the offset calculation to happen earlier.
Seems like sending a small module that only imports globals instead of functions was breaking the code.
Their code had a threading race condition between the stream and the compiler.
I tried messing around with Win32 binaries lately (this is for a big project of mine).
So after some weeks of research, I now have a solid understanding of how Assembly works, how it is converted into binary code and how x86/x64 opcodes work.
The last piece to the puzzle is figuring out how to properly call Win32 API methods.
I actually asked a question on here in relation to this, and the answer I got was, I should try and compile an Assembly or C program that does this. So I went ahead and tried this in Assembly (I'm using FASM by the way):
format PE console
entry start
section '.idata' import data readable writable
include 'win32a.inc'
library kernel,'kernel32.dll'
import kernel,\
GetStdHandle,'GetStdHandle',\
WriteConsoleA,'WriteConsoleA'
section '.data' data readable writable
string db 'Hello!', 0h
output dd ?
section '.code' code readable executable
start: push -11
call GetStdHandle
pushd 0
pushd output
pushd 7
pushd string
pushd eax
call WriteConsoleA
This is one of the many versions of this code actually. The main problem is, when I call methods like "ExitProcess", generally other functions from the kernel32.dll library, things seem to work out. It's the IO functions that bug me...
I don't understand what's wrong with this code, I don't get any compile-time errors, though when I run it, it just crashes.
So my next idea was, since this didn't work, to try the same in C.
I'm using Cygwin as a compiler and linker...
#include <windows.h>
int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow) {
MessageBox(NULL, "Hello, world!", "Test", MB_OK);
return 0;
}
This code yielded the same result, the application crashed.
Now, I am not looking for any C/C++ code. My original question of interest was to know how calling extern library function looks like in x86/x64 binary (assembled) code. But I would be very thankful for any resources regarding this topic.
Thank you in advance.
-Tom S.
Your problem is that you need to call ExitProcess at the end to properly end the process. Since you are not doing that, the code currently will continue executing and eventually segfaults because it attempts to execute junk bytes.
I'm using the WkHtmlToXSharp wrapper library in my project to generate PDF file from HTML.
I was using this library a lot of times in different PCs and, suddenly, I came across the following problem:
System.AccessViolationException: Attempted to read or write protected memory. This is often an indication that other memory is corrupt.
at WkHtmlToXSharp.WkHtmlToPdfConverter.wkhtmltopdf_convert(IntPtr converter)
at WkHtmlToXSharp.WkHtmlToPdfConverter.Convert(String inputHtml)
at WkHtmlToXSharp.WkHtmlToPdfConverter.Convert()
at WkHtmlToXSharp.MultiplexingConverter.b_8()
--- End of inner exception stack trace ---
at Sanford.Threading.DelegateQueue.EndInvoke(IAsyncResult result)
at Sanford.Threading.DelegateQueue.Invoke(Delegate method, Object[] args)
at WkHtmlToXSharp.MultiplexingConverter.Convert()
This seems to be a common problem with this library (I've found some feedback on the web about it - however no fix was provided). BTW, in my case it happens somewhat randomly. I was not experiencing this problem in other dev machines. I wonder if somebody has a fix for it. I also wonder if this is a problem with the wrapper library, if with the WkHtmlToPDF library itself.
Any suggestion? I'm also open to use another converter, as long as it is free and stable and, if possible, without spawning a new process. It must work properly and stable in all Windows versions and do a decent job converting (the HTML to be converted is fixed - contains a few pics and tables and basic CSS).
I would suggest an alternate route: simply use wkhtmltopdf.exe directly, building your own wrapper. They are not very complicated if you have control of the input and then you know exactly how to update it and how the options work. I've never encountered with that problem when using wkhtmltopdf directly (on Win7, Win server 2008 r2, Ubuntu and CentOS). They do spawn process for every conversion though.
For an example, check out the Derp class in another answer of mine regarding wkhtmltopdf. Or try something like the untested code below (your true code will be more complicated, this is just a demo/POC).
var pi = new ProcessStartInfo(#"c:\wkhtmltopdf\wkhtmltopdf.exe");
pi.CreateNoWindow = true;
pi.UseShellExecute = false;
pi.WorkingDirectory = #"c:\wkhtmltopdf\";
pi.Arguments = "http://www.google.com gogl.pdf";
using (var process = Process.Start(pi))
{
process.WaitForExit(99999);
Debug.WriteLine(process.ExitCode);
}
I'm really struggling to resolve a stack underflow that I'm getting. The traceback I get at runtime is:
VerifyError: Error #1024: Stack underflow occurred.
at flash.events::EventDispatcher/dispatchEventFunction()
at flash.events::EventDispatcher/dispatchEvent()
at flash.net::URLLoader/onComplete()
This is particularly difficult to debug because when I run in debug mode it does not happen at all. It only happens when compiled as a release.
Does anyone have any tips on how to debug a Stack Underflow? Are have a clean explanation of what that means for Flash?
In case it helps, this error is occurring when I click a button whose handler makes an RPC call, which uses a URLLoader, an AsyncToken, and then invokes the set of AsyncResponder instances associated with the AsyncToken. With some server-side logging as well as some logging hacked into the swf, I know that the UrlLoader is successfully doing and GET'ing a crossdomain.xml file, is correctly processing it (ie: if I wreck it, I get a security error), and is also successfully completing the "load" request (the server sends the data). The underflow seems to be happening in the Event.COMPLETE listening/handling process (as is, of course, implied by the traceback as well).
mxmlc used = from flex_sdk_4.5.0.20967
Example player (I've tried a few) = 10.2.153.1
UPDATE: My specific problem is solved... but I'm leaving the question as-is since I would like to know how to generally debug such a problem, rather than just getting my specific solution.
In my code I had the following Application definition:
<s:Application height="100%" width="100%"
xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx"
initialize="InitData();">
Note that the code is/was attached to the initialize event.
InitData() and relevant defintions are/were:
import classes.RpcServerProxy;
public var SP:RpcServerProxy;
public function InitData():void {
SP = new RpcServerProxy("http://192.168.1.102:1234");
}
When I switched the InitData() call to be on the onCompletion event instead of initialize (thanks J_A_X!), the problem goes away entirely. What seems to have been happening was that the Event.COMPLETE event handler (onComplete in the stack trace) was using the global SP object. Something about the release (vs debug) compilation must have been affecting the startup timing of the SP variable initialization. Moving the handler later to the onCompletion event resolved all issues.
As said above, I would still like to know what tricks/tools are available for debugging initialization issues like this.
UPDATE 2:
applicationComplete seems to be an even better event than creationComplete to put application initialization code. See this blog entry for some explanation, and and this video (around 4:25) by an Adobe Tech Evangelist for an example of simple "start of application" data initialization.
I got rid of this error by adding compiler argument:
-omit-trace-statements=false
Stack underflow basically means the compiler messed up.
You can use SWFWire Inspector to look at the bytecode of the event handler, if you want to know exactly how it messed up. You can also use SWFWire Debugger to see which methods were called, but in this case, you already knew where it was happening.
If you post the broken swf, I can give you more info.
Sean is right that to debug it you can look at the byte code, but that didn't sound appealing to me.
Based on my experience and research, it is often due to the presence of a trace statement that incorrectly gets compiled out in release mode, and generates invalid byte code. So, I would say to "debug" it, "Look for places where you are using trace. Try commenting them all out in the offending function and see if the issue goes away."
In my case, it was a trace statement as the first line of a catch block:
catch (e:TypeError) {
trace(e.getStackTrace()); //This line is the problem
throw new Error("Unexpected type encountered");
}
I found someone else with this exact issue here.
This code also leads to stack underflow only in release mode (flag -debug=false):
true && trace('123');
mxlmc flex sdk version 4.5.0.20967, flashplayer version 10.3.181.14 (linux).
Check your code for similar expressions.
This code caused me issues when I compiled a release candidate from flash builder 4.5
public function set configVO( value:PopupConfigVO ):void
{trace("CHANGING")
Resolved by inserting a space between the the trace and curly brace
public function set configVO( value:PopupConfigVO ):void
{ trace("CHANGING")
Hope this helps.
For people looking for the same problem, I just got this caused by a trace statement in the 'default' case of a switch statement. Commented out the trace, stack underflow resolved.
Interesting... I was getting this error with a SWF that I'd pulled off the web, an Away3D based graphics demo. At the time I was running this on the Tamarin VM rather than the actual Flash/AIR runtimes, so could stick a breakpoint on the "verifyFailed(kStackUnderflowError)" line and see what was happening.
The -Dverbose flag also helped find the culprit:
typecheck MethodInfo-1480()
outer-scope = [global]
[Object~ Object] {} ()
0:pop
VERIFY FAILED: Error #1024: Stack underflow occurred.
And looking at the ABC using SWFInvestigator, I found this:
var function(Object):void /* disp_id=0 method_id=1480 nameIndex = 0 */
{
// local_count=2 max_scope=0 max_stack=0 code_len=2
// method position=52968 code position=155063
0 pop
1 returnvoid
}
So there is an obvious issue where the 'trace' has been removed but the compiler has put a 'pop' in there: I wouldn't have thought this was needed as a trace call should presumably have been made via 'callpropvoid'?
Quite why this doesn't fail on AIR/Flash I don't know..
Anyway: looks to me like an ASC compiler problem i.e perhaps one of the ActionScript3 compilers had a fault with this - hence the workarounds that have been mentioned so far.
It's quite simple, and it doesn't have anything to do with spaces before or after brackets, trace commands or whatever else: it's just 1 really simple thingy:
DO NOT LOOP EMPTY!
Meaning, while developing, we all //comment some lines sometimes, and when that results in
for (...) {
// skip for now
}
the compiler gets :
for(...){}
and that my good friends, is something the compiler doesn't like!
so, NO empty loops, and you're on your way again...
Happy hunting,
P.
I had the exact same problem, but in my case the cause of the problem was a trace statement in a place where the compiler didn't expect it to find it, right after a package declaration at the beginning of the class:
package utils
{
trace ("trace something here");
And that's why compiling in debug mode removed the problem.