Hi,

Let us see into int_ctx_new() function in the pmeth_lib.c file. We see there

    ret->engine = e;

for EVP_PKEY_CTX context ret without any attempt to increase engine references. This function is called from EVP_PKEY_CTX_new(). But in other function EVP_PKEY_CTX_free() we found the code:

#ifndef OPENSSL_NO_ENGINE
    if(ctx->engine)
        /* The EVP_PKEY_CTX we used belongs to an ENGINE, release the
         * functional reference we held for this reason. */
        ENGINE_finish(ctx->engine);
#endif

ENGINE_finish() decreases engine reference counter. As a result creating and freeing context iteratively may lead to negative engine reference counter and prematurely free the engine. For example, using PKCS7_verify() more than 5 times in our test makes engine free and leads to crash.

Replacing the line

    ret->engine = e;

in int_ctx_new() function with following lines

    ret->engine = e;
#ifndef OPENSSL_NO_ENGINE
    if (e)
        ENGINE_init(e);
#endif

fixes the problem.

Valery Blazhnov
LISSI ltd.

______________________________________________________________________
OpenSSL Project                                 http://www.openssl.org
Development Mailing List                       [email protected]
Automated List Manager                           [email protected]

Reply via email to