Skip to content
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

Tracking Issue for linker arguments respecting their relative order with -l library options #99427

Open
1 of 3 tasks
petrochenkov opened this issue Jul 18, 2022 · 10 comments
Open
1 of 3 tasks
Labels
A-linkage Area: linking into static, shared libraries and binaries C-tracking-issue Category: A tracking issue for an RFC or an unstable feature. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue.

Comments

@petrochenkov
Copy link
Contributor

petrochenkov commented Jul 18, 2022

This is a tracking issue for link arguments respecting their relative order with -l library options, which is a part of RFC "Linking modifiers for native libraries" (#81490, rust-lang/rfcs#2951), https://github.com/rust-lang/rfcs/blob/master/text/2951-native-link-modifiers.md#relative-order-of--l-and--clink-args-options specifically.
There's no feature gate for the issue.

About tracking issues

Tracking issues are used to record the overall progress of implementation.
They are also used as hubs connecting to other relevant issues, e.g., bugs or open design questions.
A tracking issue is however not meant for large scale discussion, questions, or bug reports about a feature.
Instead, open a dedicated issue for the specific matter and add the relevant feature gate label.

Steps

Unresolved Questions

The feature is unlikely to be implementable in the form that is specified in the RFC, i.e. by preserving relative order of -l and -Clink-arg(s) options.
-C link-arg was usable for overriding options previously passed by the compiler for long time, so is pretty much guaranteed to be passed at the end of command line at this point.

The suggested solution (see #81490 and below) is to reuse the -l option for such arguments and introduce -l link-arg=arbitrary-link-argument, which is exactly like -C link-arg=arbitrary-link-argument, except that its relative order to other -l options is respected.

Implementation history

@petrochenkov petrochenkov added C-tracking-issue Category: A tracking issue for an RFC or an unstable feature. A-linkage Area: linking into static, shared libraries and binaries T-compiler Relevant to the compiler team, which will review and decide on the PR/issue. labels Jul 18, 2022
@petrochenkov
Copy link
Contributor Author

Implemented in #99467.

GuillaumeGomez added a commit to GuillaumeGomez/rust that referenced this issue Jul 23, 2022
GuillaumeGomez added a commit to GuillaumeGomez/rust that referenced this issue Jul 27, 2022
bors added a commit to rust-lang-ci/rust that referenced this issue Jul 29, 2022
@petrochenkov
Copy link
Contributor Author

petrochenkov commented Sep 1, 2022

There's one possible improvement to -l link-arg making it more portable between linkers and useful - befriending it with the verbatim modifier (#99425).

-l link-arg:-verbatim=-foo would add -Wl,-foo (or equivalent) when C compiler is used as a linker, and just -foo when bare linker is used.
-l link-arg:+verbatim=-bar on the other hand would always pass just -bar.
Not sure about the default here, I suspect that -verbatim would be preferable, but it's different from -C link-arg.

This would help to make link-arg usable in #[link] attributes and e.g. wrap libc and libgcc into a group (*) in the libc crate like

#[link(kind = "link-arg", name = "--start-group")]
#[link(kind = "static", name = "c")]
#[link(kind = "static", name = "gcc")]
#[link(kind = "link-arg", name = "--end-group")]

(*) to address cyclic dependencies between them

This is an analogue of CMake's LINKER: prefix (https://cmake.org/cmake/help/git-stage/command/target_link_options.html#handling-compiler-driver-differences), and was discussed as a possible future extension in the link modifier RFC (https://github.com/rust-lang/rfcs/blob/master/text/2951-native-link-modifiers.md#support-linkarg--string-in-addition-to-the-modifiers).

cc @krasimirgg

@Be-ing
Copy link
Contributor

Be-ing commented Oct 13, 2022

I think -l link-arg may have an unintended side effect: when build scripts run println!("cargo:rustc-link-lib={some_value}") to get cargo to call rustc with -l, cargo transitively passes the -l some_value down to the crates' reverse dependencies. By contrast, using the recently stabilized cargo:rustc-link-arg, which passes -C link-arg to rustc, cargo does not pass the linker argument down to reverse dependencies. I think this would be useful, but is this desired?

@petrochenkov
Copy link
Contributor Author

petrochenkov commented Oct 14, 2022

@Be-ing
It's better to ask the cargo questions on the cargo repo, but in case of rustc -l link-args are supposed to be passed from rlibs to the final linking step in the same way as other -l options, to address the use case from #99427 (comment), for example (libc crate adds --(start,end)-group, but they are actually passed to the linker later when libc crate is used as a dependency of an executable or dynamic library).

@Be-ing
Copy link
Contributor

Be-ing commented May 25, 2023

What is needed to move this forward? I have run into another situation in which -l link-arg is needed. When linking Qt6Quick statically, some .cpp.o files (compiled from a file generated by Qt's rcc tool) need to be linked too, but there's no stable interface to tell rustc and cargo to link those. I have tried using

println!("cargo:rustc-link-lib=static:+verbatim=/home/be/qt6-installed/lib/objects-Release/Quick_resources_2/.rcc/qrc_scenegraph_shaders.cpp.o");

but that fails with file too small to be an archive, an error that comes from LLVM. When implementing support for linking file paths in the pkg-config crate, I could hack around the lack of -l link-arg by splitting the path into the parent directory and file name then passing those with -L and -l, but that doesn't work for .o files because of this file too small to be an archive error.

compiler-errors added a commit to compiler-errors/rust that referenced this issue Nov 28, 2023
…, r=petrochenkov

Added linker_arg(s) Linker trait methods for link-arg to be prefixed "-Wl," for cc-like linker args and not verbatim

rust-lang#99427 (comment)

> here's one possible improvement to -l link-arg making it more portable between linkers and useful - befriending it with the verbatim modifier (rust-lang#99425).
>
> -l link-arg:-verbatim=-foo would add -Wl,-foo (or equivalent) when C compiler is used as a linker, and just -foo when bare linker is used.
> -l link-arg:+verbatim=-bar on the other hand would always pass just -bar.
rust-timer added a commit to rust-lang-ci/rust that referenced this issue Nov 28, 2023
Rollup merge of rust-lang#118202 - azhogin:azhogin/link_args_wrapping, r=petrochenkov

Added linker_arg(s) Linker trait methods for link-arg to be prefixed "-Wl," for cc-like linker args and not verbatim

rust-lang#99427 (comment)

> here's one possible improvement to -l link-arg making it more portable between linkers and useful - befriending it with the verbatim modifier (rust-lang#99425).
>
> -l link-arg:-verbatim=-foo would add -Wl,-foo (or equivalent) when C compiler is used as a linker, and just -foo when bare linker is used.
> -l link-arg:+verbatim=-bar on the other hand would always pass just -bar.
@petrochenkov
Copy link
Contributor Author

petrochenkov commented Nov 28, 2023

Update: #118202 implemented the new behavior for -l link-arg (#99427 (comment)), now it adds -Wl, to the passed linker flags automatically if the linker is a C/C++ compiler.

This may be a breaking change for the current users of -l link-arg.

If some flag needs to be passed specifically to the C/C++ compiler, and not to the underlying linker, then the +verbatim modifier can be used - -l link-arg:+verbatim=-nostartfiles.

bors added a commit to rust-lang-ci/rust that referenced this issue Nov 30, 2023
…trochenkov

Enable `link-arg` link kind inside of `#[link]` attribute

rust-lang#99427 (comment)

> ...
> This would help to make `link-arg` usable in `#[link]` attributes and e.g. wrap libc and libgcc into a group (*) in the libc crate like
>
> ```
> #[link(kind = "link-arg", name = "--start-group")]
> #[link(kind = "static", name = "c")]
> #[link(kind = "static", name = "gcc")]
> #[link(kind = "link-arg", name = "--end-group")]
> ```
>
> (*) to address cyclic dependencies between them
>
> This is an analogue of CMake's LINKER: prefix (https://cmake.org/cmake/help/git-stage/command/target_link_options.html#handling-compiler-driver-differences), and was discussed as a possible future extension in the link modifier RFC (https://github.com/rust-lang/rfcs/blob/master/text/2951-native-link-modifiers.md#support-linkarg--string-in-addition-to-the-modifiers).
bors added a commit to rust-lang-ci/rust that referenced this issue Nov 30, 2023
…trochenkov

Enable `link-arg` link kind inside of `#[link]` attribute

rust-lang#99427 (comment)

> ...
> This would help to make `link-arg` usable in `#[link]` attributes and e.g. wrap libc and libgcc into a group (*) in the libc crate like
>
> ```
> #[link(kind = "link-arg", name = "--start-group")]
> #[link(kind = "static", name = "c")]
> #[link(kind = "static", name = "gcc")]
> #[link(kind = "link-arg", name = "--end-group")]
> ```
>
> (*) to address cyclic dependencies between them
>
> This is an analogue of CMake's LINKER: prefix (https://cmake.org/cmake/help/git-stage/command/target_link_options.html#handling-compiler-driver-differences), and was discussed as a possible future extension in the link modifier RFC (https://github.com/rust-lang/rfcs/blob/master/text/2951-native-link-modifiers.md#support-linkarg--string-in-addition-to-the-modifiers).
@madsmtm
Copy link
Contributor

madsmtm commented Dec 5, 2023

Is this intended to also be used to weakly link frameworks on Apple platforms? As in, the equivalent of -weak_framework CoreFoundation would be to do the following:

#![feature(link_arg_attribute)]

#[link(name = "-weak_framework", kind = "link-arg", modifiers = "+verbatim")]
#[link(name = "CoreFoundation", kind = "link-arg", modifiers = "+verbatim")]
extern "C" {}

Or must this be implemented separately as #[link(name = "CoreFoundation", kind = "weak_framework")]?

@petrochenkov
Copy link
Contributor Author

@madsmtm
link-arg is supposed to cover any cases that are not natively supported by existing link kinds at the moment (https://github.com/rust-lang/rfcs/blob/master/text/2951-native-link-modifiers.md#support-linkarg--string-in-addition-to-the-modifiers).
The -weak_framework seems to fit that description, although I'm not personally familiar with it.

@madsmtm
Copy link
Contributor

madsmtm commented Dec 5, 2023

Cool, thanks, I've submitted a test for this in #118644.

(I actually think it works exactly like "framework" (rustc_session::utils::NativeLibKind::Framework), which seems to suggest it may need to be +verbatim to be completely correct; I've updated my previous post).

@madsmtm
Copy link
Contributor

madsmtm commented Dec 5, 2023

Also tagging @grovesNL, you asked about this functionality a while ago on this internals thread.

matthiaskrgr added a commit to matthiaskrgr/rust that referenced this issue Dec 16, 2023
…=b-naber

Add test for Apple's `-weak_framework` linker argument

The [`-weak_framework`](https://developer.apple.com/library/archive/documentation/MacOSX/Conceptual/BPFrameworks/Concepts/WeakLinking.html) linker argument can sometimes be useful to reduce startup times, and to link newer frameworks while still having older deployment targets.

So I made a test to ensure that it continues to work.

Discussed in rust-lang#99427.
GuillaumeGomez added a commit to GuillaumeGomez/rust that referenced this issue Dec 16, 2023
…=b-naber

Add test for Apple's `-weak_framework` linker argument

The [`-weak_framework`](https://developer.apple.com/library/archive/documentation/MacOSX/Conceptual/BPFrameworks/Concepts/WeakLinking.html) linker argument can sometimes be useful to reduce startup times, and to link newer frameworks while still having older deployment targets.

So I made a test to ensure that it continues to work.

Discussed in rust-lang#99427.
bors added a commit to rust-lang-ci/rust that referenced this issue Dec 17, 2023
…-naber

Add test for Apple's `-weak_framework` linker argument

The [`-weak_framework`](https://developer.apple.com/library/archive/documentation/MacOSX/Conceptual/BPFrameworks/Concepts/WeakLinking.html) linker argument can sometimes be useful to reduce startup times, and to link newer frameworks while still having older deployment targets.

So I made a test to ensure that it continues to work.

Discussed in rust-lang#99427.
bors added a commit to rust-lang-ci/rust that referenced this issue Mar 12, 2024
…ompiler-errors

Add test for Apple's `-weak_framework` linker argument

The [`-weak_framework`](https://developer.apple.com/library/archive/documentation/MacOSX/Conceptual/BPFrameworks/Concepts/WeakLinking.html) linker argument can sometimes be useful to reduce startup times, and to link newer frameworks while still having older deployment targets.

So I made a test to ensure that it continues to work.

Discussed in rust-lang#99427.
bors added a commit to rust-lang-ci/rust that referenced this issue Mar 18, 2024
…ompiler-errors

Add test for Apple's `-weak_framework` linker argument

The [`-weak_framework`](https://developer.apple.com/library/archive/documentation/MacOSX/Conceptual/BPFrameworks/Concepts/WeakLinking.html) linker argument can sometimes be useful to reduce startup times, and to link newer frameworks while still having older deployment targets.

So I made a test to ensure that it continues to work.

Discussed in rust-lang#99427.
bors added a commit to rust-lang-ci/rust that referenced this issue Mar 26, 2024
…ompiler-errors

Add test for Apple's `-weak_framework` linker argument

The [`-weak_framework`](https://developer.apple.com/library/archive/documentation/MacOSX/Conceptual/BPFrameworks/Concepts/WeakLinking.html) linker argument can sometimes be useful to reduce startup times, and to link newer frameworks while still having older deployment targets.

So I made a test to ensure that it continues to work.

Discussed in rust-lang#99427.
github-actions bot pushed a commit to rust-lang/miri that referenced this issue Mar 29, 2024
…rrors

Add test for Apple's `-weak_framework` linker argument

The [`-weak_framework`](https://developer.apple.com/library/archive/documentation/MacOSX/Conceptual/BPFrameworks/Concepts/WeakLinking.html) linker argument can sometimes be useful to reduce startup times, and to link newer frameworks while still having older deployment targets.

So I made a test to ensure that it continues to work.

Discussed in rust-lang/rust#99427.
lnicola pushed a commit to lnicola/rust-analyzer that referenced this issue Apr 7, 2024
…rrors

Add test for Apple's `-weak_framework` linker argument

The [`-weak_framework`](https://developer.apple.com/library/archive/documentation/MacOSX/Conceptual/BPFrameworks/Concepts/WeakLinking.html) linker argument can sometimes be useful to reduce startup times, and to link newer frameworks while still having older deployment targets.

So I made a test to ensure that it continues to work.

Discussed in rust-lang/rust#99427.
RalfJung pushed a commit to RalfJung/rust-analyzer that referenced this issue Apr 27, 2024
…rrors

Add test for Apple's `-weak_framework` linker argument

The [`-weak_framework`](https://developer.apple.com/library/archive/documentation/MacOSX/Conceptual/BPFrameworks/Concepts/WeakLinking.html) linker argument can sometimes be useful to reduce startup times, and to link newer frameworks while still having older deployment targets.

So I made a test to ensure that it continues to work.

Discussed in rust-lang/rust#99427.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-linkage Area: linking into static, shared libraries and binaries C-tracking-issue Category: A tracking issue for an RFC or an unstable feature. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue.
Projects
None yet
Development

No branches or pull requests

3 participants