Thread overview
How can I get a backtrace on segfault?
Sep 14, 2011
Tobias Pankrath
Sep 14, 2011
Jonathan M Davis
Sep 14, 2011
Tobias Pankrath
Sep 14, 2011
Jonathan M Davis
Sep 14, 2011
bearophile
Sep 14, 2011
Jonathan M Davis
Dec 11, 2020
Jonathan Levi
Sep 14, 2011
Tobias Pankrath
September 14, 2011
struct Foo
{
	int bar_;
	@property
	int bar() { return bar; }
}

Foo myFoo;
myFoo.bar; // (1)

The program will segfault at (1). I would have spot the error much faster, if I've got a decent backtrace, instead of "segmentation fault".

How can I get one? I've found the backtrace handler in object_.d, but I don't know how to make it work.




September 14, 2011
On Wednesday, September 14, 2011 10:07:54 Tobias Pankrath wrote:
> struct Foo
> {
> 	int bar_;
> 	@property
> 	int bar() { return bar; }
> }
> 
> Foo myFoo;
> myFoo.bar; // (1)
> 
> The program will segfault at (1). I would have spot the error much faster, if I've got a decent backtrace, instead of "segmentation fault".
> 
> How can I get one? I've found the backtrace handler in object_.d, but I don't know how to make it work.

What OS are you on? On 32-bit Linux, it should just work. On 64-bit Linux, there's a bug which makes it so that you don't get one. If you're on Windows (which I'm guessing that you're not since you're talking about segfaults rather than access violations), then I believe that it should just work, but there might be something that you have to do to get it to work (I don't use Windows much, so I'm not sure).

- Jonathan M Davis
September 14, 2011
> 
> What OS are you on? On 32-bit Linux, it should just work. On 64-bit
Linux,
> there's a bug which makes it so that you don't get one. If you're on Windows (which I'm guessing that you're not since you're talking about segfaults rather than access violations), then I believe that it should just work, but there might be something that you have to do to get it
to
> work (I don't use Windows much, so I'm not sure).
> 
> - Jonathan M Davis

