kbuild: lto: fix module versioning

With CONFIG_MODVERSIONS, version information is linked into each
compilation unit that exports symbols. With LTO, we cannot use this
method as all C code is compiled into LLVM bitcode instead. This
change collects symbol versions into .symversions files and merges
them in link-vmlinux.sh where they are all linked into vmlinux.o at
the same time.

Signed-off-by: Sami Tolvanen <samitolvanen@google.com>
Reviewed-by: Kees Cook <keescook@chromium.org>
Signed-off-by: Kees Cook <keescook@chromium.org>
Link: https://lore.kernel.org/r/20201211184633.3213045-4-samitolvanen@google.com
This commit is contained in:
Sami Tolvanen
2020-12-11 10:46:20 -08:00
committed by Kees Cook
parent dc5723b02e
commit 38e8918490
6 changed files with 61 additions and 6 deletions

View File

@@ -43,11 +43,26 @@ info()
fi
}
# If CONFIG_LTO_CLANG is selected, collect generated symbol versions into
# .tmp_symversions.lds
gen_symversions()
{
info GEN .tmp_symversions.lds
rm -f .tmp_symversions.lds
for o in ${KBUILD_VMLINUX_OBJS} ${KBUILD_VMLINUX_LIBS}; do
if [ -f ${o}.symversions ]; then
cat ${o}.symversions >> .tmp_symversions.lds
fi
done
}
# Link of vmlinux.o used for section mismatch analysis
# ${1} output file
modpost_link()
{
local objects
local lds=""
objects="--whole-archive \
${KBUILD_VMLINUX_OBJS} \
@@ -57,6 +72,11 @@ modpost_link()
--end-group"
if [ -n "${CONFIG_LTO_CLANG}" ]; then
if [ -n "${CONFIG_MODVERSIONS}" ]; then
gen_symversions
lds="${lds} -T .tmp_symversions.lds"
fi
# This might take a while, so indicate that we're doing
# an LTO link
info LTO ${1}
@@ -64,7 +84,7 @@ modpost_link()
info LD ${1}
fi
${LD} ${KBUILD_LDFLAGS} -r -o ${1} ${objects}
${LD} ${KBUILD_LDFLAGS} -r -o ${1} ${lds} ${objects}
}
objtool_link()
@@ -242,6 +262,7 @@ cleanup()
{
rm -f .btf.*
rm -f .tmp_System.map
rm -f .tmp_symversions.lds
rm -f .tmp_vmlinux*
rm -f System.map
rm -f vmlinux