Commit eb962a78b5 for openssl.org

commit eb962a78b5cda85b9ff80d2bd5981021a1a7b9cc
Author: Alexandr Nedvedicky <sashan@openssl.org>
Date:   Thu Feb 12 11:10:03 2026 +0100

    remove all atexit() tests in shlibloadtest

    The shlibloadtest used atexit() handler to verify
    library pinning works as expected. The libcrypto
    no longer arms atexit handler which also used to
    fire upon shlib unload. We can not use the atexit
    mechansim to test shared library pinning.

    If the shlibload test does not crash on exit, then
    library pinning must work.

    Fixes openssl/project#1869

    Reviewed-by: Neil Horman <nhorman@openssl.org>
    Reviewed-by: Tomas Mraz <tomas@openssl.org>
    MergeDate: Fri Feb 13 15:15:04 2026
    (Merged from https://github.com/openssl/openssl/pull/29987)

diff --git a/test/recipes/90-test_shlibload.t b/test/recipes/90-test_shlibload.t
index 7a717dd92a..61721bdd77 100644
--- a/test/recipes/90-test_shlibload.t
+++ b/test/recipes/90-test_shlibload.t
@@ -23,47 +23,20 @@ plan skip_all => "Test is disabled on AIX" if config('target') =~ m|^aix|;
 plan skip_all => "Test is disabled on NonStop" if config('target') =~ m|^nonstop|;
 plan skip_all => "Test only supported in a dso build" if disabled("dso");
 plan skip_all => "Test is disabled in an address sanitizer build" unless disabled("asan");
-plan skip_all => "Test is disabled in no-atexit build" if disabled("atexit");

-plan tests => 8;
+plan tests => 4;

 my $libcrypto = platform->sharedlib('libcrypto');
 my $libssl = platform->sharedlib('libssl');
-my $atexit_outfile;

-$atexit_outfile = 'atexit-cryptofirst.txt';
-1 while unlink $atexit_outfile;
-ok(run(test(["shlibloadtest", "-crypto_first", $libcrypto, $libssl, $atexit_outfile])),
-   "running shlibloadtest -crypto_first $atexit_outfile");
-ok(check_atexit($atexit_outfile));
+ok(run(test(["shlibloadtest", "-crypto_first", $libcrypto, $libssl])),
+   "running shlibloadtest -crypto_first");

-$atexit_outfile = 'atexit-sslfirst.txt';
-1 while unlink $atexit_outfile;
-ok(run(test(["shlibloadtest", "-ssl_first", $libcrypto, $libssl, $atexit_outfile])),
-   "running shlibloadtest -ssl_first $atexit_outfile");
-ok(check_atexit($atexit_outfile));
+ok(run(test(["shlibloadtest", "-ssl_first", $libcrypto, $libssl])),
+   "running shlibloadtest -ssl_first");

-$atexit_outfile = 'atexit-justcrypto.txt';
-1 while unlink $atexit_outfile;
-ok(run(test(["shlibloadtest", "-just_crypto", $libcrypto, $libssl, $atexit_outfile])),
-   "running shlibloadtest -just_crypto $atexit_outfile");
-ok(check_atexit($atexit_outfile));
+ok(run(test(["shlibloadtest", "-just_crypto", $libcrypto, $libssl])),
+   "running shlibloadtest -just_crypto");

-$atexit_outfile = 'atexit-dsoref.txt';
-1 while unlink $atexit_outfile;
-ok(run(test(["shlibloadtest", "-dso_ref", $libcrypto, $libssl, $atexit_outfile])),
-   "running shlibloadtest -dso_ref $atexit_outfile");
-ok(check_atexit($atexit_outfile));
-
-sub check_atexit {
-    my $filename = shift;
-
-    open my $fh, '<', $filename;
-    return 0 unless defined $fh;
-
-    my $data = <$fh>;
-
-    return 1 if (defined $data && $data =~ m/atexit\(\) run/);
-
-    return 0;
-}
+ok(run(test(["shlibloadtest", "-dso_ref", $libcrypto, $libssl])),
+   "running shlibloadtest -dso_ref");
diff --git a/test/shlibloadtest.c b/test/shlibloadtest.c
index d1b8628877..c09610cc92 100644
--- a/test/shlibloadtest.c
+++ b/test/shlibloadtest.c
@@ -38,24 +38,9 @@ typedef enum test_types_en {
 static TEST_TYPE test_type;
 static const char *path_crypto;
 static const char *path_ssl;
-static const char *path_atexit;

 #ifdef SD_INIT

-static int atexit_handler_done = 0;
-
-static void atexit_handler(void)
-{
-    FILE *atexit_file = fopen(path_atexit, "w");
-
-    if (atexit_file == NULL)
-        return;
-
-    fprintf(atexit_file, "atexit() run\n");
-    fclose(atexit_file);
-    atexit_handler_done++;
-}
-
 static int test_lib(void)
 {
     SD ssllib = SD_INIT;
@@ -143,23 +128,17 @@ static int test_lib(void)
         goto end;
     }

-    if (atexit(atexit_handler) != 0) {
-        fprintf(stderr, "Failed to register atexit handler\n");
-        goto end;
-    }
-
     if (test_type == DSO_REFTEST) {
 #ifdef DSO_DLFCN
         DSO_dsobyaddr_t myDSO_dsobyaddr;
         DSO_free_t myDSO_free;

         /*
-         * This is resembling the code used in ossl_init_base() and
-         * atexit() to block unloading the library after dlclose().
-         * We are not testing this on Windows, because it is done there in a
-         * completely different way. Especially as a call to DSO_dsobyaddr()
-         * will always return an error, because DSO_pathbyaddr() is not
-         * implemented there.
+         * This is resembling the code used in ossl_init_base() to block
+         * unloading the library after dlclose().  We are not testing this on
+         * Windows, because it is done there in a completely different way.
+         * Especially as a call to DSO_dsobyaddr() will always return an error,
+         * because DSO_pathbyaddr() is not implemented there.
          */
         if (!sd_sym(cryptolib, "DSO_dsobyaddr", &symbols[0].sym)
             || !sd_sym(cryptolib, "DSO_free", &symbols[1].sym)) {
@@ -197,23 +176,6 @@ static int test_lib(void)
         ssllib = SD_INIT;
     }

-#if defined(OPENSSL_NO_PINSHARED) \
-    && defined(__GLIBC__)         \
-    && defined(__GLIBC_PREREQ)    \
-    && defined(OPENSSL_SYS_LINUX)
-#if __GLIBC_PREREQ(2, 3)
-    /*
-     * If we didn't pin the so then we are hopefully on a platform that supports
-     * running atexit() on so unload. If not we might crash. We know this is
-     * true on linux since glibc 2.2.3
-     */
-    if (atexit_handler_done != 1) {
-        fprintf(stderr, "atexit() handler did not run\n");
-        goto end;
-    }
-#endif
-#endif
-
     result = 1;
 end:
     if (cryptolib != SD_INIT)
@@ -233,7 +195,7 @@ int main(int argc, char *argv[])
 {
     const char *p;

-    if (argc != 5) {
+    if (argc != 4) {
         fprintf(stderr, "Incorrect number of arguments\n");
         return 1;
     }
@@ -254,7 +216,6 @@ int main(int argc, char *argv[])
     }
     path_crypto = argv[2];
     path_ssl = argv[3];
-    path_atexit = argv[4];
     if (path_crypto == NULL || path_ssl == NULL) {
         fprintf(stderr, "Invalid libcrypto/libssl path\n");
         return 1;