blob: 79e76923c1398d6e3114ef9835527e30e7cc562c [file] [log] [blame]
Janis Danisevskis1af91262020-08-10 14:58:08 -07001// Copyright 2020, The Android Open Source Project
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7// http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14
Janis Danisevskis1af91262020-08-10 14:58:08 -070015//! This crate implement the core Keystore 2.0 service API as defined by the Keystore 2.0
16//! AIDL spec.
17
Max Bires8e93d2b2021-01-14 13:17:59 -080018use std::collections::HashMap;
19
Pavel Grafov94243c22021-04-21 18:03:11 +010020use crate::audit_log::log_key_deleted;
Janis Danisevskise92a5e62020-12-02 12:57:41 -080021use crate::permission::{KeyPerm, KeystorePerm};
Janis Danisevskis1af91262020-08-10 14:58:08 -070022use crate::security_level::KeystoreSecurityLevel;
Janis Danisevskis04b02832020-10-26 09:21:40 -070023use crate::utils::{
Janis Danisevskise92a5e62020-12-02 12:57:41 -080024 check_grant_permission, check_key_permission, check_keystore_permission,
Janis Danisevskisf84d0b02022-01-26 14:11:14 -080025 key_parameters_to_authorizations, list_key_entries, uid_to_android_user, watchdog as wd,
Janis Danisevskis04b02832020-10-26 09:21:40 -070026};
Hasini Gunasinghe3ed5da72021-02-04 15:18:54 +000027use crate::{
28 database::Uuid,
Janis Danisevskisf84d0b02022-01-26 14:11:14 -080029 globals::{create_thread_local_db, DB, LEGACY_BLOB_LOADER, LEGACY_IMPORTER, SUPER_KEY},
Hasini Gunasinghe3ed5da72021-02-04 15:18:54 +000030};
Max Bires8e93d2b2021-01-14 13:17:59 -080031use crate::{database::KEYSTORE_UUID, permission};
Janis Danisevskisb42fc182020-12-15 08:41:27 -080032use crate::{
33 database::{KeyEntryLoadBits, KeyType, SubComponentType},
34 error::ResponseCode,
35};
Janis Danisevskis5cb52dc2021-04-07 16:31:18 -070036use crate::{
37 error::{self, map_or_log_err, ErrorCode},
38 id_rotation::IdRotationState,
39};
Shawn Willden708744a2020-12-11 13:05:27 +000040use android_hardware_security_keymint::aidl::android::hardware::security::keymint::SecurityLevel::SecurityLevel;
Andrew Walbrande45c8b2021-04-13 14:42:38 +000041use android_hardware_security_keymint::binder::{BinderFeatures, Strong, ThreadState};
Janis Danisevskis1af91262020-08-10 14:58:08 -070042use android_system_keystore2::aidl::android::system::keystore2::{
Janis Danisevskis2c7f9622020-09-30 16:30:31 -070043 Domain::Domain, IKeystoreSecurityLevel::IKeystoreSecurityLevel,
44 IKeystoreService::BnKeystoreService, IKeystoreService::IKeystoreService,
45 KeyDescriptor::KeyDescriptor, KeyEntryResponse::KeyEntryResponse, KeyMetadata::KeyMetadata,
Janis Danisevskis1af91262020-08-10 14:58:08 -070046};
Max Bires8e93d2b2021-01-14 13:17:59 -080047use anyhow::{Context, Result};
Janis Danisevskise92a5e62020-12-02 12:57:41 -080048use error::Error;
49use keystore2_selinux as selinux;
Janis Danisevskis1af91262020-08-10 14:58:08 -070050
51/// Implementation of the IKeystoreService.
Max Bires8e93d2b2021-01-14 13:17:59 -080052#[derive(Default)]
Janis Danisevskis1af91262020-08-10 14:58:08 -070053pub struct KeystoreService {
Janis Danisevskis5f3a0572021-06-18 11:26:42 -070054 i_sec_level_by_uuid: HashMap<Uuid, Strong<dyn IKeystoreSecurityLevel>>,
Max Bires8e93d2b2021-01-14 13:17:59 -080055 uuid_by_sec_level: HashMap<SecurityLevel, Uuid>,
Janis Danisevskis1af91262020-08-10 14:58:08 -070056}
57
58impl KeystoreService {
59 /// Create a new instance of the Keystore 2.0 service.
Janis Danisevskis5cb52dc2021-04-07 16:31:18 -070060 pub fn new_native_binder(
61 id_rotation_state: IdRotationState,
62 ) -> Result<Strong<dyn IKeystoreService>> {
Max Bires8e93d2b2021-01-14 13:17:59 -080063 let mut result: Self = Default::default();
Janis Danisevskis5cb52dc2021-04-07 16:31:18 -070064 let (dev, uuid) = KeystoreSecurityLevel::new_native_binder(
65 SecurityLevel::TRUSTED_ENVIRONMENT,
66 id_rotation_state.clone(),
67 )
68 .context(concat!(
69 "In KeystoreService::new_native_binder: ",
70 "Trying to construct mandatory security level TEE."
Janis Danisevskis5f3a0572021-06-18 11:26:42 -070071 ))?;
Max Bires8e93d2b2021-01-14 13:17:59 -080072 result.i_sec_level_by_uuid.insert(uuid, dev);
73 result.uuid_by_sec_level.insert(SecurityLevel::TRUSTED_ENVIRONMENT, uuid);
Janis Danisevskisba998992020-12-29 16:08:40 -080074
Max Bires8e93d2b2021-01-14 13:17:59 -080075 // Strongbox is optional, so we ignore errors and turn the result into an Option.
Janis Danisevskis5cb52dc2021-04-07 16:31:18 -070076 if let Ok((dev, uuid)) =
77 KeystoreSecurityLevel::new_native_binder(SecurityLevel::STRONGBOX, id_rotation_state)
Max Bires8e93d2b2021-01-14 13:17:59 -080078 {
79 result.i_sec_level_by_uuid.insert(uuid, dev);
80 result.uuid_by_sec_level.insert(SecurityLevel::STRONGBOX, uuid);
81 }
82
Hasini Gunasinghe3ed5da72021-02-04 15:18:54 +000083 let uuid_by_sec_level = result.uuid_by_sec_level.clone();
Janis Danisevskis0ffb8a82022-02-06 22:37:21 -080084 LEGACY_IMPORTER
Hasini Gunasinghe3ed5da72021-02-04 15:18:54 +000085 .set_init(move || {
86 (create_thread_local_db(), uuid_by_sec_level, LEGACY_BLOB_LOADER.clone())
87 })
88 .context(
89 "In KeystoreService::new_native_binder: Trying to initialize the legacy migrator.",
90 )?;
91
Andrew Walbrande45c8b2021-04-13 14:42:38 +000092 Ok(BnKeystoreService::new_binder(
93 result,
94 BinderFeatures { set_requesting_sid: true, ..BinderFeatures::default() },
95 ))
Janis Danisevskis1af91262020-08-10 14:58:08 -070096 }
97
Max Bires8e93d2b2021-01-14 13:17:59 -080098 fn uuid_to_sec_level(&self, uuid: &Uuid) -> SecurityLevel {
99 self.uuid_by_sec_level
100 .iter()
101 .find(|(_, v)| **v == *uuid)
102 .map(|(s, _)| *s)
103 .unwrap_or(SecurityLevel::SOFTWARE)
104 }
105
Stephen Crane221bbb52020-12-16 15:52:10 -0800106 fn get_i_sec_level_by_uuid(&self, uuid: &Uuid) -> Result<Strong<dyn IKeystoreSecurityLevel>> {
Max Bires8e93d2b2021-01-14 13:17:59 -0800107 if let Some(dev) = self.i_sec_level_by_uuid.get(uuid) {
Janis Danisevskis5f3a0572021-06-18 11:26:42 -0700108 Ok(dev.clone())
Max Bires8e93d2b2021-01-14 13:17:59 -0800109 } else {
110 Err(error::Error::sys())
111 .context("In get_i_sec_level_by_uuid: KeyMint instance for key not found.")
112 }
Janis Danisevskisba998992020-12-29 16:08:40 -0800113 }
114
Janis Danisevskis1af91262020-08-10 14:58:08 -0700115 fn get_security_level(
116 &self,
Max Bires8e93d2b2021-01-14 13:17:59 -0800117 sec_level: SecurityLevel,
Stephen Crane221bbb52020-12-16 15:52:10 -0800118 ) -> Result<Strong<dyn IKeystoreSecurityLevel>> {
Max Bires8e93d2b2021-01-14 13:17:59 -0800119 if let Some(dev) = self
120 .uuid_by_sec_level
121 .get(&sec_level)
122 .and_then(|uuid| self.i_sec_level_by_uuid.get(uuid))
123 {
Janis Danisevskis5f3a0572021-06-18 11:26:42 -0700124 Ok(dev.clone())
Max Bires8e93d2b2021-01-14 13:17:59 -0800125 } else {
126 Err(error::Error::Km(ErrorCode::HARDWARE_TYPE_UNAVAILABLE))
127 .context("In get_security_level: No such security level.")
128 }
Janis Danisevskis1af91262020-08-10 14:58:08 -0700129 }
130
Janis Danisevskis2c7f9622020-09-30 16:30:31 -0700131 fn get_key_entry(&self, key: &KeyDescriptor) -> Result<KeyEntryResponse> {
Hasini Gunasinghe3ed5da72021-02-04 15:18:54 +0000132 let caller_uid = ThreadState::get_calling_uid();
Janis Danisevskisf84d0b02022-01-26 14:11:14 -0800133
134 let super_key =
135 SUPER_KEY.read().unwrap().get_per_boot_key_by_user_id(uid_to_android_user(caller_uid));
136
Janis Danisevskisaec14592020-11-12 09:41:49 -0800137 let (key_id_guard, mut key_entry) = DB
Janis Danisevskis1af91262020-08-10 14:58:08 -0700138 .with(|db| {
Janis Danisevskisf84d0b02022-01-26 14:11:14 -0800139 LEGACY_IMPORTER.with_try_import(key, caller_uid, super_key, || {
Hasini Gunasinghe3ed5da72021-02-04 15:18:54 +0000140 db.borrow_mut().load_key_entry(
Chris Wailesd5aaaef2021-07-27 16:04:33 -0700141 key,
Hasini Gunasinghe3ed5da72021-02-04 15:18:54 +0000142 KeyType::Client,
143 KeyEntryLoadBits::PUBLIC,
144 caller_uid,
Janis Danisevskis39d57e72021-10-19 16:56:20 -0700145 |k, av| check_key_permission(KeyPerm::GetInfo, k, &av),
Hasini Gunasinghe3ed5da72021-02-04 15:18:54 +0000146 )
147 })
Janis Danisevskis1af91262020-08-10 14:58:08 -0700148 })
149 .context("In get_key_entry, while trying to load key info.")?;
150
Janis Danisevskis377d1002021-01-27 19:07:48 -0800151 let i_sec_level = if !key_entry.pure_cert() {
152 Some(
Max Bires8e93d2b2021-01-14 13:17:59 -0800153 self.get_i_sec_level_by_uuid(key_entry.km_uuid())
154 .context("In get_key_entry: Trying to get security level proxy.")?,
Janis Danisevskis377d1002021-01-27 19:07:48 -0800155 )
156 } else {
157 None
158 };
Janis Danisevskis1af91262020-08-10 14:58:08 -0700159
Janis Danisevskis2c7f9622020-09-30 16:30:31 -0700160 Ok(KeyEntryResponse {
Janis Danisevskis377d1002021-01-27 19:07:48 -0800161 iSecurityLevel: i_sec_level,
Janis Danisevskis2c7f9622020-09-30 16:30:31 -0700162 metadata: KeyMetadata {
Janis Danisevskis1af91262020-08-10 14:58:08 -0700163 key: KeyDescriptor {
164 domain: Domain::KEY_ID,
Janis Danisevskisaec14592020-11-12 09:41:49 -0800165 nspace: key_id_guard.id(),
Janis Danisevskis1af91262020-08-10 14:58:08 -0700166 ..Default::default()
167 },
Max Bires8e93d2b2021-01-14 13:17:59 -0800168 keySecurityLevel: self.uuid_to_sec_level(key_entry.km_uuid()),
Janis Danisevskis2c7f9622020-09-30 16:30:31 -0700169 certificate: key_entry.take_cert(),
170 certificateChain: key_entry.take_cert_chain(),
Janis Danisevskisb42fc182020-12-15 08:41:27 -0800171 modificationTimeMs: key_entry
172 .metadata()
173 .creation_date()
174 .map(|d| d.to_millis_epoch())
175 .ok_or(Error::Rc(ResponseCode::VALUE_CORRUPTED))
176 .context("In get_key_entry: Trying to get creation date.")?,
Janis Danisevskis04b02832020-10-26 09:21:40 -0700177 authorizations: key_parameters_to_authorizations(key_entry.into_key_parameters()),
Janis Danisevskis1af91262020-08-10 14:58:08 -0700178 },
Janis Danisevskis2c7f9622020-09-30 16:30:31 -0700179 })
Janis Danisevskis1af91262020-08-10 14:58:08 -0700180 }
181
182 fn update_subcomponent(
183 &self,
184 key: &KeyDescriptor,
Janis Danisevskis2c7f9622020-09-30 16:30:31 -0700185 public_cert: Option<&[u8]>,
186 certificate_chain: Option<&[u8]>,
Janis Danisevskis1af91262020-08-10 14:58:08 -0700187 ) -> Result<()> {
Hasini Gunasinghe3ed5da72021-02-04 15:18:54 +0000188 let caller_uid = ThreadState::get_calling_uid();
Janis Danisevskisf84d0b02022-01-26 14:11:14 -0800189 let super_key =
190 SUPER_KEY.read().unwrap().get_per_boot_key_by_user_id(uid_to_android_user(caller_uid));
191
Janis Danisevskis1af91262020-08-10 14:58:08 -0700192 DB.with::<_, Result<()>>(|db| {
Janis Danisevskisf84d0b02022-01-26 14:11:14 -0800193 let entry = match LEGACY_IMPORTER.with_try_import(key, caller_uid, super_key, || {
Hasini Gunasinghe3ed5da72021-02-04 15:18:54 +0000194 db.borrow_mut().load_key_entry(
Chris Wailesd5aaaef2021-07-27 16:04:33 -0700195 key,
Hasini Gunasinghe3ed5da72021-02-04 15:18:54 +0000196 KeyType::Client,
197 KeyEntryLoadBits::NONE,
198 caller_uid,
199 |k, av| {
Janis Danisevskis39d57e72021-10-19 16:56:20 -0700200 check_key_permission(KeyPerm::Update, k, &av)
Hasini Gunasinghe3ed5da72021-02-04 15:18:54 +0000201 .context("In update_subcomponent.")
202 },
203 )
204 }) {
Janis Danisevskis377d1002021-01-27 19:07:48 -0800205 Err(e) => match e.root_cause().downcast_ref::<Error>() {
206 Some(Error::Rc(ResponseCode::KEY_NOT_FOUND)) => Ok(None),
207 _ => Err(e),
208 },
209 Ok(v) => Ok(Some(v)),
210 }
211 .context("Failed to load key entry.")?;
Janis Danisevskis1af91262020-08-10 14:58:08 -0700212
Hasini Gunasinghe3ed5da72021-02-04 15:18:54 +0000213 let mut db = db.borrow_mut();
Paul Crowleyd5653e52021-03-25 09:46:31 -0700214 if let Some((key_id_guard, _key_entry)) = entry {
Janis Danisevskis7e8b4622021-02-13 10:01:59 -0800215 db.set_blob(&key_id_guard, SubComponentType::CERT, public_cert, None)
Janis Danisevskis2c7f9622020-09-30 16:30:31 -0700216 .context("Failed to update cert subcomponent.")?;
Janis Danisevskis377d1002021-01-27 19:07:48 -0800217
Janis Danisevskis7e8b4622021-02-13 10:01:59 -0800218 db.set_blob(&key_id_guard, SubComponentType::CERT_CHAIN, certificate_chain, None)
Janis Danisevskis377d1002021-01-27 19:07:48 -0800219 .context("Failed to update cert chain subcomponent.")?;
220 return Ok(());
Janis Danisevskis1af91262020-08-10 14:58:08 -0700221 }
222
Janis Danisevskis377d1002021-01-27 19:07:48 -0800223 // If we reach this point we have to check the special condition where a certificate
224 // entry may be made.
225 if !(public_cert.is_none() && certificate_chain.is_some()) {
226 return Err(Error::Rc(ResponseCode::KEY_NOT_FOUND)).context("No key to update.");
Janis Danisevskis1af91262020-08-10 14:58:08 -0700227 }
Janis Danisevskis377d1002021-01-27 19:07:48 -0800228
229 // So we know that we have a certificate chain and no public cert.
230 // Now check that we have everything we need to make a new certificate entry.
231 let key = match (key.domain, &key.alias) {
232 (Domain::APP, Some(ref alias)) => KeyDescriptor {
233 domain: Domain::APP,
234 nspace: ThreadState::get_calling_uid() as i64,
235 alias: Some(alias.clone()),
236 blob: None,
237 },
238 (Domain::SELINUX, Some(_)) => key.clone(),
239 _ => {
240 return Err(Error::Rc(ResponseCode::INVALID_ARGUMENT))
241 .context("Domain must be APP or SELINUX to insert a certificate.")
242 }
243 };
244
245 // Security critical: This must return on failure. Do not remove the `?`;
Janis Danisevskis39d57e72021-10-19 16:56:20 -0700246 check_key_permission(KeyPerm::Rebind, &key, &None)
Janis Danisevskis377d1002021-01-27 19:07:48 -0800247 .context("Caller does not have permission to insert this certificate.")?;
248
Janis Danisevskis0cabd712021-05-25 11:07:10 -0700249 db.store_new_certificate(
250 &key,
251 KeyType::Client,
252 certificate_chain.unwrap(),
253 &KEYSTORE_UUID,
254 )
255 .context("Failed to insert new certificate.")?;
Janis Danisevskis1af91262020-08-10 14:58:08 -0700256 Ok(())
257 })
258 .context("In update_subcomponent.")
259 }
260
261 fn list_entries(&self, domain: Domain, namespace: i64) -> Result<Vec<KeyDescriptor>> {
Janis Danisevskise92a5e62020-12-02 12:57:41 -0800262 let mut k = match domain {
263 Domain::APP => KeyDescriptor {
264 domain,
265 nspace: ThreadState::get_calling_uid() as u64 as i64,
266 ..Default::default()
267 },
268 Domain::SELINUX => KeyDescriptor{domain, nspace: namespace, ..Default::default()},
269 _ => return Err(Error::perm()).context(
270 "In list_entries: List entries is only supported for Domain::APP and Domain::SELINUX."
271 ),
272 };
273
274 // First we check if the caller has the info permission for the selected domain/namespace.
275 // By default we use the calling uid as namespace if domain is Domain::APP.
276 // If the first check fails we check if the caller has the list permission allowing to list
277 // any namespace. In that case we also adjust the queried namespace if a specific uid was
278 // selected.
Janis Danisevskis39d57e72021-10-19 16:56:20 -0700279 match check_key_permission(KeyPerm::GetInfo, &k, &None) {
Janis Danisevskise92a5e62020-12-02 12:57:41 -0800280 Err(e) => {
281 if let Some(selinux::Error::PermissionDenied) =
282 e.root_cause().downcast_ref::<selinux::Error>()
283 {
Janis Danisevskisa916d992021-10-19 15:46:09 -0700284 check_keystore_permission(KeystorePerm::List)
Janis Danisevskise92a5e62020-12-02 12:57:41 -0800285 .context("In list_entries: While checking keystore permission.")?;
286 if namespace != -1 {
287 k.nspace = namespace;
288 }
289 } else {
290 return Err(e).context("In list_entries: While checking key permission.")?;
291 }
292 }
293 Ok(()) => {}
294 };
295
John Wu16db29e2022-01-13 15:21:43 -0800296 DB.with(|db| list_key_entries(&mut db.borrow_mut(), k.domain, k.nspace))
Janis Danisevskis1af91262020-08-10 14:58:08 -0700297 }
298
299 fn delete_key(&self, key: &KeyDescriptor) -> Result<()> {
Janis Danisevskis93927dd2020-12-23 12:23:08 -0800300 let caller_uid = ThreadState::get_calling_uid();
Janis Danisevskisf84d0b02022-01-26 14:11:14 -0800301 let super_key =
302 SUPER_KEY.read().unwrap().get_per_boot_key_by_user_id(uid_to_android_user(caller_uid));
303
Janis Danisevskis7e8b4622021-02-13 10:01:59 -0800304 DB.with(|db| {
Janis Danisevskisf84d0b02022-01-26 14:11:14 -0800305 LEGACY_IMPORTER.with_try_import(key, caller_uid, super_key, || {
Chris Wailesd5aaaef2021-07-27 16:04:33 -0700306 db.borrow_mut().unbind_key(key, KeyType::Client, caller_uid, |k, av| {
Janis Danisevskis39d57e72021-10-19 16:56:20 -0700307 check_key_permission(KeyPerm::Delete, k, &av).context("During delete_key.")
Hasini Gunasinghe3ed5da72021-02-04 15:18:54 +0000308 })
Janis Danisevskis93927dd2020-12-23 12:23:08 -0800309 })
Janis Danisevskis7e8b4622021-02-13 10:01:59 -0800310 })
311 .context("In delete_key: Trying to unbind the key.")?;
Janis Danisevskisa51ccbc2020-11-25 21:04:24 -0800312 Ok(())
Janis Danisevskis1af91262020-08-10 14:58:08 -0700313 }
314
315 fn grant(
316 &self,
317 key: &KeyDescriptor,
318 grantee_uid: i32,
319 access_vector: permission::KeyPermSet,
320 ) -> Result<KeyDescriptor> {
Hasini Gunasinghe3ed5da72021-02-04 15:18:54 +0000321 let caller_uid = ThreadState::get_calling_uid();
Janis Danisevskisf84d0b02022-01-26 14:11:14 -0800322 let super_key =
323 SUPER_KEY.read().unwrap().get_per_boot_key_by_user_id(uid_to_android_user(caller_uid));
324
Janis Danisevskis1af91262020-08-10 14:58:08 -0700325 DB.with(|db| {
Janis Danisevskisf84d0b02022-01-26 14:11:14 -0800326 LEGACY_IMPORTER.with_try_import(key, caller_uid, super_key, || {
Hasini Gunasinghe3ed5da72021-02-04 15:18:54 +0000327 db.borrow_mut().grant(
Chris Wailesd5aaaef2021-07-27 16:04:33 -0700328 key,
Hasini Gunasinghe3ed5da72021-02-04 15:18:54 +0000329 caller_uid,
330 grantee_uid as u32,
331 access_vector,
332 |k, av| check_grant_permission(*av, k).context("During grant."),
333 )
334 })
Janis Danisevskis1af91262020-08-10 14:58:08 -0700335 })
336 .context("In KeystoreService::grant.")
337 }
338
339 fn ungrant(&self, key: &KeyDescriptor, grantee_uid: i32) -> Result<()> {
340 DB.with(|db| {
Chris Wailesd5aaaef2021-07-27 16:04:33 -0700341 db.borrow_mut().ungrant(key, ThreadState::get_calling_uid(), grantee_uid as u32, |k| {
Janis Danisevskis39d57e72021-10-19 16:56:20 -0700342 check_key_permission(KeyPerm::Grant, k, &None)
Janis Danisevskis66784c42021-01-27 08:40:25 -0800343 })
Janis Danisevskis1af91262020-08-10 14:58:08 -0700344 })
345 .context("In KeystoreService::ungrant.")
346 }
347}
348
349impl binder::Interface for KeystoreService {}
350
351// Implementation of IKeystoreService. See AIDL spec at
352// system/security/keystore2/binder/android/security/keystore2/IKeystoreService.aidl
353impl IKeystoreService for KeystoreService {
354 fn getSecurityLevel(
355 &self,
Janis Danisevskisa53c9cf2020-10-26 11:52:33 -0700356 security_level: SecurityLevel,
Stephen Crane23cf7242022-01-19 17:49:46 +0000357 ) -> binder::Result<Strong<dyn IKeystoreSecurityLevel>> {
Hasini Gunasinghe5a893e82021-05-05 14:32:32 +0000358 let _wp = wd::watch_millis_with("IKeystoreService::getSecurityLevel", 500, move || {
359 format!("security_level: {}", security_level.0)
360 });
Max Bires8e93d2b2021-01-14 13:17:59 -0800361 map_or_log_err(self.get_security_level(security_level), Ok)
Janis Danisevskis1af91262020-08-10 14:58:08 -0700362 }
Stephen Crane23cf7242022-01-19 17:49:46 +0000363 fn getKeyEntry(&self, key: &KeyDescriptor) -> binder::Result<KeyEntryResponse> {
Hasini Gunasinghe5a893e82021-05-05 14:32:32 +0000364 let _wp = wd::watch_millis("IKeystoreService::get_key_entry", 500);
Janis Danisevskis2c7f9622020-09-30 16:30:31 -0700365 map_or_log_err(self.get_key_entry(key), Ok)
Janis Danisevskis1af91262020-08-10 14:58:08 -0700366 }
367 fn updateSubcomponent(
368 &self,
369 key: &KeyDescriptor,
Janis Danisevskis2c7f9622020-09-30 16:30:31 -0700370 public_cert: Option<&[u8]>,
371 certificate_chain: Option<&[u8]>,
Stephen Crane23cf7242022-01-19 17:49:46 +0000372 ) -> binder::Result<()> {
Hasini Gunasinghe5a893e82021-05-05 14:32:32 +0000373 let _wp = wd::watch_millis("IKeystoreService::updateSubcomponent", 500);
Janis Danisevskis1af91262020-08-10 14:58:08 -0700374 map_or_log_err(self.update_subcomponent(key, public_cert, certificate_chain), Ok)
375 }
Stephen Crane23cf7242022-01-19 17:49:46 +0000376 fn listEntries(&self, domain: Domain, namespace: i64) -> binder::Result<Vec<KeyDescriptor>> {
Hasini Gunasinghe5a893e82021-05-05 14:32:32 +0000377 let _wp = wd::watch_millis("IKeystoreService::listEntries", 500);
Janis Danisevskis1af91262020-08-10 14:58:08 -0700378 map_or_log_err(self.list_entries(domain, namespace), Ok)
379 }
Stephen Crane23cf7242022-01-19 17:49:46 +0000380 fn deleteKey(&self, key: &KeyDescriptor) -> binder::Result<()> {
Hasini Gunasinghe5a893e82021-05-05 14:32:32 +0000381 let _wp = wd::watch_millis("IKeystoreService::deleteKey", 500);
Pavel Grafov94243c22021-04-21 18:03:11 +0100382 let result = self.delete_key(key);
383 log_key_deleted(key, ThreadState::get_calling_uid(), result.is_ok());
384 map_or_log_err(result, Ok)
Janis Danisevskis1af91262020-08-10 14:58:08 -0700385 }
386 fn grant(
387 &self,
388 key: &KeyDescriptor,
389 grantee_uid: i32,
390 access_vector: i32,
Stephen Crane23cf7242022-01-19 17:49:46 +0000391 ) -> binder::Result<KeyDescriptor> {
Hasini Gunasinghe5a893e82021-05-05 14:32:32 +0000392 let _wp = wd::watch_millis("IKeystoreService::grant", 500);
Janis Danisevskis1af91262020-08-10 14:58:08 -0700393 map_or_log_err(self.grant(key, grantee_uid, access_vector.into()), Ok)
394 }
Stephen Crane23cf7242022-01-19 17:49:46 +0000395 fn ungrant(&self, key: &KeyDescriptor, grantee_uid: i32) -> binder::Result<()> {
Hasini Gunasinghe5a893e82021-05-05 14:32:32 +0000396 let _wp = wd::watch_millis("IKeystoreService::ungrant", 500);
Janis Danisevskis1af91262020-08-10 14:58:08 -0700397 map_or_log_err(self.ungrant(key, grantee_uid), Ok)
398 }
399}