From: Patrick Donnelly Date: Tue, 7 Apr 2026 20:43:56 +0000 (-0400) Subject: libcephsqlite: ensure atexit handlers are registered after openssl X-Git-Url: http://git-server-git.apps.pok.os.sepia.ceph.com/?a=commitdiff_plain;h=7949cd5f12eb7cc0dc85fd1b5c1d795fad1df922;p=ceph.git libcephsqlite: ensure atexit handlers are registered after openssl When the sqlite3 executable encounters an error with .bail=on, it will make a call to exit(). The atexit() handlers will execute in LIFO order. We need to ensure that openssl (before OpenSSL 4.0 [1]) atexit handlers are registered before libcephsqlite. [1] http://github.com/openssl/openssl/commit/31659fe32673a6bd66abf3f8a7d803e81c6ffeed (OpenSSL 4.0 no longer arms `OPENSSL_cleanup()` function as an `atexit(3)`) Fixes: https://tracker.ceph.com/issues/59335 Signed-off-by: Patrick Donnelly --- diff --git a/src/libcephsqlite.cc b/src/libcephsqlite.cc index c386271b4e89..afafe6a0d7b6 100644 --- a/src/libcephsqlite.cc +++ b/src/libcephsqlite.cc @@ -90,6 +90,8 @@ enum { using cctptr = boost::intrusive_ptr; using rsptr = std::shared_ptr; +static void cephsqlite_atexit(); + struct cephsqlite_appdata { ~cephsqlite_appdata() { { @@ -212,12 +214,18 @@ private: lderr(cct) << "cannot connect: " << cpp_strerror(rc) << dendl; return rc; } + /* This **must** occur after OpenSSL registers any atexit handlers (**sigh**). */ + std::call_once(atexit_registered, []() { + std::atexit(cephsqlite_atexit); + }); auto s = _cluster->get_addrs(); ldout(cct, 5) << "completed connection to RADOS with address " << s << dendl; cluster = std::move(_cluster); + return 0; } + std::once_flag atexit_registered; ceph::mutex cluster_mutex = ceph::make_mutex("libcephsqlite");; cctptr cct; rsptr cluster; @@ -925,10 +933,6 @@ LIBCEPHSQLITE_API int sqlite3_cephsqlite_init(sqlite3* db, char** err, const sql } } - if (int rc = std::atexit(cephsqlite_atexit); rc) { - return SQLITE_INTERNAL; - } - if (int rc = sqlite3_auto_extension((void(*)(void))autoreg); rc) { return rc; }