Skip to content

Commit 0c9860c

Browse files
imciner2giordano
andauthored
Add creation of the build-id to the linker flags (#435)
* Add creation of the build-id to the linker flags * Update test/runners.jl Co-authored-by: Mosè Giordano <[email protected]> * Tweak tests * Turns out build-id should be available everywhere except macos * Restrict windows build-id generation to GCC 5+ * Switch tests to use Julia introspection functions instead of command line --------- Co-authored-by: Mosè Giordano <[email protected]>
1 parent 19396c7 commit 0c9860c

File tree

3 files changed

+95
-1
lines changed

3 files changed

+95
-1
lines changed

Project.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
name = "BinaryBuilderBase"
22
uuid = "7f725544-6523-48cd-82d1-3fa08ff4056e"
33
authors = ["Elliot Saba <[email protected]>"]
4-
version = "1.39.1"
4+
version = "1.40.0"
55

66
[deps]
77
Bzip2_jll = "6e34b625-4abd-537c-b88f-471c36dfa7a0"

src/Runner.jl

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -436,6 +436,17 @@ function generate_compiler_wrappers!(platform::AbstractPlatform; bin_path::Abstr
436436
end
437437
end
438438

439+
function buildid_link_flags!(p::AbstractPlatform, flags::Vector{String})
440+
# build-id is not supported on macOS compilers
441+
if !Sys.isapple(p)
442+
# Windows build-id requires binutils 2.25+, which we only have for GCC 5+
443+
if !Sys.iswindows(p) || (Sys.iswindows(p) && gcc_version v"5")
444+
# Use a known algorithm to embed the build-id for reproducibility
445+
push!(flags, "-Wl,--build-id=sha1")
446+
end
447+
end
448+
end
449+
439450
function clang_compile_flags!(p::AbstractPlatform, flags::Vector{String} = String[])
440451
if lock_microarchitecture
441452
append!(flags, get_march_flags(arch(p), march(p), "clang"))
@@ -540,6 +551,9 @@ function generate_compiler_wrappers!(platform::AbstractPlatform; bin_path::Abstr
540551
append!(flags, min_macos_version_linker_flags())
541552
end
542553
end
554+
555+
buildid_link_flags!(p, flags)
556+
543557
return flags
544558
end
545559

@@ -630,6 +644,7 @@ function generate_compiler_wrappers!(platform::AbstractPlatform; bin_path::Abstr
630644
push!(flags, "-Wl,--no-insert-timestamp")
631645
end
632646
sanitize_link_flags!(p, flags)
647+
buildid_link_flags!(p, flags)
633648
return flags
634649
end
635650

test/runners.jl

Lines changed: 79 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@ using Test
22
using BinaryBuilderBase
33
using BinaryBuilderBase: platform_dlext, platform_exeext, prefer_clang
44
using Pkg
5+
using ObjectFile
56

67
@testset "Wrappers utilities" begin
78
@test nbits(Platform("i686", "linux")) == 32
@@ -130,8 +131,12 @@ end
130131
if lowercase(get(ENV, "BINARYBUILDER_FULL_SHARD_TEST", "false")) == "true"
131132
@info("Beginning full shard test... (this can take a while)")
132133
platforms = supported_platforms()
134+
elf_platforms = filter(p -> Sys.islinux(p) || Sys.isfreebsd(p), supported_platforms())
135+
win_platforms = filter(p -> Sys.iswindows(p), supported_platforms())
133136
else
134137
platforms = (default_host_platform,)
138+
elf_platforms = (default_host_platform,)
139+
win_platforms = (Platform("x86_64", "windows"),)
135140
end
136141

137142
# Checks that the wrappers provide the correct C++ string ABI
@@ -153,6 +158,80 @@ end
153158
end
154159
end
155160

161+
# Checks that the compiler/linker include a build-id
162+
# This is only available on ELF-based platforms
163+
@testset "Compilation - Linux build-id note $(platform) - $(compiler)" for platform in elf_platforms, compiler in ("cc", "gcc", "clang", "c++", "g++", "clang++")
164+
mktempdir() do dir
165+
ur = preferred_runner()(dir; platform=platform)
166+
iobuff = IOBuffer()
167+
test_c = """
168+
#include <stdlib.h>
169+
int test(void) {
170+
return 0;
171+
}
172+
"""
173+
test_script = """
174+
set -e
175+
cd /workspace
176+
# Make sure setting `CCACHE` doesn't affect the compiler wrappers.
177+
export CCACHE=pwned
178+
export USE_CCACHE=false
179+
echo '$(test_c)' > test.c
180+
# Build shared library
181+
$(compiler) -shared test.c -o libtest.\${dlext}
182+
"""
183+
cmd = `/bin/bash -c "$(test_script)"`
184+
@test run(ur, cmd, iobuff)
185+
186+
# Load the library file and test it for the build-id
187+
lib_path = joinpath(dir, "libtest."*platform_dlext(platform))
188+
lib = open(lib_path)
189+
obj_handles = readmeta(lib)
190+
obj = first(obj_handles)
191+
secs = Sections(obj)
192+
193+
# The section must exist for the build-id to be present
194+
@test !isnothing(findfirst(s -> section_name(s) == ".note.gnu.build-id", secs))
195+
end
196+
end
197+
198+
# Checks that Windows can include a build-id
199+
@testset "Compilation - Windows build-id note $(platform) - $(compiler)" for platform in win_platforms, compiler in ("cc", "gcc", "clang", "c++", "g++", "clang++")
200+
mktempdir() do dir
201+
# Windows build-id support requires binutils 2.25, which is part of our GCC 5
202+
ur = preferred_runner()(dir; platform=platform, preferred_gcc_version=v"5")
203+
iobuff = IOBuffer()
204+
test_c = """
205+
#include <stdlib.h>
206+
int test(void) {
207+
return 0;
208+
}
209+
"""
210+
test_script = """
211+
set -e
212+
cd /workspace
213+
# Make sure setting `CCACHE` doesn't affect the compiler wrappers.
214+
export CCACHE=pwned
215+
export USE_CCACHE=false
216+
echo '$(test_c)' > test.c
217+
# Build shared library
218+
$(compiler) -shared test.c -o libtest.\${dlext}
219+
"""
220+
cmd = `/bin/bash -c "$(test_script)"`
221+
@test run(ur, cmd, iobuff)
222+
223+
# Load the library file and test it for the build-id
224+
lib_path = joinpath(dir, "libtest."*platform_dlext(platform))
225+
lib = open(lib_path)
226+
obj_handles = readmeta(lib)
227+
obj = first(obj_handles)
228+
secs = Sections(obj)
229+
230+
# The section must exist for the build-id to be present
231+
@test !isnothing(findfirst(s -> section_name(s) == ".buildid", secs))
232+
end
233+
end
234+
156235
# This tests only that compilers for all platforms can build and link simple C code
157236
@testset "Compilation - $(platform) - $(compiler)" for platform in platforms, compiler in ("cc", "gcc", "clang")
158237
mktempdir() do dir

0 commit comments

Comments
 (0)