How to panic with stack, but without raw addresses?

While developing my language, there are a few situations when my VM should actually @panic, for example on a VM stack overflow. Generating the Zig stack trace then is fine, but preferably without the raw addresses, only with the source file locations.

The reasoning behind this that

  1. I won’t be able to make use of this address anyway (I won’t use the disassembly due to my lack of knowledge)

  2. For my languages test scripts, I adopted the pattern to collect stout, stderr and exit code and append it as a comment directly to the script (to detect regressions). Tiny changes in the Zig source cause the addresses to change, resulting in false positives.

The only way I found (and did not use in the end) was to duplicate half of std.debug in my own code. Is there a better way, out of curiosity?

You can have your own unwinder in root by having pub const debug = struct { ... } namespace. Until https://codeberg.org/ziglang/zig/pulls/35632 is merged, you have to copy bunch of code from the std indeed.

I don’t think 1. is good enough reason to avoid the addresses though.

To add, I think the other approach is to override panic. As panic handler is what actually dumps the stacktrace. So you can still use the default unwinder but use your own stack walking code that prints it.

With “override” you mean to modify the std/debug.zig file? That would work of course, but I want this change only for this project.

Can’t say I understand your other idea, as Codeberg isn’t working atm.

if i understood what cloudef said correctly, you can override the panic handler via:

pub const panic = std.debug.FullPanic(customPanic);

where customPanic is a function with the sig: fn ([]const u8, ?usize) noreturn. place this line in your root source file (your projects src/main.zig)

That’s what I tried, but to change the trace output, I would have to copy lots of debug.zig.

I would try to filter the addresses out of the captures @panic output. You store the filtered output and next time compare filtered with filtered, which will be the same even if the addresses changed.

It’s not really lot. All you really need is writeTrace and printSourceAtAddress

Hmm, yes, good idea! This would solve the issue I had actually, but I think it’s not a valid answer to the question.

I don’t understand how I could make the custom function call my modified printSourceAtAddress without copying several of the helper functions from debug.zig.