64 bit linux :-(. Thank you for your fast response.
September 14, 2011
On Wednesday, September 14, 2011 10:38:38 Tobias Pankrath wrote:
> > What OS are you on? On 32-bit Linux, it should just work. On 64-bit
> 
> Linux,
> 
> > there's a bug which makes it so that you don't get one. If you're on Windows (which I'm guessing that you're not since you're talking about segfaults rather than access violations), then I believe that it should just work, but there might be something that you have to do to get it
> 
> to
> 
> > work (I don't use Windows much, so I'm not sure).
> > 
> > - Jonathan M Davis
> 
> 64 bit linux :-(. Thank you for your fast response.

Actually. wait. I wasn't thinking right. You never get a backtrace from a segfault. There _is_ a bug on 64-bit Linux which makes it so that backtraces don't work, but you don't get a stacktrace from a segfault regardless. The way to handle that is to get a core dump and use gdb on it. However, unfortunately, 64-bit programs generated by dmd don't seem to be work with gdb (though 32-bit programs will). It's a result of the fact that 64-bit support for dmd is pretty new. Still, they're annoying bugs.

In any case, the best way to handle your problem would probably be to compile your program as 32-bit, run it with core dumps enabled, and use gdb on it. That should show you where the problem is unless the segfault is 64-bit specific for some reason.

- Jonathan M Davis
September 14, 2011
On 14-09-2011 11:47, Jonathan M Davis wrote:
> On Wednesday, September 14, 2011 10:38:38 Tobias Pankrath wrote:
>>> What OS are you on? On 32-bit Linux, it should just work. On 64-bit
>>
>> Linux,
>>
>>> there's a bug which makes it so that you don't get one. If you're on
>>> Windows (which I'm guessing that you're not since you're talking about
>>> segfaults rather than access violations), then I believe that it should
>>> just work, but there might be something that you have to do to get it
>>
>> to
>>
>>> work (I don't use Windows much, so I'm not sure).
>>>
>>> - Jonathan M Davis
>>
>> 64 bit linux :-(. Thank you for your fast response.
>
> Actually. wait. I wasn't thinking right. You never get a backtrace from a
> segfault. There _is_ a bug on 64-bit Linux which makes it so that backtraces
> don't work, but you don't get a stacktrace from a segfault regardless. The way
> to handle that is to get a core dump and use gdb on it. However,
> unfortunately, 64-bit programs generated by dmd don't seem to be work with gdb
> (though 32-bit programs will). It's a result of the fact that 64-bit support
> for dmd is pretty new. Still, they're annoying bugs.
>
> In any case, the best way to handle your problem would probably be to compile
> your program as 32-bit, run it with core dumps enabled, and use gdb on it.
> That should show you where the problem is unless the segfault is 64-bit
> specific for some reason.
>
> - Jonathan M Davis

As an aside, I still think DMD needs an option to insert null checks everywhere, at least for debugging...

- Alex
September 14, 2011
Alex R. Petersen:

> As an aside, I still think DMD needs an option to insert null checks everywhere, at least for debugging...

Maybe if 200 people nag Walter about it in the main D newsgroup he will change his mind...

Bye,
bearophile
September 14, 2011
On Wednesday, September 14, 2011 11:55:48 Alex Rønne Petersen wrote:
> As an aside, I still think DMD needs an option to insert null checks everywhere, at least for debugging...

That would fix only a portion of segfaults, so as far as the general segfaults go, that's not a complete solution. Regardless of that however, Walter is dead-set against adding null checks, because his take on it is that the OS does them already (hence the segfault) and that you can always get the backtrace (along with other useful information) by using a debugger, so he's not going to add null checks.

Now, I do agree that it would be nice to have them for debugging purposes, but it's just not going to happen. Walter is too opinionated on the issue.

The way to get stacktraces for all segfaults is to add a handler for SIGSEV which prints a backtrace. And arguably, it's a better solution than doing null checks anyway, because it gives you a stacktrace without the extra overhead of doing the null checks. It is an OS-specific solution though.

- Jonathan M Davis
September 14, 2011
On Wed, 14 Sep 2011 05:55:48 -0400, Alex Rønne Petersen <xtzgzorex@gmail.com> wrote:

> On 14-09-2011 11:47, Jonathan M Davis wrote:
>> On Wednesday, September 14, 2011 10:38:38 Tobias Pankrath wrote:
>>>> What OS are you on? On 32-bit Linux, it should just work. On 64-bit
>>>
>>> Linux,
>>>
>>>> there's a bug which makes it so that you don't get one. If you're on
>>>> Windows (which I'm guessing that you're not since you're talking about
>>>> segfaults rather than access violations), then I believe that it should
>>>> just work, but there might be something that you have to do to get it
>>>
>>> to
>>>
>>>> work (I don't use Windows much, so I'm not sure).
>>>>
>>>> - Jonathan M Davis
>>>
>>> 64 bit linux :-(. Thank you for your fast response.
>>
>> Actually. wait. I wasn't thinking right. You never get a backtrace from a
>> segfault. There _is_ a bug on 64-bit Linux which makes it so that backtraces
>> don't work, but you don't get a stacktrace from a segfault regardless. The way
>> to handle that is to get a core dump and use gdb on it. However,
>> unfortunately, 64-bit programs generated by dmd don't seem to be work with gdb
>> (though 32-bit programs will). It's a result of the fact that 64-bit support
>> for dmd is pretty new. Still, they're annoying bugs.
>>
>> In any case, the best way to handle your problem would probably be to compile
>> your program as 32-bit, run it with core dumps enabled, and use gdb on it.
>> That should show you where the problem is unless the segfault is 64-bit
>> specific for some reason.
>>
>> - Jonathan M Davis
>
> As an aside, I still think DMD needs an option to insert null checks everywhere, at least for debugging...

That would not fix this problem (stack overflow).

I hazard to guess that stack overflow likely would not produce a helpful stack trace either, but maybe I'm wrong.

In any case, have you tried this? Works on unixen only.

import core.stdc.signal;

extern(C) void handleSegv(int) { assert(0); }

void main()
{
   signal(SIGSEGV, &handleSegv);
   ...
}

Not sure if it prints a stack trace on a stack overflow, however.

-Steve
September 14, 2011
> 
> Actually. wait. I wasn't thinking right. You never get a backtrace from
a
> segfault. There _is_ a bug on 64-bit Linux which makes it so that backtraces don't work, but you don't get a stacktrace from a segfault regardless. The way to handle that is to get a core dump and use gdb on it.

Works fine for me so far. Thank you.

December 11, 2020
On Wednesday, 14 September 2011 at 12:16:02 UTC, Steven Schveighoffer wrote:
> In any case, have you tried this? Works on unixen only.
>
> import core.stdc.signal;
>
> extern(C) void handleSegv(int) { assert(0); }
>
> void main()
> {
>    signal(SIGSEGV, &handleSegv);
>    ...
> }
>
> Not sure if it prints a stack trace on a stack overflow, however.
>
> -Steve

Update for anyone reading this old thread:

You need to add `nothrow @nogc @system` to `handleSegv`.

```
import core.stdc.signal;

nothrow @nogc @system
extern(C) void handleSegv(int) { assert(0); }

shared static this() {
	signal(SIGSEGV, &handleSegv);
}
```

This answer worked great for me.