public inbox for git-commits@fedoraproject.org
help / color / mirror / Atom feed
* [rpms/cachelib] f44: Build with getdeps and vendored dependencies via %getdeps_* macros
@ 2026-09-18 20:43 Michel Lind
0 siblings, 0 replies; only message in thread
From: Michel Lind @ 2026-09-18 20:43 UTC (permalink / raw)
To: git-commits
A new commit has been pushed.
Repo : rpms/cachelib
Branch : f44
Commit : 7b16e3eed8b4c04fef83b98a99e69c25d95390e9
Author : Michel Lind <salimma@fedoraproject.org>
Date : 2026-09-18T18:35:24+01:00
Stats : +750/-227 in 19 file(s)
URL : https://src.fedoraproject.org/rpms/cachelib/c/7b16e3eed8b4c04fef83b98a99e69c25d95390e9?branch=f44
Log:
Build with getdeps and vendored dependencies via %getdeps_* macros
- Vendor folly, fizz, wangle, mvfst and fbthrift (and liboqs and
magic_enum, which Fedora retired or ships in an older layout) instead
of requiring lockstep Fedora packages of them; add vendor.sh to
produce Source1 from the spec
- Generate the BuildRequires from the getdeps manifests
- Ship two statically linked executables, cachebench and
cachelib_binary_trace_gen (upstream's binary_trace_gen, renamed), and
no libraries; drop -devel and obsolete it
- Version is <major>.<weekly tag>, with ^<distance>.<shortcommit> from
git describe appended for a snapshot; add snapshot.sh to print the
%%global lines; drop the forge macros, Source0 is a plain GitHub
archive URL named %%{name}-%%{version}.tar.gz like Source1
- Declare SourceLicense and list the License one identifier per line
under %%{shrink:}, with the per-project breakdown as comments; install
and verify the licenses of the vendored tree
- Update to snapshot ee4c153e (38 commits past v2026.09.14.00), drop
the four patches that no longer apply, carry seven that are all
upstream or in review
- Require folly-rpm-macros >= 46, the first version with the macros
The old spec built cachelib with %%cmake against fbthrift-devel,
fizz-devel, folly-devel, mvfst-devel and wangle-devel pinned to one
upstream tag, which meant five packages had to move together for every
update and is why the stack fell out of Fedora. Meta's own build tool,
getdeps.py (build/fbcode_builder), can now vendor the dependencies it
cannot take from the system and build offline from that tree
(facebook/CacheLib#491, #494, #495), so the spec drives it through the
%%getdeps_* macros in folly-rpm-macros 46: system packages for the
dependencies Fedora ships, with the BuildRequires generated from the
manifests in %%generate_buildrequires; the rest from Source1, a tarball
produced by ./vendor.sh with `getdeps.py vendor`; no network access; a
DESTDIR install of getdeps' build directory. bundled() Provides for each
vendored project are generated from getdeps-vendor.txt.
Everything is linked statically into the two executables. A
shared-library build (dependencies as static PIC archives linked into
cachelib's own libraries) was tried first and dropped: it links, but
each libcachelib_*.so carries its own copy of fbthrift and folly, and
the copies re-register the same gflags at startup, which gflags treats
as fatal. A -devel package would also need folly and fbthrift headers
that Fedora no longer ships, so nothing could have used the libraries.
That detour still found three upstream bugs, carried here as patches:
cachebench's binary_trace_gen library missed sources
(facebook/CacheLib#498, landed), cachelib_nvmitem had no SOVERSION
(#500), and fbthrift's THRIFT_DATA_MEMBER put relocated data in a
.rodata section, which -fPIC/-fPIE makes writable, giving every object
an RWX LOAD segment that glibc's aarch64 loader crashes on when a BTI
note is present and that Fedora's --error-rwx-segments refuses to link
(facebook/fbthrift#712, submitted internally). getdeps --shared-lib also
dropped $LDFLAGS from the shared library links (facebook/CacheLib#499).
The remaining patches make the vendored folly and wangle build against
OpenSSL 4.0 on Fedora 45+ (facebook/folly#2706, facebook/wangle#254;
verified with their test suites on F45) and let folly's FindLibDwarf
find libdwarf-2/ (facebook/folly#2707, landed after the pinned folly).
getdeps has no per-project CMake defines, so LIB_INSTALL_DIR (%%_lib),
CACHELIB_MAJOR_VERSION and CONFIGS_INSTALL_DIR are passed for every
project it builds, as the contents of a JSON object because rpm strips
the braces from a macro value that is one.
The License tag is verified in %%check against every license detected
in the source and vendor trees; getdeps-vendor-licenses.toml excludes
build tooling, test code and the liboqs algorithm families that
OQS_MINIMAL_BUILD does not compile, and pins by hash the pqcrystals
"Public Domain or Apache 2.0" notice that askalono cannot classify. The
scan is what turned up fizz being BSD-3-Clause, mvfst's BSD-2/BSD-3
third_party code and liboqs' CC0-1.0 aarch64 Kyber code (CC0-1.0 is in
Fedora's own liboqs tag).
Version 19.2026.09.14.00^38.ee4c153: kCachelibVersion 19, the weekly
tag the snapshot is based on, and git describe's distance and hash
(v2026.09.14.00-38-gee4c153), the guidelines' <number>.<revision>
snapshot form; the distance keeps several snapshots between two tags
in order. 17^20250203, the last build of the old scheme, sorts below,
so no Epoch. The spec switches to the weekly tag due 2026-09-22 next.
Tests stay disabled by default (%%bcond_with check) as before; they can
be built with %%getdeps_build -t and run with %%getdeps_test once a mock
run shows which ones need facilities a chroot lacks. EPEL 10 needs
manifest work for lz4-static and the libraries EL vendors, and EPEL 9
additionally #496; both are for later.
Assisted-by: Claude Code:claude-fable-5-1
Signed-off-by: Michel Lind <salimma@fedoraproject.org>
---
diff --git a/.gitignore b/.gitignore
index e0522c2..3d4559a 100644
--- a/.gitignore
+++ b/.gitignore
@@ -10,3 +10,5 @@
/cachelib-2024.07.22.00.tar.gz
/cachelib-2024.08.19.00.tar.gz
/cachelib-2025.02.03.00.tar.gz
+/cachelib-19.2026.09.14.00^38.ee4c153.tar.gz
+/cachelib-19.2026.09.14.00^38.ee4c153-vendor.tar.xz
diff --git a/0001-folly-FindLibDwarf-look-in-libdwarf-2.patch b/0001-folly-FindLibDwarf-look-in-libdwarf-2.patch
new file mode 100644
index 0000000..98e1f5a
--- /dev/null
+++ b/0001-folly-FindLibDwarf-look-in-libdwarf-2.patch
@@ -0,0 +1,18 @@
+folly: let FindLibDwarf find libdwarf 2.x headers
+
+libdwarf 2.x installs its headers under <includedir>/libdwarf-2/ (Fedora 44
+and later, EPEL 10); the module only searched libdwarf/ and libdwarf-0/,
+so FOLLY_HAVE_DWARF ended up FALSE and consumers of
+folly::exception_tracer::getCurrentExceptions() failed to compile.
+
+--- a/vendor/folly/CMake/FindLibDwarf.cmake 2026-09-17 17:42:24.335966817 +0100
++++ b/vendor/folly/CMake/FindLibDwarf.cmake 2026-09-17 17:42:24.337420456 +0100
+@@ -16,7 +16,7 @@
+ # Linux distributions. It is not installed in a libdwarf/ subdirectory on Mac
+ # systems when installed with Homebrew. Newer homebrew installations install
+ # it in libdwarf-0. Search for it in all locations.
+-find_path(LIBDWARF_INCLUDE_DIR NAMES dwarf.h PATH_SUFFIXES libdwarf libdwarf-0)
++find_path(LIBDWARF_INCLUDE_DIR NAMES dwarf.h PATH_SUFFIXES libdwarf libdwarf-2 libdwarf-0)
+ mark_as_advanced(LIBDWARF_INCLUDE_DIR)
+
+ find_library(LIBDWARF_LIBRARY NAMES dwarf)
diff --git a/0002-folly-build-against-OpenSSL-4.0.patch b/0002-folly-build-against-OpenSSL-4.0.patch
new file mode 100644
index 0000000..6eea3a3
--- /dev/null
+++ b/0002-folly-build-against-OpenSSL-4.0.patch
@@ -0,0 +1,105 @@
+diff --git a/vendor/folly/folly/io/async/ssl/OpenSSLUtils.cpp b/vendor/folly/folly/io/async/ssl/OpenSSLUtils.cpp
+index 4ece63edd..6f39c52f5 100644
+--- a/vendor/folly/folly/io/async/ssl/OpenSSLUtils.cpp
++++ b/vendor/folly/folly/io/async/ssl/OpenSSLUtils.cpp
+@@ -122,9 +122,11 @@ bool OpenSSLUtils::validatePeerCertNames(
+ for (int i = 0; i < sk_GENERAL_NAME_num(altNames); i++) {
+ auto name = sk_GENERAL_NAME_value(altNames, i);
+ if ((addr4 != nullptr || addr6 != nullptr) && name->type == GEN_IPADD) {
+- // Extra const-ness for paranoia
+- unsigned char const* const rawIpStr = name->d.iPAddress->data;
+- auto const rawIpLen = size_t(name->d.iPAddress->length);
++ // ASN1_STRING is opaque since OpenSSL 4.0; use the accessors, which
++ // work on all supported versions.
++ unsigned char const* const rawIpStr =
++ ASN1_STRING_get0_data(name->d.iPAddress);
++ auto const rawIpLen = size_t(ASN1_STRING_length(name->d.iPAddress));
+
+ if (rawIpLen == 4 && addr4 != nullptr) {
+ if (::memcmp(rawIpStr, &addr4->sin_addr, rawIpLen) == 0) {
+@@ -285,7 +287,9 @@ std::string OpenSSLUtils::getCommonName(X509* x509) {
+ if (x509 == nullptr) {
+ return "";
+ }
+- X509_NAME* subject = X509_get_subject_name(x509);
++ // X509_get_subject_name() returns const X509_NAME* since OpenSSL 4.0;
++ // auto keeps this compiling on older versions too.
++ auto subject = X509_get_subject_name(x509);
+ char buf[ub_common_name + 1];
+ int length =
+ X509_NAME_get_text_by_NID(subject, NID_commonName, buf, sizeof(buf));
+diff --git a/vendor/folly/folly/ssl/OpenSSLCertUtils.cpp b/vendor/folly/folly/ssl/OpenSSLCertUtils.cpp
+index 67a066d3a..b699e3b98 100644
+--- a/vendor/folly/folly/ssl/OpenSSLCertUtils.cpp
++++ b/vendor/folly/folly/ssl/OpenSSLCertUtils.cpp
+@@ -33,7 +33,7 @@ std::string getOpenSSLErrorString(unsigned long err) {
+ return std::string(errBuff.data());
+ }
+
+-std::string asn1ToString(ASN1_STRING* a) {
++std::string asn1ToString(const ASN1_STRING* a) {
+ auto strType = ASN1_STRING_type(a);
+ if (strType == V_ASN1_UTF8STRING || strType == V_ASN1_OCTET_STRING) {
+ long len = ASN1_STRING_length(a);
+@@ -90,9 +90,12 @@ std::optional<GeneralName> getSubjectAltName(const GENERAL_NAME& name) {
+ return std::nullopt;
+ }
+
+-std::string getExtOid(X509_EXTENSION* extension) {
++std::string getExtOid(const X509_EXTENSION* extension) {
+ CHECK_NOTNULL(extension);
+- ASN1_OBJECT* object = X509_EXTENSION_get_object(extension);
++ // X509_EXTENSION_get_object() takes a non-const parameter before
++ // OpenSSL 4.0; the cast is a no-op there.
++ const ASN1_OBJECT* object =
++ X509_EXTENSION_get_object(const_cast<X509_EXTENSION*>(extension));
+ // Query for extension OID
+ constexpr int buf_size = 256;
+ std::string ret(buf_size, '\0');
+@@ -107,18 +110,24 @@ std::string getExtOid(X509_EXTENSION* extension) {
+ return ret;
+ }
+
+-std::string getExtData(X509_EXTENSION* extension) {
++std::string getExtData(const X509_EXTENSION* extension) {
+ CHECK_NOTNULL(extension);
+- auto asnValue = X509_EXTENSION_get_data(extension);
++ // X509_EXTENSION_get_data() takes a non-const parameter before
++ // OpenSSL 4.0; the cast is a no-op there.
++ auto asnValue =
++ X509_EXTENSION_get_data(const_cast<X509_EXTENSION*>(extension));
+ return asnValue ? asn1ToString(asnValue) : std::string();
+ }
+
+-Optional<std::string> commonName(X509_NAME* name) {
++Optional<std::string> commonName(const X509_NAME* name) {
+ if (!name) {
+ return none;
+ }
+
+- auto cnLoc = X509_NAME_get_index_by_NID(name, NID_commonName, -1);
++ // X509_NAME_get_index_by_NID() takes a non-const parameter before
++ // OpenSSL 3.0; the cast is a no-op there.
++ auto cnLoc = X509_NAME_get_index_by_NID(
++ const_cast<X509_NAME*>(name), NID_commonName, -1);
+ if (cnLoc < 0) {
+ return none;
+ }
+@@ -276,7 +285,7 @@ std::vector<std::string> OpenSSLCertUtils::getExtension(
+ const X509& x509, folly::StringPiece oid) {
+ std::vector<std::string> extValues;
+ for (int i = 0; i < X509_get_ext_count(&x509); i++) {
+- X509_EXTENSION* extension = X509_get_ext(&x509, i);
++ const X509_EXTENSION* extension = X509_get_ext(&x509, i);
+ std::string extensionOid = getExtOid(extension);
+ if (extensionOid == oid) {
+ extValues.push_back(getExtData(extension));
+@@ -289,7 +298,7 @@ std::vector<std::pair<std::string, std::string>>
+ OpenSSLCertUtils::getAllExtensions(const X509& x509) {
+ std::vector<std::pair<std::string, std::string>> extensions;
+ for (int i = 0; i < X509_get_ext_count(&x509); i++) {
+- X509_EXTENSION* extension = X509_get_ext(&x509, i);
++ const X509_EXTENSION* extension = X509_get_ext(&x509, i);
+ std::string oid = getExtOid(extension);
+ std::string value = getExtData(extension);
+ extensions.push_back(std::make_pair(oid, value));
diff --git a/0003-wangle-build-against-OpenSSL-4.0.patch b/0003-wangle-build-against-OpenSSL-4.0.patch
new file mode 100644
index 0000000..c89e3af
--- /dev/null
+++ b/0003-wangle-build-against-OpenSSL-4.0.patch
@@ -0,0 +1,25 @@
+diff --git a/vendor/wangle/wangle/ssl/SSLUtil.cpp b/vendor/wangle/wangle/ssl/SSLUtil.cpp
+index 977ee636..9f66462b 100644
+--- a/vendor/wangle/wangle/ssl/SSLUtil.cpp
++++ b/vendor/wangle/wangle/ssl/SSLUtil.cpp
+@@ -54,7 +54,9 @@ SSLResumeEnum SSLUtil::getResumeState(folly::AsyncSSLSocket* sslSocket) {
+ }
+
+ std::unique_ptr<std::string> SSLUtil::getCommonName(const X509* cert) {
+- X509_NAME* subject = X509_get_subject_name((X509*)cert);
++ // X509_get_subject_name() returns const X509_NAME* since OpenSSL 4.0;
++ // auto keeps this compiling on older versions too.
++ auto subject = X509_get_subject_name((X509*)cert);
+ if (!subject) {
+ return nullptr;
+ }
+@@ -81,7 +83,8 @@ std::unique_ptr<std::list<std::string>> SSLUtil::getSubjectAltName(
+ for (int i = 0; i < (int)count; ++i) {
+ GENERAL_NAME* generalName = sk_GENERAL_NAME_value(names, i);
+ if (generalName->type == GEN_DNS) {
+- ASN1_STRING* s = generalName->d.dNSName;
++ // auto: GENERAL_NAME union members are const since OpenSSL 4.0.
++ auto s = generalName->d.dNSName;
+ const char* name = (const char*)ASN1_STRING_get0_data(s);
+ // I can't find any docs on what a negative return value here
+ // would mean, so I'm going to ignore it.
diff --git a/0004-cachebench-link-binary_trace_gen-against-cachelib_cachebench.patch b/0004-cachebench-link-binary_trace_gen-against-cachelib_cachebench.patch
new file mode 100644
index 0000000..e9af615
--- /dev/null
+++ b/0004-cachebench-link-binary_trace_gen-against-cachelib_cachebench.patch
@@ -0,0 +1,82 @@
+From be2afbff00abcd84cfef3d4d0c1632cd0e46dc71 Mon Sep 17 00:00:00 2001
+From: Michel Lind <salimma@fedoraproject.org>
+Date: Fri, 18 Sep 2026 12:16:05 +0100
+Subject: [PATCH] cachebench: link binary_trace_gen against cachelib_cachebench
+
+The cachelib_binary_trace_gen library duplicates a subset of the
+cachelib_cachebench sources, including runner/Runner.cpp and
+runner/Stressor.cpp, but leaves out the runner/, consistency/ and
+workload/ files those two depend on. With static libraries the linker
+only pulls the objects binary_trace_gen.cpp actually uses, so the gap
+is invisible; with BUILD_SHARED_LIBS=ON the whole library becomes a
+shared object with 36 undefined references and linking the executable
+fails:
+
+ ld: cachebench/libcachelib_binary_trace_gen.so: undefined reference
+ to `facebook::cachelib::cachebench::CacheStressorBase::finish()'
+
+It would also produce a binary_trace_gen that depends on a library the
+install rules never install. The duplicate also misses the
+SKIP_OPTION_SIZE_VERIFY definition applied to cachelib_cachebench on
+non-x86_64.
+
+Drop the duplicate and link binary_trace_gen against cachelib_cachebench,
+which already contains every source it listed.
+
+Tested with getdeps --shared-lib on Fedora Rawhide aarch64 (the Fedora
+package build): binary_trace_gen now links and depends on
+libcachelib_cachebench.so.19.
+
+Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
+Signed-off-by: Michel Lind <salimma@fedoraproject.org>
+---
+ cachelib/cachebench/CMakeLists.txt | 26 +-------------------------
+ 1 file changed, 1 insertion(+), 25 deletions(-)
+
+diff --git a/cachelib/cachebench/CMakeLists.txt b/cachelib/cachebench/CMakeLists.txt
+index 712c3d74..c0b6200e 100644
+--- a/cachelib/cachebench/CMakeLists.txt
++++ b/cachelib/cachebench/CMakeLists.txt
+@@ -61,30 +61,6 @@ target_link_libraries(cachelib_cachebench
+ Boost::boost
+ )
+
+-add_library (cachelib_binary_trace_gen
+- ./runner/Runner.cpp
+- ./runner/Stressor.cpp
+- ./util/CacheConfig.cpp
+- ./util/Config.cpp
+- ./util/MemoryMonitorScript.cpp
+- ./workload/BlockChunkCache.cpp
+- ./workload/BlockChunkReplayGenerator.cpp
+- ./workload/PieceWiseCache.cpp
+- ./workload/OnlineGenerator.cpp
+- ./workload/WorkloadGenerator.cpp
+- ./workload/PieceWiseReplayGenerator.cpp
+- ${OBJECT_CACHE_PERSISTENCE_THRIFT_FILES}
+- )
+-add_dependencies(cachelib_binary_trace_gen thrift_generated_files)
+-target_link_libraries(cachelib_binary_trace_gen
+- PUBLIC
+- cachelib_datatype
+- cachelib_allocator
+- gflags
+- PRIVATE
+- Boost::boost
+-)
+-
+ if ((CMAKE_SYSTEM_NAME STREQUAL Linux) AND
+ (CMAKE_SYSTEM_PROCESSOR STREQUAL x86_64))
+ else()
+@@ -96,7 +72,7 @@ endif()
+ add_executable (cachebench main.cpp)
+ add_executable (binary_trace_gen binary_trace_gen.cpp)
+ target_link_libraries(cachebench cachelib_cachebench)
+-target_link_libraries(binary_trace_gen cachelib_binary_trace_gen)
++target_link_libraries(binary_trace_gen cachelib_cachebench)
+
+ install(
+ TARGETS
+--
+2.55.0
+
diff --git a/0005-cmake-give-cachelib_nvmitem-a-SOVERSION.patch b/0005-cmake-give-cachelib_nvmitem-a-SOVERSION.patch
new file mode 100644
index 0000000..38367a7
--- /dev/null
+++ b/0005-cmake-give-cachelib_nvmitem-a-SOVERSION.patch
@@ -0,0 +1,33 @@
+From 1181826e57f64bde8bf4cb98ba500c649413755c Mon Sep 17 00:00:00 2001
+From: Michel Lind <salimma@fedoraproject.org>
+Date: Fri, 18 Sep 2026 15:19:56 +0100
+Subject: [PATCH] cmake: give cachelib_nvmitem a SOVERSION like the other
+ libraries
+
+cachelib_nvmitem was split out of cachelib_allocator to break a cycle
+with cachelib_navy, but it was not added to the list of targets that
+get SOVERSION/VERSION when BUILD_SHARED_LIBS is on. It is the only
+installed library that ends up as an unversioned libcachelib_nvmitem.so,
+which distribution packaging treats as a development symlink.
+
+Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
+Signed-off-by: Michel Lind <salimma@fedoraproject.org>
+---
+ cachelib/CMakeLists.txt | 1 +
+ 1 file changed, 1 insertion(+)
+
+diff --git a/cachelib/CMakeLists.txt b/cachelib/CMakeLists.txt
+index 29f3ee2c..90e88a06 100644
+--- a/cachelib/CMakeLists.txt
++++ b/cachelib/CMakeLists.txt
+@@ -412,6 +412,7 @@ if (BUILD_SHARED_LIBS)
+ cachelib_datatype
+ cachelib_interface
+ cachelib_navy
++ cachelib_nvmitem
+ cachelib_shm
+ PROPERTIES
+ SOVERSION ${CACHELIB_MAJOR_VERSION}
+--
+2.55.0
+
diff --git a/0006-fbthrift-keep-thrift-data-out-of-a-writable-rodata-section.patch b/0006-fbthrift-keep-thrift-data-out-of-a-writable-rodata-section.patch
new file mode 100644
index 0000000..55a0760
--- /dev/null
+++ b/0006-fbthrift-keep-thrift-data-out-of-a-writable-rodata-section.patch
@@ -0,0 +1,46 @@
+From 8f02f06da08cfcb33a029173838a381e41fe60da Mon Sep 17 00:00:00 2001
+From: Michel Lind <salimma@fedoraproject.org>
+Date: Fri, 18 Sep 2026 16:15:54 +0100
+Subject: [PATCH] cpp2: keep TStructDataStorage members out of a writable
+ .rodata section
+
+THRIFT_DATA_MEMBER places every TStructDataStorage<T> member in
+".rodata.thrift.data" so the linker cannot garbage-collect the unused
+ones. Some of those members (name, fields_names) hold string_views, i.e.
+pointers that need relocations, so in a -fPIC or -fPIE build the compiler
+has to make that section writable (the assembler warns "setting incorrect
+section attributes for .rodata.thrift.data"). The linker then merges a
+writable .rodata into the text segment and the resulting shared object
+or PIE has a single RWX LOAD segment. On aarch64, where -z separate-code
+is not the default, glibc's loader crashes on such an object when it also
+carries a BTI GNU_PROPERTY note (SIGSEGV in _dl_setup_hash), so every
+shared library that links thrift-generated code was unloadable; with
+binutils' --error-rwx-segments, as Fedora now passes by default, the
+link fails outright.
+
+Name the section .data.rel.ro.thrift.data instead: it still groups the
+members so gc-sections cannot strip them, and RELRO is the right home for
+constant data that carries relocations.
+
+Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
+Signed-off-by: Michel Lind <salimma@fedoraproject.org>
+---
+ thrift/lib/cpp2/gen/module_data_cpp.h | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+diff --git a/vendor/fbthrift/thrift/lib/cpp2/gen/module_data_cpp.h b/vendor/fbthrift/thrift/lib/cpp2/gen/module_data_cpp.h
+index af62970c81..6f41948cc7 100644
+--- a/vendor/fbthrift/thrift/lib/cpp2/gen/module_data_cpp.h
++++ b/vendor/fbthrift/thrift/lib/cpp2/gen/module_data_cpp.h
+@@ -32,7 +32,7 @@
+ // is then unable to remove unused data without also removing used data.
+ // This has a similar effect to the "retain" attribute, but works with older
+ // toolchains.
+-#define THRIFT_DATA_MEMBER [[gnu::used]] [[gnu::section(".rodata.thrift.data")]]
++#define THRIFT_DATA_MEMBER [[gnu::used]] [[gnu::section(".data.rel.ro.thrift.data")]]
+ #else
+ #define THRIFT_DATA_MEMBER
+ #endif
+--
+2.55.0
+
diff --git a/0007-getdeps-keep-LDFLAGS-on-the-shared-library-links.patch b/0007-getdeps-keep-LDFLAGS-on-the-shared-library-links.patch
new file mode 100644
index 0000000..5cac9e1
--- /dev/null
+++ b/0007-getdeps-keep-LDFLAGS-on-the-shared-library-links.patch
@@ -0,0 +1,109 @@
+From 47c805cd67170b14fd1ea912f4dc24895b139cb1 Mon Sep 17 00:00:00 2001
+From: Michel Lind <salimma@fedoraproject.org>
+Date: Fri, 18 Sep 2026 15:18:39 +0100
+Subject: [PATCH] getdeps: keep $LDFLAGS on the shared library links under
+ --shared-lib
+
+--shared-lib defines CMAKE_SHARED_LINKER_FLAGS and CMAKE_MODULE_LINKER_FLAGS
+on the cmake command line to append -Wl,--exclude-libs=ALL. A variable
+given on the command line is never seeded from $LDFLAGS, so the caller's
+linker flags vanished from every shared library link while the
+executables, whose CMAKE_EXE_LINKER_FLAGS we do not touch, kept them.
+For a distro build that silently dropped the hardening flags (RELRO,
+BIND_NOW, --error-rwx-segments) from the produced .so files.
+
+Seed both variables from $LDFLAGS, as CMake would, before appending.
+An explicit caller value still wins.
+
+Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
+Signed-off-by: Michel Lind <salimma@fedoraproject.org>
+---
+ build/fbcode_builder/getdeps/shared_lib.py | 11 ++++++--
+ .../getdeps/test/shared_lib_test.py | 28 ++++++++++++++++++-
+ 2 files changed, 36 insertions(+), 3 deletions(-)
+
+diff --git a/build/fbcode_builder/getdeps/shared_lib.py b/build/fbcode_builder/getdeps/shared_lib.py
+index 9d3e5593..33a6cf94 100644
+--- a/build/fbcode_builder/getdeps/shared_lib.py
++++ b/build/fbcode_builder/getdeps/shared_lib.py
+@@ -12,6 +12,7 @@ Split out from builder.py so the gating logic
+
+ from __future__ import annotations
+
++import os
+ import typing
+
+ if typing.TYPE_CHECKING:
+@@ -36,14 +37,20 @@ def apply_shared_lib_top_level_cmake_defines(
+ - On Linux: append -Wl,--exclude-libs=ALL to the shared/module linker
+ flags so the deps' symbols stay out of the produced .so's dynamic
+ export table (avoids ODR clashes if the host process loads another
+- copy of any dep).
++ copy of any dep). Defining CMAKE_*_LINKER_FLAGS on the command line
++ stops CMake from seeding them from $LDFLAGS, so start from $LDFLAGS
++ (as CMake would) to keep the caller's linker flags, e.g. a distro's
++ hardening flags, on the shared library links.
+ """
+ if not build_opts.shared_lib:
+ return
+ defines.setdefault("BUILD_SHARED_LIBS", "ON")
+ if build_opts.is_linux():
++ ldflags = os.environ.get("LDFLAGS", "")
+ for var in ("CMAKE_SHARED_LINKER_FLAGS", "CMAKE_MODULE_LINKER_FLAGS"):
+- defines[var] = _append_token(defines.get(var, ""), "-Wl,--exclude-libs=ALL")
++ defines[var] = _append_token(
++ defines.get(var, ldflags), "-Wl,--exclude-libs=ALL"
++ )
+
+
+ def apply_shared_lib_dep_env(
+diff --git a/build/fbcode_builder/getdeps/test/shared_lib_test.py b/build/fbcode_builder/getdeps/test/shared_lib_test.py
+index ef81943b..78538943 100644
+--- a/build/fbcode_builder/getdeps/test/shared_lib_test.py
++++ b/build/fbcode_builder/getdeps/test/shared_lib_test.py
+@@ -4,8 +4,9 @@
+ # LICENSE file in the root directory of this source tree.
+
+
++import os
+ import unittest
+-from unittest.mock import MagicMock
++from unittest.mock import MagicMock, patch
+
+ from ..envfuncs import Env
+ from ..shared_lib import (
+@@ -79,6 +80,31 @@ class ApplyTopLevelCmakeDefinesTest(unittest.TestCase):
+ apply_shared_lib_top_level_cmake_defines(defines, opts)
+ self.assertEqual(defines["CMAKE_SHARED_LINKER_FLAGS"], "-Wl,--exclude-libs=ALL")
+
++ def test_env_ldflags_seed_the_linker_flags(self) -> None:
++ defines = {}
++ with patch.dict(os.environ, {"LDFLAGS": "-Wl,-z,relro -Wl,-z,now"}):
++ apply_shared_lib_top_level_cmake_defines(
++ defines, make_build_opts(is_linux=True)
++ )
++ for var in ("CMAKE_SHARED_LINKER_FLAGS", "CMAKE_MODULE_LINKER_FLAGS"):
++ self.assertEqual(
++ defines[var], "-Wl,-z,relro -Wl,-z,now -Wl,--exclude-libs=ALL"
++ )
++
++ def test_explicit_linker_flags_win_over_env_ldflags(self) -> None:
++ defines = {"CMAKE_SHARED_LINKER_FLAGS": "-Wl,--as-needed"}
++ with patch.dict(os.environ, {"LDFLAGS": "-Wl,-z,now"}):
++ apply_shared_lib_top_level_cmake_defines(
++ defines, make_build_opts(is_linux=True)
++ )
++ self.assertEqual(
++ defines["CMAKE_SHARED_LINKER_FLAGS"],
++ "-Wl,--as-needed -Wl,--exclude-libs=ALL",
++ )
++ self.assertEqual(
++ defines["CMAKE_MODULE_LINKER_FLAGS"], "-Wl,-z,now -Wl,--exclude-libs=ALL"
++ )
++
+
+ class ApplyDepEnvTest(unittest.TestCase):
+ def test_no_op_when_shared_lib_off(self) -> None:
+--
+2.55.0
+
diff --git a/README.md b/README.md
index 4730e69..e2b95d8 100644
--- a/README.md
+++ b/README.md
@@ -1,3 +1,53 @@
# cachelib
-The cachelib package
+Fedora package of [CacheLib](https://github.com/facebook/CacheLib), built with
+its own `getdeps.py` via the `%getdeps_*` macros from folly-rpm-macros.
+
+Dependencies that Fedora packages (boost, fmt, glog, gflags, googletest, zstd,
+liboqs, tsl-sparse-map, ...) come from the system; the `BuildRequires` for them
+are generated from the getdeps manifests at build time. The rest of the Meta
+stack (folly, fizz, wangle, mvfst, fbthrift) is vendored: `Source1` is a
+tarball of their sources at the revisions the CacheLib snapshot pins.
+
+To update:
+
+1. Set `%global basetag vYYYY.MM.DD.00` to the weekly tag and check
+ `%major_ver` against `cachelib/allocator/CacheVersion.h`. For a tag build
+ that is all: `Version` is `<major>.<tag without its v>`. For a snapshot
+ past the tag, also paste the `%global commit` and `%global commits` lines
+ that `./snapshot.sh [ref]` prints; `Version` becomes
+ `<major>.<tag>^<distance>.<shortcommit>`, the guidelines'
+ `<number>.<revision>` snapshot form, and the distance keeps several
+ snapshots between two tags in order.
+
+ `snapshot.sh` uses the GitHub API. From a clone of any forge, one command
+ gives the same values:
+
+ git describe --tags --match 'v20??.??.??.??' $ref # v2026.09.14.00-38-gee4c153
+ git rev-parse $ref # the full commit
+
+ The `--match` keeps the distance relative to the weekly `vYYYY.MM.DD.NN`
+ tags and ignores older `vYYYYMMDD`-style ones, which sort above them.
+2. `./vendor.sh` to download `Source0` and produce the matching `Source1`.
+ getdeps only vendors what it cannot take from the system, so install the
+ generated BuildRequires first for a minimal tarball (the static
+ `dnf builddep` cannot see them; run
+ `python3 build/fbcode_builder/getdeps.py --allow-system-packages
+ install-system-deps --recursive cachelib` from the unpacked source
+ instead). A tarball made with fewer packages installed is merely larger:
+ vendored projects the build takes from the system are never consulted.
+3. `fedpkg new-sources <Source0> <Source1>`.
+
+`getdeps-vendor-licenses.toml` configures the license scan of the vendored
+tree (`%getdeps_vendor_license_check`), excluding build tooling, test code and
+the liboqs algorithm families that `OQS_MINIMAL_BUILD` leaves out, and pinning
+by hash the pqcrystals notice ("Public Domain or Apache 2.0") that askalono
+cannot classify. To regenerate the per-project breakdown behind the `License`
+tag, run the same scan the build runs, from the unpacked source root with the
+vendor tarball extracted:
+
+ awk '{ print "# " $1 " v" $2 }' vendor/getdeps-vendor.txt > vendor/modules.txt
+ go_vendor_license --config getdeps-vendor-licenses.toml report all -L
+
+After a liboqs bump, check its `OQS_MINIMAL_BUILD` line in the manifest and
+the `exclude_directories` list still agree.
diff --git a/cachelib-disable-binary_trace_gen.diff b/cachelib-disable-binary_trace_gen.diff
deleted file mode 100644
index 84b8cee..0000000
--- a/cachelib-disable-binary_trace_gen.diff
+++ /dev/null
@@ -1,43 +0,0 @@
---- a/cachelib/cachebench/CMakeLists.txt
-+++ b/cachelib/cachebench/CMakeLists.txt
-@@ -41,25 +41,6 @@ target_link_libraries(cachelib_cachebenc
- gflags
- )
-
--add_library (cachelib_binary_trace_gen
-- ./runner/Runner.cpp
-- ./runner/Stressor.cpp
-- ./util/CacheConfig.cpp
-- ./util/Config.cpp
-- ./workload/BlockChunkCache.cpp
-- ./workload/BlockChunkReplayGenerator.cpp
-- ./workload/PieceWiseCache.cpp
-- ./workload/OnlineGenerator.cpp
-- ./workload/WorkloadGenerator.cpp
-- ./workload/PieceWiseReplayGenerator.cpp
-- )
--add_dependencies(cachelib_binary_trace_gen thrift_generated_files)
--target_link_libraries(cachelib_binary_trace_gen PUBLIC
-- cachelib_datatype
-- cachelib_allocator
-- gflags
--)
--
- if ((CMAKE_SYSTEM_NAME STREQUAL Linux) AND
- (CMAKE_SYSTEM_PROCESSOR STREQUAL x86_64))
- else()
-@@ -68,14 +49,11 @@ endif()
-
-
- add_executable (cachebench main.cpp)
--add_executable (binary_trace_gen binary_trace_gen.cpp)
- target_link_libraries(cachebench cachelib_cachebench)
--target_link_libraries(binary_trace_gen cachelib_binary_trace_gen)
-
- install(
- TARGETS
- cachebench
-- binary_trace_gen
- DESTINATION ${BIN_INSTALL_DIR}
- )
-
diff --git a/cachelib-find-gtest.patch b/cachelib-find-gtest.patch
deleted file mode 100644
index 5a874d1..0000000
--- a/cachelib-find-gtest.patch
+++ /dev/null
@@ -1,69 +0,0 @@
-diff '--color=auto' -ruN CacheLib-c4904ef2524f396eb432392f8308a69dda926bd8/cachelib/cmake/FindGTest.cmake CacheLib-c4904ef2524f396eb432392f8308a69dda926bd8-find-gtest/cachelib/cmake/FindGTest.cmake
---- /dev/null
-+++ b/cachelib/cmake/FindGTest.cmake
-@@ -0,0 +1,54 @@
-+# Copyright (c) Facebook, Inc. and its affiliates.
-+#
-+# Licensed under the Apache License, Version 2.0 (the "License");
-+# you may not use this file except in compliance with the License.
-+# You may obtain a copy of the License at
-+#
-+# http://www.apache.org/licenses/LICENSE-2.0
-+#
-+# Unless required by applicable law or agreed to in writing, software
-+# distributed under the License is distributed on an "AS IS" BASIS,
-+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-+# See the License for the specific language governing permissions and
-+# limitations under the License.
-+
-+# Find GTest
-+#
-+# This will define:
-+# GTEST_FOUND
-+# GTEST_INCLUDE_DIRS
-+# GTEST_LIBRARIES
-+# GTEST_MAIN_LIBRARIES
-+# GTEST_BOTH_LIBRARIES
-+
-+find_path(GTEST_INCLUDE_DIRS gtest/gtest.h
-+ HINTS
-+ $ENV{GTEST_ROOT}/include
-+ ${GTEST_ROOT}/include
-+)
-+
-+find_library(GTEST_LIBRARIES
-+ NAMES gtest
-+ HINTS
-+ $ENV{GTEST_ROOT}
-+ ${GTEST_ROOT}
-+)
-+
-+find_library(GTEST_MAIN_LIBRARIES
-+ NAMES gtest_main
-+ HINTS
-+ $ENV{GTEST_ROOT}
-+ ${GTEST_ROOT}
-+)
-+
-+set(GTEST_BOTH_LIBRARIES ${GTEST_LIBRARIES} ${GTEST_MAIN_LIBRARIES})
-+
-+mark_as_advanced(GTEST_INCLUDE_DIRS GTEST_LIBRARIES GTEST_MAIN_LIBRARIES)
-+
-+include(FindPackageHandleStandardArgs)
-+find_package_handle_standard_args(
-+ GTest GTEST_LIBRARIES GTEST_INCLUDE_DIRS GTEST_MAIN_LIBRARIES)
-+
-+if(GTEST_FOUND AND NOT GTEST_FIND_QUIETLY)
-+ message(STATUS "GTEST: ${GTEST_INCLUDE_DIRS}")
-+endif()
---- a/cachelib/CMakeLists.txt
-+++ b/cachelib/CMakeLists.txt
-@@ -97,7 +97,7 @@ find_package(Boost REQUIRED COMPONENTS
- system filesystem regex context program_options thread)
- find_package(Gflags REQUIRED)
- find_package(Glog REQUIRED)
--find_package(GTest CONFIG REQUIRED)
-+find_package(GTest REQUIRED)
- find_package(folly CONFIG REQUIRED)
- find_package(fizz CONFIG REQUIRED)
- find_package(fmt CONFIG REQUIRED)
diff --git a/cachelib-fix-DeviceTest-FDP.diff b/cachelib-fix-DeviceTest-FDP.diff
deleted file mode 100644
index 424b24c..0000000
--- a/cachelib-fix-DeviceTest-FDP.diff
+++ /dev/null
@@ -1,11 +0,0 @@
---- a/cachelib/navy/CMakeLists.txt
-+++ b/cachelib/navy/CMakeLists.txt
-@@ -105,7 +105,7 @@ if (BUILD_TESTS)
- add_test (scheduler/tests/ThreadPoolJobSchedulerTest.cpp)
- add_test (driver/tests/DriverTest.cpp)
- if (NOT MISSING_FALLOCATE)
-- add_test (common/tests/DeviceTest.cpp)
-+# add_test (common/tests/DeviceTest.cpp)
- endif()
- add_test (block_cache/tests/AllocatorTest.cpp)
- add_test (block_cache/tests/RegionManagerTest.cpp)
diff --git a/cachelib-workaround-gcc-epel9-x86_64-bz2108665.patch b/cachelib-workaround-gcc-epel9-x86_64-bz2108665.patch
deleted file mode 100644
index 5b88103..0000000
--- a/cachelib-workaround-gcc-epel9-x86_64-bz2108665.patch
+++ /dev/null
@@ -1,11 +0,0 @@
---- a/cachelib/compact_cache/CCacheFixedLruBucket.h
-+++ b/cachelib/compact_cache/CCacheFixedLruBucket.h
-@@ -274,7 +274,7 @@ struct FixedLruBucket {
- static void copyValue(T* destPtr, const T* srcPtr) {
- XDCHECK(destPtr != nullptr);
- XDCHECK(srcPtr != nullptr);
-- memcpy(destPtr, srcPtr, sizeof(T));
-+ memcpy(reinterpret_cast<void *>(destPtr), reinterpret_cast<const void *>(srcPtr), sizeof(T));
- }
- };
- } // namespace cachelib
diff --git a/cachelib.spec b/cachelib.spec
index 28eedaf..5838ea8 100644
--- a/cachelib.spec
+++ b/cachelib.spec
@@ -4,64 +4,128 @@
%global toolchain clang
%endif
-%bcond_without build_tests
-# tests not discoverable by ctest yet
+# The test suite has not been run in this package for years (it was built
+# but never executed). Enable once a mock run shows which tests need the
+# SysV/POSIX shm and NUMA facilities a build chroot lacks.
%bcond_with check
-%global forgeurl https://github.com/facebook/CacheLib
-%global tag 2025.02.03.00
-%global date %(echo %{tag} | sed -e 's|.00$||' | sed -e 's|\\.||g')
-# disable forge macro snapinfo generation
-# https://pagure.io/fedora-infra/rpmautospec/issue/240
-%global distprefix %{nil}
-%forgemeta
+# Upstream identifies a release by two numbers: kCachelibVersion, the
+# API/format major in cachelib/allocator/CacheVersion.h (%%major_ver), and the
+# weekly tag. Version joins them, major first: <major>.<tag without its v>,
+# a plain dotted version like ImageMagick's four-part one (layout suggested
+# by Carl George). For a snapshot past the tag, also paste the two %%global
+# lines ./snapshot.sh prints (the commit and its distance from the tag):
+# Version becomes <major>.<tag>^<distance>.<shortcommit>, the guidelines'
+# <number>.<revision> snapshot form, and the distance keeps several snapshots
+# between two tags in order. 17^20250203, the last build of the old scheme,
+# sorts below.
+%global basetag v2026.09.14.00
+# Snapshot until the first weekly tag containing the getdeps vendoring
+# support this spec relies on (facebook/CacheLib#491), due 2026-09-22.
+%global commit ee4c153e648271a221f58998465cb5d1ddfe6f3c
+%global commits 38
+%global tagver %(echo %{basetag} | sed 's|^v||')
+%if 0%{?commit:1}
+%global shortcommit %(c=%{commit}; echo ${c:0:7})
+%global snapinfo ^%{commits}.%{shortcommit}
+%global archive_ref %{commit}
+%global archive_dir CacheLib-%{commit}
+%else
+%global archive_ref %{basetag}
+%global archive_dir CacheLib-%{tagver}
+%endif
# see cachelib/allocator/CacheVersion.h's kCachelibVersion
-%global major_ver 17
+%global major_ver 19
+
+# getdeps has no per-project CMake defines, so these apply to every project
+# it builds: LIB_INSTALL_DIR is the fbcode_builder-wide name for the library
+# directory (getdeps looks in both lib and lib64 of its dependencies), the
+# other two are only read by cachelib's own CMakeLists. Contents of a JSON
+# object; the macro adds the braces (rpm would strip them from the value).
+%global getdeps_extra_cmake_defines "LIB_INSTALL_DIR": "%{_lib}", "CACHELIB_MAJOR_VERSION": "%{major_ver}", "CONFIGS_INSTALL_DIR": "share/%{name}/test_configs"
Name: cachelib
-Version: %{major_ver}^%{date}
+Version: %{major_ver}.%{tagver}%{?snapinfo}
Release: %autorelease
Summary: Pluggable caching engine for scale high performance cache services
-License: Apache-2.0
-URL: %forgeurl
-Source: %{url}/archive/v%{tag}/%{name}-%{tag}.tar.gz
-# DeviceTest needs common/FdpNvme.cpp. Disable for now
-Patch: %{name}-fix-DeviceTest-FDP.diff
-# incomplete dependencies, will sort out later
-Patch: %{name}-disable-binary_trace_gen.diff
-# needed on EL8; its gtest does not come with cmake files
-Patch100: %{name}-find-gtest.patch
-# Workaround for gcc issue (still needed on epel9 x86_64)
-# https://bugzilla.redhat.com/show_bug.cgi?id=2108665
-Patch200: %{name}-workaround-gcc-epel9-x86_64-bz2108665.patch
+# cachelib itself is Apache-2.0. Vendored (see getdeps-vendor.txt in the
+# license directory): folly, wangle, fbthrift Apache-2.0; fizz BSD-3-Clause;
+# mvfst MIT with BSD-2-Clause and BSD-3-Clause third_party code; magic_enum
+# and sparse-map MIT. Verified by %%getdeps_vendor_license_check in %%check.
+# SourceLicense needs rpm >= 4.19; EPEL 9 (rpm 4.16) gets the full expression
+# on the SRPM as before
+%if !0%{?rhel} || 0%{?rhel} >= 10
+SourceLicense: Apache-2.0
+%endif
+# Vendored projects (getdeps-vendor.txt), as %%check's go_vendor_license report
+# breaks them down; the config is getdeps-vendor-licenses.toml:
+# Apache-2.0 folly, wangle, fbthrift
+# BSD-3-Clause fizz
+# MIT magic_enum
+# MIT AND BSD-2-Clause AND BSD-3-Clause mvfst (third-party code)
+# MIT AND CC0-1.0 AND (Apache-2.0 OR CC0-1.0) liboqs (Kyber/ML-KEM only)
+# CC0-1.0 is liboqs' aarch64 Kyber code, as in Fedora's own liboqs License tag.
+License: %{shrink:
+ Apache-2.0 AND
+ BSD-2-Clause AND
+ BSD-3-Clause AND
+ CC0-1.0 AND
+ MIT AND
+ (Apache-2.0 OR CC0-1.0)
+}
+URL: https://github.com/facebook/CacheLib
+# GitHub ignores the last path component of an archive URL, so the file is
+# named after the version, like Source1 (Packaging Guidelines, SourceURL:
+# git hosting services)
+Source0: %{url}/archive/%{archive_ref}/%{name}-%{version}.tar.gz
+# Third-party sources getdeps cannot take from Fedora packages, produced by
+# ./vendor.sh (getdeps.py vendor); one directory per project plus
+# getdeps-vendor.txt listing each project's pinned revision.
+Source1: %{name}-%{version}-vendor.tar.xz
+Source2: getdeps-vendor-licenses.toml
+# Patches below apply to the vendored trees under vendor/. Each is an
+# upstream fix that the dependency revision this snapshot pins does not yet
+# include; drop them as the pins move past the landed commits.
+#
+# folly's FindLibDwarf did not look in libdwarf-2/, where libdwarf 2.x
+# (Fedora 44+, EPEL 10) installs its headers, so folly built without DWARF
+# support and cachelib's use of folly::exception_tracer failed to compile.
+# Landed upstream as facebook/folly#2707 (51590144c).
+Patch0: 0001-folly-FindLibDwarf-look-in-libdwarf-2.patch
+# OpenSSL 4.0 (Fedora 45+) made ASN1_STRING opaque and the X509_get_*
+# accessors return const; folly and wangle did not compile against it.
+# facebook/folly#2706 and facebook/wangle#254, not yet landed. fizz's
+# matching fix (facebookincubator/fizz#171) only touches a test header the
+# dependency build never compiles, so it is not carried.
+Patch1: 0002-folly-build-against-OpenSSL-4.0.patch
+Patch2: 0003-wangle-build-against-OpenSSL-4.0.patch
+# binary_trace_gen fails to link with BUILD_SHARED_LIBS; drop the duplicate library.
+# Landed upstream as facebook/CacheLib#498 (1a643ff6); drop with the next snapshot.
+Patch3: 0004-cachebench-link-binary_trace_gen-against-cachelib_cachebench.patch
+# libcachelib_nvmitem.so is the one library built without a SOVERSION; facebook/CacheLib#500
+Patch4: 0005-cmake-give-cachelib_nvmitem-a-SOVERSION.patch
+# fbthrift puts relocated metadata in a .rodata section, which -fPIC makes
+# writable; the linker then emits an RWX text segment and glibc's aarch64
+# loader crashes on it (BTI note + RWX). Rename the section to RELRO; facebook/fbthrift#712
+Patch5: 0006-fbthrift-keep-thrift-data-out-of-a-writable-rodata-section.patch
+# --shared-lib dropped $LDFLAGS from the shared library links; facebook/CacheLib#499
+Patch6: 0007-getdeps-keep-LDFLAGS-on-the-shared-library-links.patch
ExclusiveArch: x86_64 aarch64 ppc64le
+# -devel (last shipped as 17^20250203 in Fedora, 16^20230424 in EPEL 9) is gone:
+# cachelib's headers include folly and fbthrift headers that Fedora no longer
+# packages, so there is nothing usable to ship. No Provides on purpose.
+Obsoletes: %{name}-devel < 19.2026.09.14.00
-BuildRequires: cmake
+BuildRequires: folly-rpm-macros >= 46
%if %{with toolchain_clang}
BuildRequires: clang
%else
BuildRequires: gcc-c++
%endif
-BuildRequires: fbthrift-devel = %{tag}
-BuildRequires: fizz-devel = %{tag}
-BuildRequires: folly-devel = %{tag}
-BuildRequires: mvfst-devel = %{tag}
-%if %{with build_tests}
-BuildRequires: gmock-devel
-%endif
-# this is actually needed, because of
-# cachelib/navy/admission_policy/DynamicRandomAP.h
-BuildRequires: gtest-devel
-BuildRequires: libdwarf-devel
-BuildRequires: libzstd-devel
-BuildRequires: numactl-devel
-BuildRequires: wangle-devel
-BuildRequires: zlib-devel
-BuildRequires: tsl-sparse-map-devel
-# BuildRequires: libatomic
+# everything else comes from %%getdeps_generate_buildrequires below
%global _description %{expand:
@@ -72,74 +136,48 @@ caching transparently.}
%description %{_description}
-%package devel
-Summary: %{summary}
-Requires: %{name}%{?_isa} = %{version}-%{release}
-Requires: cmake
-
-%description devel %{_description}
-
-The %{name}-devel package contains libraries and header files for developing
-applications that use %{name}.
+%generate_buildrequires
+%getdeps_generate_buildrequires
+%getdeps_vendor_license_buildrequires -c %{SOURCE2}
%prep
-%autosetup -n CacheLib-%{tag} -N
-%autopatch -p1 -M 99
-%if 0%{?el8}
-%autopatch -p1 -m 100 -M 199
-%endif
-%ifarch x86_64
-%if 0%{?el9}
-%autopatch -p1 -m 200 -M 209
-%endif
-%endif
+%autosetup -n %{archive_dir} -a1 -p1
%build
-pushd %{name}
-%cmake \
-%if %{with build_tests}
- -DBUILD_TESTS:BOOL=ON \
-%else
- -DBUILD_TESTS:BOOL=OFF \
-%endif
- -DCMAKE_BUILD_WITH_INSTALL_RPATH:BOOL=FALSE \
- -DCMAKE_INSTALL_DIR:PATH=%{_libdir}/cmake/%{name} \
- -DCONFIGS_INSTALL_DIR:STRING=%{_datadir}/%{name}/test_configs \
- -DINCLUDE_INSTALL_DIR:PATH=%{_includedir}/%{name} \
- -DCACHELIB_MAJOR_VERSION:STRING=%{major_ver} \
- -DPACKAGE_VERSION:STRING=%{major_ver}.%{date}
-%cmake_build
+%getdeps_build %{?with_check:-t}
%install
-pushd %{name}
-%cmake_install
-%if %{with build_tests}
-# TODO: prevent tests being installed
+%getdeps_install
+# cachelib installs its CMake config under lib/ regardless of LIB_INSTALL_DIR;
+# %%getdeps_install only prunes %%{_libdir}
+rm -rf %{buildroot}%{_prefix}/lib/cmake
+# converts CSV key-value traces into cachebench's binary replay format; give
+# the generic upstream name a package prefix
+mv %{buildroot}%{_bindir}/binary_trace_gen %{buildroot}%{_bindir}/cachelib_binary_trace_gen
+%if %{with check}
+# test binaries are installed to <prefix>/tests; they are run from the
+# build tree in %%check and not shipped
rm -rf %{buildroot}%{_prefix}/tests
%endif
+%getdeps_vendor_license_install -c %{SOURCE2}
-%if %{with check}
%check
-pushd %{name}
-%ctest
+# -L: sparse-map's LICENSE sits in a versioned subdirectory of its tree
+%getdeps_vendor_license_check -c %{SOURCE2} -L
+%if %{with check}
+%getdeps_test
%endif
-%files
-%license LICENSE
+%files -f %{getdeps_vendor_license_filelist}
%doc BENCHMARKS.md CHANGELOG.md README.md examples
%{_bindir}/cachebench
+%{_bindir}/cachelib_binary_trace_gen
%{_datadir}/%{name}
-%{_libdir}/*.so.*
-
-%files devel
-%{_includedir}/%{name}
-%{_libdir}/*.so
-%{_libdir}/cmake/%{name}
%changelog
diff --git a/getdeps-vendor-licenses.toml b/getdeps-vendor-licenses.toml
new file mode 100644
index 0000000..68cb1a0
--- /dev/null
+++ b/getdeps-vendor-licenses.toml
@@ -0,0 +1,96 @@
+# Configuration for %getdeps_vendor_license_check / _install (go-vendor-tools).
+# Paths are relative to the unpacked source tree.
+[licensing]
+detector = "askalono"
+# Not compiled into cachelib: each Meta project's copy of the fbcode_builder
+# build scripts (MIT), fbthrift's Go bindings, and magic_enum's test suite and
+# CMake helper (Catch2 BSL-1.0, Unlicense). Excluding them keeps the License
+# tag to what the binaries actually contain.
+exclude_directories = [
+ "vendor/folly/build/fbcode_builder",
+ "vendor/fizz/build/fbcode_builder",
+ "vendor/wangle/build/fbcode_builder",
+ "vendor/mvfst/build/fbcode_builder",
+ "vendor/fbthrift/build/fbcode_builder",
+ "vendor/fbthrift/thrift/lib/go",
+ "vendor/magic_enum/test",
+ "vendor/magic_enum/cmake",
+ # liboqs is built with OQS_MINIMAL_BUILD limited to Kyber and ML-KEM (see
+ # the liboqs manifest); the other algorithm families are never compiled
+ "vendor/liboqs/liboqs-0.12.0/src/kem/bike",
+ "vendor/liboqs/liboqs-0.12.0/src/kem/classic_mceliece",
+ "vendor/liboqs/liboqs-0.12.0/src/kem/frodokem",
+ "vendor/liboqs/liboqs-0.12.0/src/kem/hqc",
+ "vendor/liboqs/liboqs-0.12.0/src/kem/ntruprime",
+ "vendor/liboqs/liboqs-0.12.0/src/sig/cross",
+ "vendor/liboqs/liboqs-0.12.0/src/sig/dilithium",
+ "vendor/liboqs/liboqs-0.12.0/src/sig/falcon",
+ "vendor/liboqs/liboqs-0.12.0/src/sig/mayo",
+ "vendor/liboqs/liboqs-0.12.0/src/sig/ml_dsa",
+ "vendor/liboqs/liboqs-0.12.0/src/sig/sphincs",
+ "vendor/liboqs/liboqs-0.12.0/src/sig_stfl/lms",
+ "vendor/liboqs/liboqs-0.12.0/src/sig_stfl/xmss",
+]
+
+# The pqcrystals Kyber/ML-KEM reference and AVX2 code carries a one-line
+# notice, "Public Domain (CC0) or Apache 2.0 License", that askalono does
+# not recognise. Same file in every variant; pinned by hash.
+[[licensing.licenses]]
+path = "vendor/liboqs/liboqs-0.12.0/src/kem/kyber/pqcrystals-kyber_kyber1024_avx2/LICENSE"
+sha256sum = "53681bce13fd98721b4cabcd0b6184c6a92d9de813a02536161cc706e4ea9f2e"
+expression = "CC0-1.0 OR Apache-2.0"
+
+[[licensing.licenses]]
+path = "vendor/liboqs/liboqs-0.12.0/src/kem/kyber/pqcrystals-kyber_kyber1024_ref/LICENSE"
+sha256sum = "53681bce13fd98721b4cabcd0b6184c6a92d9de813a02536161cc706e4ea9f2e"
+expression = "CC0-1.0 OR Apache-2.0"
+
+[[licensing.licenses]]
+path = "vendor/liboqs/liboqs-0.12.0/src/kem/kyber/pqcrystals-kyber_kyber512_avx2/LICENSE"
+sha256sum = "53681bce13fd98721b4cabcd0b6184c6a92d9de813a02536161cc706e4ea9f2e"
+expression = "CC0-1.0 OR Apache-2.0"
+
+[[licensing.licenses]]
+path = "vendor/liboqs/liboqs-0.12.0/src/kem/kyber/pqcrystals-kyber_kyber512_ref/LICENSE"
+sha256sum = "53681bce13fd98721b4cabcd0b6184c6a92d9de813a02536161cc706e4ea9f2e"
+expression = "CC0-1.0 OR Apache-2.0"
+
+[[licensing.licenses]]
+path = "vendor/liboqs/liboqs-0.12.0/src/kem/kyber/pqcrystals-kyber_kyber768_avx2/LICENSE"
+sha256sum = "53681bce13fd98721b4cabcd0b6184c6a92d9de813a02536161cc706e4ea9f2e"
+expression = "CC0-1.0 OR Apache-2.0"
+
+[[licensing.licenses]]
+path = "vendor/liboqs/liboqs-0.12.0/src/kem/kyber/pqcrystals-kyber_kyber768_ref/LICENSE"
+sha256sum = "53681bce13fd98721b4cabcd0b6184c6a92d9de813a02536161cc706e4ea9f2e"
+expression = "CC0-1.0 OR Apache-2.0"
+
+[[licensing.licenses]]
+path = "vendor/liboqs/liboqs-0.12.0/src/kem/ml_kem/pqcrystals-kyber-standard_ml-kem-1024_avx2/LICENSE"
+sha256sum = "53681bce13fd98721b4cabcd0b6184c6a92d9de813a02536161cc706e4ea9f2e"
+expression = "CC0-1.0 OR Apache-2.0"
+
+[[licensing.licenses]]
+path = "vendor/liboqs/liboqs-0.12.0/src/kem/ml_kem/pqcrystals-kyber-standard_ml-kem-1024_ref/LICENSE"
+sha256sum = "53681bce13fd98721b4cabcd0b6184c6a92d9de813a02536161cc706e4ea9f2e"
+expression = "CC0-1.0 OR Apache-2.0"
+
+[[licensing.licenses]]
+path = "vendor/liboqs/liboqs-0.12.0/src/kem/ml_kem/pqcrystals-kyber-standard_ml-kem-512_avx2/LICENSE"
+sha256sum = "53681bce13fd98721b4cabcd0b6184c6a92d9de813a02536161cc706e4ea9f2e"
+expression = "CC0-1.0 OR Apache-2.0"
+
+[[licensing.licenses]]
+path = "vendor/liboqs/liboqs-0.12.0/src/kem/ml_kem/pqcrystals-kyber-standard_ml-kem-512_ref/LICENSE"
+sha256sum = "53681bce13fd98721b4cabcd0b6184c6a92d9de813a02536161cc706e4ea9f2e"
+expression = "CC0-1.0 OR Apache-2.0"
+
+[[licensing.licenses]]
+path = "vendor/liboqs/liboqs-0.12.0/src/kem/ml_kem/pqcrystals-kyber-standard_ml-kem-768_avx2/LICENSE"
+sha256sum = "53681bce13fd98721b4cabcd0b6184c6a92d9de813a02536161cc706e4ea9f2e"
+expression = "CC0-1.0 OR Apache-2.0"
+
+[[licensing.licenses]]
+path = "vendor/liboqs/liboqs-0.12.0/src/kem/ml_kem/pqcrystals-kyber-standard_ml-kem-768_ref/LICENSE"
+sha256sum = "53681bce13fd98721b4cabcd0b6184c6a92d9de813a02536161cc706e4ea9f2e"
+expression = "CC0-1.0 OR Apache-2.0"
diff --git a/series b/series
deleted file mode 100644
index e1b4b30..0000000
--- a/series
+++ /dev/null
@@ -1,2 +0,0 @@
-cachelib-fix-DeviceTest-FDP.diff
-cachelib-disable-binary_trace_gen.diff
diff --git a/snapshot.sh b/snapshot.sh
new file mode 100755
index 0000000..be64306
--- /dev/null
+++ b/snapshot.sh
@@ -0,0 +1,22 @@
+#!/bin/sh
+# Print the %global lines for building a snapshot of CacheLib: the weekly tag
+# it is based on, the full commit, and the commit's distance from the tag.
+# The spec turns them into Version <major>.<tag>^<distance>.<shortcommit>, so several
+# snapshots between two tags order correctly. This uses the GitHub API (gh,
+# logged in), no clone needed; from a clone of any forge, git describe gives
+# all three values at once:
+# git describe --tags --match 'v20??.??.??.??' <ref> # v2026.09.14.00-38-gee4c153
+# git rev-parse <ref>
+# ./snapshot.sh # upstream main
+# ./snapshot.sh <ref> # a branch, tag or commit
+set -eu
+repo=facebook/CacheLib
+ref=${1:-main}
+commit=$(gh api "repos/$repo/commits/$ref" --jq .sha)
+# weekly tags are vYYYY.MM.DD.NN; the dotted glob keeps out old-style vYYYYMMDD tags
+tag=$(git ls-remote --tags --sort=-v:refname "https://github.com/$repo" 'refs/tags/v20??.??.??.??' | head -1 | sed 's|.*refs/tags/||')
+commits=$(gh api "repos/$repo/compare/$tag...$commit" --jq .ahead_by)
+echo "# $commits commits since $tag"
+echo "%global basetag $tag"
+echo "%global commit $commit"
+echo "%global commits $commits"
diff --git a/sources b/sources
index 6d89fce..6192156 100644
--- a/sources
+++ b/sources
@@ -1 +1,2 @@
-SHA512 (cachelib-2025.02.03.00.tar.gz) = 439e4941ed0ab42916342d8e702c31def0ae36ef52153ebac9d6b8bb26e9a9cef677ba1352ec5ffb4b962db8cca54151cde534c54e4427df2820a63ffb862ecd
+SHA512 (cachelib-19.2026.09.14.00^38.ee4c153.tar.gz) = 81937b719d32c01e5b9ca1e191020395551f0bfc30aafef6f1ec254ae7d469bac40b16f6fea13c4460985502e28e8fae9d913c7f5da87c24dabbfbd90825df96
+SHA512 (cachelib-19.2026.09.14.00^38.ee4c153-vendor.tar.xz) = f26920c0d9069ef78fddc2775a2a0ea82bd45f4104570d32d8ceb0b79d50ea8e5facff8d1f3847e58eeb5a1397ceee453b818bd2ac288e369b8023307f062115
diff --git a/vendor.sh b/vendor.sh
new file mode 100755
index 0000000..e7c884b
--- /dev/null
+++ b/vendor.sh
@@ -0,0 +1,32 @@
+#!/bin/sh
+# Produce Source1, the tarball of getdeps-vendored dependencies, for the
+# Source0 the spec currently references. Nothing here is specific to cachelib
+# beyond the spec it reads. getdeps vendors whatever it cannot
+# take from installed packages, so for a minimal tarball first install the
+# packages the build will have (getdeps.py --allow-system-packages
+# install-system-deps --recursive cachelib, from the unpacked source; the
+# spec's BuildRequires are generated, so dnf builddep cannot see them). A
+# tarball made with fewer packages installed still works, it is only larger.
+set -eu
+# usage: vendor.sh [package.spec] (defaults to the single spec in the cwd)
+spec=${1:-$(ls ./*.spec)}
+name=$(rpmspec -q --srpm --qf '%{name}\n' "$spec")
+version=$(rpmspec -q --srpm --qf '%{version}\n' "$spec")
+spectool -g -s 0 "$spec"
+source0=$(spectool -S -s 0 "$spec" | awk '{print $2}')
+# on disk, not tmpfs: the extracted source plus getdeps' scratch space run to
+# gigabytes, and getdeps defaults its scratch dir to /tmp outside $tmp
+tmp=$(mktemp -d -p "${TMPDIR:-/var/tmp}")
+trap 'rm -rf "$tmp"' EXIT
+tar xf "$(basename "$source0")" -C "$tmp"
+srcdir=$(find "$tmp" -mindepth 1 -maxdepth 1 -type d)
+# the spec's patches may change what getdeps takes from the system; those
+# touching the vendored trees themselves cannot apply yet and are skipped
+for p in $(spectool -P "$spec" | awk '{print $2}'); do
+ grep -q '^+++ b/vendor/' "$p" && continue
+ patch -d "$srcdir" -p1 --quiet < "$p"
+done
+python3 "$srcdir/build/fbcode_builder/getdeps.py" --allow-system-packages \
+ --scratch-path "$tmp/scratch" vendor --no-tests --output-dir "$tmp/vendor" "${GETDEPS_PROJECT:-$name}"
+tar -C "$tmp" -cJf "$name-$version-vendor.tar.xz" vendor
+echo "wrote $name-$version-vendor.tar.xz"
^ permalink raw reply related [flat|nested] only message in thread
only message in thread, other threads:[~2026-09-18 20:43 UTC | newest]
Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2026-09-18 20:43 [rpms/cachelib] f44: Build with getdeps and vendored dependencies via %getdeps_* macros Michel Lind
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox