From bb5a196f7b94a156a20c13ab64e4e89e84c038eb Mon Sep 17 00:00:00 2001 From: "Neal H. Walfield" Date: Tue, 10 May 2022 13:30:44 +0200 Subject: [PATCH] Don't require a user of librpmio to link to librpm_sequoia When rpm is configured to use Sequoia for the OpenPGP implementation ('configure --crypto=sequoia'), librpmio is linked against librpm_sequoia. librpm_sequoia can't directly implement the OpenPGP API, because librpmio won't reexport librpm_sequoia's symbols, and we don't want a program linking against librpmio to explicitly link against (i.e., need a DT_NEEDED entry for) librpm_sequoia. We can circumvent this problem by having librpm_sequoia provide identical functions under different names, and then having librpmio provide forwarders. That's what this commit does: a Sequoia-specific file forwards pgpFoo to _pgpFoo. It's a bit ugly, but it is better than a brittle, non-portable hack. Fixes #2051. (cherry pick b76f433842c7d7f8f18f8ff05c788a08bb91ffb3) --- rpm.pc.in | 2 +- rpmio/Makefile.am | 4 +++ rpmio/rpmpgp_sequoia.c | 72 ++++++++++++++++++++++++++++++++++++++++++ tests/Makefile.am | 3 +- 4 files changed, 78 insertions(+), 3 deletions(-) create mode 100644 rpmio/rpmpgp_sequoia.c diff --git a/rpm.pc.in b/rpm.pc.in index 5449f01a04..1f76f06854 100644 --- a/rpm.pc.in +++ b/rpm.pc.in @@ -12,5 +12,5 @@ Requires: popt Requires.private: @ZSTD_REQUIRES@ # Conflicts: Cflags: -I${includedir} -Libs: -L${libdir} -lrpm -lrpmio @WITH_RPM_SEQUOIA_LIB@ +Libs: -L${libdir} -lrpm -lrpmio Libs.private: -lpopt -lrt -lpthread @WITH_LZMA_LIB@ @WITH_BZ2_LIB@ @WITH_ZLIB_LIB@ @LUA_LIBS@ diff --git a/rpmio/Makefile.am b/rpmio/Makefile.am index 106e69d00e..e302f3209f 100644 --- a/rpmio/Makefile.am +++ b/rpmio/Makefile.am @@ -32,6 +32,10 @@ librpmio_la_SOURCES += digest_openssl.c rpmpgp_internal.c rpmpgp_internal.h else if WITH_LIBGCRYPT librpmio_la_SOURCES += digest_libgcrypt.c rpmpgp_internal.c rpmpgp_internal.h +else +if WITH_RPM_SEQUOIA +librpmio_la_SOURCES += rpmpgp_sequoia.c +endif endif endif diff --git a/rpmio/rpmpgp_sequoia.c b/rpmio/rpmpgp_sequoia.c new file mode 100644 index 0000000000..4c086d7a5d --- /dev/null +++ b/rpmio/rpmpgp_sequoia.c @@ -0,0 +1,72 @@ +// When rpm is configured to use Sequoia for the OpenPGP implementation +// ('configure --crypto=sequoia'), librpmio is linked against +// librpm_sequoia. +// +// librpm_sequoia can't directly implement the OpenPGP API, because +// librpmio won't reexport librpm_sequoia's symbols, and we don't want +// a program linking against librpmio to explicitly link against +// (i.e., need a DT_NEEDED entry for) librpm_sequoia. +// +// We can circumvent this problem by having librpm_sequoia provide +// identical functions under different names, and then having librpmio +// provide forwarders. That's what this file does: it forwards pgpFoo +// to _pgpFoo. It's a bit ugly, but it is better than a brittle, +// non-portable hack. + +#include "rpmpgpval.h" + +// Wrap a function. +// +// Define f to call _f, which has an identical function signature. +#define W(rt, f, params, args) \ + extern rt _##f params; \ + rt f params { \ + return _##f args; \ + } + +W(int, pgpSignatureType, (pgpDigParams _digp), (_digp)) +W(pgpDigParams, pgpDigParamsFree, (pgpDigParams digp), (digp)) +W(int, pgpDigParamsCmp, (pgpDigParams p1, pgpDigParams p2), (p1, p2)) +W(unsigned int, pgpDigParamsAlgo, + (pgpDigParams digp, unsigned int algotype), (digp, algotype)) +W(const uint8_t *, pgpDigParamsSignID, (pgpDigParams digp), (digp)) +W(const char *, pgpDigParamsUserID, (pgpDigParams digp), (digp)) +W(int, pgpDigParamsVersion, (pgpDigParams digp), (digp)) +W(uint32_t, pgpDigParamsCreationTime, (pgpDigParams digp), (digp)) +W(rpmRC, pgpVerifySignature, + (pgpDigParams key, pgpDigParams sig, DIGEST_CTX hashctx), + (key, sig, hashctx)) +W(int, pgpPubkeyKeyID, + (const uint8_t * pkt, size_t pktlen, pgpKeyID_t keyid), + (pkt, pktlen, keyid)) +W(char *, pgpArmorWrap, + (int atype, const unsigned char * s, size_t ns), + (atype, s, ns)) +W(int, pgpPubKeyCertLen, + (const uint8_t *pkts, size_t pktslen, size_t *certlen), + (pkts, pktslen, certlen)) +W(int, pgpPrtParams, + (const uint8_t *pkts, size_t pktlen, unsigned int pkttype, pgpDigParams *ret), + (pkts, pktlen, pkttype, ret)) +W(int, pgpPrtParamsSubkeys, + (const uint8_t *pkts, size_t pktlen, + pgpDigParams mainkey, pgpDigParams **subkeys, + int *subkeysCount), + (pkts, pktlen, mainkey, subkeys, subkeysCount)) +W(pgpArmor, pgpParsePkts, + (const char *armor, uint8_t ** pkt, size_t * pktlen), + (armor, pkt, pktlen)) +W(rpmRC, pgpPubKeyLint, + (const uint8_t *pkts, size_t pktslen, char **explanation), + (pkts, pktslen, explanation)) +W(int, rpmInitCrypto, (void), ()) +W(int, rpmFreeCrypto, (void), ()) +W(DIGEST_CTX, rpmDigestInit, (int hashalgo, rpmDigestFlags flags), + (hashalgo, flags)) +W(DIGEST_CTX, rpmDigestDup, (DIGEST_CTX octx), (octx)) +W(size_t, rpmDigestLength, (int hashalgo), (hashalgo)) +W(int, rpmDigestUpdate, (DIGEST_CTX ctx, const void * data, size_t len), + (ctx, data, len)) +W(int, rpmDigestFinal, + (DIGEST_CTX ctx, void ** datap, size_t *lenp, int asAscii), + (ctx, datap, lenp, asAscii)) diff --git a/tests/Makefile.am b/tests/Makefile.am index 8f36f9fdc3..7e7806da68 100644 --- a/tests/Makefile.am +++ b/tests/Makefile.am @@ -12,8 +12,7 @@ EXTRA_DIST += local.at $(TESTSUITE) AM_CPPFLAGS = -I$(top_srcdir)/include -rpmpgpcheck_LDADD = ../rpmio/librpmio.la \ - @WITH_RPM_SEQUOIA_LIB@ +rpmpgpcheck_LDADD = ../rpmio/librpmio.la ## testsuite components TESTSUITE_AT = rpmtests.at