xref: /openbmc/linux/scripts/link-vmlinux.sh (revision ee1cd5048959de496cd005c50b137212a5b62062)
11f2bfbd0SSam Ravnborg#!/bin/sh
2b2441318SGreg Kroah-Hartman# SPDX-License-Identifier: GPL-2.0
31f2bfbd0SSam Ravnborg#
41f2bfbd0SSam Ravnborg# link vmlinux
51f2bfbd0SSam Ravnborg#
632164845SMasahiro Yamada# vmlinux is linked from the objects in vmlinux.a and $(KBUILD_VMLINUX_LIBS).
732164845SMasahiro Yamada# vmlinux.a contains objects that are linked unconditionally.
8d151e971SMasahiro Yamada# $(KBUILD_VMLINUX_LIBS) are archives which are linked conditionally
9d151e971SMasahiro Yamada# (not within --whole-archive), and do not require symbol indexes added.
101f2bfbd0SSam Ravnborg#
111f2bfbd0SSam Ravnborg# vmlinux
121f2bfbd0SSam Ravnborg#   ^
131f2bfbd0SSam Ravnborg#   |
1432164845SMasahiro Yamada#   +--< vmlinux.a
151f2bfbd0SSam Ravnborg#   |
163a166fc2SNicholas Piggin#   +--< $(KBUILD_VMLINUX_LIBS)
173a166fc2SNicholas Piggin#   |    +--< lib/lib.a + more
183a166fc2SNicholas Piggin#   |
191f2bfbd0SSam Ravnborg#   +-< ${kallsymso} (see description in KALLSYMS section)
201f2bfbd0SSam Ravnborg#
211f2bfbd0SSam Ravnborg# vmlinux version (uname -v) cannot be updated during normal
221f2bfbd0SSam Ravnborg# descending-into-subdirs phase since we do not yet know if we need to
231f2bfbd0SSam Ravnborg# update vmlinux.
241f2bfbd0SSam Ravnborg# Therefore this step is delayed until just before final link of vmlinux.
251f2bfbd0SSam Ravnborg#
261f2bfbd0SSam Ravnborg# System.map is generated to document addresses of all kernel symbols
271f2bfbd0SSam Ravnborg
281f2bfbd0SSam Ravnborg# Error out on error
291f2bfbd0SSam Ravnborgset -e
301f2bfbd0SSam Ravnborg
313ec8a5b3SMasahiro YamadaLD="$1"
323ec8a5b3SMasahiro YamadaKBUILD_LDFLAGS="$2"
333ec8a5b3SMasahiro YamadaLDFLAGS_vmlinux="$3"
343ec8a5b3SMasahiro Yamada
357d153696SMasahiro Yamadais_enabled() {
367d153696SMasahiro Yamada	grep -q "^$1=y" include/config/auto.conf
377d153696SMasahiro Yamada}
387d153696SMasahiro Yamada
391f2bfbd0SSam Ravnborg# Nice output in kbuild format
401f2bfbd0SSam Ravnborg# Will be supressed by "make -s"
411f2bfbd0SSam Ravnborginfo()
421f2bfbd0SSam Ravnborg{
43e83b9f55SAndrii Nakryiko	printf "  %-7s %s\n" "${1}" "${2}"
441f2bfbd0SSam Ravnborg}
451f2bfbd0SSam Ravnborg
461f2bfbd0SSam Ravnborg# Link of vmlinux
47341dfcf8SAndrii Nakryiko# ${1} - output file
48618916a4SAndrii Nakryiko# ${2}, ${3}, ... - optional extra .o files
491f2bfbd0SSam Ravnborgvmlinux_link()
501f2bfbd0SSam Ravnborg{
51618916a4SAndrii Nakryiko	local output=${1}
528f130512SMasahiro Yamada	local objs
538f130512SMasahiro Yamada	local libs
545df77ad6SMasahiro Yamada	local ld
555df77ad6SMasahiro Yamada	local ldflags
565df77ad6SMasahiro Yamada	local ldlibs
571f2bfbd0SSam Ravnborg
58d7b0827fSLinus Torvalds	info LD ${output}
59d7b0827fSLinus Torvalds
60618916a4SAndrii Nakryiko	# skip output file argument
61618916a4SAndrii Nakryiko	shift
62618916a4SAndrii Nakryiko
63ed53a0d9SPeter Zijlstra	if is_enabled CONFIG_LTO_CLANG || is_enabled CONFIG_X86_KERNEL_IBT; then
648f130512SMasahiro Yamada		# Use vmlinux.o instead of performing the slow LTO link again.
658f130512SMasahiro Yamada		objs=vmlinux.o
668f130512SMasahiro Yamada		libs=
678f130512SMasahiro Yamada	else
6832164845SMasahiro Yamada		objs=vmlinux.a
698f130512SMasahiro Yamada		libs="${KBUILD_VMLINUX_LIBS}"
708f130512SMasahiro Yamada	fi
718f130512SMasahiro Yamada
727b453719SMasahiro Yamada	if is_enabled CONFIG_MODULES; then
737b453719SMasahiro Yamada		objs="${objs} .vmlinux.export.o"
747b453719SMasahiro Yamada	fi
757b453719SMasahiro Yamada
762df8220cSMasahiro Yamada	objs="${objs} init/version-timestamp.o"
772df8220cSMasahiro Yamada
785df77ad6SMasahiro Yamada	if [ "${SRCARCH}" = "um" ]; then
795df77ad6SMasahiro Yamada		wl=-Wl,
805df77ad6SMasahiro Yamada		ld="${CC}"
815df77ad6SMasahiro Yamada		ldflags="${CFLAGS_vmlinux}"
825df77ad6SMasahiro Yamada		ldlibs="-lutil -lrt -lpthread"
835df77ad6SMasahiro Yamada	else
845df77ad6SMasahiro Yamada		wl=
855df77ad6SMasahiro Yamada		ld="${LD}"
865df77ad6SMasahiro Yamada		ldflags="${KBUILD_LDFLAGS} ${LDFLAGS_vmlinux}"
875df77ad6SMasahiro Yamada		ldlibs=
885df77ad6SMasahiro Yamada	fi
895df77ad6SMasahiro Yamada
905df77ad6SMasahiro Yamada	ldflags="${ldflags} ${wl}--script=${objtree}/${KBUILD_LDS}"
915df77ad6SMasahiro Yamada
92af73d78bSKees Cook	# The kallsyms linking does not need debug symbols included.
93af73d78bSKees Cook	if [ "$output" != "${output#.tmp_vmlinux.kallsyms}" ] ; then
945df77ad6SMasahiro Yamada		ldflags="${ldflags} ${wl}--strip-debug"
95af73d78bSKees Cook	fi
96af73d78bSKees Cook
977d153696SMasahiro Yamada	if is_enabled CONFIG_VMLINUX_MAP; then
985df77ad6SMasahiro Yamada		ldflags="${ldflags} ${wl}-Map=${output}.map"
995cc12472SRasmus Villemoes	fi
1005cc12472SRasmus Villemoes
1015df77ad6SMasahiro Yamada	${ld} ${ldflags} -o ${output}					\
1025df77ad6SMasahiro Yamada		${wl}--whole-archive ${objs} ${wl}--no-whole-archive	\
1035df77ad6SMasahiro Yamada		${wl}--start-group ${libs} ${wl}--end-group		\
1045df77ad6SMasahiro Yamada		$@ ${ldlibs}
1051f2bfbd0SSam Ravnborg}
1061f2bfbd0SSam Ravnborg
107e83b9f55SAndrii Nakryiko# generate .BTF typeinfo from DWARF debuginfo
108341dfcf8SAndrii Nakryiko# ${1} - vmlinux image
109341dfcf8SAndrii Nakryiko# ${2} - file to dump raw BTF data into
110e83b9f55SAndrii Nakryikogen_btf()
111e83b9f55SAndrii Nakryiko{
112341dfcf8SAndrii Nakryiko	local pahole_ver
113e83b9f55SAndrii Nakryiko
114581b31c3SAndrii Nakryiko	if ! [ -x "$(command -v ${PAHOLE})" ]; then
1152a67a6ccSChris Down		echo >&2 "BTF: ${1}: pahole (${PAHOLE}) is not available"
116341dfcf8SAndrii Nakryiko		return 1
117581b31c3SAndrii Nakryiko	fi
118581b31c3SAndrii Nakryiko
119e83b9f55SAndrii Nakryiko	pahole_ver=$(${PAHOLE} --version | sed -E 's/v([0-9]+)\.([0-9]+)/\1\2/')
12021a85bd6SLorenz Bauer	if [ "${pahole_ver}" -lt "116" ]; then
12121a85bd6SLorenz Bauer		echo >&2 "BTF: ${1}: pahole version $(${PAHOLE} --version) is too old, need at least v1.16"
122341dfcf8SAndrii Nakryiko		return 1
123e83b9f55SAndrii Nakryiko	fi
124e83b9f55SAndrii Nakryiko
125341dfcf8SAndrii Nakryiko	vmlinux_link ${1}
126af73d78bSKees Cook
127af73d78bSKees Cook	info "BTF" ${2}
1289741e07eSJiri Olsa	LLVM_OBJCOPY="${OBJCOPY}" ${PAHOLE} -J ${PAHOLE_FLAGS} ${1}
129341dfcf8SAndrii Nakryiko
13090ceddcbSFangrui Song	# Create ${2} which contains just .BTF section but no symbols. Add
13190ceddcbSFangrui Song	# SHF_ALLOC because .BTF will be part of the vmlinux image. --strip-all
13290ceddcbSFangrui Song	# deletes all symbols including __start_BTF and __stop_BTF, which will
13390ceddcbSFangrui Song	# be redefined in the linker script. Add 2>/dev/null to suppress GNU
13490ceddcbSFangrui Song	# objcopy warnings: "empty loadable segment detected at ..."
13590ceddcbSFangrui Song	${OBJCOPY} --only-section=.BTF --set-section-flags .BTF=alloc,readonly \
13690ceddcbSFangrui Song		--strip-all ${1} ${2} 2>/dev/null
13790ceddcbSFangrui Song	# Change e_type to ET_REL so that it can be used to link final vmlinux.
13804c0dbdbSNathan Chancellor	# GNU ld 2.35+ and lld do not allow an ET_EXEC input.
13904c0dbdbSNathan Chancellor	if is_enabled CONFIG_CPU_BIG_ENDIAN; then
14004c0dbdbSNathan Chancellor		et_rel='\0\1'
14104c0dbdbSNathan Chancellor	else
14204c0dbdbSNathan Chancellor		et_rel='\1\0'
14304c0dbdbSNathan Chancellor	fi
14404c0dbdbSNathan Chancellor	printf "${et_rel}" | dd of=${2} conv=notrunc bs=1 seek=16 status=none
145e83b9f55SAndrii Nakryiko}
1461f2bfbd0SSam Ravnborg
14708beb669SMasahiro Yamada# Create ${2} .S file with all symbols from the ${1} object file
1481f2bfbd0SSam Ravnborgkallsyms()
1491f2bfbd0SSam Ravnborg{
1501f2bfbd0SSam Ravnborg	local kallsymopt;
1511f2bfbd0SSam Ravnborg
1527d153696SMasahiro Yamada	if is_enabled CONFIG_KALLSYMS_ALL; then
1536895f97eSJames Hogan		kallsymopt="${kallsymopt} --all-symbols"
1541f2bfbd0SSam Ravnborg	fi
1551f2bfbd0SSam Ravnborg
1567d153696SMasahiro Yamada	if is_enabled CONFIG_KALLSYMS_ABSOLUTE_PERCPU; then
157c6bda7c9SRusty Russell		kallsymopt="${kallsymopt} --absolute-percpu"
158c6bda7c9SRusty Russell	fi
159c6bda7c9SRusty Russell
1607d153696SMasahiro Yamada	if is_enabled CONFIG_KALLSYMS_BASE_RELATIVE; then
1612213e9a6SArd Biesheuvel		kallsymopt="${kallsymopt} --base-relative"
1622213e9a6SArd Biesheuvel	fi
1632213e9a6SArd Biesheuvel
164010a0aadSZhen Lei	if is_enabled CONFIG_LTO_CLANG; then
165010a0aadSZhen Lei		kallsymopt="${kallsymopt} --lto-clang"
166010a0aadSZhen Lei	fi
167010a0aadSZhen Lei
16808beb669SMasahiro Yamada	info KSYMS ${2}
169aa221f2eSMasahiro Yamada	scripts/kallsyms ${kallsymopt} ${1} > ${2}
1701f2bfbd0SSam Ravnborg}
1711f2bfbd0SSam Ravnborg
1728959e392SKees Cook# Perform one step in kallsyms generation, including temporary linking of
1738959e392SKees Cook# vmlinux.
1748959e392SKees Cookkallsyms_step()
1758959e392SKees Cook{
1768959e392SKees Cook	kallsymso_prev=${kallsymso}
177af73d78bSKees Cook	kallsyms_vmlinux=.tmp_vmlinux.kallsyms${1}
178af73d78bSKees Cook	kallsymso=${kallsyms_vmlinux}.o
17908beb669SMasahiro Yamada	kallsyms_S=${kallsyms_vmlinux}.S
1808959e392SKees Cook
181d7b0827fSLinus Torvalds	vmlinux_link ${kallsyms_vmlinux} "${kallsymso_prev}" ${btf_vmlinux_bin_o}
182ca09bf48SMasahiro Yamada	mksysmap ${kallsyms_vmlinux} ${kallsyms_vmlinux}.syms ${kallsymso_prev}
18394ff2f63SMasahiro Yamada	kallsyms ${kallsyms_vmlinux}.syms ${kallsyms_S}
18408beb669SMasahiro Yamada
185*9db55f64SMasahiro Yamada	info AS ${kallsymso}
18608beb669SMasahiro Yamada	${CC} ${NOSTDINC_FLAGS} ${LINUXINCLUDE} ${KBUILD_CPPFLAGS} \
18708beb669SMasahiro Yamada	      ${KBUILD_AFLAGS} ${KBUILD_AFLAGS_KERNEL} \
18808beb669SMasahiro Yamada	      -c -o ${kallsymso} ${kallsyms_S}
1898959e392SKees Cook}
1908959e392SKees Cook
1911f2bfbd0SSam Ravnborg# Create map file with all symbols from ${1}
1921f2bfbd0SSam Ravnborg# See mksymap for additional details
1931f2bfbd0SSam Ravnborgmksysmap()
1941f2bfbd0SSam Ravnborg{
19594ff2f63SMasahiro Yamada	info NM ${2}
196ca09bf48SMasahiro Yamada	${CONFIG_SHELL} "${srctree}/scripts/mksysmap" ${1} ${2} ${3}
1971f2bfbd0SSam Ravnborg}
1981f2bfbd0SSam Ravnborg
19910916706SShile Zhangsorttable()
2001347a2ceSLinus Torvalds{
20110916706SShile Zhang	${objtree}/scripts/sorttable ${1}
2021347a2ceSLinus Torvalds}
2031347a2ceSLinus Torvalds
2041f2bfbd0SSam Ravnborg# Delete output files in case of error
2051f2bfbd0SSam Ravnborgcleanup()
2061f2bfbd0SSam Ravnborg{
207341dfcf8SAndrii Nakryiko	rm -f .btf.*
2081f2bfbd0SSam Ravnborg	rm -f System.map
2091f2bfbd0SSam Ravnborg	rm -f vmlinux
2105cc12472SRasmus Villemoes	rm -f vmlinux.map
2111f2bfbd0SSam Ravnborg}
2121f2bfbd0SSam Ravnborg
2131f2bfbd0SSam Ravnborg# Use "make V=1" to debug this script
2141f2bfbd0SSam Ravnborgcase "${KBUILD_VERBOSE}" in
2151f2bfbd0SSam Ravnborg*1*)
2161f2bfbd0SSam Ravnborg	set -x
2171f2bfbd0SSam Ravnborg	;;
2181f2bfbd0SSam Ravnborgesac
2191f2bfbd0SSam Ravnborg
2201f2bfbd0SSam Ravnborgif [ "$1" = "clean" ]; then
2211f2bfbd0SSam Ravnborg	cleanup
2221f2bfbd0SSam Ravnborg	exit 0
2231f2bfbd0SSam Ravnborgfi
2241f2bfbd0SSam Ravnborg
2252df8220cSMasahiro Yamada${MAKE} -f "${srctree}/scripts/Makefile.build" obj=init init/version-timestamp.o
2262df8220cSMasahiro Yamada
2277fd78568SAndrii Nakryikobtf_vmlinux_bin_o=""
2287d153696SMasahiro Yamadaif is_enabled CONFIG_DEBUG_INFO_BTF; then
2297fd78568SAndrii Nakryiko	btf_vmlinux_bin_o=.btf.vmlinux.bin.o
230af73d78bSKees Cook	if ! gen_btf .tmp_vmlinux.btf $btf_vmlinux_bin_o ; then
231da5fb182SStanislav Fomichev		echo >&2 "Failed to generate BTF for vmlinux"
232da5fb182SStanislav Fomichev		echo >&2 "Try to disable CONFIG_DEBUG_INFO_BTF"
233da5fb182SStanislav Fomichev		exit 1
234341dfcf8SAndrii Nakryiko	fi
235341dfcf8SAndrii Nakryikofi
236341dfcf8SAndrii Nakryiko
2371f2bfbd0SSam Ravnborgkallsymso=""
2388959e392SKees Cookkallsymso_prev=""
2391f2bfbd0SSam Ravnborgkallsyms_vmlinux=""
2407d153696SMasahiro Yamadaif is_enabled CONFIG_KALLSYMS; then
2411f2bfbd0SSam Ravnborg
2421f2bfbd0SSam Ravnborg	# kallsyms support
2431f2bfbd0SSam Ravnborg	# Generate section listing all symbols and add it into vmlinux
2441f2bfbd0SSam Ravnborg	# It's a three step process:
2452216cf68SHui Su	# 1)  Link .tmp_vmlinux.kallsyms1 so it has all symbols and sections,
2461f2bfbd0SSam Ravnborg	#     but __kallsyms is empty.
2471f2bfbd0SSam Ravnborg	#     Running kallsyms on that gives us .tmp_kallsyms1.o with
2481f2bfbd0SSam Ravnborg	#     the right size
2492216cf68SHui Su	# 2)  Link .tmp_vmlinux.kallsyms2 so it now has a __kallsyms section of
2501f2bfbd0SSam Ravnborg	#     the right size, but due to the added section, some
2511f2bfbd0SSam Ravnborg	#     addresses have shifted.
2522216cf68SHui Su	#     From here, we generate a correct .tmp_vmlinux.kallsyms2.o
2537e2b37c9SNicholas Piggin	# 3)  That link may have expanded the kernel image enough that
2547e2b37c9SNicholas Piggin	#     more linker branch stubs / trampolines had to be added, which
2557e2b37c9SNicholas Piggin	#     introduces new names, which further expands kallsyms. Do another
2567e2b37c9SNicholas Piggin	#     pass if that is the case. In theory it's possible this results
2577e2b37c9SNicholas Piggin	#     in even more stubs, but unlikely.
2587e2b37c9SNicholas Piggin	#     KALLSYMS_EXTRA_PASS=1 may also used to debug or work around
2597e2b37c9SNicholas Piggin	#     other bugs.
2607e2b37c9SNicholas Piggin	# 4)  The correct ${kallsymso} is linked into the final vmlinux.
2611f2bfbd0SSam Ravnborg	#
2621f2bfbd0SSam Ravnborg	# a)  Verify that the System.map from vmlinux matches the map from
2631f2bfbd0SSam Ravnborg	#     ${kallsymso}.
2641f2bfbd0SSam Ravnborg
2658959e392SKees Cook	kallsyms_step 1
2668959e392SKees Cook	kallsyms_step 2
2671f2bfbd0SSam Ravnborg
2687e2b37c9SNicholas Piggin	# step 3
2698959e392SKees Cook	size1=$(${CONFIG_SHELL} "${srctree}/scripts/file-size.sh" ${kallsymso_prev})
2708959e392SKees Cook	size2=$(${CONFIG_SHELL} "${srctree}/scripts/file-size.sh" ${kallsymso})
2717e2b37c9SNicholas Piggin
2727e2b37c9SNicholas Piggin	if [ $size1 -ne $size2 ] || [ -n "${KALLSYMS_EXTRA_PASS}" ]; then
2738959e392SKees Cook		kallsyms_step 3
2741f2bfbd0SSam Ravnborg	fi
2751f2bfbd0SSam Ravnborgfi
2761f2bfbd0SSam Ravnborg
277d7b0827fSLinus Torvaldsvmlinux_link vmlinux "${kallsymso}" ${btf_vmlinux_bin_o}
278e83b9f55SAndrii Nakryiko
279c9a0f3b8SJiri Olsa# fill in BTF IDs
2807d153696SMasahiro Yamadaif is_enabled CONFIG_DEBUG_INFO_BTF && is_enabled CONFIG_BPF; then
281c9a0f3b8SJiri Olsa	info BTFIDS vmlinux
282c9a0f3b8SJiri Olsa	${RESOLVE_BTFIDS} vmlinux
283c9a0f3b8SJiri Olsafi
284c9a0f3b8SJiri Olsa
285ca09bf48SMasahiro Yamadamksysmap vmlinux System.map ${kallsymso}
28672b3942aSYinan Liu
2877d153696SMasahiro Yamadaif is_enabled CONFIG_BUILDTIME_TABLE_SORT; then
28810916706SShile Zhang	info SORTTAB vmlinux
289f14bf6a3SShile Zhang	if ! sorttable vmlinux; then
290f14bf6a3SShile Zhang		echo >&2 Failed to sort kernel tables
291f14bf6a3SShile Zhang		exit 1
292f14bf6a3SShile Zhang	fi
2931347a2ceSLinus Torvaldsfi
2941347a2ceSLinus Torvalds
2951f2bfbd0SSam Ravnborg# step a (see comment above)
2967d153696SMasahiro Yamadaif is_enabled CONFIG_KALLSYMS; then
29794ff2f63SMasahiro Yamada	if ! cmp -s System.map ${kallsyms_vmlinux}.syms; then
2985369f550SMichal Marek		echo >&2 Inconsistent kallsyms data
2994b3d049fSAndrew Morton		echo >&2 'Try "make KALLSYMS_EXTRA_PASS=1" as a workaround'
3001f2bfbd0SSam Ravnborg		exit 1
3011f2bfbd0SSam Ravnborg	fi
3021f2bfbd0SSam Ravnborgfi
3030b956e20SRasmus Villemoes
3040b956e20SRasmus Villemoes# For fixdep
3050b956e20SRasmus Villemoesecho "vmlinux: $0" > .vmlinux.d
306