Stream: git-wasmtime

Topic: wasmtime / PR #12791 Debugging: allow breakpoints to be s...


view this post on Zulip Wasmtime GitHub notifications bot (Mar 17 2026 at 01:16):

cfallin opened PR #12791 from cfallin:lets-make-breakpoints-a-little-fuzzier-please to bytecodealliance:main:

LLDB, when instructed to break main, looks at the DWARF metadata for main and finds its PC range, then sets a breakpoint at the first PC. This is reasonable behavior for native ISAs! That PC better be a real instruction!

On Wasm, however, (i) toolchains typically emit the PC range as including the locals count, a leb128 value that precedes the first opcode and any types of locals; (ii) our gdbstub component that bridges LLDB to our debug APIs (#12771) only supports exact PCs for breakpoints, so when presented with a PC that does not actually point to an opcode, setting the breakpoint is effectively a no-op. There will always be a difference of at least 1 byte between the start-of-function offset and first-opcode offset (for a leb128 of 0 for no locals), so a breakpoint "on" a function will never work.

I initially prototyped a fix that adds a sequence point at the start of every function (which, again, is guaranteed to be distinct from the first opcode), and the branch is [here], but I didn't like the developer experience: this meant that when a breakpoint at a function start fired, LLDB had a weird interstitial state where no line-number applied.

The behavior that would be closer in line with "native" debug expectations is that we add a bit of fuzzy-ish matching: setting a breakpoint at function start should break at the first opcode, even if that's a few (or many) bytes later. There are two options here: special-case function start, or generally change the semantics of our breakpoint API so that "add breakpoint at pc" means "add breakpoint at next opcode at or after pc". I opted for the latter in this PR because it's more consistent.

The logic is a little subtle because we're effectively defining an n-to-1 mapping with this "snap-to-next" behavior, so we have to refcount each breakpoint (consider setting a breakpoint at function start and at the first opcode, then deleting them, one at a time). I believe the result is self-consistent, even if a little more complicated now. And, importantly, with #12771 on top of this change, it produces the expected behavior for the (very simple!) debug script "b main; continue".

[here]: https://github.com/cfallin/wasmtime/tree/breakpoint-at-func-start

<!--
Please make sure you include the following information:

Our development process is documented in the Wasmtime book:
https://docs.wasmtime.dev/contributing-development-process.html

Please ensure all communication follows the code of conduct:
https://github.com/bytecodealliance/wasmtime/blob/main/CODE_OF_CONDUCT.md
-->

view this post on Zulip Wasmtime GitHub notifications bot (Mar 17 2026 at 01:16):

cfallin requested dicej for a review on PR #12791.

view this post on Zulip Wasmtime GitHub notifications bot (Mar 17 2026 at 01:16):

cfallin requested wasmtime-core-reviewers for a review on PR #12791.

view this post on Zulip Wasmtime GitHub notifications bot (Mar 17 2026 at 01:26):

cfallin unassigned dicej from PR #12791 Debugging: allow breakpoints to be set at "function start" by slipping forward to first opcode..

view this post on Zulip Wasmtime GitHub notifications bot (Mar 17 2026 at 01:26):

cfallin requested alexcrichton for a review on PR #12791.

view this post on Zulip Wasmtime GitHub notifications bot (Mar 17 2026 at 01:56):

alexcrichton submitted PR review.

view this post on Zulip Wasmtime GitHub notifications bot (Mar 17 2026 at 01:56):

alexcrichton created PR review comment:

Technically this is required from an lldb/gdbstub perspective I think anyway, right? In that if I set a breakpoint on a symbol and the same address and remove one the other should stay.

One option would be to return a bool in Wasmtime if a breakpoint is set and push the refcounting up to the gdbstub itself, but I think it's fine to live in wasmtime too.

view this post on Zulip Wasmtime GitHub notifications bot (Mar 17 2026 at 04:25):

github-actions[bot] added the label wasmtime:api on PR #12791.

view this post on Zulip Wasmtime GitHub notifications bot (Mar 19 2026 at 01:43):

cfallin submitted PR review.

view this post on Zulip Wasmtime GitHub notifications bot (Mar 19 2026 at 01:43):

cfallin created PR review comment:

I'm actually not sure how much dedup lldb does but I believe it does track which addresses already have breakpoints -- otherwise even a simple gdbstub in say an embedded device that directly patches code would have to do refcounting, so in a "precise PC only" world it's likely not needed. In any case, it's needed now!

And yeah, I played around with where to put this but I think I prefer the complexity to live right where the breakpoint set is managed so we don't need to separately track it in every debug adapter we write.

view this post on Zulip Wasmtime GitHub notifications bot (Mar 19 2026 at 01:43):

cfallin added PR #12791 Debugging: allow breakpoints to be set at "function start" by slipping forward to first opcode. to the merge queue

view this post on Zulip Wasmtime GitHub notifications bot (Mar 19 2026 at 02:07):

cfallin merged PR #12791.

view this post on Zulip Wasmtime GitHub notifications bot (Mar 19 2026 at 02:07):

cfallin removed PR #12791 Debugging: allow breakpoints to be set at "function start" by slipping forward to first opcode. from the merge queue


Last updated: Mar 23 2026 at 16:19 UTC