From: Anthony F. <ant...@gm...> - 2013-05-02 16:15:30
|
Greetings! I believe that I'm seeing memory leaks similar to those reported in this message: http://opensc.1086184.n5.nabble.com/engine-pkcs11-libp11-leaking-memory-td4529.html#a32328925 In particular, doing about 1 sign/minute, I'm leaking about 2MB/hr. Valgrind is noisy, but I believe the culprit is here: ==4912== 36,771 (80 direct, 36,691 indirect) bytes in 1 blocks are definitely lost in loss record 164 of 164 ==4912== at 0x4A0887C: malloc (/builddir/build/BUILD/valgrind-3.8.1/coregrind/m_replacemalloc/vg_replace_malloc.c:270) ==4912== by 0x5FA7F52: default_malloc_ex (/openssl-build/crypto/mem.c:79) ==4912== by 0x5FA85E1: CRYPTO_malloc (/openssl-build/crypto/mem.c:308) ==4912== by 0x5ABF641: pkcs11_malloc (/libp11-0.2.8/src/p11_misc.c:26) ==4912== by 0x5AC0AEE: PKCS11_enumerate_slots (/libp11-0.2.8/src/p11_slot.c:61) ==4912== by 0x89F054F: pkcs11_load_key.isra.2 (/engine_pkcs11-0.1.8/src/engine_pkcs11.c:584) ==4912== by 0x89F1AA3: pkcs11_load_private_key (/engine_pkcs11-0.1.8/src/engine_pkcs11.c:811) ==4912== by 0x603CA15: ENGINE_load_private_key (/openssl-build/crypto/engine/eng_pkey.c:122) ==4912== by 0x53CDBA7: Foo::OpenSSL::TokenEngine::getPrivKey(std::string const&) (/home/tony/FoianiLLC/foo/src/crypto/OpenSSLWrappers.cpp:258) ==4912== by 0x53C4249: Foo::CryptoService::signFileIncremental(std::string const&, unsigned long, unsigned long, std::vector<char, std::allocator<char> >&, std::string const&) (/home/tony/FoianiLLC/foo/src/crypto/CryptoService.cpp:440) ==4912== by 0x53C5617: Foo::CryptoService::signFile(std::string const&, unsigned long, std::string const&) (/home/tony/FoianiLLC/foo/src/crypto/CryptoService.cpp:401) ==4912== by 0x4127C4: boost::detail::function::void_function_obj_invoker0<test_main(int, char**)::{lambda()#1}, void>::invoke(boost::detail::function::function_buffer&) (/home/tony/FoianiLLC/foo/src/crypto/CryptoServiceTest.cpp:97) That is, pkcs11_load_key is doing an enumeration over the slots, and that enumeration is never released. The numbers work out about right -- 60 reps/hr * 36KiB/rep is pretty close to my rough estimate of 2MiB/hr. Is it possible to release the enumeration before returning the private key? Or does the private key structure rely on information held in the enumeration? If the latter, do we need to somehow provide a way for the key to release the entire enumeration when the key itself is freed? Best regards, Anthony Foiani p.s. I know that the answer might be "just get the key once, not each time you need to sign something". But for an embedded device that is designed to go months or years without reboots, a memory leak is bad news, even if it's only each time the token is inserted. |