dd0ef3c3d35a1e93a10f672f7886056751c21c3c
[platform/framework/web/crosswalk.git] / src / content / child / webcrypto / nss / util_nss.cc
1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "content/child/webcrypto/nss/util_nss.h"
6
7 #include "base/lazy_instance.h"
8 #include "content/child/webcrypto/crypto_data.h"
9 #include "crypto/nss_util.h"
10 #include "crypto/scoped_nss_types.h"
11
12 #if defined(USE_NSS)
13 #include <dlfcn.h>
14 #include <secoid.h>
15 #endif
16
17 namespace content {
18
19 namespace webcrypto {
20
21 namespace {
22 base::LazyInstance<NssRuntimeSupport>::Leaky g_nss_runtime_support =
23     LAZY_INSTANCE_INITIALIZER;
24 }  // namespace
25
26 // Creates a SECItem for the data in |buffer|. This does NOT make a copy, so
27 // |buffer| should outlive the SECItem.
28 SECItem MakeSECItemForBuffer(const CryptoData& buffer) {
29   SECItem item = {
30       siBuffer,
31       // NSS requires non-const data even though it is just for input.
32       const_cast<unsigned char*>(buffer.bytes()), buffer.byte_length()};
33   return item;
34 }
35
36 CryptoData SECItemToCryptoData(const SECItem& item) {
37   return CryptoData(item.data, item.len);
38 }
39
40 NssRuntimeSupport* NssRuntimeSupport::Get() {
41   return &g_nss_runtime_support.Get();
42 }
43
44 NssRuntimeSupport::NssRuntimeSupport() : internal_slot_does_oaep_(false) {
45 #if !defined(USE_NSS)
46   // Using a bundled version of NSS that is guaranteed to have this symbol.
47   pk11_encrypt_func_ = PK11_Encrypt;
48   pk11_decrypt_func_ = PK11_Decrypt;
49   pk11_pub_encrypt_func_ = PK11_PubEncrypt;
50   pk11_priv_decrypt_func_ = PK11_PrivDecrypt;
51   internal_slot_does_oaep_ = true;
52 #else
53   // Using system NSS libraries and PCKS #11 modules, which may not have the
54   // necessary function (PK11_Encrypt) or mechanism support (CKM_AES_GCM).
55
56   // If PK11_Encrypt() was successfully resolved, then NSS will support
57   // AES-GCM directly. This was introduced in NSS 3.15.
58   pk11_encrypt_func_ = reinterpret_cast<PK11_EncryptDecryptFunction>(
59       dlsym(RTLD_DEFAULT, "PK11_Encrypt"));
60   pk11_decrypt_func_ = reinterpret_cast<PK11_EncryptDecryptFunction>(
61       dlsym(RTLD_DEFAULT, "PK11_Decrypt"));
62
63   // Even though NSS's pk11wrap layer may support
64   // PK11_PubEncrypt/PK11_PubDecrypt (introduced in NSS 3.16.2), it may have
65   // loaded a softoken that does not include OAEP support.
66   pk11_pub_encrypt_func_ = reinterpret_cast<PK11_PubEncryptFunction>(
67       dlsym(RTLD_DEFAULT, "PK11_PubEncrypt"));
68   pk11_priv_decrypt_func_ = reinterpret_cast<PK11_PrivDecryptFunction>(
69       dlsym(RTLD_DEFAULT, "PK11_PrivDecrypt"));
70   if (pk11_priv_decrypt_func_ && pk11_pub_encrypt_func_) {
71     crypto::ScopedPK11Slot slot(PK11_GetInternalKeySlot());
72     internal_slot_does_oaep_ =
73         !!PK11_DoesMechanism(slot.get(), CKM_RSA_PKCS_OAEP);
74   }
75 #endif
76 }
77
78 void PlatformInit() {
79   crypto::EnsureNSSInit();
80 }
81
82 }  // namespace webcrypto
83
84 }  // namespace content