-
-
Notifications
You must be signed in to change notification settings - Fork 1.6k
Improve Exception backtrace API #10681
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
Comments
It looks Rust is currently (although for quite some time already) refactoring their backtrace API with a |
I think it's worth pointing out the two PRs open about this are mutually exclusive. We should probably figure out which one we want to move forward with and go from there, versus needing to review both all the time... |
True. Also probably discuss outside of here what to expose. What's the reason to expose the address and the cryptic function name? |
Is there reason to not expose the address? I guess my thinking was even if most people won't ever need it, still might be helpful to expose; especially if we're going for a 1:1 mapping between the backtrace string and a Regarding the function name, I combined both names into 1 |
Let's say someone implements an interpreter for Crystal. What would be the address? |
Ah, nevermind, in any case it won't happen. |
Let's please focus the discussion on the proposed API here in this issue, instead of arguing over details in the competing PRs. |
I think we should start with ironing out the data format for a frame. I've looked at Rust's implementation (https://doc.rust-lang.org/src/std/backtrace.rs.html#152-155) and they actually separate frame and symbols and multiple symbols can be associated with one frame. I don't know when you would have multiple symbols per frame. But there must be a reason for that. The data structures (converted to the Crystal equivalent) look like this: record BacktraceFrame,
frame : RawFrame,
symbols : Array(BacktraceSymbol)
record BacktraceSymbol,
name : String?,
filename : String?,
line_number : Int32?,
column_number : Int32? The process is also split into two parts, first retrieving the raw frames from whatever backend is used to walk the stack. The result is a collection of |
Rust exposes the ip addresses. No idea who would use them though, but I guess since it's a struct people are free to ignore it. Crystal even has an "original_ip" but again not sure if anyone cares but might not hurt. The reason Rust does multiple symbols per frame is |
Not to derail the thread, but I just noticed @asterite's foreshadowing 😂 ☝️ #10681 (comment) |
It's fine, we can leave the ip address as zero for interpreted mode. In the end backtraces in the interpreter are done in a completely different way, so it makes sense that the values there will also be slightly different. |
(I also wrote that comment while I was writing the interpreter, so I knew what was coming :-P) |
Getting back to this issue again and got the data model proposed in #10681 (comment) working, but still have a few questions:
Based on #10681 (comment), I'm just not sure if this is a rust specific compiler thing, or if it's also applicable to us given it also uses LLVM. Prob worth investigating/finding a scenario where there would be more than one to test with/how to extract that data.
Currently i'm still doing essentially what it was before by using
I'm assuming yes based on the past comments.
Do we want to actually expose the
Do we care at all this would be a mutable struct no? |
My wont would be to have lots of info returned, people can choose not to
use it if they care. Maybe nodoc the ip address, can't imagine someone
needing it externally? :)
…On Mon, Sep 5, 2022 at 8:58 PM George Dietrich ***@***.***> wrote:
Getting back to this issue again and got the data model proposed in #10681
(comment)
<#10681 (comment)>
working, but still have a few questions:
Do we still think its necessary to support having multiple symbols per
frame?
Based on #10681 (comment)
<#10681 (comment)>,
I'm just not sure if this is a rust specific compiler thing, or if it's
also applicable to us given it also uses LLVM. Prob worth
investigating/finding a scenario where there would be more than one to test
with/how to extract that data.
What to do with CRYSTAL_CALLSTACK_FULL_INFO ENV var?
Currently i'm still doing essentially what it was before by using sname
as function and also having it set the ip address on each symbol if its
set.
Do we actually want to still expose the address?
I'm assuming yes based on the past comments.
What do we ultimately want the API for this to be like?
Do we want to actually expose the BacktraceFrame type, versus like
yielding each of its symbols? If not, then Exception#frames and
Exception#each_frame that returns an array of/yields each BacktraceSymbol
would comes to mind first. Tho the naming of that is a bit weird given its
called "frames" but you get a "symbol"?
—
Reply to this email directly, view it on GitHub
<#10681 (comment)>,
or unsubscribe
<https://github.com/notifications/unsubscribe-auth/AAADBUGDDBKXQ4N2ZH47XTTV42XNHANCNFSM44GCZ55Q>
.
You are receiving this because you commented.Message ID:
***@***.***>
|
This issue has been mentioned on Crystal Forum. There might be relevant details there: https://forum.crystal-lang.org/t/ruby-caller-location/7391/2 |
Currently an exception's backtrace is an
Array(String)
. This is usually fine, however there are some use cases where you may want to present the trace in a different way; such as pretty printing an exception. Currently this is not very easy to do as each portion of the trace needs to be manually parsed either manually or via an external shard.I propose that the backtrace is also exposed an a like
Array(Frame)
, where eachFrame
would have getters for the related info of that line. E.g. filename, method name, line/column etc. This would provide a much cleaner API to work with.Given Crystal handles printing each line I would assume it inherently has access to each portion of data. This could be kept backwards compatible by exposing the frames as another method that the current one could leverage. E.g.
@frames.map &.to_s
.The text was updated successfully, but these errors were encountered: