Skip to content

Commit

Permalink
Fix rustc bug on windows by symlinking all transitive deps into a lin…
Browse files Browse the repository at this point in the history
…ked directory.
  • Loading branch information
timbess committed Aug 16, 2023
1 parent 959db8e commit 09def9d
Showing 1 changed file with 49 additions and 8 deletions.
57 changes: 49 additions & 8 deletions rust/private/rustc.bzl
Original file line number Diff line number Diff line change
Expand Up @@ -1008,7 +1008,7 @@ def construct_arguments(
use_metadata = _depend_on_metadata(crate_info, force_depend_on_objects)

# These always need to be added, even if not linking this crate.
add_crate_link_flags(rustc_flags, dep_info, force_all_deps_direct, use_metadata)
add_crate_link_flags(rustc_flags, dep_info, crate_info, force_all_deps_direct, use_metadata, toolchain.target_os == "windows")

needs_extern_proc_macro_flag = _is_proc_macro(crate_info) and crate_info.edition != "2015"
if needs_extern_proc_macro_flag:
Expand Down Expand Up @@ -1151,6 +1151,10 @@ def rustc_compile_action(
experimental_use_cc_common_link = experimental_use_cc_common_link,
)

if toolchain.target_os == "windows":
symlink_deps = windows_symlink_transitive_deps(ctx, crate_info, dep_info)
compile_inputs = depset(symlink_deps, transitive = [compile_inputs])

# The types of rustc outputs to emit.
# If we build metadata, we need to keep the command line of the two invocations
# (rlib and rmeta) as similar as possible, otherwise rustc rejects the rmeta as
Expand Down Expand Up @@ -1686,15 +1690,46 @@ def _get_dir_names(files):
dirs[f.dirname] = None
return dirs.keys()

def add_crate_link_flags(args, dep_info, force_all_deps_direct = False, use_metadata = False):
def windows_symlink_transitive_deps(ctx, crate_info, dep_info):
"""Symlinks in transitive dependencies to fix rustc bug on Windows: https://github.com/rust-lang/rust/issues/79923
Args:
ctx (ctx): The source rule's context object
crate_info (CrateInfo): A CrateInfo provider
dep_info (DepInfo): The current target's dependency info
Returns:
list: A list of all symlinked transitive dependencies
"""
symlink_deps = []
if crate_info.output == None:
return []
for dep in (dep_info.direct_crates.to_list() + dep_info.transitive_crates.to_list()):
if hasattr(dep, "dep"):
dep = dep.dep

if dep.output == None:
continue

symlink_dir = ctx.actions.declare_file("rlib_sym/" + dep.output.basename, sibling = crate_info.output)
ctx.actions.symlink(
output = symlink_dir,
target_file = dep.output,
)
symlink_deps.append(symlink_dir)
return symlink_deps

def add_crate_link_flags(args, dep_info, crate_info, force_all_deps_direct = False, use_metadata = False, for_windows = False):
"""Adds link flags to an Args object reference
Args:
args (Args): An arguments object reference
dep_info (DepInfo): The current target's dependency info
crate_info (CrateInfo): A CrateInfo provider
force_all_deps_direct (bool, optional): Whether to pass the transitive rlibs with --extern
to the commandline as opposed to -L.
use_metadata (bool, optional): Build command line arugments using metadata for crates that provide it.
for_windows (bool, optional): Whether to add the rlib_sym directory to the linker search path.
"""

direct_crates = depset(
Expand All @@ -1707,12 +1742,18 @@ def add_crate_link_flags(args, dep_info, force_all_deps_direct = False, use_meta
crate_to_link_flags = _crate_to_link_flag_metadata if use_metadata else _crate_to_link_flag
args.add_all(direct_crates, uniquify = True, map_each = crate_to_link_flags)

args.add_all(
dep_info.transitive_crates,
map_each = _get_crate_dirname,
uniquify = True,
format_each = "-Ldependency=%s",
)
# crate_info.output is None when building rust_doc targets
if for_windows and crate_info.output != None:
args.add(
"-Ldependency={}".format(crate_info.output.dirname + "/rlib_sym"),
)
else:
args.add_all(
dep_info.transitive_crates,
map_each = _get_crate_dirname,
uniquify = True,
format_each = "-Ldependency=%s",
)

def _crate_to_link_flag_metadata(crate):
"""A helper macro used by `add_crate_link_flags` for adding crate link flags to a Arg object
Expand Down

0 comments on commit 09def9d

Please sign in to comment.