From a6eaf55d7d0f3ae4ffa593c6b4d5c37fff08679b Mon Sep 17 00:00:00 2001 From: Shikha Panwar Date: Thu, 19 Oct 2023 16:32:40 +0000 Subject: [PATCH] VTS test for ISecretkeeper Add VTS for testing ISecretkeeper implementation. At present, VTS is limited to testing GetVersion operation of SecretManagement. Test: atest VtsSecretkeeperTargetTest Bug: 291224769 Change-Id: I6084af2fa6cb578e27996e26a0505b267a10b4ef --- security/secretkeeper/aidl/vts/Android.bp | 35 ++++++ .../aidl/vts/secretkeeper_test_client.rs | 109 ++++++++++++++++++ 2 files changed, 144 insertions(+) create mode 100644 security/secretkeeper/aidl/vts/Android.bp create mode 100644 security/secretkeeper/aidl/vts/secretkeeper_test_client.rs diff --git a/security/secretkeeper/aidl/vts/Android.bp b/security/secretkeeper/aidl/vts/Android.bp new file mode 100644 index 0000000000..6818298926 --- /dev/null +++ b/security/secretkeeper/aidl/vts/Android.bp @@ -0,0 +1,35 @@ +/* + * Copyright (C) 2023 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. + */ + +package { + default_applicable_licenses: ["Android-Apache-2.0"], +} + +rust_test { + name: "VtsSecretkeeperTargetTest", + srcs: ["secretkeeper_test_client.rs"], + test_suites: [ + "general-tests", + "vts", + ], + rustlibs: [ + "libsecretkeeper_comm_nostd", + "android.hardware.security.secretkeeper-V1-rust", + "libbinder_rs", + "liblog_rust", + ], + require_root: true, +} diff --git a/security/secretkeeper/aidl/vts/secretkeeper_test_client.rs b/security/secretkeeper/aidl/vts/secretkeeper_test_client.rs new file mode 100644 index 0000000000..28923f7120 --- /dev/null +++ b/security/secretkeeper/aidl/vts/secretkeeper_test_client.rs @@ -0,0 +1,109 @@ +/* + * Copyright (C) 2023 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. + */ + +#[cfg(test)] +use binder::StatusCode; +use log::warn; +use secretkeeper_comm::data_types::error::SecretkeeperError; +use secretkeeper_comm::data_types::request::Request; +use secretkeeper_comm::data_types::request_response_impl::{ + GetVersionRequest, GetVersionResponse, +}; +use secretkeeper_comm::data_types::response::Response; +use secretkeeper_comm::data_types::packet::{ResponsePacket, ResponseType}; +use android_hardware_security_secretkeeper::aidl::android::hardware::security::secretkeeper::ISecretkeeper::ISecretkeeper; + +const SECRETKEEPER_IDENTIFIER: &str = + "android.hardware.security.secretkeeper.ISecretkeeper/nonsecure"; +const CURRENT_VERSION: u64 = 1; + +fn get_connection() -> Option> { + match binder::get_interface(SECRETKEEPER_IDENTIFIER) { + Ok(sk) => Some(sk), + Err(StatusCode::NAME_NOT_FOUND) => None, + Err(e) => { + panic!( + "unexpected error while fetching connection to Secretkeeper {:?}", + e + ); + } + } +} + +// TODO(b/2797757): Add tests that match different HAL defined objects (like request/response) +// with expected bytes. + +#[test] +fn secret_management_get_version() { + let secretkeeper = match get_connection() { + Some(sk) => sk, + None => { + warn!("Secretkeeper HAL is unavailable, skipping test"); + return; + } + }; + let request = GetVersionRequest {}; + let request_packet = request.serialize_to_packet(); + let request_bytes = request_packet.into_bytes().unwrap(); + + // TODO(b/291224769) The request will need to be encrypted & response need to be decrypted + // with key & related artifacts pre-shared via Authgraph Key Exchange HAL. + + let response_bytes = secretkeeper + .processSecretManagementRequest(&request_bytes) + .unwrap(); + + let response_packet = ResponsePacket::from_bytes(&response_bytes).unwrap(); + assert_eq!( + response_packet.response_type().unwrap(), + ResponseType::Success + ); + let get_version_response = + *GetVersionResponse::deserialize_from_packet(response_packet).unwrap(); + assert_eq!(get_version_response.version(), CURRENT_VERSION); +} + +#[test] +fn secret_management_malformed_request() { + let secretkeeper = match get_connection() { + Some(sk) => sk, + None => { + warn!("Secretkeeper HAL is unavailable, skipping test"); + return; + } + }; + let request = GetVersionRequest {}; + let request_packet = request.serialize_to_packet(); + let mut request_bytes = request_packet.into_bytes().unwrap(); + + // Deform the request + request_bytes[0] = !request_bytes[0]; + + // TODO(b/291224769) The request will need to be encrypted & response need to be decrypted + // with key & related artifacts pre-shared via Authgraph Key Exchange HAL. + + let response_bytes = secretkeeper + .processSecretManagementRequest(&request_bytes) + .unwrap(); + + let response_packet = ResponsePacket::from_bytes(&response_bytes).unwrap(); + assert_eq!( + response_packet.response_type().unwrap(), + ResponseType::Error + ); + let err = *SecretkeeperError::deserialize_from_packet(response_packet).unwrap(); + assert_eq!(err, SecretkeeperError::RequestMalformed); +}