blob: 847abc1b4993001cf0b20fd2de31d2cb40de7ffc [file] [log] [blame]
Kenny Root07438c82012-11-02 15:41:02 -07001/*
2**
3** Copyright 2008, 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#include <stdint.h>
Chad Brubaker9899d6b2015-02-03 13:03:00 -080019#include <sys/limits.h>
Kenny Root07438c82012-11-02 15:41:02 -070020#include <sys/types.h>
21
22#define LOG_TAG "KeystoreService"
23#include <utils/Log.h>
24
25#include <binder/Parcel.h>
26#include <binder/IPCThreadState.h>
27#include <binder/IServiceManager.h>
28
29#include <keystore/IKeystoreService.h>
30
31namespace android {
32
Shawn Willden77d71ca2014-11-12 16:45:12 -070033const ssize_t MAX_GENERATE_ARGS = 3;
Chad Brubaker9899d6b2015-02-03 13:03:00 -080034static keymaster_key_param_t* readParamList(const Parcel& in, size_t* length);
Shawn Willden77d71ca2014-11-12 16:45:12 -070035
Kenny Root96427ba2013-08-16 14:02:41 -070036KeystoreArg::KeystoreArg(const void* data, size_t len)
37 : mData(data), mSize(len) {
38}
39
40KeystoreArg::~KeystoreArg() {
41}
42
43const void *KeystoreArg::data() const {
44 return mData;
45}
46
47size_t KeystoreArg::size() const {
48 return mSize;
49}
50
Chad Brubakerc3a18562015-03-17 18:21:35 -070051OperationResult::OperationResult() : resultCode(0), token(), handle(0), inputConsumed(0),
Chad Brubaker9899d6b2015-02-03 13:03:00 -080052 data(NULL), dataLength(0) {
53}
54
55OperationResult::~OperationResult() {
56}
57
58void OperationResult::readFromParcel(const Parcel& in) {
59 resultCode = in.readInt32();
60 token = in.readStrongBinder();
Chad Brubakerc3a18562015-03-17 18:21:35 -070061 handle = static_cast<keymaster_operation_handle_t>(in.readInt64());
Chad Brubaker9899d6b2015-02-03 13:03:00 -080062 inputConsumed = in.readInt32();
63 ssize_t length = in.readInt32();
64 dataLength = 0;
65 if (length > 0) {
66 const void* buf = in.readInplace(length);
67 if (buf) {
68 data.reset(reinterpret_cast<uint8_t*>(malloc(length)));
69 if (data.get()) {
70 memcpy(data.get(), buf, length);
71 dataLength = (size_t) length;
72 } else {
73 ALOGE("Failed to allocate OperationResult buffer");
74 }
75 } else {
76 ALOGE("Failed to readInplace OperationResult data");
77 }
78 }
Chad Brubaker57e106d2015-06-01 12:59:00 -070079 outParams.readFromParcel(in);
Chad Brubaker9899d6b2015-02-03 13:03:00 -080080}
81
82void OperationResult::writeToParcel(Parcel* out) const {
83 out->writeInt32(resultCode);
84 out->writeStrongBinder(token);
Chad Brubakerc3a18562015-03-17 18:21:35 -070085 out->writeInt64(handle);
Chad Brubaker9899d6b2015-02-03 13:03:00 -080086 out->writeInt32(inputConsumed);
87 out->writeInt32(dataLength);
88 if (dataLength && data) {
89 void* buf = out->writeInplace(dataLength);
90 if (buf) {
91 memcpy(buf, data.get(), dataLength);
92 } else {
93 ALOGE("Failed to writeInplace OperationResult data.");
94 }
95 }
Chad Brubaker57e106d2015-06-01 12:59:00 -070096 outParams.writeToParcel(out);
Chad Brubaker9899d6b2015-02-03 13:03:00 -080097}
98
99ExportResult::ExportResult() : resultCode(0), exportData(NULL), dataLength(0) {
100}
101
102ExportResult::~ExportResult() {
103}
104
105void ExportResult::readFromParcel(const Parcel& in) {
106 resultCode = in.readInt32();
107 ssize_t length = in.readInt32();
108 dataLength = 0;
109 if (length > 0) {
110 const void* buf = in.readInplace(length);
111 if (buf) {
112 exportData.reset(reinterpret_cast<uint8_t*>(malloc(length)));
113 if (exportData.get()) {
114 memcpy(exportData.get(), buf, length);
115 dataLength = (size_t) length;
116 } else {
117 ALOGE("Failed to allocate ExportData buffer");
118 }
119 } else {
120 ALOGE("Failed to readInplace ExportData data");
121 }
122 }
123}
124
125void ExportResult::writeToParcel(Parcel* out) const {
126 out->writeInt32(resultCode);
127 out->writeInt32(dataLength);
128 if (exportData && dataLength) {
129 void* buf = out->writeInplace(dataLength);
130 if (buf) {
131 memcpy(buf, exportData.get(), dataLength);
132 } else {
133 ALOGE("Failed to writeInplace ExportResult data.");
134 }
135 }
136}
137
138KeymasterArguments::KeymasterArguments() {
139}
140
141KeymasterArguments::~KeymasterArguments() {
142 keymaster_free_param_values(params.data(), params.size());
143}
144
145void KeymasterArguments::readFromParcel(const Parcel& in) {
146 ssize_t length = in.readInt32();
147 size_t ulength = (size_t) length;
148 if (length < 0) {
149 ulength = 0;
150 }
151 keymaster_free_param_values(params.data(), params.size());
152 params.clear();
153 for(size_t i = 0; i < ulength; i++) {
154 keymaster_key_param_t param;
155 if (!readKeymasterArgumentFromParcel(in, &param)) {
156 ALOGE("Error reading keymaster argument from parcel");
157 break;
158 }
159 params.push_back(param);
160 }
161}
162
163void KeymasterArguments::writeToParcel(Parcel* out) const {
164 out->writeInt32(params.size());
165 for (auto param : params) {
166 out->writeInt32(1);
167 writeKeymasterArgumentToParcel(param, out);
168 }
169}
170
171KeyCharacteristics::KeyCharacteristics() {
172 memset((void*) &characteristics, 0, sizeof(characteristics));
173}
174
175KeyCharacteristics::~KeyCharacteristics() {
176 keymaster_free_characteristics(&characteristics);
177}
178
179void KeyCharacteristics::readFromParcel(const Parcel& in) {
180 size_t length = 0;
181 keymaster_key_param_t* params = readParamList(in, &length);
182 characteristics.sw_enforced.params = params;
183 characteristics.sw_enforced.length = length;
184
185 params = readParamList(in, &length);
186 characteristics.hw_enforced.params = params;
187 characteristics.hw_enforced.length = length;
188}
189
190void KeyCharacteristics::writeToParcel(Parcel* out) const {
191 if (characteristics.sw_enforced.params) {
192 out->writeInt32(characteristics.sw_enforced.length);
193 for (size_t i = 0; i < characteristics.sw_enforced.length; i++) {
194 out->writeInt32(1);
195 writeKeymasterArgumentToParcel(characteristics.sw_enforced.params[i], out);
196 }
197 } else {
198 out->writeInt32(0);
199 }
200 if (characteristics.hw_enforced.params) {
201 out->writeInt32(characteristics.hw_enforced.length);
202 for (size_t i = 0; i < characteristics.hw_enforced.length; i++) {
203 out->writeInt32(1);
204 writeKeymasterArgumentToParcel(characteristics.hw_enforced.params[i], out);
205 }
206 } else {
207 out->writeInt32(0);
208 }
209}
210
Shawn Willden50eb1b22016-01-21 12:41:23 -0700211KeymasterCertificateChain::KeymasterCertificateChain() {
212 memset(&chain, 0, sizeof(chain));
213}
214
215KeymasterCertificateChain::~KeymasterCertificateChain() {
216 keymaster_free_cert_chain(&chain);
217}
218
219static bool readKeymasterBlob(const Parcel& in, keymaster_blob_t* blob) {
220 if (in.readInt32() != 1) {
221 return false;
222 }
223
Shawn Willden50eb1b22016-01-21 12:41:23 -0700224 ssize_t length = in.readInt32();
225 if (length <= 0) {
Shawn Willden50eb1b22016-01-21 12:41:23 -0700226 return false;
227 }
228
Bin Chen2cbb7ce2016-09-02 22:06:29 +1000229 blob->data = static_cast<const uint8_t*>(malloc(length));
Shawn Willden067042f2016-02-02 17:32:31 -0700230 if (!blob->data)
231 return false;
232
233 const void* buf = in.readInplace(length);
234 if (!buf)
235 return false;
236
237 blob->data_length = static_cast<size_t>(length);
238 memcpy(const_cast<uint8_t*>(blob->data), buf, length);
239
Shawn Willden50eb1b22016-01-21 12:41:23 -0700240 return true;
241}
242
243void KeymasterCertificateChain::readFromParcel(const Parcel& in) {
Shawn Willden067042f2016-02-02 17:32:31 -0700244 keymaster_free_cert_chain(&chain);
245
Shawn Willden50eb1b22016-01-21 12:41:23 -0700246 ssize_t count = in.readInt32();
247 size_t ucount = count;
Shawn Willden067042f2016-02-02 17:32:31 -0700248 if (count <= 0) {
249 return;
Shawn Willden50eb1b22016-01-21 12:41:23 -0700250 }
Shawn Willden067042f2016-02-02 17:32:31 -0700251
252 chain.entries = reinterpret_cast<keymaster_blob_t*>(malloc(sizeof(keymaster_blob_t) * ucount));
253 if (!chain.entries) {
254 ALOGE("Error allocating memory for certificate chain");
255 return;
256 }
257
Shawn Willden50eb1b22016-01-21 12:41:23 -0700258 memset(chain.entries, 0, sizeof(keymaster_blob_t) * ucount);
259 for (size_t i = 0; i < ucount; ++i) {
260 if (!readKeymasterBlob(in, &chain.entries[i])) {
Shawn Willden067042f2016-02-02 17:32:31 -0700261 ALOGE("Error reading certificate from parcel");
Shawn Willden50eb1b22016-01-21 12:41:23 -0700262 keymaster_free_cert_chain(&chain);
263 return;
264 }
265 }
266}
267
268void KeymasterCertificateChain::writeToParcel(Parcel* out) const {
269 out->writeInt32(chain.entry_count);
270 for (size_t i = 0; i < chain.entry_count; ++i) {
271 if (chain.entries[i].data) {
Shawn Willden50eb1b22016-01-21 12:41:23 -0700272 out->writeInt32(chain.entries[i].data_length);
273 void* buf = out->writeInplace(chain.entries[i].data_length);
274 if (buf) {
275 memcpy(buf, chain.entries[i].data, chain.entries[i].data_length);
276 } else {
277 ALOGE("Failed to writeInplace keymaster cert chain entry");
278 }
279 } else {
280 out->writeInt32(0); // Tell Java side this object is NULL.
281 ALOGE("Found NULL certificate chain entry");
282 }
283 }
284}
285
Chad Brubaker9899d6b2015-02-03 13:03:00 -0800286void writeKeymasterArgumentToParcel(const keymaster_key_param_t& param, Parcel* out) {
287 switch (keymaster_tag_get_type(param.tag)) {
288 case KM_ENUM:
289 case KM_ENUM_REP: {
290 out->writeInt32(param.tag);
291 out->writeInt32(param.enumerated);
292 break;
293 }
Shawn Willden0ebf13d2015-06-24 16:29:45 -0700294 case KM_UINT:
295 case KM_UINT_REP: {
Chad Brubaker9899d6b2015-02-03 13:03:00 -0800296 out->writeInt32(param.tag);
297 out->writeInt32(param.integer);
298 break;
299 }
Shawn Willden0ebf13d2015-06-24 16:29:45 -0700300 case KM_ULONG:
301 case KM_ULONG_REP: {
Chad Brubaker9899d6b2015-02-03 13:03:00 -0800302 out->writeInt32(param.tag);
303 out->writeInt64(param.long_integer);
304 break;
305 }
306 case KM_DATE: {
307 out->writeInt32(param.tag);
308 out->writeInt64(param.date_time);
309 break;
310 }
311 case KM_BOOL: {
312 out->writeInt32(param.tag);
313 break;
314 }
315 case KM_BIGNUM:
316 case KM_BYTES: {
317 out->writeInt32(param.tag);
318 out->writeInt32(param.blob.data_length);
319 void* buf = out->writeInplace(param.blob.data_length);
320 if (buf) {
321 memcpy(buf, param.blob.data, param.blob.data_length);
322 } else {
323 ALOGE("Failed to writeInplace keymaster blob param");
324 }
325 break;
326 }
327 default: {
328 ALOGE("Failed to write argument: Unsupported keymaster_tag_t %d", param.tag);
329 }
330 }
331}
332
333
334bool readKeymasterArgumentFromParcel(const Parcel& in, keymaster_key_param_t* out) {
335 if (in.readInt32() == 0) {
336 return false;
337 }
338 keymaster_tag_t tag = static_cast<keymaster_tag_t>(in.readInt32());
339 switch (keymaster_tag_get_type(tag)) {
340 case KM_ENUM:
341 case KM_ENUM_REP: {
342 uint32_t value = in.readInt32();
343 *out = keymaster_param_enum(tag, value);
344 break;
345 }
Shawn Willden0ebf13d2015-06-24 16:29:45 -0700346 case KM_UINT:
347 case KM_UINT_REP: {
Chad Brubaker9899d6b2015-02-03 13:03:00 -0800348 uint32_t value = in.readInt32();
349 *out = keymaster_param_int(tag, value);
350 break;
351 }
Shawn Willden0ebf13d2015-06-24 16:29:45 -0700352 case KM_ULONG:
353 case KM_ULONG_REP: {
Chad Brubaker9899d6b2015-02-03 13:03:00 -0800354 uint64_t value = in.readInt64();
355 *out = keymaster_param_long(tag, value);
356 break;
357 }
358 case KM_DATE: {
359 uint64_t value = in.readInt64();
360 *out = keymaster_param_date(tag, value);
361 break;
362 }
363 case KM_BOOL: {
364 *out = keymaster_param_bool(tag);
365 break;
366 }
367 case KM_BIGNUM:
368 case KM_BYTES: {
369 ssize_t length = in.readInt32();
370 uint8_t* data = NULL;
371 size_t ulength = 0;
372 if (length >= 0) {
373 ulength = (size_t) length;
374 // use malloc here so we can use keymaster_free_param_values
375 // consistently.
376 data = reinterpret_cast<uint8_t*>(malloc(ulength));
377 const void* buf = in.readInplace(ulength);
378 if (!buf || !data) {
379 ALOGE("Failed to allocate buffer for keymaster blob param");
Shawn Willden067042f2016-02-02 17:32:31 -0700380 free(data);
Chad Brubaker9899d6b2015-02-03 13:03:00 -0800381 return false;
382 }
383 memcpy(data, buf, ulength);
384 }
385 *out = keymaster_param_blob(tag, data, ulength);
386 break;
387 }
388 default: {
389 ALOGE("Unsupported keymaster_tag_t %d", tag);
390 return false;
391 }
392 }
393 return true;
394}
395
Chad Brubaker6432df72015-03-20 16:23:04 -0700396/**
397 * Read a byte array from in. The data at *data is still owned by the parcel
398 */
399static void readByteArray(const Parcel& in, const uint8_t** data, size_t* length) {
400 ssize_t slength = in.readInt32();
401 if (slength > 0) {
402 *data = reinterpret_cast<const uint8_t*>(in.readInplace(slength));
403 if (*data) {
404 *length = static_cast<size_t>(slength);
405 } else {
406 *length = 0;
407 }
408 } else {
409 *data = NULL;
410 *length = 0;
411 }
412}
413
Chad Brubaker9899d6b2015-02-03 13:03:00 -0800414// Read a keymaster_key_param_t* from a Parcel for use in a
415// keymaster_key_characteristics_t. This will be free'd by calling
416// keymaster_free_key_characteristics.
417static keymaster_key_param_t* readParamList(const Parcel& in, size_t* length) {
418 ssize_t slength = in.readInt32();
419 *length = 0;
420 if (slength < 0) {
421 return NULL;
422 }
423 *length = (size_t) slength;
424 if (*length >= UINT_MAX / sizeof(keymaster_key_param_t)) {
425 return NULL;
426 }
427 keymaster_key_param_t* list =
428 reinterpret_cast<keymaster_key_param_t*>(malloc(*length *
429 sizeof(keymaster_key_param_t)));
430 if (!list) {
431 ALOGD("Failed to allocate buffer for generateKey outCharacteristics");
432 goto err;
433 }
434 for (size_t i = 0; i < *length ; i++) {
435 if (!readKeymasterArgumentFromParcel(in, &list[i])) {
436 ALOGE("Failed to read keymaster argument");
437 keymaster_free_param_values(list, i);
438 goto err;
439 }
440 }
441 return list;
442err:
443 free(list);
444 return NULL;
445}
446
Chad Brubakerd6634422015-03-21 22:36:07 -0700447static std::unique_ptr<keymaster_blob_t> readKeymasterBlob(const Parcel& in) {
Shawn Willden50eb1b22016-01-21 12:41:23 -0700448 std::unique_ptr<keymaster_blob_t> blob (new keymaster_blob_t);
449 if (!readKeymasterBlob(in, blob.get())) {
450 blob.reset();
Chad Brubaker9899d6b2015-02-03 13:03:00 -0800451 }
Chad Brubakerd6634422015-03-21 22:36:07 -0700452 return blob;
Chad Brubaker9899d6b2015-02-03 13:03:00 -0800453}
454
Kenny Root07438c82012-11-02 15:41:02 -0700455class BpKeystoreService: public BpInterface<IKeystoreService>
456{
457public:
Chih-Hung Hsiehd3bccc82016-04-25 12:11:44 -0700458 explicit BpKeystoreService(const sp<IBinder>& impl)
Kenny Root07438c82012-11-02 15:41:02 -0700459 : BpInterface<IKeystoreService>(impl)
460 {
461 }
462
463 // test ping
Chad Brubakere6c3bfa2015-05-12 15:18:26 -0700464 virtual int32_t getState(int32_t userId)
Kenny Root07438c82012-11-02 15:41:02 -0700465 {
466 Parcel data, reply;
467 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
Chad Brubakere6c3bfa2015-05-12 15:18:26 -0700468 data.writeInt32(userId);
469 status_t status = remote()->transact(BnKeystoreService::GET_STATE, data, &reply);
Kenny Root07438c82012-11-02 15:41:02 -0700470 if (status != NO_ERROR) {
Chad Brubakere6c3bfa2015-05-12 15:18:26 -0700471 ALOGD("getState() could not contact remote: %d\n", status);
Kenny Root07438c82012-11-02 15:41:02 -0700472 return -1;
473 }
474 int32_t err = reply.readExceptionCode();
475 int32_t ret = reply.readInt32();
476 if (err < 0) {
Chad Brubakere6c3bfa2015-05-12 15:18:26 -0700477 ALOGD("getState() caught exception %d\n", err);
Kenny Root07438c82012-11-02 15:41:02 -0700478 return -1;
479 }
480 return ret;
481 }
482
Chad Brubakerad6a7f52015-09-09 14:55:22 -0700483 virtual int32_t get(const String16& name, int32_t uid, uint8_t** item, size_t* itemLength)
Kenny Root07438c82012-11-02 15:41:02 -0700484 {
485 Parcel data, reply;
486 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
487 data.writeString16(name);
Chad Brubakerad6a7f52015-09-09 14:55:22 -0700488 data.writeInt32(uid);
Kenny Root07438c82012-11-02 15:41:02 -0700489 status_t status = remote()->transact(BnKeystoreService::GET, data, &reply);
490 if (status != NO_ERROR) {
491 ALOGD("get() could not contact remote: %d\n", status);
492 return -1;
493 }
494 int32_t err = reply.readExceptionCode();
495 ssize_t len = reply.readInt32();
496 if (len >= 0 && (size_t) len <= reply.dataAvail()) {
497 size_t ulen = (size_t) len;
498 const void* buf = reply.readInplace(ulen);
499 *item = (uint8_t*) malloc(ulen);
500 if (*item != NULL) {
501 memcpy(*item, buf, ulen);
502 *itemLength = ulen;
503 } else {
504 ALOGE("out of memory allocating output array in get");
505 *itemLength = 0;
506 }
507 } else {
508 *itemLength = 0;
509 }
510 if (err < 0) {
511 ALOGD("get() caught exception %d\n", err);
512 return -1;
513 }
514 return 0;
515 }
516
Kenny Root0c540aa2013-04-03 09:22:15 -0700517 virtual int32_t insert(const String16& name, const uint8_t* item, size_t itemLength, int uid,
518 int32_t flags)
Kenny Root07438c82012-11-02 15:41:02 -0700519 {
520 Parcel data, reply;
521 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
522 data.writeString16(name);
523 data.writeInt32(itemLength);
524 void* buf = data.writeInplace(itemLength);
525 memcpy(buf, item, itemLength);
Kenny Rootb88c3eb2013-02-13 14:43:43 -0800526 data.writeInt32(uid);
Kenny Root0c540aa2013-04-03 09:22:15 -0700527 data.writeInt32(flags);
Kenny Root07438c82012-11-02 15:41:02 -0700528 status_t status = remote()->transact(BnKeystoreService::INSERT, data, &reply);
529 if (status != NO_ERROR) {
530 ALOGD("import() could not contact remote: %d\n", status);
531 return -1;
532 }
533 int32_t err = reply.readExceptionCode();
534 int32_t ret = reply.readInt32();
535 if (err < 0) {
536 ALOGD("import() caught exception %d\n", err);
537 return -1;
538 }
539 return ret;
540 }
541
Kenny Rootb88c3eb2013-02-13 14:43:43 -0800542 virtual int32_t del(const String16& name, int uid)
Kenny Root07438c82012-11-02 15:41:02 -0700543 {
544 Parcel data, reply;
545 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
546 data.writeString16(name);
Kenny Rootb88c3eb2013-02-13 14:43:43 -0800547 data.writeInt32(uid);
Kenny Root07438c82012-11-02 15:41:02 -0700548 status_t status = remote()->transact(BnKeystoreService::DEL, data, &reply);
549 if (status != NO_ERROR) {
550 ALOGD("del() could not contact remote: %d\n", status);
551 return -1;
552 }
553 int32_t err = reply.readExceptionCode();
554 int32_t ret = reply.readInt32();
555 if (err < 0) {
556 ALOGD("del() caught exception %d\n", err);
557 return -1;
558 }
559 return ret;
560 }
561
Kenny Rootb88c3eb2013-02-13 14:43:43 -0800562 virtual int32_t exist(const String16& name, int uid)
Kenny Root07438c82012-11-02 15:41:02 -0700563 {
564 Parcel data, reply;
565 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
566 data.writeString16(name);
Kenny Rootb88c3eb2013-02-13 14:43:43 -0800567 data.writeInt32(uid);
Kenny Root07438c82012-11-02 15:41:02 -0700568 status_t status = remote()->transact(BnKeystoreService::EXIST, data, &reply);
569 if (status != NO_ERROR) {
570 ALOGD("exist() could not contact remote: %d\n", status);
571 return -1;
572 }
573 int32_t err = reply.readExceptionCode();
574 int32_t ret = reply.readInt32();
575 if (err < 0) {
576 ALOGD("exist() caught exception %d\n", err);
577 return -1;
578 }
579 return ret;
580 }
581
Chad Brubakere6c3bfa2015-05-12 15:18:26 -0700582 virtual int32_t list(const String16& prefix, int uid, Vector<String16>* matches)
Kenny Root07438c82012-11-02 15:41:02 -0700583 {
584 Parcel data, reply;
585 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
Chad Brubakere6c3bfa2015-05-12 15:18:26 -0700586 data.writeString16(prefix);
Kenny Rootb88c3eb2013-02-13 14:43:43 -0800587 data.writeInt32(uid);
Chad Brubakere6c3bfa2015-05-12 15:18:26 -0700588 status_t status = remote()->transact(BnKeystoreService::LIST, data, &reply);
Kenny Root07438c82012-11-02 15:41:02 -0700589 if (status != NO_ERROR) {
Chad Brubakere6c3bfa2015-05-12 15:18:26 -0700590 ALOGD("list() could not contact remote: %d\n", status);
Kenny Root07438c82012-11-02 15:41:02 -0700591 return -1;
592 }
593 int32_t err = reply.readExceptionCode();
594 int32_t numMatches = reply.readInt32();
595 for (int32_t i = 0; i < numMatches; i++) {
596 matches->push(reply.readString16());
597 }
598 int32_t ret = reply.readInt32();
599 if (err < 0) {
Chad Brubakere6c3bfa2015-05-12 15:18:26 -0700600 ALOGD("list() caught exception %d\n", err);
Kenny Root07438c82012-11-02 15:41:02 -0700601 return -1;
602 }
603 return ret;
604 }
605
606 virtual int32_t reset()
607 {
608 Parcel data, reply;
609 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
610 status_t status = remote()->transact(BnKeystoreService::RESET, data, &reply);
611 if (status != NO_ERROR) {
612 ALOGD("reset() could not contact remote: %d\n", status);
613 return -1;
614 }
615 int32_t err = reply.readExceptionCode();
616 int32_t ret = reply.readInt32();
617 if (err < 0) {
618 ALOGD("reset() caught exception %d\n", err);
619 return -1;
620 }
621 return ret;
622 }
623
Chad Brubaker96d6d782015-05-07 10:19:40 -0700624 virtual int32_t onUserPasswordChanged(int32_t userId, const String16& password)
Kenny Root07438c82012-11-02 15:41:02 -0700625 {
626 Parcel data, reply;
627 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
Chad Brubaker96d6d782015-05-07 10:19:40 -0700628 data.writeInt32(userId);
Kenny Root07438c82012-11-02 15:41:02 -0700629 data.writeString16(password);
Chad Brubaker96d6d782015-05-07 10:19:40 -0700630 status_t status = remote()->transact(BnKeystoreService::ON_USER_PASSWORD_CHANGED, data,
631 &reply);
Kenny Root07438c82012-11-02 15:41:02 -0700632 if (status != NO_ERROR) {
Chad Brubaker96d6d782015-05-07 10:19:40 -0700633 ALOGD("onUserPasswordChanged() could not contact remote: %d\n", status);
Kenny Root07438c82012-11-02 15:41:02 -0700634 return -1;
635 }
636 int32_t err = reply.readExceptionCode();
637 int32_t ret = reply.readInt32();
638 if (err < 0) {
Chad Brubaker96d6d782015-05-07 10:19:40 -0700639 ALOGD("onUserPasswordChanged() caught exception %d\n", err);
Kenny Root07438c82012-11-02 15:41:02 -0700640 return -1;
641 }
642 return ret;
643 }
644
Chad Brubakere6c3bfa2015-05-12 15:18:26 -0700645 virtual int32_t lock(int32_t userId)
Kenny Root07438c82012-11-02 15:41:02 -0700646 {
647 Parcel data, reply;
648 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
Chad Brubakere6c3bfa2015-05-12 15:18:26 -0700649 data.writeInt32(userId);
Kenny Root07438c82012-11-02 15:41:02 -0700650 status_t status = remote()->transact(BnKeystoreService::LOCK, data, &reply);
651 if (status != NO_ERROR) {
652 ALOGD("lock() could not contact remote: %d\n", status);
653 return -1;
654 }
655 int32_t err = reply.readExceptionCode();
656 int32_t ret = reply.readInt32();
657 if (err < 0) {
658 ALOGD("lock() caught exception %d\n", err);
659 return -1;
660 }
661 return ret;
662 }
663
Chad Brubaker96d6d782015-05-07 10:19:40 -0700664 virtual int32_t unlock(int32_t userId, const String16& password)
Kenny Root07438c82012-11-02 15:41:02 -0700665 {
666 Parcel data, reply;
667 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
Chad Brubaker96d6d782015-05-07 10:19:40 -0700668 data.writeInt32(userId);
Kenny Root07438c82012-11-02 15:41:02 -0700669 data.writeString16(password);
670 status_t status = remote()->transact(BnKeystoreService::UNLOCK, data, &reply);
671 if (status != NO_ERROR) {
672 ALOGD("unlock() could not contact remote: %d\n", status);
673 return -1;
674 }
675 int32_t err = reply.readExceptionCode();
676 int32_t ret = reply.readInt32();
677 if (err < 0) {
678 ALOGD("unlock() caught exception %d\n", err);
679 return -1;
680 }
681 return ret;
682 }
683
Chad Brubakere6c3bfa2015-05-12 15:18:26 -0700684 virtual bool isEmpty(int32_t userId)
Kenny Root07438c82012-11-02 15:41:02 -0700685 {
686 Parcel data, reply;
687 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
Chad Brubakere6c3bfa2015-05-12 15:18:26 -0700688 data.writeInt32(userId);
689 status_t status = remote()->transact(BnKeystoreService::IS_EMPTY, data, &reply);
Kenny Root07438c82012-11-02 15:41:02 -0700690 if (status != NO_ERROR) {
Chad Brubakere6c3bfa2015-05-12 15:18:26 -0700691 ALOGD("isEmpty() could not contact remote: %d\n", status);
692 return false;
Kenny Root07438c82012-11-02 15:41:02 -0700693 }
694 int32_t err = reply.readExceptionCode();
695 int32_t ret = reply.readInt32();
696 if (err < 0) {
Chad Brubakere6c3bfa2015-05-12 15:18:26 -0700697 ALOGD("isEmpty() caught exception %d\n", err);
698 return false;
Kenny Root07438c82012-11-02 15:41:02 -0700699 }
Chad Brubakere6c3bfa2015-05-12 15:18:26 -0700700 return ret != 0;
Kenny Root07438c82012-11-02 15:41:02 -0700701 }
702
Kenny Root96427ba2013-08-16 14:02:41 -0700703 virtual int32_t generate(const String16& name, int32_t uid, int32_t keyType, int32_t keySize,
704 int32_t flags, Vector<sp<KeystoreArg> >* args)
Kenny Root07438c82012-11-02 15:41:02 -0700705 {
706 Parcel data, reply;
707 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
708 data.writeString16(name);
Kenny Rootb88c3eb2013-02-13 14:43:43 -0800709 data.writeInt32(uid);
Kenny Root96427ba2013-08-16 14:02:41 -0700710 data.writeInt32(keyType);
711 data.writeInt32(keySize);
Kenny Root0c540aa2013-04-03 09:22:15 -0700712 data.writeInt32(flags);
Chad Brubaker468fc692015-01-13 17:33:14 -0800713 data.writeInt32(1);
Kenny Root96427ba2013-08-16 14:02:41 -0700714 data.writeInt32(args->size());
715 for (Vector<sp<KeystoreArg> >::iterator it = args->begin(); it != args->end(); ++it) {
716 sp<KeystoreArg> item = *it;
717 size_t keyLength = item->size();
718 data.writeInt32(keyLength);
719 void* buf = data.writeInplace(keyLength);
720 memcpy(buf, item->data(), keyLength);
721 }
Kenny Root07438c82012-11-02 15:41:02 -0700722 status_t status = remote()->transact(BnKeystoreService::GENERATE, data, &reply);
723 if (status != NO_ERROR) {
724 ALOGD("generate() could not contact remote: %d\n", status);
725 return -1;
726 }
727 int32_t err = reply.readExceptionCode();
728 int32_t ret = reply.readInt32();
729 if (err < 0) {
730 ALOGD("generate() caught exception %d\n", err);
731 return -1;
732 }
733 return ret;
734 }
735
Kenny Root0c540aa2013-04-03 09:22:15 -0700736 virtual int32_t import(const String16& name, const uint8_t* key, size_t keyLength, int uid,
737 int flags)
Kenny Root07438c82012-11-02 15:41:02 -0700738 {
739 Parcel data, reply;
740 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
741 data.writeString16(name);
742 data.writeInt32(keyLength);
743 void* buf = data.writeInplace(keyLength);
744 memcpy(buf, key, keyLength);
Kenny Rootb88c3eb2013-02-13 14:43:43 -0800745 data.writeInt32(uid);
Kenny Root0c540aa2013-04-03 09:22:15 -0700746 data.writeInt32(flags);
Kenny Root07438c82012-11-02 15:41:02 -0700747 status_t status = remote()->transact(BnKeystoreService::IMPORT, data, &reply);
748 if (status != NO_ERROR) {
749 ALOGD("import() could not contact remote: %d\n", status);
750 return -1;
751 }
752 int32_t err = reply.readExceptionCode();
753 int32_t ret = reply.readInt32();
754 if (err < 0) {
755 ALOGD("import() caught exception %d\n", err);
756 return -1;
757 }
758 return ret;
759 }
760
761 virtual int32_t sign(const String16& name, const uint8_t* in, size_t inLength, uint8_t** out,
762 size_t* outLength)
763 {
764 Parcel data, reply;
765 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
766 data.writeString16(name);
767 data.writeInt32(inLength);
768 void* buf = data.writeInplace(inLength);
769 memcpy(buf, in, inLength);
770 status_t status = remote()->transact(BnKeystoreService::SIGN, data, &reply);
771 if (status != NO_ERROR) {
772 ALOGD("import() could not contact remote: %d\n", status);
773 return -1;
774 }
775 int32_t err = reply.readExceptionCode();
776 ssize_t len = reply.readInt32();
777 if (len >= 0 && (size_t) len <= reply.dataAvail()) {
778 size_t ulen = (size_t) len;
779 const void* outBuf = reply.readInplace(ulen);
780 *out = (uint8_t*) malloc(ulen);
781 if (*out != NULL) {
782 memcpy((void*) *out, outBuf, ulen);
783 *outLength = ulen;
784 } else {
785 ALOGE("out of memory allocating output array in sign");
786 *outLength = 0;
787 }
788 } else {
789 *outLength = 0;
790 }
791 if (err < 0) {
792 ALOGD("import() caught exception %d\n", err);
793 return -1;
794 }
795 return 0;
796 }
797
798 virtual int32_t verify(const String16& name, const uint8_t* in, size_t inLength,
799 const uint8_t* signature, size_t signatureLength)
800 {
801 Parcel data, reply;
802 void* buf;
803
804 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
805 data.writeString16(name);
806 data.writeInt32(inLength);
807 buf = data.writeInplace(inLength);
808 memcpy(buf, in, inLength);
809 data.writeInt32(signatureLength);
810 buf = data.writeInplace(signatureLength);
811 memcpy(buf, signature, signatureLength);
812 status_t status = remote()->transact(BnKeystoreService::VERIFY, data, &reply);
813 if (status != NO_ERROR) {
814 ALOGD("verify() could not contact remote: %d\n", status);
815 return -1;
816 }
817 int32_t err = reply.readExceptionCode();
818 int32_t ret = reply.readInt32();
819 if (err < 0) {
820 ALOGD("verify() caught exception %d\n", err);
821 return -1;
822 }
823 return ret;
824 }
825
826 virtual int32_t get_pubkey(const String16& name, uint8_t** pubkey, size_t* pubkeyLength)
827 {
828 Parcel data, reply;
829 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
830 data.writeString16(name);
831 status_t status = remote()->transact(BnKeystoreService::GET_PUBKEY, data, &reply);
832 if (status != NO_ERROR) {
833 ALOGD("get_pubkey() could not contact remote: %d\n", status);
834 return -1;
835 }
836 int32_t err = reply.readExceptionCode();
837 ssize_t len = reply.readInt32();
838 if (len >= 0 && (size_t) len <= reply.dataAvail()) {
839 size_t ulen = (size_t) len;
840 const void* buf = reply.readInplace(ulen);
841 *pubkey = (uint8_t*) malloc(ulen);
842 if (*pubkey != NULL) {
843 memcpy(*pubkey, buf, ulen);
844 *pubkeyLength = ulen;
845 } else {
846 ALOGE("out of memory allocating output array in get_pubkey");
847 *pubkeyLength = 0;
848 }
849 } else {
850 *pubkeyLength = 0;
851 }
852 if (err < 0) {
853 ALOGD("get_pubkey() caught exception %d\n", err);
854 return -1;
855 }
856 return 0;
857 }
858
Kenny Root07438c82012-11-02 15:41:02 -0700859 virtual int32_t grant(const String16& name, int32_t granteeUid)
860 {
861 Parcel data, reply;
862 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
863 data.writeString16(name);
864 data.writeInt32(granteeUid);
865 status_t status = remote()->transact(BnKeystoreService::GRANT, data, &reply);
866 if (status != NO_ERROR) {
867 ALOGD("grant() could not contact remote: %d\n", status);
868 return -1;
869 }
870 int32_t err = reply.readExceptionCode();
871 int32_t ret = reply.readInt32();
872 if (err < 0) {
873 ALOGD("grant() caught exception %d\n", err);
874 return -1;
875 }
876 return ret;
877 }
878
879 virtual int32_t ungrant(const String16& name, int32_t granteeUid)
880 {
881 Parcel data, reply;
882 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
883 data.writeString16(name);
884 data.writeInt32(granteeUid);
885 status_t status = remote()->transact(BnKeystoreService::UNGRANT, data, &reply);
886 if (status != NO_ERROR) {
887 ALOGD("ungrant() could not contact remote: %d\n", status);
888 return -1;
889 }
890 int32_t err = reply.readExceptionCode();
891 int32_t ret = reply.readInt32();
892 if (err < 0) {
893 ALOGD("ungrant() caught exception %d\n", err);
894 return -1;
895 }
896 return ret;
897 }
898
Chad Brubakerad6a7f52015-09-09 14:55:22 -0700899 int64_t getmtime(const String16& name, int32_t uid)
Kenny Root07438c82012-11-02 15:41:02 -0700900 {
901 Parcel data, reply;
902 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
903 data.writeString16(name);
Chad Brubakerad6a7f52015-09-09 14:55:22 -0700904 data.writeInt32(uid);
Kenny Root07438c82012-11-02 15:41:02 -0700905 status_t status = remote()->transact(BnKeystoreService::GETMTIME, data, &reply);
906 if (status != NO_ERROR) {
907 ALOGD("getmtime() could not contact remote: %d\n", status);
908 return -1;
909 }
910 int32_t err = reply.readExceptionCode();
911 int64_t ret = reply.readInt64();
912 if (err < 0) {
913 ALOGD("getmtime() caught exception %d\n", err);
914 return -1;
915 }
916 return ret;
917 }
Kenny Root02254072013-03-20 11:48:19 -0700918
Kenny Rootd53bc922013-03-21 14:10:15 -0700919 virtual int32_t duplicate(const String16& srcKey, int32_t srcUid, const String16& destKey,
920 int32_t destUid)
Kenny Root02254072013-03-20 11:48:19 -0700921 {
922 Parcel data, reply;
923 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
Kenny Rootd53bc922013-03-21 14:10:15 -0700924 data.writeString16(srcKey);
925 data.writeInt32(srcUid);
926 data.writeString16(destKey);
927 data.writeInt32(destUid);
928 status_t status = remote()->transact(BnKeystoreService::DUPLICATE, data, &reply);
Kenny Root02254072013-03-20 11:48:19 -0700929 if (status != NO_ERROR) {
Kenny Rootd53bc922013-03-21 14:10:15 -0700930 ALOGD("duplicate() could not contact remote: %d\n", status);
Kenny Root02254072013-03-20 11:48:19 -0700931 return -1;
932 }
933 int32_t err = reply.readExceptionCode();
934 int32_t ret = reply.readInt32();
935 if (err < 0) {
Kenny Rootd53bc922013-03-21 14:10:15 -0700936 ALOGD("duplicate() caught exception %d\n", err);
Kenny Root02254072013-03-20 11:48:19 -0700937 return -1;
938 }
939 return ret;
940 }
Kenny Root43061232013-03-29 11:15:50 -0700941
Kenny Root1b0e3932013-09-05 13:06:32 -0700942 virtual int32_t is_hardware_backed(const String16& keyType)
Kenny Root43061232013-03-29 11:15:50 -0700943 {
944 Parcel data, reply;
945 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
Kenny Root1b0e3932013-09-05 13:06:32 -0700946 data.writeString16(keyType);
Kenny Root43061232013-03-29 11:15:50 -0700947 status_t status = remote()->transact(BnKeystoreService::IS_HARDWARE_BACKED, data, &reply);
948 if (status != NO_ERROR) {
949 ALOGD("is_hardware_backed() could not contact remote: %d\n", status);
950 return -1;
951 }
952 int32_t err = reply.readExceptionCode();
953 int32_t ret = reply.readInt32();
954 if (err < 0) {
955 ALOGD("is_hardware_backed() caught exception %d\n", err);
956 return -1;
957 }
958 return ret;
959 }
Kenny Root2ecc7a12013-04-01 16:29:11 -0700960
961 virtual int32_t clear_uid(int64_t uid)
962 {
963 Parcel data, reply;
964 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
965 data.writeInt64(uid);
966 status_t status = remote()->transact(BnKeystoreService::CLEAR_UID, data, &reply);
967 if (status != NO_ERROR) {
968 ALOGD("clear_uid() could not contact remote: %d\n", status);
969 return -1;
970 }
971 int32_t err = reply.readExceptionCode();
972 int32_t ret = reply.readInt32();
973 if (err < 0) {
974 ALOGD("clear_uid() caught exception %d\n", err);
975 return -1;
976 }
977 return ret;
978 }
Robin Lee4e865752014-08-19 17:37:55 +0100979
Chad Brubaker9899d6b2015-02-03 13:03:00 -0800980 virtual int32_t addRngEntropy(const uint8_t* buf, size_t bufLength)
981 {
982 Parcel data, reply;
983 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
Chad Brubaker9899d6b2015-02-03 13:03:00 -0800984 data.writeByteArray(bufLength, buf);
985 status_t status = remote()->transact(BnKeystoreService::ADD_RNG_ENTROPY, data, &reply);
986 if (status != NO_ERROR) {
987 ALOGD("addRngEntropy() could not contact remote: %d\n", status);
988 return -1;
989 }
990 int32_t err = reply.readExceptionCode();
991 int32_t ret = reply.readInt32();
992 if (err < 0) {
993 ALOGD("addRngEntropy() caught exception %d\n", err);
994 return -1;
995 }
996 return ret;
997 };
998
999 virtual int32_t generateKey(const String16& name, const KeymasterArguments& params,
Chad Brubaker154d7692015-03-27 13:59:31 -07001000 const uint8_t* entropy, size_t entropyLength, int uid, int flags,
1001 KeyCharacteristics* outCharacteristics)
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001002 {
1003 Parcel data, reply;
1004 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
1005 data.writeString16(name);
1006 data.writeInt32(1);
1007 params.writeToParcel(&data);
Chad Brubaker154d7692015-03-27 13:59:31 -07001008 data.writeByteArray(entropyLength, entropy);
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001009 data.writeInt32(uid);
1010 data.writeInt32(flags);
1011 status_t status = remote()->transact(BnKeystoreService::GENERATE_KEY, data, &reply);
1012 if (status != NO_ERROR) {
1013 ALOGD("generateKey() could not contact remote: %d\n", status);
1014 return KM_ERROR_UNKNOWN_ERROR;
1015 }
1016 int32_t err = reply.readExceptionCode();
1017 int32_t ret = reply.readInt32();
1018 if (err < 0) {
1019 ALOGD("generateKey() caught exception %d\n", err);
1020 return KM_ERROR_UNKNOWN_ERROR;
1021 }
1022 if (reply.readInt32() != 0 && outCharacteristics) {
1023 outCharacteristics->readFromParcel(reply);
1024 }
1025 return ret;
1026 }
1027 virtual int32_t getKeyCharacteristics(const String16& name,
Chad Brubakerd6634422015-03-21 22:36:07 -07001028 const keymaster_blob_t* clientId,
1029 const keymaster_blob_t* appData,
Chad Brubakerad6a7f52015-09-09 14:55:22 -07001030 int32_t uid, KeyCharacteristics* outCharacteristics)
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001031 {
1032 Parcel data, reply;
1033 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
1034 data.writeString16(name);
Chad Brubakerd6634422015-03-21 22:36:07 -07001035 if (clientId) {
1036 data.writeByteArray(clientId->data_length, clientId->data);
1037 } else {
1038 data.writeInt32(-1);
1039 }
1040 if (appData) {
1041 data.writeByteArray(appData->data_length, appData->data);
1042 } else {
1043 data.writeInt32(-1);
1044 }
Chad Brubakerad6a7f52015-09-09 14:55:22 -07001045 data.writeInt32(uid);
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001046 status_t status = remote()->transact(BnKeystoreService::GET_KEY_CHARACTERISTICS,
1047 data, &reply);
1048 if (status != NO_ERROR) {
1049 ALOGD("getKeyCharacteristics() could not contact remote: %d\n", status);
1050 return KM_ERROR_UNKNOWN_ERROR;
1051 }
1052 int32_t err = reply.readExceptionCode();
1053 int32_t ret = reply.readInt32();
1054 if (err < 0) {
1055 ALOGD("getKeyCharacteristics() caught exception %d\n", err);
1056 return KM_ERROR_UNKNOWN_ERROR;
1057 }
1058 if (reply.readInt32() != 0 && outCharacteristics) {
1059 outCharacteristics->readFromParcel(reply);
1060 }
1061 return ret;
1062 }
1063 virtual int32_t importKey(const String16& name, const KeymasterArguments& params,
1064 keymaster_key_format_t format, const uint8_t *keyData,
1065 size_t keyLength, int uid, int flags,
1066 KeyCharacteristics* outCharacteristics)
1067 {
1068 Parcel data, reply;
1069 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
1070 data.writeString16(name);
1071 data.writeInt32(1);
1072 params.writeToParcel(&data);
1073 data.writeInt32(format);
1074 data.writeByteArray(keyLength, keyData);
1075 data.writeInt32(uid);
1076 data.writeInt32(flags);
1077 status_t status = remote()->transact(BnKeystoreService::IMPORT_KEY, data, &reply);
1078 if (status != NO_ERROR) {
1079 ALOGD("importKey() could not contact remote: %d\n", status);
1080 return KM_ERROR_UNKNOWN_ERROR;
1081 }
1082 int32_t err = reply.readExceptionCode();
1083 int32_t ret = reply.readInt32();
1084 if (err < 0) {
1085 ALOGD("importKey() caught exception %d\n", err);
1086 return KM_ERROR_UNKNOWN_ERROR;
1087 }
1088 if (reply.readInt32() != 0 && outCharacteristics) {
1089 outCharacteristics->readFromParcel(reply);
1090 }
1091 return ret;
1092 }
1093
1094 virtual void exportKey(const String16& name, keymaster_key_format_t format,
Chad Brubakerd6634422015-03-21 22:36:07 -07001095 const keymaster_blob_t* clientId,
Chad Brubakerad6a7f52015-09-09 14:55:22 -07001096 const keymaster_blob_t* appData, int32_t uid, ExportResult* result)
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001097 {
1098 if (!result) {
1099 return;
1100 }
1101
1102 Parcel data, reply;
1103 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
1104 data.writeString16(name);
1105 data.writeInt32(format);
Chad Brubakerd6634422015-03-21 22:36:07 -07001106 if (clientId) {
1107 data.writeByteArray(clientId->data_length, clientId->data);
1108 } else {
1109 data.writeInt32(-1);
1110 }
1111 if (appData) {
1112 data.writeByteArray(appData->data_length, appData->data);
1113 } else {
1114 data.writeInt32(-1);
1115 }
Chad Brubakerad6a7f52015-09-09 14:55:22 -07001116 data.writeInt32(uid);
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001117 status_t status = remote()->transact(BnKeystoreService::EXPORT_KEY, data, &reply);
1118 if (status != NO_ERROR) {
1119 ALOGD("exportKey() could not contact remote: %d\n", status);
1120 result->resultCode = KM_ERROR_UNKNOWN_ERROR;
1121 return;
1122 }
1123 int32_t err = reply.readExceptionCode();
1124 if (err < 0) {
1125 ALOGD("exportKey() caught exception %d\n", err);
1126 result->resultCode = KM_ERROR_UNKNOWN_ERROR;
1127 return;
1128 }
1129 if (reply.readInt32() != 0) {
1130 result->readFromParcel(reply);
1131 }
1132 }
1133
1134 virtual void begin(const sp<IBinder>& appToken, const String16& name,
1135 keymaster_purpose_t purpose, bool pruneable,
Chad Brubaker154d7692015-03-27 13:59:31 -07001136 const KeymasterArguments& params, const uint8_t* entropy,
Chad Brubakerad6a7f52015-09-09 14:55:22 -07001137 size_t entropyLength, int32_t uid, OperationResult* result)
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001138 {
Chad Brubaker57e106d2015-06-01 12:59:00 -07001139 if (!result) {
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001140 return;
1141 }
1142 Parcel data, reply;
1143 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
1144 data.writeStrongBinder(appToken);
1145 data.writeString16(name);
1146 data.writeInt32(purpose);
1147 data.writeInt32(pruneable ? 1 : 0);
1148 data.writeInt32(1);
1149 params.writeToParcel(&data);
Chad Brubaker154d7692015-03-27 13:59:31 -07001150 data.writeByteArray(entropyLength, entropy);
Chad Brubakerad6a7f52015-09-09 14:55:22 -07001151 data.writeInt32(uid);
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001152 status_t status = remote()->transact(BnKeystoreService::BEGIN, data, &reply);
1153 if (status != NO_ERROR) {
1154 ALOGD("begin() could not contact remote: %d\n", status);
1155 result->resultCode = KM_ERROR_UNKNOWN_ERROR;
1156 return;
1157 }
1158 int32_t err = reply.readExceptionCode();
1159 if (err < 0) {
1160 ALOGD("begin() caught exception %d\n", err);
1161 result->resultCode = KM_ERROR_UNKNOWN_ERROR;
1162 return;
1163 }
1164 if (reply.readInt32() != 0) {
1165 result->readFromParcel(reply);
1166 }
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001167 }
1168
1169 virtual void update(const sp<IBinder>& token, const KeymasterArguments& params,
Chad Brubaker40a1a9b2015-02-20 14:08:13 -08001170 const uint8_t* opData, size_t dataLength, OperationResult* result)
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001171 {
1172 if (!result) {
1173 return;
1174 }
1175 Parcel data, reply;
1176 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
1177 data.writeStrongBinder(token);
1178 data.writeInt32(1);
1179 params.writeToParcel(&data);
1180 data.writeByteArray(dataLength, opData);
1181 status_t status = remote()->transact(BnKeystoreService::UPDATE, data, &reply);
1182 if (status != NO_ERROR) {
1183 ALOGD("update() could not contact remote: %d\n", status);
1184 result->resultCode = KM_ERROR_UNKNOWN_ERROR;
1185 return;
1186 }
1187 int32_t err = reply.readExceptionCode();
1188 if (err < 0) {
1189 ALOGD("update() caught exception %d\n", err);
1190 result->resultCode = KM_ERROR_UNKNOWN_ERROR;
1191 return;
1192 }
1193 if (reply.readInt32() != 0) {
1194 result->readFromParcel(reply);
1195 }
1196 }
1197
1198 virtual void finish(const sp<IBinder>& token, const KeymasterArguments& params,
Chad Brubaker0d33e0b2015-05-29 12:30:19 -07001199 const uint8_t* signature, size_t signatureLength,
1200 const uint8_t* entropy, size_t entropyLength,
1201 OperationResult* result)
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001202 {
1203 if (!result) {
1204 return;
1205 }
1206 Parcel data, reply;
1207 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
1208 data.writeStrongBinder(token);
1209 data.writeInt32(1);
1210 params.writeToParcel(&data);
1211 data.writeByteArray(signatureLength, signature);
Chad Brubaker0d33e0b2015-05-29 12:30:19 -07001212 data.writeByteArray(entropyLength, entropy);
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001213 status_t status = remote()->transact(BnKeystoreService::FINISH, data, &reply);
1214 if (status != NO_ERROR) {
1215 ALOGD("finish() could not contact remote: %d\n", status);
1216 result->resultCode = KM_ERROR_UNKNOWN_ERROR;
1217 return;
1218 }
1219 int32_t err = reply.readExceptionCode();
1220 if (err < 0) {
1221 ALOGD("finish() caught exception %d\n", err);
1222 result->resultCode = KM_ERROR_UNKNOWN_ERROR;
1223 return;
1224 }
1225 if (reply.readInt32() != 0) {
1226 result->readFromParcel(reply);
1227 }
1228 }
1229
1230 virtual int32_t abort(const sp<IBinder>& token)
1231 {
1232 Parcel data, reply;
1233 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
1234 data.writeStrongBinder(token);
Chad Brubaker2ed2baa2015-03-21 21:20:10 -07001235 status_t status = remote()->transact(BnKeystoreService::ABORT, data, &reply);
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001236 if (status != NO_ERROR) {
1237 ALOGD("abort() could not contact remote: %d\n", status);
1238 return KM_ERROR_UNKNOWN_ERROR;
1239 }
1240 int32_t err = reply.readExceptionCode();
1241 int32_t ret = reply.readInt32();
1242 if (err < 0) {
1243 ALOGD("abort() caught exception %d\n", err);
1244 return KM_ERROR_UNKNOWN_ERROR;
1245 }
1246 return ret;
1247 }
Chad Brubaker2ed2baa2015-03-21 21:20:10 -07001248
1249 virtual bool isOperationAuthorized(const sp<IBinder>& token)
1250 {
1251 Parcel data, reply;
1252 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
1253 data.writeStrongBinder(token);
1254 status_t status = remote()->transact(BnKeystoreService::IS_OPERATION_AUTHORIZED, data,
1255 &reply);
1256 if (status != NO_ERROR) {
1257 ALOGD("isOperationAuthorized() could not contact remote: %d\n", status);
1258 return false;
1259 }
1260 int32_t err = reply.readExceptionCode();
1261 int32_t ret = reply.readInt32();
1262 if (err < 0) {
1263 ALOGD("isOperationAuthorized() caught exception %d\n", err);
1264 return false;
1265 }
1266 return ret == 1;
1267 }
1268
1269 virtual int32_t addAuthToken(const uint8_t* token, size_t length)
1270 {
1271 Parcel data, reply;
1272 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
1273 data.writeByteArray(length, token);
1274 status_t status = remote()->transact(BnKeystoreService::ADD_AUTH_TOKEN, data, &reply);
1275 if (status != NO_ERROR) {
1276 ALOGD("addAuthToken() could not contact remote: %d\n", status);
1277 return -1;
1278 }
1279 int32_t err = reply.readExceptionCode();
1280 int32_t ret = reply.readInt32();
1281 if (err < 0) {
1282 ALOGD("addAuthToken() caught exception %d\n", err);
1283 return -1;
1284 }
1285 return ret;
1286 };
Chad Brubakerc0f031a2015-05-12 10:43:10 -07001287
1288 virtual int32_t onUserAdded(int32_t userId, int32_t parentId)
1289 {
1290 Parcel data, reply;
1291 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
1292 data.writeInt32(userId);
1293 data.writeInt32(parentId);
1294 status_t status = remote()->transact(BnKeystoreService::ON_USER_ADDED, data, &reply);
1295 if (status != NO_ERROR) {
1296 ALOGD("onUserAdded() could not contact remote: %d\n", status);
1297 return -1;
1298 }
1299 int32_t err = reply.readExceptionCode();
1300 int32_t ret = reply.readInt32();
1301 if (err < 0) {
1302 ALOGD("onUserAdded() caught exception %d\n", err);
1303 return -1;
1304 }
1305 return ret;
1306 }
1307
1308 virtual int32_t onUserRemoved(int32_t userId)
1309 {
1310 Parcel data, reply;
1311 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
1312 data.writeInt32(userId);
1313 status_t status = remote()->transact(BnKeystoreService::ON_USER_REMOVED, data, &reply);
1314 if (status != NO_ERROR) {
1315 ALOGD("onUserRemoved() could not contact remote: %d\n", status);
1316 return -1;
1317 }
1318 int32_t err = reply.readExceptionCode();
1319 int32_t ret = reply.readInt32();
1320 if (err < 0) {
1321 ALOGD("onUserRemoved() caught exception %d\n", err);
1322 return -1;
1323 }
1324 return ret;
1325 }
1326
Shawn Willden50eb1b22016-01-21 12:41:23 -07001327 virtual int32_t attestKey(const String16& name, const KeymasterArguments& params,
1328 KeymasterCertificateChain* outChain) {
1329 if (!outChain)
1330 return KM_ERROR_OUTPUT_PARAMETER_NULL;
1331
1332 Parcel data, reply;
1333 data.writeInterfaceToken(IKeystoreService::getInterfaceDescriptor());
1334 data.writeString16(name);
1335 data.writeInt32(1); // params is not NULL.
1336 params.writeToParcel(&data);
1337
1338 status_t status = remote()->transact(BnKeystoreService::ATTEST_KEY, data, &reply);
1339 if (status != NO_ERROR) {
1340 ALOGD("attestkey() count not contact remote: %d\n", status);
1341 return KM_ERROR_UNKNOWN_ERROR;
1342 }
1343 int32_t err = reply.readExceptionCode();
1344 int32_t ret = reply.readInt32();
1345 if (err < 0) {
1346 ALOGD("attestKey() caught exception %d\n", err);
1347 return KM_ERROR_UNKNOWN_ERROR;
1348 }
1349 if (reply.readInt32() != 0) {
1350 outChain->readFromParcel(reply);
1351 }
1352 return ret;
1353 }
1354
Kenny Root07438c82012-11-02 15:41:02 -07001355};
1356
Chad Brubaker468fc692015-01-13 17:33:14 -08001357IMPLEMENT_META_INTERFACE(KeystoreService, "android.security.IKeystoreService");
Kenny Root07438c82012-11-02 15:41:02 -07001358
1359// ----------------------------------------------------------------------
1360
1361status_t BnKeystoreService::onTransact(
1362 uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags)
1363{
1364 switch(code) {
Chad Brubakere6c3bfa2015-05-12 15:18:26 -07001365 case GET_STATE: {
Kenny Root07438c82012-11-02 15:41:02 -07001366 CHECK_INTERFACE(IKeystoreService, data, reply);
Chad Brubakere6c3bfa2015-05-12 15:18:26 -07001367 int32_t userId = data.readInt32();
1368 int32_t ret = getState(userId);
Kenny Root07438c82012-11-02 15:41:02 -07001369 reply->writeNoException();
1370 reply->writeInt32(ret);
1371 return NO_ERROR;
1372 } break;
1373 case GET: {
1374 CHECK_INTERFACE(IKeystoreService, data, reply);
1375 String16 name = data.readString16();
Chad Brubakerad6a7f52015-09-09 14:55:22 -07001376 int32_t uid = data.readInt32();
Kenny Root07438c82012-11-02 15:41:02 -07001377 void* out = NULL;
1378 size_t outSize = 0;
Chad Brubakerad6a7f52015-09-09 14:55:22 -07001379 int32_t ret = get(name, uid, (uint8_t**) &out, &outSize);
Kenny Root07438c82012-11-02 15:41:02 -07001380 reply->writeNoException();
1381 if (ret == 1) {
1382 reply->writeInt32(outSize);
1383 void* buf = reply->writeInplace(outSize);
1384 memcpy(buf, out, outSize);
1385 free(out);
1386 } else {
1387 reply->writeInt32(-1);
1388 }
1389 return NO_ERROR;
1390 } break;
1391 case INSERT: {
1392 CHECK_INTERFACE(IKeystoreService, data, reply);
1393 String16 name = data.readString16();
1394 ssize_t inSize = data.readInt32();
1395 const void* in;
1396 if (inSize >= 0 && (size_t) inSize <= data.dataAvail()) {
1397 in = data.readInplace(inSize);
1398 } else {
1399 in = NULL;
1400 inSize = 0;
1401 }
Kenny Rootb88c3eb2013-02-13 14:43:43 -08001402 int uid = data.readInt32();
Kenny Root0c540aa2013-04-03 09:22:15 -07001403 int32_t flags = data.readInt32();
1404 int32_t ret = insert(name, (const uint8_t*) in, (size_t) inSize, uid, flags);
Kenny Root07438c82012-11-02 15:41:02 -07001405 reply->writeNoException();
1406 reply->writeInt32(ret);
1407 return NO_ERROR;
1408 } break;
1409 case DEL: {
1410 CHECK_INTERFACE(IKeystoreService, data, reply);
1411 String16 name = data.readString16();
Kenny Rootb88c3eb2013-02-13 14:43:43 -08001412 int uid = data.readInt32();
1413 int32_t ret = del(name, uid);
Kenny Root07438c82012-11-02 15:41:02 -07001414 reply->writeNoException();
1415 reply->writeInt32(ret);
1416 return NO_ERROR;
1417 } break;
1418 case EXIST: {
1419 CHECK_INTERFACE(IKeystoreService, data, reply);
1420 String16 name = data.readString16();
Kenny Rootb88c3eb2013-02-13 14:43:43 -08001421 int uid = data.readInt32();
1422 int32_t ret = exist(name, uid);
Kenny Root07438c82012-11-02 15:41:02 -07001423 reply->writeNoException();
1424 reply->writeInt32(ret);
1425 return NO_ERROR;
1426 } break;
Chad Brubakere6c3bfa2015-05-12 15:18:26 -07001427 case LIST: {
Kenny Root07438c82012-11-02 15:41:02 -07001428 CHECK_INTERFACE(IKeystoreService, data, reply);
Chad Brubakere6c3bfa2015-05-12 15:18:26 -07001429 String16 prefix = data.readString16();
Kenny Rootb88c3eb2013-02-13 14:43:43 -08001430 int uid = data.readInt32();
Kenny Root07438c82012-11-02 15:41:02 -07001431 Vector<String16> matches;
Chad Brubakere6c3bfa2015-05-12 15:18:26 -07001432 int32_t ret = list(prefix, uid, &matches);
Kenny Root07438c82012-11-02 15:41:02 -07001433 reply->writeNoException();
1434 reply->writeInt32(matches.size());
1435 Vector<String16>::const_iterator it = matches.begin();
1436 for (; it != matches.end(); ++it) {
1437 reply->writeString16(*it);
1438 }
1439 reply->writeInt32(ret);
1440 return NO_ERROR;
1441 } break;
1442 case RESET: {
1443 CHECK_INTERFACE(IKeystoreService, data, reply);
1444 int32_t ret = reset();
1445 reply->writeNoException();
1446 reply->writeInt32(ret);
1447 return NO_ERROR;
1448 } break;
Chad Brubaker96d6d782015-05-07 10:19:40 -07001449 case ON_USER_PASSWORD_CHANGED: {
Kenny Root07438c82012-11-02 15:41:02 -07001450 CHECK_INTERFACE(IKeystoreService, data, reply);
Chad Brubaker96d6d782015-05-07 10:19:40 -07001451 int32_t userId = data.readInt32();
Kenny Root07438c82012-11-02 15:41:02 -07001452 String16 pass = data.readString16();
Chad Brubaker96d6d782015-05-07 10:19:40 -07001453 int32_t ret = onUserPasswordChanged(userId, pass);
Kenny Root07438c82012-11-02 15:41:02 -07001454 reply->writeNoException();
1455 reply->writeInt32(ret);
1456 return NO_ERROR;
1457 } break;
1458 case LOCK: {
1459 CHECK_INTERFACE(IKeystoreService, data, reply);
Chad Brubakere6c3bfa2015-05-12 15:18:26 -07001460 int32_t userId = data.readInt32();
1461 int32_t ret = lock(userId);
Kenny Root07438c82012-11-02 15:41:02 -07001462 reply->writeNoException();
1463 reply->writeInt32(ret);
1464 return NO_ERROR;
1465 } break;
1466 case UNLOCK: {
1467 CHECK_INTERFACE(IKeystoreService, data, reply);
Chad Brubaker96d6d782015-05-07 10:19:40 -07001468 int32_t userId = data.readInt32();
Kenny Root07438c82012-11-02 15:41:02 -07001469 String16 pass = data.readString16();
Chad Brubaker96d6d782015-05-07 10:19:40 -07001470 int32_t ret = unlock(userId, pass);
Kenny Root07438c82012-11-02 15:41:02 -07001471 reply->writeNoException();
1472 reply->writeInt32(ret);
1473 return NO_ERROR;
1474 } break;
Chad Brubakere6c3bfa2015-05-12 15:18:26 -07001475 case IS_EMPTY: {
Kenny Root07438c82012-11-02 15:41:02 -07001476 CHECK_INTERFACE(IKeystoreService, data, reply);
Chad Brubakere6c3bfa2015-05-12 15:18:26 -07001477 int32_t userId = data.readInt32();
1478 bool ret = isEmpty(userId);
Kenny Root07438c82012-11-02 15:41:02 -07001479 reply->writeNoException();
Chad Brubakere6c3bfa2015-05-12 15:18:26 -07001480 reply->writeInt32(ret ? 1 : 0);
Kenny Root07438c82012-11-02 15:41:02 -07001481 return NO_ERROR;
1482 } break;
1483 case GENERATE: {
1484 CHECK_INTERFACE(IKeystoreService, data, reply);
1485 String16 name = data.readString16();
Kenny Root96427ba2013-08-16 14:02:41 -07001486 int32_t uid = data.readInt32();
1487 int32_t keyType = data.readInt32();
1488 int32_t keySize = data.readInt32();
Kenny Root0c540aa2013-04-03 09:22:15 -07001489 int32_t flags = data.readInt32();
Kenny Root96427ba2013-08-16 14:02:41 -07001490 Vector<sp<KeystoreArg> > args;
Chad Brubaker468fc692015-01-13 17:33:14 -08001491 int32_t argsPresent = data.readInt32();
1492 if (argsPresent == 1) {
1493 ssize_t numArgs = data.readInt32();
Chad Brubakered4f5662015-01-14 19:22:09 -08001494 if (numArgs > MAX_GENERATE_ARGS) {
1495 return BAD_VALUE;
1496 }
Chad Brubaker468fc692015-01-13 17:33:14 -08001497 if (numArgs > 0) {
1498 for (size_t i = 0; i < (size_t) numArgs; i++) {
1499 ssize_t inSize = data.readInt32();
1500 if (inSize >= 0 && (size_t) inSize <= data.dataAvail()) {
1501 sp<KeystoreArg> arg = new KeystoreArg(data.readInplace(inSize),
1502 inSize);
1503 args.push_back(arg);
1504 } else {
1505 args.push_back(NULL);
1506 }
Kenny Root96427ba2013-08-16 14:02:41 -07001507 }
1508 }
1509 }
1510 int32_t ret = generate(name, uid, keyType, keySize, flags, &args);
Kenny Root07438c82012-11-02 15:41:02 -07001511 reply->writeNoException();
1512 reply->writeInt32(ret);
1513 return NO_ERROR;
1514 } break;
1515 case IMPORT: {
1516 CHECK_INTERFACE(IKeystoreService, data, reply);
1517 String16 name = data.readString16();
1518 ssize_t inSize = data.readInt32();
1519 const void* in;
1520 if (inSize >= 0 && (size_t) inSize <= data.dataAvail()) {
1521 in = data.readInplace(inSize);
1522 } else {
1523 in = NULL;
1524 inSize = 0;
1525 }
Kenny Rootb88c3eb2013-02-13 14:43:43 -08001526 int uid = data.readInt32();
Kenny Root0c540aa2013-04-03 09:22:15 -07001527 int32_t flags = data.readInt32();
1528 int32_t ret = import(name, (const uint8_t*) in, (size_t) inSize, uid, flags);
Kenny Root07438c82012-11-02 15:41:02 -07001529 reply->writeNoException();
1530 reply->writeInt32(ret);
1531 return NO_ERROR;
1532 } break;
1533 case SIGN: {
1534 CHECK_INTERFACE(IKeystoreService, data, reply);
1535 String16 name = data.readString16();
1536 ssize_t inSize = data.readInt32();
1537 const void* in;
1538 if (inSize >= 0 && (size_t) inSize <= data.dataAvail()) {
1539 in = data.readInplace(inSize);
1540 } else {
1541 in = NULL;
1542 inSize = 0;
1543 }
1544 void* out = NULL;
1545 size_t outSize = 0;
1546 int32_t ret = sign(name, (const uint8_t*) in, (size_t) inSize, (uint8_t**) &out, &outSize);
1547 reply->writeNoException();
Kenny Rootb03c9fb2013-02-04 16:42:51 -08001548 if (outSize > 0 && out != NULL) {
1549 reply->writeInt32(outSize);
1550 void* buf = reply->writeInplace(outSize);
1551 memcpy(buf, out, outSize);
Chad Brubaker3a7d9e62015-06-04 15:01:46 -07001552 delete[] reinterpret_cast<uint8_t*>(out);
Kenny Rootb03c9fb2013-02-04 16:42:51 -08001553 } else {
Kenny Roote289c402013-02-14 11:31:53 -08001554 reply->writeInt32(-1);
Kenny Rootb03c9fb2013-02-04 16:42:51 -08001555 }
Kenny Root07438c82012-11-02 15:41:02 -07001556 reply->writeInt32(ret);
1557 return NO_ERROR;
1558 } break;
1559 case VERIFY: {
1560 CHECK_INTERFACE(IKeystoreService, data, reply);
1561 String16 name = data.readString16();
1562 ssize_t inSize = data.readInt32();
1563 const void* in;
1564 if (inSize >= 0 && (size_t) inSize <= data.dataAvail()) {
1565 in = data.readInplace(inSize);
1566 } else {
1567 in = NULL;
1568 inSize = 0;
1569 }
1570 ssize_t sigSize = data.readInt32();
1571 const void* sig;
1572 if (sigSize >= 0 && (size_t) sigSize <= data.dataAvail()) {
1573 sig = data.readInplace(sigSize);
1574 } else {
1575 sig = NULL;
1576 sigSize = 0;
1577 }
1578 bool ret = verify(name, (const uint8_t*) in, (size_t) inSize, (const uint8_t*) sig,
1579 (size_t) sigSize);
1580 reply->writeNoException();
1581 reply->writeInt32(ret ? 1 : 0);
1582 return NO_ERROR;
1583 } break;
1584 case GET_PUBKEY: {
1585 CHECK_INTERFACE(IKeystoreService, data, reply);
1586 String16 name = data.readString16();
1587 void* out = NULL;
1588 size_t outSize = 0;
1589 int32_t ret = get_pubkey(name, (unsigned char**) &out, &outSize);
1590 reply->writeNoException();
Kenny Rootb03c9fb2013-02-04 16:42:51 -08001591 if (outSize > 0 && out != NULL) {
1592 reply->writeInt32(outSize);
1593 void* buf = reply->writeInplace(outSize);
1594 memcpy(buf, out, outSize);
1595 free(out);
1596 } else {
Kenny Roote289c402013-02-14 11:31:53 -08001597 reply->writeInt32(-1);
Kenny Rootb03c9fb2013-02-04 16:42:51 -08001598 }
Kenny Root07438c82012-11-02 15:41:02 -07001599 reply->writeInt32(ret);
1600 return NO_ERROR;
Kenny Rootb03c9fb2013-02-04 16:42:51 -08001601 } break;
Kenny Root07438c82012-11-02 15:41:02 -07001602 case GRANT: {
1603 CHECK_INTERFACE(IKeystoreService, data, reply);
1604 String16 name = data.readString16();
1605 int32_t granteeUid = data.readInt32();
1606 int32_t ret = grant(name, granteeUid);
1607 reply->writeNoException();
1608 reply->writeInt32(ret);
1609 return NO_ERROR;
1610 } break;
1611 case UNGRANT: {
1612 CHECK_INTERFACE(IKeystoreService, data, reply);
1613 String16 name = data.readString16();
1614 int32_t granteeUid = data.readInt32();
1615 int32_t ret = ungrant(name, granteeUid);
1616 reply->writeNoException();
1617 reply->writeInt32(ret);
1618 return NO_ERROR;
1619 } break;
1620 case GETMTIME: {
1621 CHECK_INTERFACE(IKeystoreService, data, reply);
1622 String16 name = data.readString16();
Chad Brubakerad6a7f52015-09-09 14:55:22 -07001623 int32_t uid = data.readInt32();
1624 int64_t ret = getmtime(name, uid);
Kenny Root07438c82012-11-02 15:41:02 -07001625 reply->writeNoException();
1626 reply->writeInt64(ret);
1627 return NO_ERROR;
1628 } break;
Kenny Rootd53bc922013-03-21 14:10:15 -07001629 case DUPLICATE: {
Kenny Root02254072013-03-20 11:48:19 -07001630 CHECK_INTERFACE(IKeystoreService, data, reply);
Kenny Rootd53bc922013-03-21 14:10:15 -07001631 String16 srcKey = data.readString16();
1632 int32_t srcUid = data.readInt32();
1633 String16 destKey = data.readString16();
1634 int32_t destUid = data.readInt32();
1635 int32_t ret = duplicate(srcKey, srcUid, destKey, destUid);
Kenny Root02254072013-03-20 11:48:19 -07001636 reply->writeNoException();
1637 reply->writeInt32(ret);
1638 return NO_ERROR;
1639 } break;
Kenny Root43061232013-03-29 11:15:50 -07001640 case IS_HARDWARE_BACKED: {
1641 CHECK_INTERFACE(IKeystoreService, data, reply);
Kenny Root1b0e3932013-09-05 13:06:32 -07001642 String16 keyType = data.readString16();
1643 int32_t ret = is_hardware_backed(keyType);
Kenny Root43061232013-03-29 11:15:50 -07001644 reply->writeNoException();
1645 reply->writeInt32(ret);
1646 return NO_ERROR;
1647 }
Kenny Root2ecc7a12013-04-01 16:29:11 -07001648 case CLEAR_UID: {
1649 CHECK_INTERFACE(IKeystoreService, data, reply);
1650 int64_t uid = data.readInt64();
1651 int32_t ret = clear_uid(uid);
1652 reply->writeNoException();
1653 reply->writeInt32(ret);
1654 return NO_ERROR;
1655 }
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001656 case ADD_RNG_ENTROPY: {
1657 CHECK_INTERFACE(IKeystoreService, data, reply);
Chad Brubaker6432df72015-03-20 16:23:04 -07001658 const uint8_t* bytes = NULL;
1659 size_t size = 0;
1660 readByteArray(data, &bytes, &size);
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001661 int32_t ret = addRngEntropy(bytes, size);
1662 reply->writeNoException();
1663 reply->writeInt32(ret);
1664 return NO_ERROR;
1665 }
1666 case GENERATE_KEY: {
1667 CHECK_INTERFACE(IKeystoreService, data, reply);
1668 String16 name = data.readString16();
1669 KeymasterArguments args;
1670 if (data.readInt32() != 0) {
1671 args.readFromParcel(data);
1672 }
Chad Brubaker154d7692015-03-27 13:59:31 -07001673 const uint8_t* entropy = NULL;
1674 size_t entropyLength = 0;
1675 readByteArray(data, &entropy, &entropyLength);
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001676 int32_t uid = data.readInt32();
1677 int32_t flags = data.readInt32();
1678 KeyCharacteristics outCharacteristics;
Chad Brubaker154d7692015-03-27 13:59:31 -07001679 int32_t ret = generateKey(name, args, entropy, entropyLength, uid, flags,
1680 &outCharacteristics);
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001681 reply->writeNoException();
1682 reply->writeInt32(ret);
1683 reply->writeInt32(1);
1684 outCharacteristics.writeToParcel(reply);
1685 return NO_ERROR;
1686 }
1687 case GET_KEY_CHARACTERISTICS: {
1688 CHECK_INTERFACE(IKeystoreService, data, reply);
1689 String16 name = data.readString16();
Chad Brubakerd6634422015-03-21 22:36:07 -07001690 std::unique_ptr<keymaster_blob_t> clientId = readKeymasterBlob(data);
1691 std::unique_ptr<keymaster_blob_t> appData = readKeymasterBlob(data);
Chad Brubakerad6a7f52015-09-09 14:55:22 -07001692 int32_t uid = data.readInt32();
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001693 KeyCharacteristics outCharacteristics;
Chad Brubakerad6a7f52015-09-09 14:55:22 -07001694 int ret = getKeyCharacteristics(name, clientId.get(), appData.get(), uid,
Chad Brubakerd6634422015-03-21 22:36:07 -07001695 &outCharacteristics);
Bin Chen62ddfe02016-09-02 22:01:36 +10001696 if (clientId.get() && clientId->data) {
1697 free(const_cast<void*>(static_cast<const void*>(clientId->data)));
1698 }
1699 if (appData.get() && appData->data) {
1700 free(const_cast<void*>(static_cast<const void*>(appData->data)));
1701 }
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001702 reply->writeNoException();
1703 reply->writeInt32(ret);
1704 reply->writeInt32(1);
1705 outCharacteristics.writeToParcel(reply);
1706 return NO_ERROR;
1707 }
1708 case IMPORT_KEY: {
1709 CHECK_INTERFACE(IKeystoreService, data, reply);
1710 String16 name = data.readString16();
1711 KeymasterArguments args;
1712 if (data.readInt32() != 0) {
1713 args.readFromParcel(data);
1714 }
1715 keymaster_key_format_t format = static_cast<keymaster_key_format_t>(data.readInt32());
Chad Brubaker6432df72015-03-20 16:23:04 -07001716 const uint8_t* keyData = NULL;
1717 size_t keyLength = 0;
1718 readByteArray(data, &keyData, &keyLength);
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001719 int32_t uid = data.readInt32();
1720 int32_t flags = data.readInt32();
1721 KeyCharacteristics outCharacteristics;
Chad Brubaker6432df72015-03-20 16:23:04 -07001722 int32_t ret = importKey(name, args, format, keyData, keyLength, uid, flags,
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001723 &outCharacteristics);
1724 reply->writeNoException();
1725 reply->writeInt32(ret);
1726 reply->writeInt32(1);
1727 outCharacteristics.writeToParcel(reply);
1728
1729 return NO_ERROR;
1730 }
1731 case EXPORT_KEY: {
1732 CHECK_INTERFACE(IKeystoreService, data, reply);
1733 String16 name = data.readString16();
1734 keymaster_key_format_t format = static_cast<keymaster_key_format_t>(data.readInt32());
Chad Brubakerd6634422015-03-21 22:36:07 -07001735 std::unique_ptr<keymaster_blob_t> clientId = readKeymasterBlob(data);
1736 std::unique_ptr<keymaster_blob_t> appData = readKeymasterBlob(data);
Chad Brubakerad6a7f52015-09-09 14:55:22 -07001737 int32_t uid = data.readInt32();
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001738 ExportResult result;
Chad Brubakerad6a7f52015-09-09 14:55:22 -07001739 exportKey(name, format, clientId.get(), appData.get(), uid, &result);
Bin Chen62ddfe02016-09-02 22:01:36 +10001740 if (clientId.get() && clientId->data) {
1741 free(const_cast<void*>(static_cast<const void*>(clientId->data)));
1742 }
1743 if (appData.get() && appData->data) {
1744 free(const_cast<void*>(static_cast<const void*>(appData->data)));
1745 }
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001746 reply->writeNoException();
1747 reply->writeInt32(1);
1748 result.writeToParcel(reply);
1749
1750 return NO_ERROR;
1751 }
1752 case BEGIN: {
1753 CHECK_INTERFACE(IKeystoreService, data, reply);
1754 sp<IBinder> token = data.readStrongBinder();
1755 String16 name = data.readString16();
1756 keymaster_purpose_t purpose = static_cast<keymaster_purpose_t>(data.readInt32());
1757 bool pruneable = data.readInt32() != 0;
1758 KeymasterArguments args;
1759 if (data.readInt32() != 0) {
1760 args.readFromParcel(data);
1761 }
Chad Brubaker154d7692015-03-27 13:59:31 -07001762 const uint8_t* entropy = NULL;
1763 size_t entropyLength = 0;
1764 readByteArray(data, &entropy, &entropyLength);
Chad Brubakerad6a7f52015-09-09 14:55:22 -07001765 int32_t uid = data.readInt32();
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001766 OperationResult result;
Chad Brubakerad6a7f52015-09-09 14:55:22 -07001767 begin(token, name, purpose, pruneable, args, entropy, entropyLength, uid, &result);
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001768 reply->writeNoException();
1769 reply->writeInt32(1);
1770 result.writeToParcel(reply);
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001771
1772 return NO_ERROR;
1773 }
1774 case UPDATE: {
1775 CHECK_INTERFACE(IKeystoreService, data, reply);
1776 sp<IBinder> token = data.readStrongBinder();
1777 KeymasterArguments args;
1778 if (data.readInt32() != 0) {
1779 args.readFromParcel(data);
1780 }
Chad Brubaker6432df72015-03-20 16:23:04 -07001781 const uint8_t* buf = NULL;
1782 size_t bufLength = 0;
1783 readByteArray(data, &buf, &bufLength);
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001784 OperationResult result;
Chad Brubaker6432df72015-03-20 16:23:04 -07001785 update(token, args, buf, bufLength, &result);
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001786 reply->writeNoException();
1787 reply->writeInt32(1);
1788 result.writeToParcel(reply);
1789
1790 return NO_ERROR;
1791 }
1792 case FINISH: {
1793 CHECK_INTERFACE(IKeystoreService, data, reply);
1794 sp<IBinder> token = data.readStrongBinder();
1795 KeymasterArguments args;
1796 if (data.readInt32() != 0) {
1797 args.readFromParcel(data);
1798 }
Chad Brubaker0d33e0b2015-05-29 12:30:19 -07001799 const uint8_t* signature = NULL;
1800 size_t signatureLength = 0;
1801 readByteArray(data, &signature, &signatureLength);
1802 const uint8_t* entropy = NULL;
1803 size_t entropyLength = 0;
1804 readByteArray(data, &entropy, &entropyLength);
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001805 OperationResult result;
Chad Brubaker0d33e0b2015-05-29 12:30:19 -07001806 finish(token, args, signature, signatureLength, entropy, entropyLength, &result);
Chad Brubaker9899d6b2015-02-03 13:03:00 -08001807 reply->writeNoException();
1808 reply->writeInt32(1);
1809 result.writeToParcel(reply);
1810
1811 return NO_ERROR;
1812 }
1813 case ABORT: {
1814 CHECK_INTERFACE(IKeystoreService, data, reply);
1815 sp<IBinder> token = data.readStrongBinder();
1816 int32_t result = abort(token);
1817 reply->writeNoException();
1818 reply->writeInt32(result);
1819
1820 return NO_ERROR;
1821 }
Chad Brubaker2ed2baa2015-03-21 21:20:10 -07001822 case IS_OPERATION_AUTHORIZED: {
1823 CHECK_INTERFACE(IKeystoreService, data, reply);
1824 sp<IBinder> token = data.readStrongBinder();
1825 bool result = isOperationAuthorized(token);
1826 reply->writeNoException();
1827 reply->writeInt32(result ? 1 : 0);
1828
1829 return NO_ERROR;
1830 }
1831 case ADD_AUTH_TOKEN: {
1832 CHECK_INTERFACE(IKeystoreService, data, reply);
Chad Brubaker2ed2baa2015-03-21 21:20:10 -07001833 const uint8_t* token_bytes = NULL;
1834 size_t size = 0;
1835 readByteArray(data, &token_bytes, &size);
1836 int32_t result = addAuthToken(token_bytes, size);
1837 reply->writeNoException();
1838 reply->writeInt32(result);
1839
1840 return NO_ERROR;
1841 }
Chad Brubakerc0f031a2015-05-12 10:43:10 -07001842 case ON_USER_ADDED: {
1843 CHECK_INTERFACE(IKeystoreService, data, reply);
1844 int32_t userId = data.readInt32();
1845 int32_t parentId = data.readInt32();
1846 int32_t result = onUserAdded(userId, parentId);
1847 reply->writeNoException();
1848 reply->writeInt32(result);
1849
1850 return NO_ERROR;
1851 }
1852 case ON_USER_REMOVED: {
1853 CHECK_INTERFACE(IKeystoreService, data, reply);
1854 int32_t userId = data.readInt32();
1855 int32_t result = onUserRemoved(userId);
1856 reply->writeNoException();
1857 reply->writeInt32(result);
1858
1859 return NO_ERROR;
1860 }
Shawn Willden3976b6c2016-02-06 20:31:15 -07001861 case ATTEST_KEY: {
1862 CHECK_INTERFACE(IKeystoreService, data, reply);
1863 String16 name = data.readString16();
1864 KeymasterArguments params;
1865 if (data.readInt32() != 0) {
1866 params.readFromParcel(data);
1867 }
1868 KeymasterCertificateChain chain;
1869 int ret = attestKey(name, params, &chain);
1870 reply->writeNoException();
1871 reply->writeInt32(ret);
1872 reply->writeInt32(1);
1873 chain.writeToParcel(reply);
1874
1875 return NO_ERROR;
1876 }
Kenny Root07438c82012-11-02 15:41:02 -07001877 default:
1878 return BBinder::onTransact(code, data, reply, flags);
1879 }
1880}
1881
1882// ----------------------------------------------------------------------------
1883
1884}; // namespace android