blob: fbd52b4d13b35c9e775e99af5aed3e040033a408 [file] [log] [blame]
Janis Danisevskisff3d7f42018-10-08 07:15:09 -07001/*
2**
3** Copyright 2018, The Android Open Source Project
4**
5** Licensed under the Apache License, Version 2.0 (the "License");
6** you may not use this file except in compliance with the License.
7** You may obtain a copy of the License at
8**
9** http://www.apache.org/licenses/LICENSE-2.0
10**
11** Unless required by applicable law or agreed to in writing, software
12** distributed under the License is distributed on an "AS IS" BASIS,
13** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14** See the License for the specific language governing permissions and
15** limitations under the License.
16*/
17
18#ifndef KEYSTORE_KEYMASTER_WORKER_H_
19#define KEYSTORE_KEYMASTER_WORKER_H_
20
21#include <condition_variable>
22#include <functional>
Shawn Willdena97aea42020-01-16 13:27:49 -070023#include <keymasterV4_1/Keymaster.h>
Janis Danisevskisff3d7f42018-10-08 07:15:09 -070024#include <memory>
25#include <mutex>
26#include <optional>
27#include <queue>
28#include <thread>
29#include <tuple>
30
31#include <keystore/ExportResult.h>
32#include <keystore/KeyCharacteristics.h>
33#include <keystore/KeymasterBlob.h>
34#include <keystore/OperationResult.h>
Shawn Willdena97aea42020-01-16 13:27:49 -070035#include <keystore/keymaster_types.h>
Janis Danisevskisff3d7f42018-10-08 07:15:09 -070036#include <keystore/keystore_return_types.h>
37
38#include "blob.h"
39#include "operation.h"
40
41namespace keystore {
42
43using android::sp;
44using ::android::hardware::hidl_vec;
45using ::android::hardware::Return;
46using ::android::hardware::Void;
Shawn Willdena97aea42020-01-16 13:27:49 -070047using android::hardware::keymaster::V4_1::support::Keymaster;
Janis Danisevskisff3d7f42018-10-08 07:15:09 -070048using ::android::security::keymaster::KeymasterBlob;
49
50class KeyStore;
51
52class Worker {
53
54 /*
55 * NonCopyableFunction works similar to std::function in that it wraps callable objects and
56 * erases their type. The rationale for using a custom class instead of
57 * std::function is that std::function requires the wrapped object to be copy contructible.
58 * NonCopyableFunction is itself not copyable and never attempts to copy the wrapped object.
59 * TODO use similar optimization as std::function to remove the extra make_unique allocation.
60 */
61 template <typename Fn> class NonCopyableFunction;
62
63 template <typename Ret, typename... Args> class NonCopyableFunction<Ret(Args...)> {
64
65 class NonCopyableFunctionBase {
66 public:
67 NonCopyableFunctionBase() = default;
68 virtual ~NonCopyableFunctionBase() {}
69 virtual Ret operator()(Args... args) = 0;
70 NonCopyableFunctionBase(const NonCopyableFunctionBase&) = delete;
71 NonCopyableFunctionBase& operator=(const NonCopyableFunctionBase&) = delete;
72 };
73
74 template <typename Fn>
75 class NonCopyableFunctionTypeEraser : public NonCopyableFunctionBase {
76 private:
77 Fn f_;
78
79 public:
80 NonCopyableFunctionTypeEraser() = default;
81 explicit NonCopyableFunctionTypeEraser(Fn f) : f_(std::move(f)) {}
82 Ret operator()(Args... args) override { return f_(std::move(args)...); }
83 };
84
85 private:
86 std::unique_ptr<NonCopyableFunctionBase> f_;
87
88 public:
89 NonCopyableFunction() = default;
Chih-Hung Hsieh4fa39ef2019-01-04 13:34:17 -080090 // NOLINTNEXTLINE(google-explicit-constructor)
Janis Danisevskisff3d7f42018-10-08 07:15:09 -070091 template <typename F> NonCopyableFunction(F f) {
92 f_ = std::make_unique<NonCopyableFunctionTypeEraser<F>>(std::move(f));
93 }
94 NonCopyableFunction(NonCopyableFunction&& other) = default;
95 NonCopyableFunction& operator=(NonCopyableFunction&& other) = default;
96 NonCopyableFunction(const NonCopyableFunction& other) = delete;
97 NonCopyableFunction& operator=(const NonCopyableFunction& other) = delete;
98
99 Ret operator()(Args... args) {
100 if (f_) return (*f_)(std::move(args)...);
101 }
102 };
103
104 using WorkerTask = NonCopyableFunction<void()>;
105
106 std::queue<WorkerTask> pending_requests_;
107 std::mutex pending_requests_mutex_;
108 std::condition_variable pending_requests_cond_var_;
Janis Danisevskisff3d7f42018-10-08 07:15:09 -0700109 bool running_ = false;
Janis Danisevskisc2f1f722019-08-16 14:54:55 -0700110 bool terminate_ = false;
Janis Danisevskisff3d7f42018-10-08 07:15:09 -0700111
112 public:
113 Worker();
114 ~Worker();
115 void addRequest(WorkerTask request);
116};
117
118template <typename... Args> struct MakeKeymasterWorkerCB;
119
120template <typename ErrorType, typename... Args>
121struct MakeKeymasterWorkerCB<ErrorType, std::function<void(Args...)>> {
122 using type = std::function<void(ErrorType, std::tuple<std::decay_t<Args>...>&&)>;
123};
124
125template <typename ErrorType> struct MakeKeymasterWorkerCB<ErrorType> {
126 using type = std::function<void(ErrorType)>;
127};
128
129template <typename... Args>
130using MakeKeymasterWorkerCB_t = typename MakeKeymasterWorkerCB<Args...>::type;
131
132class KeymasterWorker : protected Worker {
133 private:
134 sp<Keymaster> keymasterDevice_;
135 OperationMap operationMap_;
136 KeyStore* keyStore_;
137
Edman Anjosba9b7d32020-09-02 17:34:54 +0200138 /**
139 * Models the security level of this worker internal to KeyStore.
140 *
141 * When the device has only a software Keymaster, KeyStore will set it on the TEE slot and
142 * instantiate a new in-process software Keymaster. In that case there is a mismatch between the
143 * security level used by KeyStore and what is reported from the HAL. This represents the level
144 * used internally by KeyStore.
145 *
146 * This value is used to associate blobs to the corresponding Keymaster backend. It does not
147 * indicate an actual Keymaster HAL security level and should never be exposed to users.
148 */
149 SecurityLevel internalSecurityLevel_;
150
Janis Danisevskisff3d7f42018-10-08 07:15:09 -0700151 template <typename KMFn, typename ErrorType, typename... Args, size_t... I>
152 void unwrap_tuple(KMFn kmfn, std::function<void(ErrorType)> cb,
153 const std::tuple<Args...>& tuple, std::index_sequence<I...>) {
154 cb(((*keymasterDevice_).*kmfn)(std::get<I>(tuple)...));
155 }
156
157 template <typename KMFn, typename ErrorType, typename... ReturnTypes, typename... Args,
158 size_t... I>
159 void unwrap_tuple(KMFn kmfn, std::function<void(ErrorType, std::tuple<ReturnTypes...>&&)> cb,
160 const std::tuple<Args...>& tuple, std::index_sequence<I...>) {
161 std::tuple<ReturnTypes...> returnValue;
162 auto result = ((*keymasterDevice_).*kmfn)(
163 std::get<I>(tuple)...,
164 [&returnValue](const ReturnTypes&... args) { returnValue = std::make_tuple(args...); });
165 cb(std::move(result), std::move(returnValue));
166 }
167
168 template <typename KMFn, typename ErrorType, typename... Args>
169 void addRequest(KMFn kmfn, std::function<void(ErrorType)> cb, Args&&... args) {
170 Worker::addRequest([this, kmfn, cb = std::move(cb),
171 tuple = std::make_tuple(std::forward<Args>(args)...)]() {
172 unwrap_tuple(kmfn, std::move(cb), tuple, std::index_sequence_for<Args...>{});
173 });
174 }
175
176 template <typename KMFn, typename ErrorType, typename... ReturnTypes, typename... Args>
177 void addRequest(KMFn kmfn, std::function<void(ErrorType, std::tuple<ReturnTypes...>&&)> cb,
178 Args&&... args) {
179 Worker::addRequest([this, kmfn, cb = std::move(cb),
180 tuple = std::make_tuple(std::forward<Args>(args)...)]() {
181 unwrap_tuple(kmfn, std::move(cb), tuple, std::index_sequence_for<Args...>{});
182 });
183 }
Janis Danisevskis6a0d9982019-04-30 15:43:59 -0700184
185 void deleteOldKeyOnUpgrade(const LockedKeyBlobEntry& blobfile, Blob keyBlob);
Janis Danisevskisff3d7f42018-10-08 07:15:09 -0700186 std::tuple<KeyStoreServiceReturnCode, Blob>
187 upgradeKeyBlob(const LockedKeyBlobEntry& lockedEntry, const AuthorizationSet& params);
188 std::tuple<KeyStoreServiceReturnCode, KeyCharacteristics, Blob, Blob>
189 createKeyCharacteristicsCache(const LockedKeyBlobEntry& lockedEntry,
190 const hidl_vec<uint8_t>& clientId,
191 const hidl_vec<uint8_t>& appData, Blob keyBlob, Blob charBlob);
192
193 /**
194 * Get the auth token for this operation from the auth token table.
195 *
196 * Returns NO_ERROR if the auth token was found or none was required. If not needed, the
197 * token will be empty (which keymaster interprets as no auth token).
198 * OP_AUTH_NEEDED if it is a per op authorization, no authorization token exists for
199 * that operation and failOnTokenMissing is false.
200 * KM_ERROR_KEY_USER_NOT_AUTHENTICATED if there is no valid auth token for the operation
201 */
202 std::pair<KeyStoreServiceReturnCode, HardwareAuthToken>
203 getAuthToken(const KeyCharacteristics& characteristics, uint64_t handle, KeyPurpose purpose,
204 bool failOnTokenMissing = true);
205
Hasini Gunasinghe242460e2020-06-05 14:06:02 +0000206 KeyStoreServiceReturnCode abort(const sp<IBinder>& token, ResponseCode reason_for_abort);
Janis Danisevskisff3d7f42018-10-08 07:15:09 -0700207
208 bool pruneOperation();
209
210 KeyStoreServiceReturnCode getOperationAuthTokenIfNeeded(std::shared_ptr<Operation> op);
211
212 void appendConfirmationTokenIfNeeded(const KeyCharacteristics& keyCharacteristics,
213 hidl_vec<KeyParameter>* params);
214
215 public:
Edman Anjosba9b7d32020-09-02 17:34:54 +0200216 KeymasterWorker(sp<Keymaster> keymasterDevice, KeyStore* keyStore,
217 SecurityLevel internalSecurityLevel);
Janis Danisevskisff3d7f42018-10-08 07:15:09 -0700218
Janis Danisevskis37896102019-03-14 17:15:06 -0700219 void logIfKeymasterVendorError(ErrorCode ec) const;
220
Janis Danisevskisff3d7f42018-10-08 07:15:09 -0700221 using worker_begin_cb = std::function<void(::android::security::keymaster::OperationResult)>;
222 void begin(LockedKeyBlobEntry, sp<IBinder> appToken, Blob keyBlob, Blob charBlob,
223 bool pruneable, KeyPurpose purpose, AuthorizationSet opParams,
224 hidl_vec<uint8_t> entropy, worker_begin_cb worker_cb);
225
226 using update_cb = std::function<void(::android::security::keymaster::OperationResult)>;
227 void update(sp<IBinder> token, AuthorizationSet params, hidl_vec<uint8_t> data,
228 update_cb _hidl_cb);
229
230 using finish_cb = std::function<void(::android::security::keymaster::OperationResult)>;
231 void finish(sp<IBinder> token, AuthorizationSet params, hidl_vec<uint8_t> input,
232 hidl_vec<uint8_t> signature, hidl_vec<uint8_t> entorpy, finish_cb worker_cb);
233
234 using abort_cb = std::function<void(KeyStoreServiceReturnCode)>;
235 void abort(sp<IBinder> token, abort_cb _hidl_cb);
236
237 using getHardwareInfo_cb = MakeKeymasterWorkerCB_t<Return<void>, Keymaster::getHardwareInfo_cb>;
238 void getHardwareInfo(getHardwareInfo_cb _hidl_cb);
239
240 using getHmacSharingParameters_cb =
241 MakeKeymasterWorkerCB_t<Return<void>, Keymaster::getHmacSharingParameters_cb>;
242 void getHmacSharingParameters(getHmacSharingParameters_cb _hidl_cb);
243
244 using computeSharedHmac_cb =
245 MakeKeymasterWorkerCB_t<Return<void>, Keymaster::computeSharedHmac_cb>;
246 void computeSharedHmac(hidl_vec<HmacSharingParameters> params, computeSharedHmac_cb _hidl_cb);
247
248 using verifyAuthorization_cb =
249 std::function<void(KeyStoreServiceReturnCode ec, HardwareAuthToken, VerificationToken)>;
250 void verifyAuthorization(uint64_t challenge, hidl_vec<KeyParameter> params,
251 HardwareAuthToken token, verifyAuthorization_cb _hidl_cb);
252
253 using addRngEntropy_cb = MakeKeymasterWorkerCB_t<Return<ErrorCode>>;
254 void addRngEntropy(hidl_vec<uint8_t> data, addRngEntropy_cb _hidl_cb);
255
256 using generateKey_cb = std::function<void(
257 KeyStoreServiceReturnCode, ::android::hardware::keymaster::V4_0::KeyCharacteristics)>;
258 void generateKey(LockedKeyBlobEntry, hidl_vec<KeyParameter> keyParams,
259 hidl_vec<uint8_t> entropy, int flags, generateKey_cb _hidl_cb);
260
261 using generateKey2_cb = MakeKeymasterWorkerCB_t<Return<void>, Keymaster::generateKey_cb>;
262 void generateKey(hidl_vec<KeyParameter> keyParams, generateKey2_cb _hidl_cb);
263
264 using getKeyCharacteristics_cb = std::function<void(
265 KeyStoreServiceReturnCode, ::android::hardware::keymaster::V4_0::KeyCharacteristics)>;
266 void getKeyCharacteristics(LockedKeyBlobEntry lockedEntry, hidl_vec<uint8_t> clientId,
267 hidl_vec<uint8_t> appData, Blob keyBlob, Blob charBlob,
268 getKeyCharacteristics_cb _hidl_cb);
269
270 using importKey_cb = std::function<void(
271 KeyStoreServiceReturnCode, ::android::hardware::keymaster::V4_0::KeyCharacteristics)>;
272 void importKey(LockedKeyBlobEntry lockedEntry, hidl_vec<KeyParameter> params,
273 KeyFormat keyFormat, hidl_vec<uint8_t> keyData, int flags,
274 importKey_cb _hidl_cb);
275
276 using importWrappedKey_cb = std::function<void(
277 KeyStoreServiceReturnCode, ::android::hardware::keymaster::V4_0::KeyCharacteristics)>;
278 void importWrappedKey(LockedKeyBlobEntry wrappingLockedEntry,
279 LockedKeyBlobEntry wrapppedLockedEntry, hidl_vec<uint8_t> wrappedKeyData,
280 hidl_vec<uint8_t> maskingKey, hidl_vec<KeyParameter> unwrappingParams,
281 Blob wrappingBlob, Blob wrappingCharBlob, uint64_t passwordSid,
282 uint64_t biometricSid, importWrappedKey_cb worker_cb);
283
284 using exportKey_cb = std::function<void(::android::security::keymaster::ExportResult)>;
285 void exportKey(LockedKeyBlobEntry lockedEntry, KeyFormat exportFormat,
286 hidl_vec<uint8_t> clientId, hidl_vec<uint8_t> appData, Blob keyBlob,
287 Blob charBlob, exportKey_cb _hidl_cb);
288
289 using attestKey_cb = MakeKeymasterWorkerCB_t<Return<void>, Keymaster::attestKey_cb>;
290 void attestKey(hidl_vec<uint8_t> keyToAttest, hidl_vec<KeyParameter> attestParams,
291 attestKey_cb _hidl_cb);
292
Janis Danisevskisff3d7f42018-10-08 07:15:09 -0700293 using deleteKey_cb = MakeKeymasterWorkerCB_t<Return<ErrorCode>>;
294 void deleteKey(hidl_vec<uint8_t> keyBlob, deleteKey_cb _hidl_cb);
295
Janis Danisevskisff3d7f42018-10-08 07:15:09 -0700296 using begin_cb = MakeKeymasterWorkerCB_t<Return<void>, Keymaster::begin_cb>;
297 void begin(KeyPurpose purpose, hidl_vec<uint8_t> key, hidl_vec<KeyParameter> inParams,
298 HardwareAuthToken authToken, begin_cb _hidl_cb);
299
300 void binderDied(android::wp<IBinder> who);
301
302 const Keymaster::VersionResult& halVersion() { return keymasterDevice_->halVersion(); }
303};
304
305} // namespace keystore
306
307#endif // KEYSTORE_KEYMASTER_WORKER_H_