-
Notifications
You must be signed in to change notification settings - Fork 9
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add debug symbols #87
Merged
uncomputable
merged 8 commits into
BlockstreamResearch:master
from
uncomputable:2024-09-debug-symbols
Sep 16, 2024
Merged
Add debug symbols #87
uncomputable
merged 8 commits into
BlockstreamResearch:master
from
uncomputable:2024-09-debug-symbols
Sep 16, 2024
Conversation
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
code review ack 88d15d3 CI failure looks real (I'll wait til it's green to run my local CI). Super cool concept! |
Introduce a helper method for each step of the analysis. Analyze each call variant in terms of the steps. This refactor makes the code easier to read.
I find it much easier to read hex arrays than long decimal strings.
A Simfony function call f(x) is usually compiled as the following Simplicity expression, where [x] is the compilation of x, and so on. comp [x] [f] However, we can write a different Simplicity target expression that has the same semantics. The input is paired with a false bit. This is piped into an assertion that checks if the bit is false. The assertion always succeeds. comp (pair false [x]) (assertl (drop [f]) CMR) The lower expression is a more convoluted way of writing the upper expression. The benefit of the lower expression is that it includes a CMR that we can use to inject arbitrary data. We use the hash of the position of the call inside the original Simfony source code as CMR. This is the debug symbol. For now, I insert debug symbols into every call that is fallible. Any failure on the Simplicity Bit Machine can be associated with a Simfony call expression via the CMR. Currently, debug symbols are inserted into every compiled program. We don't want programs bloated with debug symbols on the blockchain. It is easy to add a "release" mode next to a "debug" mode to the Simfony compiler. For brevity, I chose to leave this for later. Note that I had to compile unwraps with slightly more combinators in order to fit the shape comp [function args] [function body]. I plan to revert this change in the "release" mod of the Simfony compiler.
We want to use debug symbols to produce helpful error messages on the Bit Machine. The debug symbols cover all cases where the Simplicity target code may fail (assertl, assertr, fail). We want to produce error messages of the following kind: Assertion failed: false Called `unwrap()` on a `None` value Called `unwrap_left()` on a `Right` value: 1 Called `unwrap_right()` on a `Left` value: 1 Some errors display the input value (unwrap_left, unwrap_right); some errors are always the same (assert, unwrap). TrackedCallName includes type information to reconstruct the input value at runtime from the Bit Machine. FallibleCallName includes the reconstructed value. TrackedCall and FallibleCall include the Simfony text of the call expression, so we can print it alongside the error. We might choose to include the span, too, in the future, depending on where we want to go with this design.
Return a plain-old-data type that wraps the Simplicity target code and its debug symbols. When we add a "release" mode to the Simfony compiler, we won't return debug symbols.
dbg!(x) behaves in Simfony like in Rust: It is a NOP that prints its input value as a side effect. The Simfony compiler adds a debug symbol for this purpose. I split FallibleCall from DebugValue in the debug symbol API because FallibleCall is supposed to be used in error messages, while DebugValue is used for logging on the side. I don't want to handle dbg! as a case in an error message, even though dbg! is infallible.
uncomputable
force-pushed
the
2024-09-debug-symbols
branch
from
September 16, 2024 16:08
22a3ab5
to
0a67719
Compare
Fixed CI. Also made sure that
|
apoelstra
approved these changes
Sep 16, 2024
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ACK 0a67719 successfully ran local tests
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Track fallible Simfony expressions via debug symbols that are included in the Simplicity target code (more details are in the commit message).
Add public methods to convert debug symbols into helpful error messages by providing the values that the Bit Machine sees at runtime. Debug symbols cover all failure cases, so the Bit Machine should always be able to display a helpful Simfony error.
Add
dbg!
expressions that can be used print their input value at runtime.