[openssl-users] [openssl-user] How to use memory debug functions (CRYPTO_mem_leaks) in OpenSSL 1.1.0 (pre6 release) ?

Wei, Changzheng changzheng.wei at intel.com
Thu Aug 25 01:04:54 UTC 2016


I used memory debug functions (such as CRYPTO_mem_leaks/CRYPTO_mem_leaks_fp) to check the memory leak. In the old version, such as openssl-1.0.2d, I can call CRYPTO_mem_leaks() functions any time in my application to dump the memory information. But in OpenSSL-1.1.0, it will fail due to the new CRYPTO_mem_leaks() introduce the RUN_ONCE() function to initialize the memory lock and cleanup the locks at the end of the function.
My application is a multi-process application, parent process will perform the memory lock initialization once, so in child process the RUN_ONCE() function will never be performed. After I perform CRYPTO_mem_leaks(), at the end of this function, the malloc_lock will be freed, so it will cause unexpected coredump if I insert CRYPTO_mem_leaks() function in my code. What I can do now is register this function to atexit(), when the process exit, CRYPTO_mem_leaks() will be performed to dump the memory leakage information.
Is this behavior expected?

int CRYPTO_mem_leaks(BIO *b)
{
    MEM_LEAK ml;

    /*
     * OPENSSL_cleanup() will free the ex_data locks so we can't have any
     * ex_data hanging around
     */
    bio_free_ex_data(b);

    /* Ensure all resources are released */
    OPENSSL_cleanup();

    if (!RUN_ONCE(&memdbg_init, do_memdbg_init))
        return -1;

    CRYPTO_mem_ctrl(CRYPTO_MEM_CHECK_DISABLE);

    ml.bio = b;
    ml.bytes = 0;
    ml.chunks = 0;
    if (mh != NULL)
        lh_MEM_doall_MEM_LEAK(mh, print_leak, &ml);

    if (ml.chunks != 0) {
        BIO_printf(b, "%ld bytes leaked in %d chunks\n", ml.bytes, ml.chunks);
    } else {
        /*
         * Make sure that, if we found no leaks, memory-leak debugging itself
         * does not introduce memory leaks (which might irritate external
         * debugging tools). (When someone enables leak checking, but does not
         * call this function, we declare it to be their fault.)
         */
        int old_mh_mode;

        CRYPTO_THREAD_write_lock(malloc_lock);

        /*
         * avoid deadlock when lh_free() uses CRYPTO_mem_debug_free(), which uses
         * mem_check_on
         */
        old_mh_mode = mh_mode;
        mh_mode = CRYPTO_MEM_CHECK_OFF;

        lh_MEM_free(mh);
        mh = NULL;

        mh_mode = old_mh_mode;
        CRYPTO_THREAD_unlock(malloc_lock);
    }
    CRYPTO_mem_ctrl(CRYPTO_MEM_CHECK_OFF);

    /* Clean up locks etc */
    CRYPTO_THREAD_cleanup_local(&appinfokey);
    CRYPTO_THREAD_lock_free(malloc_lock);
    CRYPTO_THREAD_lock_free(long_malloc_lock);
    malloc_lock = NULL;
    long_malloc_lock = NULL;

    return ml.chunks == 0 ? 1 : 0;
}


-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mta.openssl.org/pipermail/openssl-users/attachments/20160825/45a32167/attachment-0001.html>


More information about the openssl-users mailing list