1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- 2 * 3 * This Source Code Form is subject to the terms of the Mozilla Public 4 * License, v. 2.0. If a copy of the MPL was not distributed with this 5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 6 7 // Generic key store implementation for platforms that we don't support with OS 8 // specific implementations. 9 10 #ifndef OSKeyStore_h 11 #define OSKeyStore_h 12 13 #include "nsCOMPtr.h" 14 #include "nsIOSKeyStore.h" 15 #include "nsString.h" 16 #include "ScopedNSSTypes.h" 17 18 #include <memory> 19 #include <vector> 20 21 class AbstractOSKeyStore { 22 public: 23 // Retrieve a secret with the given label. 24 virtual nsresult RetrieveSecret(const nsACString& aLabel, 25 /* out */ nsACString& aSecret) = 0; 26 // Store a new secret with the given label. 27 virtual nsresult StoreSecret(const nsACString& secret, 28 const nsACString& label) = 0; 29 // Delete the secret with the given label. 30 virtual nsresult DeleteSecret(const nsACString& label) = 0; 31 // Lock the key store. 32 virtual nsresult Lock() = 0; 33 // Unlock the key store. 34 virtual nsresult Unlock() = 0; 35 virtual ~AbstractOSKeyStore() = default; 36 37 // Returns true if the secret with the given label is available in the key 38 // store, false otherwise. 39 virtual bool SecretAvailable(const nsACString& label); 40 // Perform encryption or decryption operation with the given secret and input 41 // bytes. The output is written in outBytes. This function can make use of the 42 // AesGcm class to use NSS for encryption and decryption. 43 virtual nsresult EncryptDecrypt(const nsACString& label, 44 const std::vector<uint8_t>& inBytes, 45 std::vector<uint8_t>& outBytes, bool encrypt); 46 GetKeyByteLength()47 size_t GetKeyByteLength() { return mKeyByteLength; } 48 49 protected: 50 /* These helper functions are implemented in OSKeyStore.cpp and implement 51 * common functionality of the abstract key store to encrypt and decrypt. 52 */ 53 nsresult DoCipher(const mozilla::UniquePK11SymKey& aSymKey, 54 const std::vector<uint8_t>& inBytes, 55 std::vector<uint8_t>& outBytes, bool aEncrypt); 56 nsresult BuildAesGcmKey(std::vector<uint8_t> keyBytes, 57 /* out */ mozilla::UniquePK11SymKey& aKey); 58 59 private: 60 const size_t mKeyByteLength = 16; 61 const size_t mIVLength = 12; 62 }; 63 64 #define NS_OSKEYSTORE_CONTRACTID "@mozilla.org/security/oskeystore;1" 65 #define NS_OSKEYSTORE_CID \ 66 { \ 67 0x57972956, 0x5718, 0x42d2, { \ 68 0x80, 0x70, 0xb3, 0xfc, 0x72, 0x21, 0x2e, 0xaf \ 69 } \ 70 } 71 72 nsresult GetPromise(JSContext* aCx, 73 /* out */ RefPtr<mozilla::dom::Promise>& aPromise); 74 75 class OSKeyStore final : public nsIOSKeyStore { 76 public: 77 NS_DECL_THREADSAFE_ISUPPORTS 78 NS_DECL_NSIOSKEYSTORE 79 80 OSKeyStore(); 81 nsresult GenerateSecret(const nsACString& aLabel, 82 /* out */ nsACString& aRecoveryPhrase); 83 nsresult SecretAvailable(const nsACString& aLabel, 84 /* out */ bool* aAvailable); 85 nsresult RecoverSecret(const nsACString& aLabel, 86 const nsACString& aRecoveryPhrase); 87 nsresult DeleteSecret(const nsACString& aLabel); 88 nsresult EncryptBytes(const nsACString& aLabel, 89 const std::vector<uint8_t>& aInBytes, 90 /*out*/ nsACString& aEncryptedBase64Text); 91 nsresult DecryptBytes(const nsACString& aLabel, 92 const nsACString& aEncryptedBase64Text, 93 /*out*/ uint32_t* outLen, 94 /*out*/ uint8_t** outBytes); 95 nsresult Lock(); 96 nsresult Unlock(); 97 98 private: 99 ~OSKeyStore() = default; 100 101 std::unique_ptr<AbstractOSKeyStore> mKs; 102 bool mKsIsNSSKeyStore; 103 const nsCString mLabelPrefix = 104 NS_LITERAL_CSTRING("org.mozilla.nss.keystore."); 105 }; 106 107 #endif // OSKeyStore_h 108