[erlang-bugs] Unloading then reloading crypto.so causes erlang core dump on Solaris 11

Sverker Eriksson sverker.eriksson@REDACTED
Fri Sep 7 11:05:38 CEST 2012


Dave Cottlehuber wrote:
> On 6 September 2012 18:27, Sverker Eriksson
> <sverker.eriksson@REDACTED> wrote:
>   
>> XinFeng Liu wrote:
>>     
>>> Hi,
>>> I'm trying CouchDB (version 1.2) on Solaris 11 Sparc, but running CouchDB
>>> testsuite in browser caused erlang process core dumped. I tried both erlang
>>> 14B04 and 15B01.
>>> After investigation, I found it occurred when couchDB restarted itself.
>>> During restarting, erlang unloaded crypto.so then reloaded it into a
>>> different address, but openssl library libcrypto.so still using the old call
>>> back address of  crypto_alloc() in lib/crypto/c_src/crypto.c. In fact,
>>> crypto_alloc() is shown as a local function from "nm" command.
>>>
>>> The temporary workaround is modifying crypto.c:
>>> replace   CRYPTO_set_mem_functions(crypto_alloc, crypto_realloc,
>>> crypto_free);
>>> to:
>>>              CRYPTO_set_mem_functions(enif_alloc, enif_realloc,
>>> enif_free);
>>>
>>> I'm not sure it is erlang bug or bug of openssl  for solaris, please help
>>> clarify?
>>>
>>>       
>> This is crypto trying to do something which openssl does not support.
>>
>> The workaround you suggested using enif_alloc instead of crypto_alloc seems
>> like a good start if it solves your problem. There are however other
>> callbacks for locking (see CRYPTO_set_locking_callback) that maybe could
>> cause the same kind of problem.
>>
>> The root problem is that openssl does not support "unregistering" of
>> callbacks. The solution is probably some feature that would allow a NIF
>> library to be kept in memory and be reused if/when the erlang module is
>> loaded again.
>>
>>
>>
>>
>> XinFeng Liu wrote:
>>     
>>> I also tried another workaround in lib/crypto/c_src/crypto.c:
>>> add
>>> CRYPTO_set_mem_functions(crypto_alloc, crypto_realloc, crypto_free);
>>> in reload(ErlNifEnv* env, void** priv_data, ERL_NIF_TERM load_info) before
>>> "return 0;"
>>> The couchDB testsuite runs fine.
>>> Is this way O.K.?
>>>
>>>
>>>       
>> This I don't understand at all.
>> reload() in crypto.c should only be called if the module is upgraded, not if
>> it is unloaded and later loaded again.
>>
>> /Sverker, Erlang/OTP
>>     
>
> The CouchDB test suite does init:restart() several times, does that make sense?
>
> A+
> Dave
>   
No, init:restart() should not cause a module upgrade. It should delete 
and purge the module and then load it again (when its first called upon) 
as if it had never been loaded before.

@XinFeng Liu: Are you really sure that reload() is called? If so, then I would be interested in how it got there. Put a call to abort() in reload() and inspect the core dump for example.


/Sverker, Erlang/OTP





More information about the erlang-bugs mailing list