-
Notifications
You must be signed in to change notification settings - Fork 13k
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 BestEffortDebug<T>, an always-Debug wrapper over T irrespective of T: Debug / T: !Debug #49071
Conversation
r? @Kimundi (rust_highfive has picked a reviewer for you, use r? to override) |
I do like the "there's a way to get debug output without threading Bikeshed: |
🚲🏘️@scottmcm The name comes from: https://docs.rs/wrap-debug/0.1.1/wrap_debug/struct.WrapDebug.html but I'm not super excited about it as well.
|
More 🚲🏘️
Since we've been OK historically with 3-worded types such as |
MaybeDebug, LazyDebug, ForceDebug also come to mind. |
I'd like to see an extension of this that shows the ptr (either directly or hashed) to the object in question for non-Debug references. This has precedence in languages like Java, where the standard |
@llogiq I specifically did not opt for such a design; the reason why is explained here: rust-lang/rfcs#2173 (comment) Relevant snippet:
In Java, the address is stable, so it is useful - this is not the case for the intended use case in Rust. Additionally, the output format of |
default fn fmt(&self, fmt: &mut Formatter) -> Result { | ||
use intrinsics::type_name; | ||
write!(fmt, "[<unknown> of type {} is !Debug]", | ||
unsafe { type_name::<T>() }) |
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.
I think the is !Debug
part of the message is jargon-y and hard to understand. My idea of an improvement would be "[<unknown value> of type {}]"
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.
I agree on the hard to understand bit, how about this?
"[<unknown value> of type {}, which does not implement Debug]"
The point of this being that if a library user sees this, they will know that they should bug the library author with a request to add #[derive(Debug)]
.
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.
(That's much better, and I think the reason for that is good)
From my discussions with @nikomatsakis (ping) on WG-traits, it seems that this particular specialization would not be permitted under max-min specialization (bummer :/) and would require specialization predicates. Niko did say that it would be useful, but that the PR should probably be closed. So I'm not sure how to proceed... |
Ping from triage, @Kimundi and @nikomatsakis ! Should we put this PR to bed, for now? |
☔ The latest upstream changes (presumably #49661) made this pull request unmergeable. Please resolve the merge conflicts. |
An update: @aturon's recent blog post on pub struct BED<T>(pub T);
impl<T> Debug for BED<T> { .. }
impl<T> Debug for BED<T> where specialize(T: Debug) { .. } this would still support all types, but |
Ping from triage! What's the status of this PR? |
This seems like a generally useful addition. As the comment thread shows, it's building on aspects of rusts specialization rules that are in flux, but in the worst case it just makes the proposed functionality useless, not breaking. Since this developed as part of the much discussed @bors fcp merge |
Team member @aturon has proposed to merge this. The next step is review by the rest of the tagged teams: Concerns:
Once a majority of reviewers approve (and none object), this will enter its final comment period. If you spot a major issue that hasn't been raised at any point in this process, please speak up! See this document for info about what commands tagged team members can give me. |
@rfcbot concern not-useful-if-specialization-does-not-work Specialization is still very much in flux AFAIK and it seems like it's still not 100% clear that there's a path to stability for functionality like this. @aturon's recent blog post is indeed one possible path but I don't think we're sure that it's sound and working, right? Additionally I do not think that functionality like this is useful in libstd if specialization is removed. That's "basically a breaking change" as the whole point of this type would be specialization. Otherwise it's not offering much utility over a crates.io crate that just calls This to me seems like something that should live on crates.io until we know specialization works, then it can move into libstd. |
@alexcrichton Excuse the tardy reply ;) I'll defer to @aturon re. the pace of implementation and stabilization of specialization. However, you could leave
Granted; It would become effectively useless. My biggest fear is not that the helper type itself becomes useless, but that its reverse dependency, and primary usecase,
It already does ;) Not as a standalone crate, but it does exist in the
Aside: Speaking of |
I think it seems fine to have this live in crates.io and not std until such time as stabilization is on a clear path to stability (implemented in the way we would want, etc) |
Hm ok so given that specialization is not on a clear path to stabilization, @Centril are you ok holding off on this PR for now? |
@alexcrichton Sure thing :) |
Ok! |
This adds the
BestEffortDebug
(formerlyWrapDebug
) wrapper discussed in rust-lang/rfcs#2361 and rust-lang/rfcs#2173.Motivation
This allows macros such as
debugit
,dbg
,p-macro
to work in generic code withoutT: Debug
bounds infecting the call stack. The reason for having it in libcore is that specialization is unstable, and thattype_name
is part ofcore_instrinsics
which is forever unstable. In addition, the macros in question can reuse this type and so we get some code reuse.Does this expose specialization?
Yes in the sense that you have to fall back to
type_name
andimpl<T> BEDInternal for BestEffortDebug<T>
if we decide to remove specialization entirely. The output thus becomes effectively useless, but no code will break as a result of removing specialization. The guarantees section in the documentation also explicitly states that the output format is not guaranteed.No in the sense that specialization is not effectively stabilized as a result of this. The "inner helper trait" hack is used in other places such as:
ArcFromSlice
.