summaryrefslogtreecommitdiff
path: root/keystore2/tests
diff options
context:
space:
mode:
authorRajesh Nyamagoud <nyamagoud@google.com>2022-07-26 18:45:55 +0000
committerRajesh Nyamagoud <nyamagoud@google.com>2022-08-12 00:03:57 +0000
commit16198a3ca9224b1546471dc97a6ea3e7a0c2882b (patch)
treefeb83772b47b8cc9c89a3f7ea69afa3eb233dc7d /keystore2/tests
parenta00741ceb6fff4ab670fa3942c030254efcf8769 (diff)
downloadsecurity-16198a3ca9224b1546471dc97a6ea3e7a0c2882b.tar.gz
Updated `listEntries` API response code with invalid domain field.
Updated to return `INVALID_ARGUMENT` instead of `PERMISSION_DENIED` response code when domain is other than `APP` or `SELINUX`. Added tests to validate `listEntries` API with valid domains `APP and SELINUX` and invalid domains like `BLOB`. Bug: 239719010 Test: atest CtsKeystoreTestCases; atest keystore2_client_tests; Change-Id: I7d10c13342ca5719682e371e428fa42f992ba07d
Diffstat (limited to 'keystore2/tests')
-rw-r--r--keystore2/tests/keystore2_client_list_entries_tests.rs187
-rw-r--r--keystore2/tests/keystore2_client_tests.rs1
2 files changed, 188 insertions, 0 deletions
diff --git a/keystore2/tests/keystore2_client_list_entries_tests.rs b/keystore2/tests/keystore2_client_list_entries_tests.rs
new file mode 100644
index 00000000..d50ef5c3
--- /dev/null
+++ b/keystore2/tests/keystore2_client_list_entries_tests.rs
@@ -0,0 +1,187 @@
+// Copyright 2022, The Android Open Source Project
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+use nix::unistd::{getuid, Gid, Uid};
+use rustutils::users::AID_USER_OFFSET;
+
+use android_hardware_security_keymint::aidl::android::hardware::security::keymint::SecurityLevel::SecurityLevel;
+use android_system_keystore2::aidl::android::system::keystore2::{
+ Domain::Domain, IKeystoreService::IKeystoreService, KeyDescriptor::KeyDescriptor,
+ KeyPermission::KeyPermission, ResponseCode::ResponseCode,
+};
+
+use keystore2_test_utils::{get_keystore_service, key_generations, key_generations::Error, run_as};
+
+/// Try to find a key with given key parameters using `listEntries` API.
+fn is_key_alias_exist(
+ keystore2: &binder::Strong<dyn IKeystoreService>,
+ domain: Domain,
+ nspace: i64,
+ alias: String,
+) -> bool {
+ let key_descriptors = keystore2.listEntries(domain, nspace).unwrap();
+ let alias_count = key_descriptors
+ .into_iter()
+ .map(|key| key.alias.unwrap())
+ .filter(|key_alias| *key_alias == alias)
+ .count();
+
+ alias_count != 0
+}
+
+/// List key entries with domain as SELINUX and APP.
+/// 1. Generate a key with domain as SELINUX and find this key entry in list of keys retrieved from
+/// `listEntries` with domain SELINUX. Test should be able find this key entry successfully.
+/// 2. Grant above generated Key to a user.
+/// 3. In a user context, generate a new key with domain as APP. Try to list the key entries with
+/// domain APP. Test should find only one key entry that should be the key generated in user
+/// context. GRANT keys shouldn't be part of this list.
+#[test]
+fn keystore2_list_entries_success() {
+ static GRANTOR_SU_CTX: &str = "u:r:su:s0";
+ static GRANTEE_CTX: &str = "u:r:untrusted_app:s0:c91,c256,c10,c20";
+
+ const USER_ID: u32 = 91;
+ const APPLICATION_ID: u32 = 10006;
+ static GRANTEE_UID: u32 = USER_ID * AID_USER_OFFSET + APPLICATION_ID;
+ static GRANTEE_GID: u32 = GRANTEE_UID;
+
+ unsafe {
+ run_as::run_as(GRANTOR_SU_CTX, Uid::from_raw(0), Gid::from_raw(0), || {
+ let keystore2 = get_keystore_service();
+ let sec_level = keystore2.getSecurityLevel(SecurityLevel::TRUSTED_ENVIRONMENT).unwrap();
+
+ let alias = format!("list_entries_grant_key1_{}", getuid());
+
+ // Make sure there is no key exist with this `alias` in `SELINUX` domain and
+ // `SELINUX_SHELL_NAMESPACE` namespace.
+ if is_key_alias_exist(
+ &keystore2,
+ Domain::SELINUX,
+ key_generations::SELINUX_SHELL_NAMESPACE,
+ alias.to_string(),
+ ) {
+ keystore2
+ .deleteKey(&KeyDescriptor {
+ domain: Domain::SELINUX,
+ nspace: key_generations::SELINUX_SHELL_NAMESPACE,
+ alias: Some(alias.to_string()),
+ blob: None,
+ })
+ .unwrap();
+ }
+
+ // Generate a key with above defined `alias`.
+ let key_metadata = key_generations::generate_ec_p256_signing_key(
+ &sec_level,
+ Domain::SELINUX,
+ key_generations::SELINUX_SHELL_NAMESPACE,
+ Some(alias.to_string()),
+ None,
+ None,
+ )
+ .unwrap();
+
+ // Verify that above generated key entry is listed with domain SELINUX and
+ // namespace SELINUX_SHELL_NAMESPACE
+ assert!(is_key_alias_exist(
+ &keystore2,
+ Domain::SELINUX,
+ key_generations::SELINUX_SHELL_NAMESPACE,
+ alias,
+ ));
+
+ // Grant a key with GET_INFO permission.
+ let access_vector = KeyPermission::GET_INFO.0;
+ keystore2
+ .grant(&key_metadata.key, GRANTEE_UID.try_into().unwrap(), access_vector)
+ .unwrap();
+ })
+ };
+
+ // In user context validate list of key entries associated with it.
+ unsafe {
+ run_as::run_as(
+ GRANTEE_CTX,
+ Uid::from_raw(GRANTEE_UID),
+ Gid::from_raw(GRANTEE_GID),
+ move || {
+ let keystore2 = get_keystore_service();
+ let sec_level =
+ keystore2.getSecurityLevel(SecurityLevel::TRUSTED_ENVIRONMENT).unwrap();
+ let alias = format!("list_entries_success_key{}", getuid());
+
+ let key_metadata = key_generations::generate_ec_p256_signing_key(
+ &sec_level,
+ Domain::APP,
+ -1,
+ Some(alias.to_string()),
+ None,
+ None,
+ )
+ .unwrap();
+
+ // Make sure there is only one key entry exist and that should be the same key
+ // generated in this user context. Granted key shouldn't be included in this list.
+ let key_descriptors = keystore2.listEntries(Domain::APP, -1).unwrap();
+ assert_eq!(1, key_descriptors.len());
+
+ let key = key_descriptors.get(0).unwrap();
+ assert_eq!(key.alias, Some(alias));
+ assert_eq!(key.nspace, GRANTEE_UID.try_into().unwrap());
+ assert_eq!(key.domain, Domain::APP);
+
+ keystore2.deleteKey(&key_metadata.key).unwrap();
+
+ let key_descriptors = keystore2.listEntries(Domain::APP, -1).unwrap();
+ assert_eq!(0, key_descriptors.len());
+ },
+ )
+ };
+}
+
+/// Try to list the key entries with domain SELINUX from user context where user doesn't possesses
+/// `GET_INFO` permission for specified namespace. Test should fail to list key entries with error
+/// response code `PERMISSION_DENIED`.
+#[test]
+fn keystore2_list_entries_fails_perm_denied() {
+ let auid = 91 * AID_USER_OFFSET + 10001;
+ let agid = 91 * AID_USER_OFFSET + 10001;
+ static TARGET_CTX: &str = "u:r:untrusted_app:s0:c91,c256,c10,c20";
+
+ unsafe {
+ run_as::run_as(TARGET_CTX, Uid::from_raw(auid), Gid::from_raw(agid), move || {
+ let keystore2 = get_keystore_service();
+
+ let result = key_generations::map_ks_error(
+ keystore2.listEntries(Domain::SELINUX, key_generations::SELINUX_SHELL_NAMESPACE),
+ );
+ assert!(result.is_err());
+ assert_eq!(Error::Rc(ResponseCode::PERMISSION_DENIED), result.unwrap_err());
+ })
+ };
+}
+
+/// Try to list key entries with domain BLOB. Test should fail with error repose code
+/// `INVALID_ARGUMENT`.
+#[test]
+fn keystore2_list_entries_fails_invalid_arg() {
+ let keystore2 = get_keystore_service();
+
+ let result = key_generations::map_ks_error(
+ keystore2.listEntries(Domain::BLOB, key_generations::SELINUX_SHELL_NAMESPACE),
+ );
+ assert!(result.is_err());
+ assert_eq!(Error::Rc(ResponseCode::INVALID_ARGUMENT), result.unwrap_err());
+}
diff --git a/keystore2/tests/keystore2_client_tests.rs b/keystore2/tests/keystore2_client_tests.rs
index 3fb3e153..1cda123c 100644
--- a/keystore2/tests/keystore2_client_tests.rs
+++ b/keystore2/tests/keystore2_client_tests.rs
@@ -16,6 +16,7 @@ pub mod keystore2_client_aes_key_tests;
pub mod keystore2_client_ec_key_tests;
pub mod keystore2_client_grant_key_tests;
pub mod keystore2_client_key_id_domain_tests;
+pub mod keystore2_client_list_entries_tests;
pub mod keystore2_client_operation_tests;
pub mod keystore2_client_rsa_key_tests;
pub mod keystore2_client_test_utils;