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

feat: Strip debug info from opt builds #2513

Merged
merged 3 commits into from
Apr 2, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion docs/flatten.md
Original file line number Diff line number Diff line change
Expand Up @@ -1180,7 +1180,7 @@ rust_toolchain(<a href="#rust_toolchain-name">name</a>, <a href="#rust_toolchain
<a href="#rust_toolchain-experimental_use_cc_common_link">experimental_use_cc_common_link</a>, <a href="#rust_toolchain-extra_exec_rustc_flags">extra_exec_rustc_flags</a>, <a href="#rust_toolchain-extra_rustc_flags">extra_rustc_flags</a>,
<a href="#rust_toolchain-extra_rustc_flags_for_crate_types">extra_rustc_flags_for_crate_types</a>, <a href="#rust_toolchain-global_allocator_library">global_allocator_library</a>, <a href="#rust_toolchain-llvm_cov">llvm_cov</a>, <a href="#rust_toolchain-llvm_profdata">llvm_profdata</a>,
<a href="#rust_toolchain-llvm_tools">llvm_tools</a>, <a href="#rust_toolchain-opt_level">opt_level</a>, <a href="#rust_toolchain-per_crate_rustc_flags">per_crate_rustc_flags</a>, <a href="#rust_toolchain-rust_doc">rust_doc</a>, <a href="#rust_toolchain-rust_std">rust_std</a>, <a href="#rust_toolchain-rustc">rustc</a>, <a href="#rust_toolchain-rustc_lib">rustc_lib</a>,
<a href="#rust_toolchain-rustfmt">rustfmt</a>, <a href="#rust_toolchain-staticlib_ext">staticlib_ext</a>, <a href="#rust_toolchain-stdlib_linkflags">stdlib_linkflags</a>, <a href="#rust_toolchain-target_json">target_json</a>, <a href="#rust_toolchain-target_triple">target_triple</a>)
<a href="#rust_toolchain-rustfmt">rustfmt</a>, <a href="#rust_toolchain-staticlib_ext">staticlib_ext</a>, <a href="#rust_toolchain-stdlib_linkflags">stdlib_linkflags</a>, <a href="#rust_toolchain-strip_level">strip_level</a>, <a href="#rust_toolchain-target_json">target_json</a>, <a href="#rust_toolchain-target_triple">target_triple</a>)
</pre>

