-
Notifications
You must be signed in to change notification settings - Fork 211
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
figure out some mechanism to alias symbols #70
Comments
Just an idea: one could add a perma-unstable feature to rust that gives you support to add aliases. This worked great for "unadjusted" and i128. |
LLVM has IR for this so we could implement it. The issue, I think, is picking a syntax. In C, one writes: void __aeabi_memcpy2() {}
void __aeabi_memcpy4() __attribute__((alias("__aeabi_memcpy2"))); But in Rust we don't have syntax for function declarations (without definition). Perhaps we could implement a reverse syntax like this: #[aliases(__aeabi_memcpy2, __aeabi_mecpy4)]
fn memcpy() { .. } |
I'm likely going to have to figure out something to handle this on #166 as the tests aren't passing (lots of duplicate symbols) if this isn't handled. Right now my current strategy is to use a macro to deal with the ABI switches between __aeabi and the non-prefixed version, define both symbols, and basically "duplicate the routine". The routine is only defined in one place but LLVM's likely to inline it into both anyway. |
Another interesting thing is being able to replace a symbol by a different one if a third symbol is used in the final program, and I have no idea how we would model that in Rust. To take an example, AFAIU there is 2 translation units in musl to support syscalls that are cancellation points, the first one defines Or is my understanding of this stuff completely wrong? If I'm correct, how would do this dance in Rust? |
The problem
Some symbols, like the
__aeabi_*
ones, are defined as "aliases" of others in the C implementation of compiler-rt. For example:__aeabi_dadd
is an alias of__adddf3
. This means that both symbols, the original and its alias, refer to the same routine and use of either will result in a call to the same routine.Rust doesn't have a mechanism for aliasing symbols and right now we are "emulating" aliases like this:
Although this works (calling that "alias" does the right thing), it also incurrs in an extra function call everytime the alias is used:
Attempted solutions
Use
#[link_args]
to ask the linker to duplicate the symbol. See #39. Sadly, this didn't work because#[link_args]
is not propagated through crates and also that feature is slated for removal so we can't rely on it anyway.Possible non-ideal solutions
export_name
Most (all?) ARM builtins have the form
__aeabi_*
.compiler-rt
implements them as aliases to the non-aeabi symbols. For example:__aeabi_dadd
is an alias of__adddf3
and both symbols appear inlibcompiler-rt.a
. Given that ARM executables never use the non-aeabi symbols, we could simply expose the__adddf3
routine as the__aeabi_dadd
symbol without providing the__adddf3
symbol. In Rust code this would look like this:The result would be:
rustc_builtins
on x86 exposes the__adddf3
symbolrustc_builtins
on ARM exposes the__aeabi_dadd
symbolIn contrast,
libcompiler-rt.a
on ARM exposes both the__adddf3
and the__aeabi_dadd
symbolsThis approach can only be used if the implementation resides in
rustc-builtins
. For instance, we can't use this to expose the__aeabi_memcpy*
symbols which are all aliases tomemcpy
.Just duplicate the routine
This would get rid of the extra function call in the "alias" but would probably result in duplicate code/instructions in the final executable (unless LLVM is smart enough to deduplicate two routines that have the same instructions)
Anyone has any other idea about how to solve this?
The text was updated successfully, but these errors were encountered: