-
Notifications
You must be signed in to change notification settings - Fork 13.4k
When writing LLVM IR output demangled fn name in comments #42971
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
Conversation
(rust_highfive has picked a reviewer for you, use r? to override) |
fc5cd2c
to
6404a90
Compare
Updated PR with
|
Sample source code and output: gist. |
src/libstd/lib.rs
Outdated
pub mod demangle_for_rustc { | ||
pub use sys_common::backtrace::demangle; | ||
pub use sys_common::backtrace::PrintFormat; | ||
} |
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.
IMO it is a shame that we’re exposing more unstable stuff from libstd. Would it be possible to extract the functionality into a crate and make both libstd and librustc_trans use that?
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.
Yes, I'll try to do that now. What should be crate name, librust_demange
?
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.
Well there’s technically a rustc-demangle already, although I do not know how easy/hard it is to integrate an external crate into libstd. I know there are a few already integrated in other places such as librustc_trans, could take a look there.
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.
@alexcrichton any suggestions on that issue?
src/rustllvm/PassWrapper.cpp
Outdated
// return empty string if demangle failed | ||
// or if name does not need to be demangled | ||
StringRef CallDemangle(StringRef name) { | ||
if (!Demangle) { |
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.
Could the constructor use a default no-op demangle callback instead?
EDIT: And yes, it seems fairly plausible for somebody to pass in NULL for this.
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 can just remove the comment. No-op demangle would be overengineering IMHO.
src/rustllvm/PassWrapper.cpp
Outdated
class RustAssemblyAnnotationWriter : public AssemblyAnnotationWriter { | ||
DemangleFn Demangle; | ||
static const size_t BufCap = 500; | ||
char Buf[BufCap]; |
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.
Could the output buffer size derived from the input symbol instead? Something like a std::vector that only ever expands when it sees an input symbol longer than its current output buffer.
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.
OK, I'll do that.
formatted_raw_ostream &OS) override { | ||
const char *Name; | ||
const Value *Value; | ||
if (const CallInst *CI = dyn_cast<CallInst>(I)) { |
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.
Some other cases where a demangle could be relevant is taking the address of the function.
That would be store %place, @function
.
Maybe it is worth to always look at the instruction operands and output a demangled version if there’s a function operand?
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'll keep printing only invoke
and call
for now (which covers 99% of cases), and probably do more printing in another PR, if that's OK with you.
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.
Yeah, that’s fine.
src/rustllvm/PassWrapper.cpp
Outdated
bool runOnModule(Module &M) override { | ||
RustAssemblyAnnotationWriter AW(Demangle); | ||
|
||
// Copy-paste of PrintModulePass::run |
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.
Remove the comments?
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.
OK.
r? @nagisa |
Updated the PR. Removed comments, replace fixed size buf with
|
Awesome, thanks! @bors r+ |
📌 Commit 8f6ac5b has been approved by |
`--emit=llvm-ir` looks like this now: ``` ; <alloc::vec::Vec<T> as core::ops::index::IndexMut<core::ops::range::RangeFull>>::index_mut ; Function Attrs: inlinehint uwtable define internal { i8*, i64 } @"_ZN106_$LT$alloc..vec..Vec$LT$T$GT$$u20$as$u20$core..ops..index..IndexMut$LT$core..ops..range..RangeFull$GT$$GT$9index_mut17h7f7b576609f30262E"(%"alloc::vec::Vec<u8>"* dereferenceable(24)) unnamed_addr #0 { start: ... ``` cc rust-lang/rust-playground#15
After changing to I've pushed a fix to the branch. The only change is this:
Someone do |
@bors r- (Can I do that?) |
@stepancheg: 🔑 Insufficient privileges: Not in reviewers |
@bors r=nagisa |
📌 Commit b62bdaa has been approved by |
When writing LLVM IR output demangled fn name in comments `--emit=llvm-ir` looks like this now: ``` ; <alloc::vec::Vec<T> as core::ops::index::IndexMut<core::ops::range::RangeFull>>::index_mut ; Function Attrs: inlinehint uwtable define internal { i8*, i64 } @"_ZN106_$LT$alloc..vec..Vec$LT$T$GT$$u20$as$u20$core..ops..index..IndexMut$LT$core..ops..range..RangeFull$GT$$GT$9index_mut17h7f7b576609f30262E"(%"alloc::vec::Vec<u8>"* dereferenceable(24)) unnamed_addr #0 { start: ... ``` cc rust-lang/rust-playground#15
☀️ Test successful - status-appveyor, status-travis |
With this patch `--emit=asm` looks like this: ``` ; <alloc::vec::Vec<T> as core::ops::index::IndexMut<core::ops::range::RangeFull>>::index_mut __ZN106_$LT$alloc..vec..Vec$LT$T$GT$$u20$as$u20$core..ops..index..IndexMut$LT$core..ops..range..RangeFull$GT$$GT$9index_mut17h8ecb05aacf724133E: ... Lcfi2: .cfi_def_cfa_register %rbp subq $16, %rsp ; <alloc::vec::Vec<T> as core::ops::deref::DerefMut>::deref_mut callq __ZN71_$LT$alloc..vec..Vec$LT$T$GT$$u20$as$u20$core..ops..deref..DerefMut$GT$9deref_mut17heae350c695265f00E ``` Unlike writing LLVM IR, it is hard to plug into LLVM to output comments without duplicating large amount of LLVM code (because LLVM doesn't have hooks, or at least I haven't found them). So it is implemented by post-processing assembly text. cc rust-lang/rust-playground#15 cc rust-lang#42971 r? nagisa
--emit=llvm-ir
looks like this now:cc rust-lang/rust-playground#15