Skip to content
Open
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
32 changes: 27 additions & 5 deletions zig/private/common/zig_build.bzl
Original file line number Diff line number Diff line change
Expand Up @@ -277,6 +277,16 @@ def zig_build_impl(ctx, *, kind):
use_cc_common_link = settings.use_cc_common_link
use_test_obj = kind == "zig_test" and use_cc_common_link and semver.gte(zigtoolchaininfo.zig_version, "0.16.0")

cc_toolchain = None
feature_configuration = None
generate_dsym_file = False
if use_cc_common_link and kind != "zig_static_library":
cc_toolchain, feature_configuration = find_cc_toolchain(ctx, mandatory = True)
generate_dsym_file = cc_common.is_enabled(
feature_configuration = feature_configuration,
feature_name = "generate_dsym_file",
)

providers = []
exported_library_to_link = None
direct_data = []
Expand Down Expand Up @@ -317,8 +327,11 @@ def zig_build_impl(ctx, *, kind):
elif ctx.attr.compiler_runtime == "exclude":
args.add("-fno-compiler-rt")

if ctx.attr.strip_debug_symbols and not settings.strip:
args.add("-fstrip")
if ctx.attr.strip_debug_symbols:
if generate_dsym_file:
fail("'strip_debug_symbols' cannot be enabled when generating a dSYM")
if not settings.strip:
args.add("-fstrip")

zig_lib_dir(
zigtoolchaininfo = zigtoolchaininfo,
Expand Down Expand Up @@ -361,6 +374,15 @@ def zig_build_impl(ctx, *, kind):
bin_output = ctx.actions.declare_file(bin_output_name)
solib_parents = [""]

cc_link_kwargs = {}
if generate_dsym_file:
dsym_file = ctx.actions.declare_directory(ctx.label.name + ".dSYM", sibling = bin_output)
cc_link_kwargs = {
"additional_outputs": [dsym_file],
"variables_extension": {"dsym_path": dsym_file.path},
}
output_groups["dsyms"] = depset([dsym_file])

if kind == "zig_test" and ctx.attr.test_runner:
args.add("--test-runner", ctx.file.test_runner)
direct_inputs.append(ctx.file.test_runner)
Expand Down Expand Up @@ -547,7 +569,6 @@ def zig_build_impl(ctx, *, kind):
**zig_build_kwargs
)

cc_toolchain, feature_configuration = find_cc_toolchain(ctx, mandatory = True)
library_to_link = cc_common.create_library_to_link(
actions = ctx.actions,
feature_configuration = feature_configuration,
Expand All @@ -571,6 +592,7 @@ def zig_build_impl(ctx, *, kind):
main_output = bin_output,
linking_contexts = [linking_context, root_module.cc_info.linking_context],
user_link_flags = linkopts,
**cc_link_kwargs
)
else:
args.add(bin_output, format = "-femit-bin=%s")
Expand Down Expand Up @@ -638,7 +660,6 @@ def zig_build_impl(ctx, *, kind):
**zig_build_kwargs
)

cc_toolchain, feature_configuration = find_cc_toolchain(ctx, mandatory = True)
library_to_link = cc_common.create_library_to_link(
actions = ctx.actions,
feature_configuration = feature_configuration,
Expand All @@ -662,6 +683,7 @@ def zig_build_impl(ctx, *, kind):
main_output = bin_output,
linking_contexts = [linking_context, root_module.cc_info.linking_context],
user_link_flags = linkopts,
**cc_link_kwargs
)
else:
args.add(bin_output, format = "-femit-bin=%s")
Expand Down Expand Up @@ -713,7 +735,6 @@ def zig_build_impl(ctx, *, kind):
**zig_build_kwargs
)

cc_toolchain, feature_configuration = find_cc_toolchain(ctx, mandatory = True)
library_to_link = cc_common.create_library_to_link(
actions = ctx.actions,
feature_configuration = feature_configuration,
Expand All @@ -738,6 +759,7 @@ def zig_build_impl(ctx, *, kind):
main_output = bin_output,
linking_contexts = [linking_context, root_module.cc_info.linking_context],
user_link_flags = linkopts,
**cc_link_kwargs
)

exported_library_to_link = link_outputs.library_to_link
Expand Down
3 changes: 3 additions & 0 deletions zig/tests/BUILD.bazel
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ load("@bazel_skylib//:bzl_library.bzl", "bzl_library")
load(":bzlmod_zig_test.bzl", "bzlmod_zig_test_suite")
load(":cache_test.bzl", "cache_test_suite")
load(":config_test.bzl", "config_test_suite")
load(":dsym_test.bzl", "dsym_test_suite")
load(":emit_attr_test.bzl", "emit_attr_test_suite")
load(":mode_test.bzl", "mode_test_suite")
load(":module_info_test.bzl", "module_info_test_suite")
Expand All @@ -26,6 +27,8 @@ cache_test_suite(name = "cache_test")

config_test_suite(name = "config_test")

dsym_test_suite(name = "dsym_test")

emit_attr_test_suite(name = "emit_attr_test")

use_cc_common_link_test_suite(name = "use_cc_common_link_test")
Expand Down
142 changes: 142 additions & 0 deletions zig/tests/dsym_test.bzl
Original file line number Diff line number Diff line change
@@ -0,0 +1,142 @@
"""Analysis tests for dSYM outputs from cc_common.link."""

load("@bazel_features//:features.bzl", "bazel_features")
load("@bazel_skylib//lib:partial.bzl", "partial")
load("@bazel_skylib//lib:sets.bzl", "sets")
load("@bazel_skylib//lib:unittest.bzl", "analysistest", "asserts", "unittest")
load(
":util.bzl",
"assert_find_action",
"assert_flag_set",
"assert_flag_unset",
"canonical_label",
)

_APPLE_GENERATE_DSYM = "//command_line_option:apple_generate_dsym"
_EXTRA_TOOLCHAINS = "//command_line_option:extra_toolchains"
_STRIP = "//command_line_option:strip"
_TARGET_PLATFORM = "//command_line_option:platforms"
_SETTINGS_USE_CC_COMMON_LINK = canonical_label("@//zig/settings:use_cc_common_link")

_PLATFORM_ZIG_ONLY_X86_64_LINUX = canonical_label("@//zig/tests/platforms:zig-only-x86_64-linux")
_TOOLCHAIN_UNCONSTRAINED_DEFAULT_TEST = canonical_label("@//zig/tests/platforms:unconstrained_default_test_toolchain")
_TOOLCHAIN_ZIG_ONLY_X86_64_LINUX = canonical_label("@//zig/tests/platforms:zig-only-x86_64-linux_toolchain")

def _dsyms_enabled_test_impl(ctx):
env = analysistest.begin(ctx)
target = analysistest.target_under_test(env)
output_groups = target[OutputGroupInfo]

asserts.true(env, hasattr(output_groups, "dsyms"), "dSYMs should be exposed when the C++ toolchain enables generate_dsym_file.")
dsyms = output_groups.dsyms.to_list() if hasattr(output_groups, "dsyms") else []
asserts.equals(env, 1, len(dsyms), "Exactly one dSYM should be exposed.")
if dsyms:
dsym = dsyms[0]
asserts.true(env, dsym.is_directory, "The dSYM should be a directory artifact.")
asserts.equals(env, target.label.name + ".dSYM", dsym.basename)

link = assert_find_action(env, "CppLink")
asserts.true(env, sets.contains(sets.make(link.outputs.to_list()), dsym), "The CppLink action should produce the dSYM.")

link_variables = link.argv + getattr(link, "env", {}).values()
asserts.true(
env,
any([dsym.path in value for value in link_variables]),
"The CppLink command line or environment should contain the dSYM path.",
)

for action in analysistest.target_actions(env):
if action.mnemonic in ["ZigBuildLib", "ZigBuildTest"]:
assert_flag_unset(env, "-fstrip", action.argv)

return analysistest.end(env)

_dsyms_enabled_test = analysistest.make(
_dsyms_enabled_test_impl,
config_settings = {
_APPLE_GENERATE_DSYM: True,
_SETTINGS_USE_CC_COMMON_LINK: True,
_STRIP: "never",
},
)

def _dsyms_strip_debug_symbols_test_impl(ctx):
env = analysistest.begin(ctx)
asserts.expect_failure(env, "'strip_debug_symbols' cannot be enabled when generating a dSYM")
return analysistest.end(env)

_dsyms_strip_debug_symbols_test = analysistest.make(
_dsyms_strip_debug_symbols_test_impl,
config_settings = {
_APPLE_GENERATE_DSYM: True,
_SETTINGS_USE_CC_COMMON_LINK: True,
},
expect_failure = True,
)

def _dsyms_disabled_test_impl(ctx):
env = analysistest.begin(ctx)
target = analysistest.target_under_test(env)
output_groups = target[OutputGroupInfo]

asserts.false(env, hasattr(output_groups, "dsyms"), "dSYMs should not be exposed when generate_dsym_file is disabled.")
assert_find_action(env, "CppLink")
assert_flag_set(env, "-fstrip", assert_find_action(env, "ZigBuildLib").argv)

return analysistest.end(env)

_dsyms_disabled_test = analysistest.make(
_dsyms_disabled_test_impl,
config_settings = {
_APPLE_GENERATE_DSYM: False,
_SETTINGS_USE_CC_COMMON_LINK: True,
_STRIP: "always",
},
)

def _dsyms_without_cc_toolchain_test_impl(ctx):
env = analysistest.begin(ctx)
target = analysistest.target_under_test(env)
output_groups = target[OutputGroupInfo]

asserts.false(env, hasattr(output_groups, "dsyms"), "A Zig-only target should not expose a dSYM that no action can create.")
assert_find_action(env, "ZigBuildExe")
asserts.false(
env,
any([action.mnemonic == "CppLink" for action in analysistest.target_actions(env)]),
"A Zig-only target should not create a CppLink action.",
)

return analysistest.end(env)

def _zig_only_config(generate_dsym):
return {
_APPLE_GENERATE_DSYM: generate_dsym,
_EXTRA_TOOLCHAINS: ",".join([
_TOOLCHAIN_ZIG_ONLY_X86_64_LINUX,
] + ([_TOOLCHAIN_UNCONSTRAINED_DEFAULT_TEST] if bazel_features.toolchains.has_default_test_toolchain_type else [])),
_SETTINGS_USE_CC_COMMON_LINK: False,
_TARGET_PLATFORM: _PLATFORM_ZIG_ONLY_X86_64_LINUX,
}

_dsyms_without_cc_toolchain_requested_test = analysistest.make(
_dsyms_without_cc_toolchain_test_impl,
config_settings = _zig_only_config(True),
)

_dsyms_without_cc_toolchain_unrequested_test = analysistest.make(
_dsyms_without_cc_toolchain_test_impl,
config_settings = _zig_only_config(False),
)

def dsym_test_suite(name):
unittest.suite(
name,
partial.make(_dsyms_enabled_test, name = "dsym_binary_enabled_test", target_under_test = "//zig/tests/simple-binary:binary", size = "small", target_compatible_with = ["@platforms//os:macos"]),
partial.make(_dsyms_enabled_test, name = "dsym_shared_library_enabled_test", target_under_test = "//zig/tests/simple-shared-library:shared", size = "small", target_compatible_with = ["@platforms//os:macos"]),
partial.make(_dsyms_enabled_test, name = "dsym_test_enabled_test", target_under_test = "//zig/tests/simple-test:test", size = "small", target_compatible_with = ["@platforms//os:macos"]),
partial.make(_dsyms_strip_debug_symbols_test, name = "dsym_strip_debug_symbols_test", target_under_test = "//zig/tests/strip_debug_symbols:binary-strip", size = "small", target_compatible_with = ["@platforms//os:macos"]),
partial.make(_dsyms_disabled_test, name = "dsym_binary_disabled_test", target_under_test = "//zig/tests/simple-binary:binary", size = "small"),
partial.make(_dsyms_without_cc_toolchain_requested_test, name = "dsym_zig_only_requested_test", target_under_test = "//zig/tests/simple-binary:binary", size = "small"),
partial.make(_dsyms_without_cc_toolchain_unrequested_test, name = "dsym_zig_only_unrequested_test", target_under_test = "//zig/tests/simple-binary:binary", size = "small"),
)
Loading