xref: /aosp_15_r20/system/vold/Keystore.h (revision f40fafd4c6c2594924d919feffc1a1fd6e3b30f3)
1*f40fafd4SAndroid Build Coastguard Worker /*
2*f40fafd4SAndroid Build Coastguard Worker  * Copyright (C) 2016 The Android Open Source Project
3*f40fafd4SAndroid Build Coastguard Worker  *
4*f40fafd4SAndroid Build Coastguard Worker  * Licensed under the Apache License, Version 2.0 (the "License");
5*f40fafd4SAndroid Build Coastguard Worker  * you may not use this file except in compliance with the License.
6*f40fafd4SAndroid Build Coastguard Worker  * You may obtain a copy of the License at
7*f40fafd4SAndroid Build Coastguard Worker  *
8*f40fafd4SAndroid Build Coastguard Worker  *      http://www.apache.org/licenses/LICENSE-2.0
9*f40fafd4SAndroid Build Coastguard Worker  *
10*f40fafd4SAndroid Build Coastguard Worker  * Unless required by applicable law or agreed to in writing, software
11*f40fafd4SAndroid Build Coastguard Worker  * distributed under the License is distributed on an "AS IS" BASIS,
12*f40fafd4SAndroid Build Coastguard Worker  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13*f40fafd4SAndroid Build Coastguard Worker  * See the License for the specific language governing permissions and
14*f40fafd4SAndroid Build Coastguard Worker  * limitations under the License.
15*f40fafd4SAndroid Build Coastguard Worker  */
16*f40fafd4SAndroid Build Coastguard Worker #ifndef ANDROID_VOLD_KEYSTORE_H
17*f40fafd4SAndroid Build Coastguard Worker #define ANDROID_VOLD_KEYSTORE_H
18*f40fafd4SAndroid Build Coastguard Worker 
19*f40fafd4SAndroid Build Coastguard Worker #include "KeyBuffer.h"
20*f40fafd4SAndroid Build Coastguard Worker 
21*f40fafd4SAndroid Build Coastguard Worker #include <memory>
22*f40fafd4SAndroid Build Coastguard Worker #include <string>
23*f40fafd4SAndroid Build Coastguard Worker #include <utility>
24*f40fafd4SAndroid Build Coastguard Worker 
25*f40fafd4SAndroid Build Coastguard Worker #include <android-base/macros.h>
26*f40fafd4SAndroid Build Coastguard Worker #include <keymint_support/authorization_set.h>
27*f40fafd4SAndroid Build Coastguard Worker #include <keymint_support/keymint_tags.h>
28*f40fafd4SAndroid Build Coastguard Worker 
29*f40fafd4SAndroid Build Coastguard Worker #include <aidl/android/hardware/security/keymint/ErrorCode.h>
30*f40fafd4SAndroid Build Coastguard Worker #include <aidl/android/system/keystore2/IKeystoreService.h>
31*f40fafd4SAndroid Build Coastguard Worker #include <android/binder_manager.h>
32*f40fafd4SAndroid Build Coastguard Worker 
33*f40fafd4SAndroid Build Coastguard Worker namespace android {
34*f40fafd4SAndroid Build Coastguard Worker namespace vold {
35*f40fafd4SAndroid Build Coastguard Worker 
36*f40fafd4SAndroid Build Coastguard Worker namespace ks2 = ::aidl::android::system::keystore2;
37*f40fafd4SAndroid Build Coastguard Worker namespace km = ::aidl::android::hardware::security::keymint;
38*f40fafd4SAndroid Build Coastguard Worker 
39*f40fafd4SAndroid Build Coastguard Worker // C++ wrappers to the Keystore2 AIDL interface.
40*f40fafd4SAndroid Build Coastguard Worker // This is tailored to the needs of KeyStorage, but could be extended to be
41*f40fafd4SAndroid Build Coastguard Worker // a more general interface.
42*f40fafd4SAndroid Build Coastguard Worker 
43*f40fafd4SAndroid Build Coastguard Worker // Wrapper for a Keystore2 operation handle representing an
44*f40fafd4SAndroid Build Coastguard Worker // ongoing Keystore2 operation.  Aborts the operation
45*f40fafd4SAndroid Build Coastguard Worker // in the destructor if it is unfinished. Methods log failures
46*f40fafd4SAndroid Build Coastguard Worker // to LOG(ERROR).
47*f40fafd4SAndroid Build Coastguard Worker class KeystoreOperation {
48*f40fafd4SAndroid Build Coastguard Worker   public:
49*f40fafd4SAndroid Build Coastguard Worker     ~KeystoreOperation();
50*f40fafd4SAndroid Build Coastguard Worker     // Is this instance valid? This is false if creation fails, and becomes
51*f40fafd4SAndroid Build Coastguard Worker     // false on finish or if an update fails.
52*f40fafd4SAndroid Build Coastguard Worker     explicit operator bool() const { return (bool)ks2Operation; }
getErrorCode()53*f40fafd4SAndroid Build Coastguard Worker     km::ErrorCode getErrorCode() const { return errorCode; }
getUpgradedBlob()54*f40fafd4SAndroid Build Coastguard Worker     std::optional<std::string> getUpgradedBlob() const { return upgradedBlob; }
55*f40fafd4SAndroid Build Coastguard Worker     // Call "update" repeatedly until all of the input is consumed, and
56*f40fafd4SAndroid Build Coastguard Worker     // concatenate the output. Return true on success.
57*f40fafd4SAndroid Build Coastguard Worker     template <class TI, class TO>
updateCompletely(TI & input,TO * output)58*f40fafd4SAndroid Build Coastguard Worker     bool updateCompletely(TI& input, TO* output) {
59*f40fafd4SAndroid Build Coastguard Worker         if (output) output->clear();
60*f40fafd4SAndroid Build Coastguard Worker         return updateCompletely(input.data(), input.size(), [&](const char* b, size_t n) {
61*f40fafd4SAndroid Build Coastguard Worker             if (output) std::copy(b, b + n, std::back_inserter(*output));
62*f40fafd4SAndroid Build Coastguard Worker         });
63*f40fafd4SAndroid Build Coastguard Worker     }
64*f40fafd4SAndroid Build Coastguard Worker 
65*f40fafd4SAndroid Build Coastguard Worker     // Finish and write the output to this string, unless pointer is null.
66*f40fafd4SAndroid Build Coastguard Worker     bool finish(std::string* output);
67*f40fafd4SAndroid Build Coastguard Worker     // Move constructor
KeystoreOperation(KeystoreOperation && rhs)68*f40fafd4SAndroid Build Coastguard Worker     KeystoreOperation(KeystoreOperation&& rhs) { *this = std::move(rhs); }
69*f40fafd4SAndroid Build Coastguard Worker     // Construct an object in an error state for error returns
KeystoreOperation()70*f40fafd4SAndroid Build Coastguard Worker     KeystoreOperation() { errorCode = km::ErrorCode::UNKNOWN_ERROR; }
71*f40fafd4SAndroid Build Coastguard Worker     // Move Assignment
72*f40fafd4SAndroid Build Coastguard Worker     KeystoreOperation& operator=(KeystoreOperation&& rhs) {
73*f40fafd4SAndroid Build Coastguard Worker         ks2Operation = rhs.ks2Operation;
74*f40fafd4SAndroid Build Coastguard Worker         rhs.ks2Operation = nullptr;
75*f40fafd4SAndroid Build Coastguard Worker 
76*f40fafd4SAndroid Build Coastguard Worker         upgradedBlob = rhs.upgradedBlob;
77*f40fafd4SAndroid Build Coastguard Worker         rhs.upgradedBlob = std::nullopt;
78*f40fafd4SAndroid Build Coastguard Worker 
79*f40fafd4SAndroid Build Coastguard Worker         errorCode = rhs.errorCode;
80*f40fafd4SAndroid Build Coastguard Worker         rhs.errorCode = km::ErrorCode::UNKNOWN_ERROR;
81*f40fafd4SAndroid Build Coastguard Worker 
82*f40fafd4SAndroid Build Coastguard Worker         return *this;
83*f40fafd4SAndroid Build Coastguard Worker     }
84*f40fafd4SAndroid Build Coastguard Worker 
85*f40fafd4SAndroid Build Coastguard Worker   private:
KeystoreOperation(std::shared_ptr<ks2::IKeystoreOperation> ks2Op,std::optional<std::vector<uint8_t>> blob)86*f40fafd4SAndroid Build Coastguard Worker     KeystoreOperation(std::shared_ptr<ks2::IKeystoreOperation> ks2Op,
87*f40fafd4SAndroid Build Coastguard Worker                       std::optional<std::vector<uint8_t>> blob)
88*f40fafd4SAndroid Build Coastguard Worker         : ks2Operation{ks2Op}, errorCode{km::ErrorCode::OK} {
89*f40fafd4SAndroid Build Coastguard Worker         if (blob)
90*f40fafd4SAndroid Build Coastguard Worker             upgradedBlob = std::optional(std::string(blob->begin(), blob->end()));
91*f40fafd4SAndroid Build Coastguard Worker         else
92*f40fafd4SAndroid Build Coastguard Worker             upgradedBlob = std::nullopt;
93*f40fafd4SAndroid Build Coastguard Worker     }
94*f40fafd4SAndroid Build Coastguard Worker 
KeystoreOperation(km::ErrorCode errCode)95*f40fafd4SAndroid Build Coastguard Worker     KeystoreOperation(km::ErrorCode errCode) : errorCode{errCode} {}
96*f40fafd4SAndroid Build Coastguard Worker 
97*f40fafd4SAndroid Build Coastguard Worker     bool updateCompletely(const char* input, size_t inputLen,
98*f40fafd4SAndroid Build Coastguard Worker                           const std::function<void(const char*, size_t)> consumer);
99*f40fafd4SAndroid Build Coastguard Worker 
100*f40fafd4SAndroid Build Coastguard Worker     std::shared_ptr<ks2::IKeystoreOperation> ks2Operation;
101*f40fafd4SAndroid Build Coastguard Worker     std::optional<std::string> upgradedBlob;
102*f40fafd4SAndroid Build Coastguard Worker     km::ErrorCode errorCode;
103*f40fafd4SAndroid Build Coastguard Worker     DISALLOW_COPY_AND_ASSIGN(KeystoreOperation);
104*f40fafd4SAndroid Build Coastguard Worker     friend class Keystore;
105*f40fafd4SAndroid Build Coastguard Worker };
106*f40fafd4SAndroid Build Coastguard Worker 
107*f40fafd4SAndroid Build Coastguard Worker // Wrapper for keystore2 methods that vold uses.
108*f40fafd4SAndroid Build Coastguard Worker class Keystore {
109*f40fafd4SAndroid Build Coastguard Worker   public:
110*f40fafd4SAndroid Build Coastguard Worker     Keystore();
111*f40fafd4SAndroid Build Coastguard Worker     // false if we failed to get a keystore2 security level.
112*f40fafd4SAndroid Build Coastguard Worker     explicit operator bool() { return (bool)securityLevel; }
113*f40fafd4SAndroid Build Coastguard Worker     // Generate a key using keystore2 from the given params.
114*f40fafd4SAndroid Build Coastguard Worker     bool generateKey(const km::AuthorizationSet& inParams, std::string* key);
115*f40fafd4SAndroid Build Coastguard Worker     // Exports a keystore2 key with STORAGE_KEY tag wrapped with a per-boot ephemeral key
116*f40fafd4SAndroid Build Coastguard Worker     bool exportKey(const KeyBuffer& ksKey, std::string* key);
117*f40fafd4SAndroid Build Coastguard Worker     // If supported, permanently delete a key from the keymint device it belongs to.
118*f40fafd4SAndroid Build Coastguard Worker     bool deleteKey(const std::string& key);
119*f40fafd4SAndroid Build Coastguard Worker     // Begin a new cryptographic operation, collecting output parameters if pointer is non-null
120*f40fafd4SAndroid Build Coastguard Worker     // If the key was upgraded as a result of a call to this method, the returned KeystoreOperation
121*f40fafd4SAndroid Build Coastguard Worker     // also stores the upgraded key blob.
122*f40fafd4SAndroid Build Coastguard Worker     KeystoreOperation begin(const std::string& key, const km::AuthorizationSet& inParams,
123*f40fafd4SAndroid Build Coastguard Worker                             km::AuthorizationSet* outParams);
124*f40fafd4SAndroid Build Coastguard Worker 
125*f40fafd4SAndroid Build Coastguard Worker     // Tell all Keymint devices that early boot has ended and early boot-only keys can no longer
126*f40fafd4SAndroid Build Coastguard Worker     // be created or used.
127*f40fafd4SAndroid Build Coastguard Worker     static void earlyBootEnded();
128*f40fafd4SAndroid Build Coastguard Worker 
129*f40fafd4SAndroid Build Coastguard Worker     // Tell all Keymint devices to delete all rollback-protected keys.
130*f40fafd4SAndroid Build Coastguard Worker     static void deleteAllKeys();
131*f40fafd4SAndroid Build Coastguard Worker 
132*f40fafd4SAndroid Build Coastguard Worker   private:
133*f40fafd4SAndroid Build Coastguard Worker     std::shared_ptr<ks2::IKeystoreSecurityLevel> securityLevel;
134*f40fafd4SAndroid Build Coastguard Worker     DISALLOW_COPY_AND_ASSIGN(Keystore);
135*f40fafd4SAndroid Build Coastguard Worker };
136*f40fafd4SAndroid Build Coastguard Worker 
137*f40fafd4SAndroid Build Coastguard Worker }  // namespace vold
138*f40fafd4SAndroid Build Coastguard Worker }  // namespace android
139*f40fafd4SAndroid Build Coastguard Worker 
140*f40fafd4SAndroid Build Coastguard Worker #endif
141