git: 968bcca262a2 - main - libkldelf: add a private library for kernel/kld-related ELF parsing

From: Ka Ho Ng <khng_at_FreeBSD.org>
Date: Fri, 18 Oct 2024 20:21:39 UTC
The branch main has been updated by khng:

URL: https://cgit.FreeBSD.org/src/commit/?id=968bcca262a2ea8025924fe10e449bf89caf74bc

commit 968bcca262a2ea8025924fe10e449bf89caf74bc
Author:     Ka Ho Ng <khng@FreeBSD.org>
AuthorDate: 2024-10-08 04:24:07 +0000
Commit:     Ka Ho Ng <khng@FreeBSD.org>
CommitDate: 2024-10-18 20:20:13 +0000

    libkldelf: add a private library for kernel/kld-related ELF parsing
    
    The libkldelf library was originally a part of kldxref(8). It exposed
    ELF parsing helpers specialized in parsing KLDs and the kernel
    executable. The library can be used to read metadata such as linker_set,
    mod_depend, mod_version and PNP match info, and raw data from the ELF.
    
    To promote the reuse of the facilities the ELF parsing code is separated
    from kldxref(8) into a new private library.
    
    For now, libkldelf's source files will be compiled into kldxref(8)
    directly if kldxref is built during bootstrapping phase. The reason is
    linking kldxref(8) against the libkldelf static library has an unwanted
    side effect which renders the linker sets inside the libkldelf
    implementation empty if the static library is not build by ld -r all the
    .o files into a single .o before producing the static library.
    
    Sponsored by:   Juniper Networks, Inc.
    Reviewed by:    markj
    Suggested by:   jrtc27, markj
    Differential Revision:  https://reviews.freebsd.org/D46719
---
 Makefile.inc1                                    | 11 +++++++--
 lib/Makefile                                     |  1 +
 lib/libkldelf/Makefile                           | 21 ++++++++++++++++
 lib/libkldelf/Makefile.depend                    | 16 ++++++++++++
 {usr.sbin/kldxref => lib/libkldelf}/ef.c         |  2 +-
 {usr.sbin/kldxref => lib/libkldelf}/ef_aarch64.c |  2 +-
 {usr.sbin/kldxref => lib/libkldelf}/ef_amd64.c   |  2 +-
 {usr.sbin/kldxref => lib/libkldelf}/ef_arm.c     |  2 +-
 {usr.sbin/kldxref => lib/libkldelf}/ef_i386.c    |  2 +-
 {usr.sbin/kldxref => lib/libkldelf}/ef_mips.c    |  2 +-
 {usr.sbin/kldxref => lib/libkldelf}/ef_obj.c     |  2 +-
 {usr.sbin/kldxref => lib/libkldelf}/ef_powerpc.c |  2 +-
 {usr.sbin/kldxref => lib/libkldelf}/ef_riscv.c   |  2 +-
 {usr.sbin/kldxref => lib/libkldelf}/elf.c        |  2 +-
 usr.sbin/kldxref/ef.h => lib/libkldelf/kldelf.h  |  6 ++---
 share/mk/src.libnames.mk                         |  2 ++
 usr.sbin/kldxref/Makefile                        | 31 ++++++++++++++++++------
 usr.sbin/kldxref/kldxref.c                       |  2 +-
 18 files changed, 86 insertions(+), 24 deletions(-)

diff --git a/Makefile.inc1 b/Makefile.inc1
index 55d49d5760f2..0a8895933bea 100644
--- a/Makefile.inc1
+++ b/Makefile.inc1
@@ -2527,8 +2527,12 @@ ${_bt}-lib/libdwarf: ${_bt_m4_depend}
 _bt_libelf_depend=${_bt}-lib/libelf
 .endif
 
+_libkldelf=	lib/libkldelf
+${_bt}-lib/libkldelf: ${_bt_libelf_depend}
+_bt_libkldelf_depend=${_bt}-lib/libkldelf
+
 _kldxref=	usr.sbin/kldxref
-${_bt}-usr.sbin/kldxref: ${_bt_libelf_depend}
+${_bt}-usr.sbin/kldxref: ${_bt_libelf_depend} ${_bt_libkldelf_depend}
 
 # flua is required to regenerate syscall files.  It first appeared during the
 # 13.0-CURRENT cycle, thus needs to be built on -older releases and stable
@@ -2791,6 +2795,7 @@ bootstrap-tools: ${_bt}-links .PHONY
     ${_cat} \
     ${_kbdcontrol} \
     ${_elftoolchain_libs} \
+    ${_libkldelf} \
     ${_kldxref} \
     lib/libopenbsd \
     usr.bin/mandoc \
@@ -3234,7 +3239,8 @@ _prebuild_libs=	${_kerberos5_lib_libasn1} \
 		lib/libfigpar \
 		${_lib_libgssapi} \
 		lib/libjail \
-		lib/libkiconv lib/libkvm lib/liblzma lib/libmd lib/libnv \
+		lib/libkiconv lib/libkldelf lib/libkvm \
+		lib/liblzma lib/libmd lib/libnv \
 		lib/libzstd \
 		${_lib_casper} \
 		lib/ncurses/tinfo \
@@ -3269,6 +3275,7 @@ _prebuild_libs+= lib/libregex
 .endif
 
 lib/libgeom__L: lib/libexpat__L lib/libsbuf__L
+lib/libkldelf__L: lib/libelf__L
 lib/libkvm__L: lib/libelf__L
 
 .if ${MK_RADIUS_SUPPORT} != "no"
diff --git a/lib/Makefile b/lib/Makefile
index 221eac74ee26..e4a4aa95a1ef 100644
--- a/lib/Makefile
+++ b/lib/Makefile
@@ -66,6 +66,7 @@ SUBDIR=	${SUBDIR_BOOTSTRAP} \
 	libiscsiutil \
 	libjail \
 	libkiconv \
+	libkldelf \
 	libkvm \
 	liblua \
 	liblzma \
diff --git a/lib/libkldelf/Makefile b/lib/libkldelf/Makefile
new file mode 100644
index 000000000000..0d1716f17fca
--- /dev/null
+++ b/lib/libkldelf/Makefile
@@ -0,0 +1,21 @@
+.include <bsd.own.mk>
+
+PACKAGE=	runtime
+LIB=		kldelf
+PRIVATELIB=	yes
+
+SRCS=	ef.c \
+	ef_obj.c \
+	elf.c \
+	ef_aarch64.c \
+	ef_arm.c \
+	ef_amd64.c \
+	ef_i386.c \
+	ef_mips.c \
+	ef_powerpc.c \
+	ef_riscv.c
+WARNS?=	2
+
+LIBADD=	elf
+
+.include <bsd.lib.mk>
diff --git a/lib/libkldelf/Makefile.depend b/lib/libkldelf/Makefile.depend
new file mode 100644
index 000000000000..b0aa274151ad
--- /dev/null
+++ b/lib/libkldelf/Makefile.depend
@@ -0,0 +1,16 @@
+# Autogenerated - do NOT edit!
+
+DIRDEPS = \
+	include \
+	include/xlocale \
+	lib/${CSU_DIR} \
+	lib/libc \
+	lib/libcompiler_rt \
+	lib/libelf \
+
+
+.include <dirdeps.mk>
+
+.if ${DEP_RELDIR} == ${_DEP_RELDIR}
+# local dependencies - needed for -jN in clean tree
+.endif
diff --git a/usr.sbin/kldxref/ef.c b/lib/libkldelf/ef.c
similarity index 99%
rename from usr.sbin/kldxref/ef.c
rename to lib/libkldelf/ef.c
index 975626e46046..052798ee31e4 100644
--- a/usr.sbin/kldxref/ef.c
+++ b/lib/libkldelf/ef.c
@@ -41,7 +41,7 @@
 #include <stdlib.h>
 #include <string.h>
 
