From 19aa1216358e84a0bb538008d333e6356697c49f Mon Sep 17 00:00:00 2001 From: Marcel Hlopko Date: Thu, 24 Mar 2022 08:52:11 +0100 Subject: [PATCH] DO_NOT_SUBMIT: Do not provide CrateInfo from staticlib/cdylib This draft should be split into smaller PRs and needs tests. This draft addresses https://github.com/bazelbuild/rules_rust/issues/1063. There are multiple small fixes: * currently we don't include the output hash for cdylib, but we do for staticlib. It's more accurate to not include the output hash for staticlib as well. * currently rust_static_library and rust_shared_library announce they provide CrateInfo, DepInfo, and DefaultInfo. They should announce providing CcInfo (and maybe DefaultInfo - I thought that is implied by default so there's no need to explicitly mention that) * currently rust_static_library and rust_shared_library actually provide CrateInfo and DepInfo. That is incorrect - outputs of these rules are not meant for consumption by Rust rules. These rules are meant to be used when leaving the world of Rust rules and entering the world of other language that wants to depend on native library (and it doesn't matter to this user if the library is written in Rust, C, C++, or other) Lastly, this PR makes https://github.com/boxdot/bazel-rust-linking-issue build. Surprising plot twist - it is actually not supported to link rust_static_library into a rust_binary. From rustc docs: > --crate-type=staticlib, #[crate_type = "staticlib"] - A static system > library will be produced. This is different from other library outputs > in that the compiler will never attempt to link to staticlib outputs. > The purpose of this output type is to create a static library containing > all of the local crate's code along with all upstream dependencies. This > output type will create *.a files on Linux, macOS and Windows (MinGW), > and *.lib files on Windows (MSVC). This format is recommended for use in > situations such as linking Rust code into an existing non-Rust > application because it will not have dynamic dependencies on other Rust > code. https://doc.rust-lang.org/reference/linkage.html#linkage. The `bazel-rust-linking-issue` fails at linktime since there are multiple definitions of allocator stubs. We may want to consider detecting this situation and failing the build with a nice error message saying this is not how these rules are intended to be used. --- rust/private/rust.bzl | 6 +++--- rust/private/rustc.bzl | 5 +++-- 2 files changed, 6 insertions(+), 5 deletions(-) diff --git a/rust/private/rust.bzl b/rust/private/rust.bzl index 3c2c6b5189..ed3b8d416e 100644 --- a/rust/private/rust.bzl +++ b/rust/private/rust.bzl @@ -249,7 +249,7 @@ def _rust_library_common(ctx, crate_type): # deterministic name is important since it ends up embedded in the executable. This is problematic when one needs # to include the library with a specific filename into a larger application. # (see https://github.com/bazelbuild/rules_rust/issues/405#issuecomment-993089889 for more details) - if crate_type != "cdylib": + if crate_type not in ["cdylib", "staticlib"]: output_hash = determine_output_hash(crate_root, ctx.label) else: output_hash = None @@ -731,7 +731,7 @@ rust_library = rule( rust_static_library = rule( implementation = _rust_static_library_impl, - provides = _common_providers, + provides = [CcInfo], attrs = dict(_common_attrs.items()), fragments = ["cpp"], host_fragments = ["cpp"], @@ -755,7 +755,7 @@ rust_static_library = rule( rust_shared_library = rule( implementation = _rust_shared_library_impl, - provides = _common_providers, + provides = [CcInfo], attrs = dict(_common_attrs.items()), fragments = ["cpp"], host_fragments = ["cpp"], diff --git a/rust/private/rustc.bzl b/rust/private/rustc.bzl index 982dbc273e..7f8040b8f9 100644 --- a/rust/private/rustc.bzl +++ b/rust/private/rustc.bzl @@ -967,8 +967,6 @@ def rustc_compile_action( out_binary = getattr(attr, "out_binary", False) providers = [ - crate_info, - dep_info, DefaultInfo( # nb. This field is required for cc_library to depend on our output. files = depset(outputs), @@ -976,6 +974,9 @@ def rustc_compile_action( executable = crate_info.output if crate_info.type == "bin" or crate_info.is_test or out_binary else None, ), ] + if crate_info.type not in ["cdylib", "staticlib"]: + providers.append(crate_info) + providers.append(dep_info) if toolchain.target_arch != "wasm32": providers += establish_cc_info(ctx, attr, crate_info, toolchain, cc_toolchain, feature_configuration, interface_library) if pdb_file: