diff --git a/security/keymint/aidl/vts/functional/AttestKeyTest.cpp b/security/keymint/aidl/vts/functional/AttestKeyTest.cpp index b8699e9d50..ae2becdf9b 100644 --- a/security/keymint/aidl/vts/functional/AttestKeyTest.cpp +++ b/security/keymint/aidl/vts/functional/AttestKeyTest.cpp @@ -141,11 +141,18 @@ TEST_P(AttestKeyTest, AllRsaSizes) { attest_key, &attested_key_blob, &attested_key_characteristics, &attested_key_cert_chain)); + // The returned key characteristics will include CREATION_DATETIME (checked below) + // in SecurityLevel::KEYSTORE; this will be stripped out in the CheckCharacteristics() + // call below, to match what getKeyCharacteristics() returns (which doesn't include + // any SecurityLevel::KEYSTORE characteristics). + CheckCharacteristics(attested_key_blob, attested_key_characteristics); + CheckedDeleteKey(&attested_key_blob); CheckedDeleteKey(&attest_key.keyBlob); hw_enforced = HwEnforcedAuthorizations(attested_key_characteristics); sw_enforced = SwEnforcedAuthorizations(attested_key_characteristics); + // The client-specified CREATION_DATETIME should be in sw_enforced. // Its presence will also trigger verify_attestation_record() to check that it // is in the attestation extension with a matching value. diff --git a/security/keymint/aidl/vts/functional/KeyMintAidlTestBase.cpp b/security/keymint/aidl/vts/functional/KeyMintAidlTestBase.cpp index a9a67bcc50..44b8274540 100644 --- a/security/keymint/aidl/vts/functional/KeyMintAidlTestBase.cpp +++ b/security/keymint/aidl/vts/functional/KeyMintAidlTestBase.cpp @@ -142,6 +142,15 @@ AuthorizationSet filtered_tags(const AuthorizationSet& set) { return filtered; } +// Remove any SecurityLevel::KEYSTORE entries from a list of key characteristics. +void strip_keystore_tags(vector* characteristics) { + characteristics->erase(std::remove_if(characteristics->begin(), characteristics->end(), + [](const auto& entry) { + return entry.securityLevel == SecurityLevel::KEYSTORE; + }), + characteristics->end()); +} + string x509NameToStr(X509_NAME* name) { char* s = X509_NAME_oneline(name, nullptr, 0); string retval(s); @@ -320,6 +329,65 @@ ErrorCode KeyMintAidlTestBase::ImportWrappedKey(string wrapped_key, string wrapp return GetReturnErrorCode(result); } +ErrorCode KeyMintAidlTestBase::GetCharacteristics(const vector& key_blob, + const vector& app_id, + const vector& app_data, + vector* key_characteristics) { + Status result = + keymint_->getKeyCharacteristics(key_blob, app_id, app_data, key_characteristics); + return GetReturnErrorCode(result); +} + +ErrorCode KeyMintAidlTestBase::GetCharacteristics(const vector& key_blob, + vector* key_characteristics) { + vector empty_app_id, empty_app_data; + return GetCharacteristics(key_blob, empty_app_id, empty_app_data, key_characteristics); +} + +void KeyMintAidlTestBase::CheckCharacteristics( + const vector& key_blob, + const vector& generate_characteristics) { + // Any key characteristics that were in SecurityLevel::KEYSTORE when returned from + // generateKey() should be excluded, as KeyMint will have no record of them. + // This applies to CREATION_DATETIME in particular. + vector expected_characteristics(generate_characteristics); + strip_keystore_tags(&expected_characteristics); + + vector retrieved; + ASSERT_EQ(ErrorCode::OK, GetCharacteristics(key_blob, &retrieved)); + EXPECT_EQ(expected_characteristics, retrieved); +} + +void KeyMintAidlTestBase::CheckAppIdCharacteristics( + const vector& key_blob, std::string_view app_id_string, + std::string_view app_data_string, + const vector& generate_characteristics) { + // Exclude any SecurityLevel::KEYSTORE characteristics for comparisons. + vector expected_characteristics(generate_characteristics); + strip_keystore_tags(&expected_characteristics); + + vector app_id(app_id_string.begin(), app_id_string.end()); + vector app_data(app_data_string.begin(), app_data_string.end()); + vector retrieved; + ASSERT_EQ(ErrorCode::OK, GetCharacteristics(key_blob, app_id, app_data, &retrieved)); + EXPECT_EQ(expected_characteristics, retrieved); + + // Check that key characteristics can't be retrieved if the app ID or app data is missing. + vector empty; + vector not_retrieved; + EXPECT_EQ(ErrorCode::INVALID_KEY_BLOB, + GetCharacteristics(key_blob, empty, app_data, ¬_retrieved)); + EXPECT_EQ(not_retrieved.size(), 0); + + EXPECT_EQ(ErrorCode::INVALID_KEY_BLOB, + GetCharacteristics(key_blob, app_id, empty, ¬_retrieved)); + EXPECT_EQ(not_retrieved.size(), 0); + + EXPECT_EQ(ErrorCode::INVALID_KEY_BLOB, + GetCharacteristics(key_blob, empty, empty, ¬_retrieved)); + EXPECT_EQ(not_retrieved.size(), 0); +} + ErrorCode KeyMintAidlTestBase::DeleteKey(vector* key_blob, bool keep_key_blob) { Status result = keymint_->deleteKey(*key_blob); if (!keep_key_blob) { diff --git a/security/keymint/aidl/vts/functional/KeyMintAidlTestBase.h b/security/keymint/aidl/vts/functional/KeyMintAidlTestBase.h index d8f1bb3dbe..c49b303f50 100644 --- a/security/keymint/aidl/vts/functional/KeyMintAidlTestBase.h +++ b/security/keymint/aidl/vts/functional/KeyMintAidlTestBase.h @@ -16,6 +16,8 @@ #pragma once +#include + #include #include #include @@ -104,6 +106,18 @@ class KeyMintAidlTestBase : public ::testing::TestWithParam { unwrapping_params, 0 /* password_sid */, 0 /* biometric_sid */); } + ErrorCode GetCharacteristics(const vector& key_blob, const vector& app_id, + const vector& app_data, + vector* key_characteristics); + ErrorCode GetCharacteristics(const vector& key_blob, + vector* key_characteristics); + + void CheckCharacteristics(const vector& key_blob, + const vector& generate_characteristics); + void CheckAppIdCharacteristics(const vector& key_blob, std::string_view app_id_string, + std::string_view app_data_string, + const vector& generate_characteristics); + ErrorCode DeleteKey(vector* key_blob, bool keep_key_blob = false); ErrorCode DeleteKey(bool keep_key_blob = false); diff --git a/security/keymint/aidl/vts/functional/KeyMintTest.cpp b/security/keymint/aidl/vts/functional/KeyMintTest.cpp index 8b1eb30959..5dcfcaaa63 100644 --- a/security/keymint/aidl/vts/functional/KeyMintTest.cpp +++ b/security/keymint/aidl/vts/functional/KeyMintTest.cpp @@ -560,6 +560,7 @@ TEST_P(NewKeyGenerationTest, Aes) { EXPECT_GT(key_blob.size(), 0U); CheckSymmetricParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); @@ -742,6 +743,7 @@ TEST_P(NewKeyGenerationTest, TripleDes) { EXPECT_GT(key_blob.size(), 0U); CheckSymmetricParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); @@ -788,6 +790,7 @@ TEST_P(NewKeyGenerationTest, TripleDesWithAttestation) { EXPECT_GT(key_blob.size(), 0U); CheckSymmetricParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); @@ -865,6 +868,7 @@ TEST_P(NewKeyGenerationTest, Rsa) { ASSERT_GT(key_blob.size(), 0U); CheckBaseParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); @@ -911,6 +915,7 @@ TEST_P(NewKeyGenerationTest, RsaWithAttestation) { ASSERT_GT(key_blob.size(), 0U); CheckBaseParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); @@ -978,6 +983,7 @@ TEST_P(NewKeyGenerationTest, RsaWithRpkAttestation) { ASSERT_GT(key_blob.size(), 0U); CheckBaseParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); @@ -1108,6 +1114,7 @@ TEST_P(NewKeyGenerationTest, RsaWithSelfSign) { ASSERT_GT(key_blob.size(), 0U); CheckBaseParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); @@ -1176,6 +1183,7 @@ TEST_P(NewKeyGenerationTest, RsaWithAttestationAppIdIgnored) { ASSERT_GT(key_blob.size(), 0U); CheckBaseParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); @@ -1211,6 +1219,7 @@ TEST_P(NewKeyGenerationTest, LimitedUsageRsa) { ASSERT_GT(key_blob.size(), 0U); CheckBaseParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); @@ -1266,6 +1275,7 @@ TEST_P(NewKeyGenerationTest, LimitedUsageRsaWithAttestation) { ASSERT_GT(key_blob.size(), 0U); CheckBaseParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); @@ -1362,6 +1372,7 @@ TEST_P(NewKeyGenerationTest, Ecdsa) { &key_blob, &key_characteristics)); ASSERT_GT(key_blob.size(), 0U); CheckBaseParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); @@ -1405,6 +1416,7 @@ TEST_P(NewKeyGenerationTest, EcdsaAttestation) { &key_blob, &key_characteristics)); ASSERT_GT(key_blob.size(), 0U); CheckBaseParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); @@ -1452,6 +1464,7 @@ TEST_P(NewKeyGenerationTest, EcdsaSelfSignAttestation) { &key_blob, &key_characteristics)); ASSERT_GT(key_blob.size(), 0U); CheckBaseParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); @@ -1511,6 +1524,7 @@ TEST_P(NewKeyGenerationTest, EcdsaIgnoreAppId) { ASSERT_GT(key_blob.size(), 0U); CheckBaseParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); @@ -1555,6 +1569,7 @@ TEST_P(NewKeyGenerationTest, AttestationApplicationIDLengthProperlyEncoded) { &key_blob, &key_characteristics)); ASSERT_GT(key_blob.size(), 0U); CheckBaseParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); @@ -1594,6 +1609,7 @@ TEST_P(NewKeyGenerationTest, LimitedUsageEcdsa) { ASSERT_GT(key_blob.size(), 0U); CheckBaseParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); @@ -1726,6 +1742,7 @@ TEST_P(NewKeyGenerationTest, Hmac) { ASSERT_GT(key_blob.size(), 0U); CheckBaseParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); EXPECT_TRUE(crypto_params.Contains(TAG_ALGORITHM, Algorithm::HMAC)); @@ -1761,6 +1778,7 @@ TEST_P(NewKeyGenerationTest, HmacNoAttestation) { ASSERT_GT(key_blob.size(), 0U); ASSERT_EQ(cert_chain_.size(), 0); CheckBaseParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); EXPECT_TRUE(crypto_params.Contains(TAG_ALGORITHM, Algorithm::HMAC)); @@ -1791,6 +1809,7 @@ TEST_P(NewKeyGenerationTest, LimitedUsageHmac) { ASSERT_GT(key_blob.size(), 0U); CheckBaseParams(key_characteristics); + CheckCharacteristics(key_blob, key_characteristics); AuthorizationSet crypto_params = SecLevelAuthorizations(key_characteristics); EXPECT_TRUE(crypto_params.Contains(TAG_ALGORITHM, Algorithm::HMAC)); @@ -2044,6 +2063,9 @@ TEST_P(SigningOperationsTest, RsaUseRequiresCorrectAppIdAppData) { .Authorization(TAG_APPLICATION_ID, "clientid") .Authorization(TAG_APPLICATION_DATA, "appdata") .SetDefaultValidity())); + + CheckAppIdCharacteristics(key_blob_, "clientid", "appdata", key_characteristics_); + EXPECT_EQ(ErrorCode::INVALID_KEY_BLOB, Begin(KeyPurpose::SIGN, AuthorizationSetBuilder().Digest(Digest::NONE).Padding(PaddingMode::NONE))); @@ -2558,6 +2580,9 @@ TEST_P(SigningOperationsTest, EcUseRequiresCorrectAppIdAppData) { .Authorization(TAG_APPLICATION_ID, "clientid") .Authorization(TAG_APPLICATION_DATA, "appdata") .SetDefaultValidity())); + + CheckAppIdCharacteristics(key_blob_, "clientid", "appdata", key_characteristics_); + EXPECT_EQ(ErrorCode::INVALID_KEY_BLOB, Begin(KeyPurpose::SIGN, AuthorizationSetBuilder().Digest(Digest::NONE))); AbortIfNeeded();