-#include "ef.h"
+#include "kldelf.h"
 
 #define	MAXSEGS 16
 struct ef_file {
diff --git a/usr.sbin/kldxref/ef_aarch64.c b/lib/libkldelf/ef_aarch64.c
similarity index 99%
rename from usr.sbin/kldxref/ef_aarch64.c
rename to lib/libkldelf/ef_aarch64.c
index b61de3b032ab..d2db29f22891 100644
--- a/usr.sbin/kldxref/ef_aarch64.c
+++ b/lib/libkldelf/ef_aarch64.c
@@ -31,7 +31,7 @@
 #include <errno.h>
 #include <gelf.h>
 
-#include "ef.h"
+#include "kldelf.h"
 
 /*
  * Apply relocations to the values obtained from the file. `relbase' is the
diff --git a/usr.sbin/kldxref/ef_amd64.c b/lib/libkldelf/ef_amd64.c
similarity index 99%
rename from usr.sbin/kldxref/ef_amd64.c
rename to lib/libkldelf/ef_amd64.c
index fde032dcabc2..7295835f75b3 100644
--- a/usr.sbin/kldxref/ef_amd64.c
+++ b/lib/libkldelf/ef_amd64.c
@@ -33,7 +33,7 @@
 #include <errno.h>
 #include <gelf.h>
 
-#include "ef.h"
+#include "kldelf.h"
 
 /*
  * Apply relocations to the values obtained from the file. `relbase' is the
diff --git a/usr.sbin/kldxref/ef_arm.c b/lib/libkldelf/ef_arm.c
similarity index 99%
rename from usr.sbin/kldxref/ef_arm.c
rename to lib/libkldelf/ef_arm.c
index cc5e265f821e..657294dc9fb0 100644
--- a/usr.sbin/kldxref/ef_arm.c
+++ b/lib/libkldelf/ef_arm.c
@@ -34,7 +34,7 @@
 #include <errno.h>
 #include <gelf.h>
 
-#include "ef.h"
+#include "kldelf.h"
 
 /*
  * Apply relocations to the values obtained from the file. `relbase' is the
diff --git a/usr.sbin/kldxref/ef_i386.c b/lib/libkldelf/ef_i386.c
similarity index 99%
rename from usr.sbin/kldxref/ef_i386.c
rename to lib/libkldelf/ef_i386.c
index 962ed2bc0664..ae571e2d50f2 100644
--- a/usr.sbin/kldxref/ef_i386.c
+++ b/lib/libkldelf/ef_i386.c
@@ -33,7 +33,7 @@
 #include <errno.h>
 #include <gelf.h>
 
-#include "ef.h"
+#include "kldelf.h"
 
 /*
  * Apply relocations to the values obtained from the file. `relbase' is the
diff --git a/usr.sbin/kldxref/ef_mips.c b/lib/libkldelf/ef_mips.c
similarity index 99%
rename from usr.sbin/kldxref/ef_mips.c
rename to lib/libkldelf/ef_mips.c
index e4aeedb5c08b..99790e11a9c3 100644
--- a/usr.sbin/kldxref/ef_mips.c
+++ b/lib/libkldelf/ef_mips.c
@@ -36,7 +36,7 @@
 #include <errno.h>
 #include <gelf.h>
 
-#include "ef.h"
+#include "kldelf.h"
 
 /*
  * Apply relocations to the values obtained from the file. `relbase' is the
diff --git a/usr.sbin/kldxref/ef_obj.c b/lib/libkldelf/ef_obj.c
similarity index 99%
rename from usr.sbin/kldxref/ef_obj.c
rename to lib/libkldelf/ef_obj.c
index ac83137cd394..e09bd036b71e 100644
--- a/usr.sbin/kldxref/ef_obj.c
+++ b/lib/libkldelf/ef_obj.c
@@ -43,7 +43,7 @@
 #include <stdlib.h>
 #include <string.h>
 
-#include "ef.h"
+#include "kldelf.h"
 
 typedef struct {
 	GElf_Addr	addr;
diff --git a/usr.sbin/kldxref/ef_powerpc.c b/lib/libkldelf/ef_powerpc.c
similarity index 99%
rename from usr.sbin/kldxref/ef_powerpc.c
rename to lib/libkldelf/ef_powerpc.c
index f72cc1d85e20..33f09c0d69ef 100644
--- a/usr.sbin/kldxref/ef_powerpc.c
+++ b/lib/libkldelf/ef_powerpc.c
@@ -33,7 +33,7 @@
 #include <errno.h>
 #include <gelf.h>
 
-#include "ef.h"
+#include "kldelf.h"
 
 /*
  * Apply relocations to the values obtained from the file. `relbase' is the
diff --git a/usr.sbin/kldxref/ef_riscv.c b/lib/libkldelf/ef_riscv.c
similarity index 99%
rename from usr.sbin/kldxref/ef_riscv.c
rename to lib/libkldelf/ef_riscv.c
index 46b9b66bee58..bda04bb2c39a 100644
--- a/usr.sbin/kldxref/ef_riscv.c
+++ b/lib/libkldelf/ef_riscv.c
@@ -36,7 +36,7 @@
 #include <errno.h>
 #include <gelf.h>
 
-#include "ef.h"
+#include "kldelf.h"
 
 /*
  * Apply relocations to the values obtained from the file. `relbase' is the
diff --git a/usr.sbin/kldxref/elf.c b/lib/libkldelf/elf.c
similarity index 99%
rename from usr.sbin/kldxref/elf.c
rename to lib/libkldelf/elf.c
index f98c39b69c0b..da319ffc6c98 100644
--- a/usr.sbin/kldxref/elf.c
+++ b/lib/libkldelf/elf.c
@@ -44,7 +44,7 @@
 #include <string.h>
 #include <unistd.h>
 
-#include "ef.h"
+#include "kldelf.h"
 
 SET_DECLARE(elf_reloc, struct elf_reloc_data);
 
diff --git a/usr.sbin/kldxref/ef.h b/lib/libkldelf/kldelf.h
similarity index 99%
rename from usr.sbin/kldxref/ef.h
rename to lib/libkldelf/kldelf.h
index 9d3dc1b1b435..e0a8cc627ff2 100644
--- a/usr.sbin/kldxref/ef.h
+++ b/lib/libkldelf/kldelf.h
@@ -32,8 +32,8 @@
  * SUCH DAMAGE.
  */
 
-#ifndef _EF_H_
-#define _EF_H_
+#ifndef _KLDELF_H_
+#define _KLDELF_H_
 
 #include <sys/linker_set.h>
 #include <stdbool.h>
@@ -312,4 +312,4 @@ int	elf_reloc(struct elf_file *ef, const void *reldata, Elf_Type reltype,
 
 __END_DECLS
 
-#endif /* _EF_H_*/
+#endif /* _KLDELF_H_*/
diff --git a/share/mk/src.libnames.mk b/share/mk/src.libnames.mk
index 1e0a04e83fe3..092e1b444beb 100644
--- a/share/mk/src.libnames.mk
+++ b/share/mk/src.libnames.mk
@@ -27,6 +27,7 @@ _PRIVATELIBS=	\
 		gtest_main \
 		heimipcc \
 		heimipcs \
+		kldelf \
 		ldns \
 		sqlite3 \
 		ssh \
@@ -312,6 +313,7 @@ _DP_bsnmp=	crypto
 .endif
 _DP_geom=	bsdxml sbuf
 _DP_cam=	sbuf
+_DP_kldelf=	elf
 _DP_kvm=	elf
 _DP_casper=	nv
 _DP_cap_dns=	nv
diff --git a/usr.sbin/kldxref/Makefile b/usr.sbin/kldxref/Makefile
index fc9b0b4215fc..ab7b373a45cc 100644
--- a/usr.sbin/kldxref/Makefile
+++ b/usr.sbin/kldxref/Makefile
@@ -1,17 +1,32 @@
 PACKAGE=	runtime
 PROG=	kldxref
 MAN=	kldxref.8
-SRCS=	kldxref.c ef.c ef_obj.c elf.c
-SRCS+=	ef_aarch64.c \
-	ef_arm.c \
-	ef_amd64.c \
-	ef_i386.c \
-	ef_mips.c \
-	ef_powerpc.c \
-	ef_riscv.c
+SRCS=	kldxref.c
+
+CFLAGS+=-I${SRCTOP}/lib/libkldelf
 
 WARNS?=	2
 
 LIBADD=	elf
 
+.if defined(BOOTSTRAPPING)
+#
+# XXX: Fix libprivatelibkldelf.a linker set issue before removing this block
+#
+.PATH: ${SRCTOP}/lib/libkldelf
+KLDELF_SRCS=	ef.c \
+		ef_obj.c \
+		elf.c \
+		ef_aarch64.c \
+		ef_arm.c \
+		ef_amd64.c \
+		ef_i386.c \
+		ef_mips.c \
+		ef_powerpc.c \
+		ef_riscv.c
+SRCS+=	${KLDELF_SRCS}
+.else
+LIBADD+=	kldelf
+.endif
+
 .include <bsd.prog.mk>
diff --git a/usr.sbin/kldxref/kldxref.c b/usr.sbin/kldxref/kldxref.c
index 6bb0469a9ff5..eed754e1e730 100644
--- a/usr.sbin/kldxref/kldxref.c
+++ b/usr.sbin/kldxref/kldxref.c
@@ -51,7 +51,7 @@
 #include <string.h>
 #include <unistd.h>
 
-#include "ef.h"
+#include <kldelf.h>
 
 #define	MAXRECSIZE	(64 << 10)	/* 64k */
 #define check(val)	if ((error = (val)) != 0) break