Verify mac change on time stamp change
am: 33d75d090b
Change-Id: I00092609f97d985d203ca5df6987a05fa9b0ae6c
diff --git a/keymaster/4.0/vts/functional/VerificationTokenTest.cpp b/keymaster/4.0/vts/functional/VerificationTokenTest.cpp
index 3876b16..de28683 100644
--- a/keymaster/4.0/vts/functional/VerificationTokenTest.cpp
+++ b/keymaster/4.0/vts/functional/VerificationTokenTest.cpp
@@ -124,6 +124,65 @@
// report if times aren't nearly always <1ms apart.
EXPECT_LE(host_time_delta, km_time_delta + 2);
EXPECT_LE(km_time_delta, host_time_delta + 2);
+ ASSERT_EQ(result1.token.mac.size(), result2.token.mac.size());
+ ASSERT_NE(0,
+ memcmp(result1.token.mac.data(), result2.token.mac.data(), result1.token.mac.size()));
+}
+
+/*
+ * Test that the mac changes when the time stamp changes. This is does not guarantee that the time
+ * stamp is included in the mac but on failure we know that it is not. Other than in the test
+ * case above we call verifyAuthorization with the exact same set of parameters.
+ */
+TEST_F(VerificationTokenTest, MacChangesOnChangingTimestamp) {
+ auto result1 =
+ verifyAuthorization(0 /* operation handle */,
+ AuthorizationSet() /* paramtersToVerify */, HardwareAuthToken());
+ ASSERT_TRUE(result1.callSuccessful);
+ auto result1_time = getTime();
+
+ if (SecLevel() == SecurityLevel::STRONGBOX) {
+ // StrongBox should not implement verifyAuthorization.
+ EXPECT_EQ(ErrorCode::UNIMPLEMENTED, result1.error);
+ return;
+ }
+
+ EXPECT_EQ(ErrorCode::OK, result1.error);
+ EXPECT_EQ(0U, result1.token.challenge);
+ EXPECT_EQ(SecLevel(), result1.token.securityLevel);
+ EXPECT_EQ(0U, result1.token.parametersVerified.size())
+ << "We didn't supply any parameters to verify";
+ EXPECT_GT(result1.token.timestamp, 0U);
+
+ constexpr uint32_t time_to_sleep = 200;
+ sleep_ms(time_to_sleep);
+
+ auto result2 =
+ verifyAuthorization(0 /* operation handle */,
+ AuthorizationSet() /* paramtersToVerify */, HardwareAuthToken());
+ ASSERT_TRUE(result2.callSuccessful);
+ auto result2_time = getTime();
+ EXPECT_EQ(ErrorCode::OK, result2.error);
+ EXPECT_EQ(0U, result2.token.challenge);
+ EXPECT_EQ(SecLevel(), result2.token.securityLevel);
+ EXPECT_EQ(0U, result2.token.parametersVerified.size())
+ << "We didn't supply any parameters to verify";
+
+ auto host_time_delta = result2_time - result1_time;
+
+ EXPECT_GE(host_time_delta, time_to_sleep)
+ << "We slept for " << time_to_sleep << " ms, the clock must have advanced by that much";
+ EXPECT_LE(host_time_delta, time_to_sleep + 20)
+ << "The verifyAuthorization call took " << (host_time_delta - time_to_sleep)
+ << " ms? That's awful!";
+
+ auto km_time_delta = result2.token.timestamp - result1.token.timestamp;
+
+ EXPECT_LE(host_time_delta, km_time_delta + 2);
+ EXPECT_LE(km_time_delta, host_time_delta + 2);
+ ASSERT_EQ(result1.token.mac.size(), result2.token.mac.size());
+ ASSERT_NE(0,
+ memcmp(result1.token.mac.data(), result2.token.mac.data(), result1.token.mac.size()));
}
} // namespace test