[Lazarus] Assembler window shows but without Debugger Exception popup

Martin Frb lazarus at mfriebe.de
Tue Nov 14 13:16:18 CET 2017

The info is enough for explaining what happens.

Before I go to the reason: It is strange the debugger does not indicate 
that your app was killed by a signal SigTrap. (That should be reported 
as bug)

The signal is actually caused by FPC (more below), and it looks like 
this causes windows to create an additional thread in your app. That 
explains the stacktrace. You may need to select the other thread, to see 
where in your app the issue occurred. (missing auto selecting the 
correct thread, is a bug too, but may not always be possible)
But even the other stack trace may not be of use, see below.

So what happened is:
You have code that writes to memory that was already freed. Most likely 
you freed an object, and then accessed the no longer existing object. 
You may have a 2nd variable holding a pointer to it.

Of course it can be any other memory access, not necessarily a freed 
object. Maybe you used GetMem/FreeMem. Or you used a pchar to a no 
longer existing string. Or you incorrectly used a const param. Or 
something else...

Your app is compiled with -gh (that is HeapTRC). and this checks (to a 
limited extend) if freed memory is later modified.
The message "HEAP: Free Heap block 105AA5B0 modified at 105AA5D0 after 
it was freed" is from HeapTRC. It normally is printed to stderr. You can 
see that, if you compile with console window -WC (there is also an 
option in project options, but it uses a different switch)

Those errors are often very hard to trace.
AFAIK Heaptrc checks for the modification when you allocate/free memory. 
But by that time the code that incorrectly wrote to it has long been 
executed. So the stacktrace will help very little.

You can try to inspect the memory at this address.
Not sure maybe a watch like PByte($105AA5D0)^
Maybe this will show some data you can identify. From my experience 
though, this is unlikely.

Not sure if HeapTRC can get you better info.

The best way I know to get results are:
Either inspecting code to find theĀ  issue without debug.

Or use valgrind on linux (If you can reproduce on linux)

Or use watchpoints (data break points). You need a reproducible test 
case that always gets you the same address for the error. You need to 
use a PByte as above to set the watchpoint (I haven't done it in a 
while, you may have to play around). But that will give a lot of false 
positives. Too many.

There is the environment variable HEAPTRC which you can set to keepreleased
Then the memory will be used only once.
Find the address of the error with keepreleased, then track this address 
with a watchpoint, and you find the object that uses the memory. Then - 
once the object is freed - the watchpoint will trigger, when the memory 
is incorrectly accessed.

That is the theory. The praxis can be a long and painful search.

On 14/11/17 10:17, Lubos Pintes via Lazarus wrote:
> Oh, View menu, of course. I am stupid indeed. :)
> I just updated a GDB to version 7.7.1 and now at least the stack trace 
> makes more sense. It is full of Windows API calls. However, here is a 
> part of debug output which seems to be relevant, at least I am not 
> sure what exactly this can be:
> &"warning: HEAP[project1.exe]: \n"
> &"warning: HEAP: Free Heap block 105AA5B0 modified at 105AA5D0 after 
> it was freed\n"
> &"\n"
> ~"[Switching to Thread 4928.0x13e8]\n"
> *stopped,reason="signal-received",signal-name="SIGTRAP",signal-meaning="Trace/breakpoint 
> trap",frame={addr="0x778661e2",func="ntdll!RtlCaptureStackContext",args=[],from="C:\\WINDOWS\\SYSTEM32\\ntdll.dll"},thread-id="9",stopped-threads="all" 
> =thread-selected,id="9"
> I extracted this output immediately after the Assembler window appeared.
> Other things there are library loaded, thread created, etc.
> If you still thinks it makes sense to post the Lazarus debug output 
> you suggested, I can of course do it. 

More information about the Lazarus mailing list