If I have correctly understood the FAQ about the OPENSSL_applink. It applies only in the Win32 version:

    * If OPENSSL_USE_APPLINK is not defined at the compilation stage of
      OpenSSL, the snippet applink.c is not mandatory BUT I have to
      build a debug and a release version of OpenSSL DLLs.
      I don't know why but it seems to be related with FILE functions.
    * If OPENSSL_USE_APPLINK is defined, the snippet applink.c is
      mandatory in an application and the release version of OpenSSL
      DLLs can be used in any case.

Well, OPENSSL_USE_APPLINK is always defined in Win32 builds. applink.c is required if a) application uses certain subset of OpenSSL API and b) application and DLL are compiled with different flags, debug vs. non-debug, or different compilers.

The OPENSSL_applink function is searched only in the application module,

Which is why it's called *app*link.

so it's necessary to add or include the snippet with any application that use OpensSSL.

It should be noted that applink was introduced primarily in order to facilitate migration for legacy applications. New code should rather abstain from using above mentioned subset of OpenSSL API (whatever using FILE *) and simply avoid applink.

In the case of a unique DLL that use OpenSSL, what do think about the following way to define and use OPENSSL_applink (I've tried this with success with 0.9.8.n but implement it in a brute force manner) :

ms/uplink.h
Added the following declaration next to extern void *OPENSSL_UplinkTable[]; :

    extern void OPENSSL_SetApplink( void** (*foo)() );

ms/uplink.c
Added :

    static    void** (*applink_foo)() = NULL;
    void OPENSSL_SetApplink( void** (*foo)() )
    {
        applink_foo = foo;
    }

and modifiy OPENSSL_Uplink(). Priority is given to OPENSSL_Applink if it's found in the current module. If it's not, if applink_foo is not set, give the error message else use applink_foo.

            applink=(void**(*)())GetProcAddress(h,"OPENSSL_Applink");
            if (applink==NULL)
            {    if( applink_foo == NULL )
                {    apphandle=(HMODULE)-1;
                    _tcscpy (msg+len,_T("no OPENSSL_Applink"));
                    break;
                }
                else applink = applink_foo;
            }

In the user DLL that uses OpenSSL, add or include the snippet applink.c in the DLL project and Add the following declaration (I don't know where to put it in OpenSSL include files)

        extern "C" {
            void **OPENSSL_Applink();
            void OPENSSL_SetApplink( void **(*foo)() );
            };

and add the following in the initialisation function or dllmain:

        CRYPTO_malloc_init();
        OPENSSL_SetApplink( OPENSSL_Applink );
        SSL_library_init(); /* load encryption & hash algorithms for SSL
*/ SSL_load_error_strings(); /* load the error strings for good
    error reporting */

This way, OPENSSL_Applink can be used inside DLLs, but I'm not sure of implications so I need your advices.

As there is no way to ensure/know that there is only one DLL using OpenSSL, it's not appropriate for main stream. If it helps to develop and debug your application, there is nothing that prevents you from doing so.

I want to point to your attention that the call ERR_print_errors_fp( stderr ) from the user DLL lead to an Access violation (0xc0000005). This situation arises in mixing debug and release versions and is probably due to the fact that ERR_print_errors_fp( stderr ) calls fwrite directly. UP_fwrite should be used instead.

This is bug. It was fixed in development branch and is not present in 1.0.0. http://cvs.openssl.org/chngview?cn=19607 is committed even to 0.9.8. A.
______________________________________________________________________
OpenSSL Project                                 http://www.openssl.org
Development Mailing List                       openssl-dev@openssl.org
Automated List Manager                           majord...@openssl.org

Reply via email to