Closed Pesa closed 4 years ago
Reproducible build is now available for make cmds
target, under the following conditions:
make goget
at the same time, or copying $GOPATH/src
foldermake cmds
A recent test on commit bdb376136f2645f78144dd17aa76ac48b30756e8 indicates that the builds are still unreproducible, even on the same machine.
I used the following sequence of commands:
npm install
make
find build -type f | xargs openssl sha256 | sort >1.txt
make clean
make
find build -type f | xargs openssl sha256 | sort >2.txt
diff 1.txt 2.txt
If the builds were reproducible, the last command should have empty output.
Instead, it reports that build/bin/ndnfw-dpdk
has a different digest.
To diagnose this issue, I decompiled both programs with objdump -D build/bin/ndnfw-dpdk
: https://pastebin.com/Ux0GPqZD
The assembly has difference in the following sections:
.note.go.buildid
and .note.gnu.build-id
: some instructions are different; the symbol per_lcore_gPccDebugString
(a global variable) appears, but a large offset like 0x400321
suggests that it may be unrelatedndn-dpdk/strategy/strategy_elf.fastrouteO
(and all other strategy ELF objects): one instruction movabs $0xed654aafd,%rcx
has a different number in itbuildid is stored in a Go package or binary, and it's supposed to "accurately record a content hash of the file". Therefore, I believe the difference in buildid sections is caused by the difference in strategy sections.
Strategy ELF objects, as produced by clang-8, are the same. Therefore, go-bindata
is likely the troublemaker here. I'll see what adjustment can be made to resolve this issue.
Fixed in a0172a047d2ecf9dc7e9f6528efc814e36e031b8.
It turns out that go-bindata
is including metadata for the binary assets, which contains file modification time. Since the strategy ELF objects are freshly compiled, their modification times will differ.
Setting go-bindata -nometadata
flag solves this problem.
Due to recent changes in build procedure, find build -type f | xargs openssl sha256 | sort
would capture the digest of meson and ninja logs.
Ignoring the difference on these log files, the binary files compiled in two different virtual machines are identical.
We should make the build process reproducible.
The first problem I've noticed is that
app/version/make-version.sh
embeds a timestamp in the generatedversion.go
. We should get rid of the timestamp. There may be other sources of non-reproducibility in the build system.