Declares a Rust toolchain for use.
Expand Down Expand Up @@ -1260,6 +1260,7 @@ See `@rules_rust//rust:repositories.bzl` for examples of defining the `@rust_cpu
| <a id="rust_toolchain-rustfmt"></a>rustfmt | **Deprecated**: Instead see [rustfmt_toolchain](#rustfmt_toolchain) | <a href="https://bazel.build/concepts/labels">Label</a> | optional | <code>None</code> |
| <a id="rust_toolchain-staticlib_ext"></a>staticlib_ext | The extension for static libraries created from rustc. | String | required | |
| <a id="rust_toolchain-stdlib_linkflags"></a>stdlib_linkflags | Additional linker flags to use when Rust standard library is linked by a C++ linker (rustc will deal with these automatically). Subject to location expansion with respect to the srcs of the <code>rust_std</code> attribute. | List of strings | required | |
| <a id="rust_toolchain-strip_level"></a>strip_level | Rustc strip levels. For all potential options, see https://doc.rust-lang.org/rustc/codegen-options/index.html#strip | <a href="https://bazel.build/rules/lib/dict">Dictionary: String -> String</a> | optional | <code>{"dbg": "none", "fastbuild": "none", "opt": "debuginfo"}</code> |
| <a id="rust_toolchain-target_json"></a>target_json | Override the target_triple with a custom target specification. For more details see: https://doc.rust-lang.org/rustc/targets/custom.html | String | optional | <code>""</code> |
| <a id="rust_toolchain-target_triple"></a>target_triple | The platform triple for the toolchains target environment. For more details see: https://docs.bazel.build/versions/master/skylark/rules.html#configurations | String | optional | <code>""</code> |

Expand Down
3 changes: 2 additions & 1 deletion docs/rust_repositories.md
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ rust_toolchain(<a href="#rust_toolchain-name">name</a>, <a href="#rust_toolchain
<a href="#rust_toolchain-experimental_use_cc_common_link">experimental_use_cc_common_link</a>, <a href="#rust_toolchain-extra_exec_rustc_flags">extra_exec_rustc_flags</a>, <a href="#rust_toolchain-extra_rustc_flags">extra_rustc_flags</a>,
<a href="#rust_toolchain-extra_rustc_flags_for_crate_types">extra_rustc_flags_for_crate_types</a>, <a href="#rust_toolchain-global_allocator_library">global_allocator_library</a>, <a href="#rust_toolchain-llvm_cov">llvm_cov</a>, <a href="#rust_toolchain-llvm_profdata">llvm_profdata</a>,
<a href="#rust_toolchain-llvm_tools">llvm_tools</a>, <a href="#rust_toolchain-opt_level">opt_level</a>, <a href="#rust_toolchain-per_crate_rustc_flags">per_crate_rustc_flags</a>, <a href="#rust_toolchain-rust_doc">rust_doc</a>, <a href="#rust_toolchain-rust_std">rust_std</a>, <a href="#rust_toolchain-rustc">rustc</a>, <a href="#rust_toolchain-rustc_lib">rustc_lib</a>,
<a href="#rust_toolchain-rustfmt">rustfmt</a>, <a href="#rust_toolchain-staticlib_ext">staticlib_ext</a>, <a href="#rust_toolchain-stdlib_linkflags">stdlib_linkflags</a>, <a href="#rust_toolchain-target_json">target_json</a>, <a href="#rust_toolchain-target_triple">target_triple</a>)
<a href="#rust_toolchain-rustfmt">rustfmt</a>, <a href="#rust_toolchain-staticlib_ext">staticlib_ext</a>, <a href="#rust_toolchain-stdlib_linkflags">stdlib_linkflags</a>, <a href="#rust_toolchain-strip_level">strip_level</a>, <a href="#rust_toolchain-target_json">target_json</a>, <a href="#rust_toolchain-target_triple">target_triple</a>)
</pre>

Declares a Rust toolchain for use.
Expand Down Expand Up @@ -121,6 +121,7 @@ See `@rules_rust//rust:repositories.bzl` for examples of defining the `@rust_cpu
| <a id="rust_toolchain-rustfmt"></a>rustfmt | **Deprecated**: Instead see [rustfmt_toolchain](#rustfmt_toolchain) | <a href="https://bazel.build/concepts/labels">Label</a> | optional | <code>None</code> |
| <a id="rust_toolchain-staticlib_ext"></a>staticlib_ext | The extension for static libraries created from rustc. | String | required | |
| <a id="rust_toolchain-stdlib_linkflags"></a>stdlib_linkflags | Additional linker flags to use when Rust standard library is linked by a C++ linker (rustc will deal with these automatically). Subject to location expansion with respect to the srcs of the <code>rust_std</code> attribute. | List of strings | required | |
| <a id="rust_toolchain-strip_level"></a>strip_level | Rustc strip levels. For all potential options, see https://doc.rust-lang.org/rustc/codegen-options/index.html#strip | <a href="https://bazel.build/rules/lib/dict">Dictionary: String -> String</a> | optional | <code>{"dbg": "none", "fastbuild": "none", "opt": "debuginfo"}</code> |
| <a id="rust_toolchain-target_json"></a>target_json | Override the target_triple with a custom target specification. For more details see: https://doc.rust-lang.org/rustc/targets/custom.html | String | optional | <code>""</code> |
| <a id="rust_toolchain-target_triple"></a>target_triple | The platform triple for the toolchains target environment. For more details see: https://docs.bazel.build/versions/master/skylark/rules.html#configurations | String | optional | <code>""</code> |

Expand Down
6 changes: 5 additions & 1 deletion rust/private/rustc.bzl
Original file line number Diff line number Diff line change
Expand Up @@ -959,6 +959,7 @@ def construct_arguments(
compilation_mode = get_compilation_mode_opts(ctx, toolchain)
rustc_flags.add(compilation_mode.opt_level, format = "--codegen=opt-level=%s")
rustc_flags.add(compilation_mode.debug_info, format = "--codegen=debuginfo=%s")
rustc_flags.add(compilation_mode.strip_level, format = "--codegen=strip=%s")

# For determinism to help with build distribution and such
if remap_path_prefix != None:
Expand Down Expand Up @@ -1288,12 +1289,15 @@ def rustc_compile_action(
if rustc_output:
action_outputs.append(rustc_output)

# Get the compilation mode for the current target.
compilation_mode = get_compilation_mode_opts(ctx, toolchain)

# Rustc generates a pdb file (on Windows) or a dsym folder (on macos) so provide it in an output group for crate
# types that benefit from having debug information in a separate file.
pdb_file = None
dsym_folder = None
if crate_info.type in ("cdylib", "bin"):
if toolchain.target_os == "windows":
if toolchain.target_os == "windows" and compilation_mode.strip_level == "none":
pdb_file = ctx.actions.declare_file(crate_info.output.basename[:-len(crate_info.output.extension)] + "pdb", sibling = crate_info.output)
action_outputs.append(pdb_file)
elif toolchain.target_os == "darwin":
Expand Down
19 changes: 16 additions & 3 deletions rust/toolchain.bzl
Original file line number Diff line number Diff line change
Expand Up @@ -490,11 +490,13 @@ def _rust_toolchain_impl(ctx):
list: A list containing the target's toolchain Provider info
"""
compilation_mode_opts = {}
for k, v in ctx.attr.opt_level.items():
for k, opt_level in ctx.attr.opt_level.items():
if not k in ctx.attr.debug_info:
fail("Compilation mode {} is not defined in debug_info but is defined opt_level".format(k))
compilation_mode_opts[k] = struct(debug_info = ctx.attr.debug_info[k], opt_level = v)
for k, v in ctx.attr.debug_info.items():
if not k in ctx.attr.strip_level:
fail("Compilation mode {} is not defined in strip_level but is defined opt_level".format(k))
compilation_mode_opts[k] = struct(debug_info = ctx.attr.debug_info[k], opt_level = opt_level, strip_level = ctx.attr.strip_level[k])
for k in ctx.attr.debug_info.keys():
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think v here wasn't actually being used but the linter wasn't catching it because v was defined and used above.

if not k in ctx.attr.opt_level:
fail("Compilation mode {} is not defined in opt_level but is defined debug_info".format(k))

Expand Down Expand Up @@ -817,6 +819,17 @@ rust_toolchain = rule(
),
mandatory = True,
),
"strip_level": attr.string_dict(
doc = (
"Rustc strip levels. For all potential options, see " +
"https://doc.rust-lang.org/rustc/codegen-options/index.html#strip"
),
default = {
"dbg": "none",
"fastbuild": "none",
"opt": "debuginfo",
},
),
"target_json": attr.string(
doc = ("Override the target_triple with a custom target specification. " +
"For more details see: https://doc.rust-lang.org/rustc/targets/custom.html"),
Expand Down
94 changes: 72 additions & 22 deletions test/unit/debug_info/debug_info_analysis_test.bzl
Original file line number Diff line number Diff line change
Expand Up @@ -3,18 +3,59 @@
load("@bazel_skylib//lib:unittest.bzl", "analysistest", "asserts")
load("//rust:defs.bzl", "rust_binary", "rust_shared_library", "rust_test")

def _pdb_file_test_impl(ctx):
def _pdb_file_test_impl(ctx, expect_pdb_file):
env = analysistest.begin(ctx)
target = analysistest.target_under_test(env)

files = target[DefaultInfo].files.to_list()

if not expect_pdb_file:
asserts.equals(env, len(files), 0)
return analysistest.end(env)

asserts.equals(env, len(files), 1)
file = files[0]
asserts.equals(env, file.extension, "pdb")

return analysistest.end(env)

pdb_file_test = analysistest.make(_pdb_file_test_impl)
def _pdb_file_for_dbg_test_impl(ctx):
"""Test for dbg compilation mode."""
return _pdb_file_test_impl(ctx, True)

pdb_file_dbg_test = analysistest.make(
_pdb_file_for_dbg_test_impl,
config_settings = {
"//command_line_option:compilation_mode": "dbg",
},
)

def _pdb_file_for_fastbuild_test_impl(ctx):
"""Test for fastbuild compilation mode."""
return _pdb_file_test_impl(ctx, True)

pdb_file_fastbuild_test = analysistest.make(
_pdb_file_for_fastbuild_test_impl,
config_settings = {
"//command_line_option:compilation_mode": "fastbuild",
},
)

def _pdb_file_for_opt_test_impl(ctx):
"""Test for opt compilation mode."""
return _pdb_file_test_impl(ctx, False)

pdb_file_opt_test = analysistest.make(
_pdb_file_for_opt_test_impl,
config_settings = {
"//command_line_option:compilation_mode": "opt",
},
)

# Mapping from compilation mode to pdb file test.
pdb_file_tests = {
"dbg": pdb_file_dbg_test,
"fastbuild": pdb_file_fastbuild_test,
"opt": pdb_file_opt_test,
}

def _dsym_folder_test_impl(ctx):
env = analysistest.begin(ctx)
Expand Down Expand Up @@ -47,11 +88,12 @@ def debug_info_analysis_test_suite(name):
output_group = "pdb_file",
)

pdb_file_test(
name = "lib_pdb_test",
target_under_test = ":mylib.pdb",
target_compatible_with = ["@platforms//os:windows"],
)
for compilation_mode, pdb_test in pdb_file_tests.items():
pdb_test(
name = "lib_pdb_test_{}".format(compilation_mode),
target_under_test = ":mylib.pdb",
target_compatible_with = ["@platforms//os:windows"],
)

native.filegroup(
name = "mylib.dSYM",
Expand All @@ -77,11 +119,12 @@ def debug_info_analysis_test_suite(name):
output_group = "pdb_file",
)

pdb_file_test(
name = "bin_pdb_test",
target_under_test = ":mybin.pdb",
target_compatible_with = ["@platforms//os:windows"],
)
for compilation_mode, pdb_test in pdb_file_tests.items():
pdb_test(
name = "bin_pdb_test_{}".format(compilation_mode),
target_under_test = ":mybin.pdb",
target_compatible_with = ["@platforms//os:windows"],
)

native.filegroup(
name = "mybin.dSYM",
Expand All @@ -108,11 +151,12 @@ def debug_info_analysis_test_suite(name):
testonly = True,
)

pdb_file_test(
name = "test_pdb_test",
target_under_test = ":mytest.pdb",
target_compatible_with = ["@platforms//os:windows"],
)
for compilation_mode, pdb_test in pdb_file_tests.items():
pdb_test(
name = "test_pdb_test_{}".format(compilation_mode),
target_under_test = ":mytest.pdb",
target_compatible_with = ["@platforms//os:windows"],
)

native.filegroup(
name = "mytest.dSYM",
Expand All @@ -130,11 +174,17 @@ def debug_info_analysis_test_suite(name):
native.test_suite(
name = name,
tests = [
":lib_pdb_test",
":lib_dsym_test",
":bin_pdb_test",
":bin_dsym_test",
":test_pdb_test",
":test_dsym_test",
] + [
":lib_pdb_test_{}".format(compilation_mode)
for compilation_mode in pdb_file_tests
] + [
":bin_pdb_test_{}".format(compilation_mode)
for compilation_mode in pdb_file_tests
] + [
":test_pdb_test_{}".format(compilation_mode)
for compilation_mode in pdb_file_tests
],
)
5 changes: 5 additions & 0 deletions test/unit/strip_level/BUILD.bazel
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
load(":strip_level_test_suite.bzl", "strip_level_test_suite")

strip_level_test_suite(
name = "strip_level_test_suite",
)
95 changes: 95 additions & 0 deletions test/unit/strip_level/strip_level_test_suite.bzl
Original file line number Diff line number Diff line change
@@ -0,0 +1,95 @@
"""Starlark tests for `rust_toolchain.strip_level`"""

load("@bazel_skylib//lib:unittest.bzl", "analysistest")
load("@bazel_skylib//rules:write_file.bzl", "write_file")
load("//rust:defs.bzl", "rust_binary")
load(
"//test/unit:common.bzl",
"assert_action_mnemonic",
"assert_argv_contains",
)

def _strip_level_test_impl(ctx, expected_level):
env = analysistest.begin(ctx)
target = analysistest.target_under_test(env)

action = target.actions[0]
assert_action_mnemonic(env, action, "Rustc")

assert_argv_contains(env, action, "--codegen=strip={}".format(expected_level))
return analysistest.end(env)

def _strip_level_for_dbg_test_impl(ctx):
return _strip_level_test_impl(ctx, "none")

_strip_level_for_dbg_test = analysistest.make(
_strip_level_for_dbg_test_impl,
config_settings = {
"//command_line_option:compilation_mode": "dbg",
},
)

def _strip_level_for_fastbuild_test_impl(ctx):
return _strip_level_test_impl(ctx, "none")

_strip_level_for_fastbuild_test = analysistest.make(
_strip_level_for_fastbuild_test_impl,
config_settings = {
"//command_line_option:compilation_mode": "fastbuild",
},
)

def _strip_level_for_opt_test_impl(ctx):
return _strip_level_test_impl(ctx, "debuginfo")

_strip_level_for_opt_test = analysistest.make(
_strip_level_for_opt_test_impl,
config_settings = {
"//command_line_option:compilation_mode": "opt",
},
)

def strip_level_test_suite(name):
"""Entry-point macro called from the BUILD file.

Args:
name (str): The name of the test suite.
"""
write_file(
name = "bin_main",
out = "main.rs",
content = [
"fn main() {}",
"",
],
)

rust_binary(
name = "bin",
srcs = [":main.rs"],
edition = "2021",
)

_strip_level_for_dbg_test(
name = "strip_level_for_dbg_test",
target_under_test = ":bin",
)

_strip_level_for_fastbuild_test(
name = "strip_level_for_fastbuild_test",
target_under_test = ":bin",
)

_strip_level_for_opt_test(
name = "strip_level_for_opt_test",
target_under_test = ":bin",
)

native.test_suite(
name = name,
tests = [
":strip_level_for_dbg_test",
":strip_level_for_fastbuild_test",
":strip_level_for_opt_test",
],
)
Loading