constellation/bazel/patchelf/patchelf.bzl
Malte Poll e174c4dfe1 bazel: add patchelf rule
This rule allows overwriting a binaries' rpath.
This is required to use binaries built by Bazel that link against cc_library
targets from nix (like `/nix/store/<hash>/lib/*.so`).
2023-12-01 09:35:33 +01:00

52 lines
2.0 KiB
Python

""" Bazel rule for postprocessing elf files with patchelf """
def _patchelf_impl(ctx):
output = ctx.outputs.out
ctx.actions.run_shell(
inputs = [ctx.file.src, ctx.file.rpath, ctx.file.interpreter],
tools = [ctx.executable._patchelf_binary],
outputs = [output],
arguments = [
ctx.executable._patchelf_binary.path,
ctx.file.rpath.path,
ctx.file.interpreter.path,
output.path,
ctx.file.src.path,
],
command = "\"$1\" --set-rpath \"$(cat \"$2\")\" --set-interpreter \"$(cat \"$3\")\" --output \"$4\" \"$5\"",
progress_message = "Patching ELF binary " + ctx.file.src.basename,
)
return DefaultInfo(
files = depset([output]),
executable = output,
)
patchelf = rule(
implementation = _patchelf_impl,
attrs = {
"interpreter": attr.label(mandatory = True, allow_single_file = True),
"out": attr.output(mandatory = True),
"rpath": attr.label(mandatory = True, allow_single_file = True),
"src": attr.label(mandatory = True, allow_single_file = True),
"_patchelf_binary": attr.label(
default = Label("@patchelf//:bin/patchelf"),
allow_single_file = True,
executable = True,
cfg = "exec",
),
},
doc = """Uses patchelf to set the rpath and interpreter of an ELF binary.
This is a post processing step for binaries that are built by Bazel
that link shared libraries from Nix.
Native nix binaries always use absolute paths to a specific linker and
embed the rpath for each linked library as an absolute nix store path.
Bazel embeds rpaths using $ORIGIN and uses paths relative to
the binaries output location. Without patchelf, the binary would only
work if we also ship all runfiles with the binary and preserve the relative
directory structure.
See https://github.com/tweag/rules_nixpkgs/issues/449 for more details.
""",
executable = True,
)