Created attachment 143357 [details]
Fix Rust v0 demangling.
Rust has an old symbol mangling scheme ("legacy") and a new scheme ("v0"). The tracking issue for switching to the new scheme is at https://github.com/rust-lang/rust/issues/60705.
Valgrind has supported the legacy scheme for a long time. Bug #431306 added code to support the v0 scheme, which was released in 3.18. Unfortunately, due to an erroneous condition in the outer layer of the demangling code, the v0 demangling code is never reached. C++ and legacy symbols start with "_Z", but v0 symbols start with "_R", and this erroneous condition only checks for the former.
It's possible that this wasn't noticed because the Rust compiler is still using legacy mangling; you need to run with `-Z symbol-mangling-version=v0` to enable v0 mangling.
The attachment fixes the problem and adds a test. I have confirmed that the test fails without the fix -- because the one legacy symbol is demangled correctly, but the two v0 symbols are not. I have also confirmed the validity of the fix by doing large scale profiling of the Rust compiler, which is using v0 symbols internally.
I have push permission for the repository, so once people are happy with this (assuming they are) I can push it myself. Thanks!
This looks correct. Sorry for missing this myself when I merged the libiberty support. And thanks for the testcases.
One question which was also true before your fix, so do don't hold pushing this if you don't know the answer.
What about the Java Ada/gnat and D demangling defined in ML_(cplus_demangle)?
We seem to miss demangling them too because they (probably) don't start with _Z or _R and aren't guarded by AUTO_DEMANGLING.
Has that also always been broken? Did we simple not notice because nobody uses valgrind with those languages?
> What about the Java Ada/gnat and D demangling defined in ML_(cplus_demangle)?
> We seem to miss demangling them too because they (probably) don't start with
> _Z or _R and aren't guarded by AUTO_DEMANGLING.
> Has that also always been broken? Did we simple not notice because nobody
> uses valgrind with those languages?
From a quick look at the code, I think the following is true.
- C++ symbols usually start with "_Z", but "_GLOBAL_" is also possible, which won't work.
- Java symbols are a subset of C++ symbols, so should be ok, modulo possible "_GLOBAL_" cases, and possible AUTO_DEMANGLING problems.
- D symbols start with "_D", and so will be broken.
- Ada symbols can start with "_ada_", or with a lower-case letter, and so will be broken.
I found the AUTO_DEMANGLING stuff a bit confusing, but you are right that the code for Rust and C++ looks a bit different to the code for Java/Ada/D, in that respect. I suspect that you are also right about Java/Ada/D demangling being broken but nobody noticing due to low levels of usage.
Fixing the Java/Ada/D problems is outside the scope of this bug, and I'm not familiar enough with those languages to fix and test things anyway.
Here's what I'll do: I'll file a new bug pointing out the problems, update my commit to include a comment in `VG_(demangle)` that points to the bug, and then push. That way the Rust problems will be fixed, and the Java/Ada/D problems at least will be documented.
I filed #445235 for Java/Ada/D.
commit 4831385c6706b377851284adc4c4545fff4c6564 (HEAD -> master, origin/master, origin/HEAD)
Author: Nicholas Nethercote <email@example.com>
Date: Tue Nov 9 12:30:07 2021 +1100
Fix Rust v0 demangling.
It's currently broken due to a silly test that prevents the v0
demangling code from even running.
The commit also adds a test, to avoid such problems in the future.