Merge changes from topic "141995149"
* changes:
Creating IRadio 1.5 vts framework.
Create IRadio 1.5 folder and empty files.
diff --git a/TEST_MAPPING b/TEST_MAPPING
new file mode 100644
index 0000000..98e125b
--- /dev/null
+++ b/TEST_MAPPING
@@ -0,0 +1,8 @@
+{
+ "presubmit": [
+ {
+ "name": "hidl_implementation_test"
+ }
+ ]
+}
+
diff --git a/boot/1.0/vts/functional/Android.bp b/boot/1.0/vts/functional/Android.bp
index 5d1a9cb..5244b95 100644
--- a/boot/1.0/vts/functional/Android.bp
+++ b/boot/1.0/vts/functional/Android.bp
@@ -19,5 +19,5 @@
defaults: ["VtsHalTargetTestDefaults"],
srcs: ["VtsHalBootV1_0TargetTest.cpp"],
static_libs: ["android.hardware.boot@1.0"],
- test_suites: ["general-tests"],
+ test_suites: ["general-tests", "vts-core"],
}
diff --git a/boot/1.0/vts/functional/VtsHalBootV1_0TargetTest.cpp b/boot/1.0/vts/functional/VtsHalBootV1_0TargetTest.cpp
index 2f2052c..fbddf6d 100644
--- a/boot/1.0/vts/functional/VtsHalBootV1_0TargetTest.cpp
+++ b/boot/1.0/vts/functional/VtsHalBootV1_0TargetTest.cpp
@@ -21,8 +21,9 @@
#include <android/hardware/boot/1.0/IBootControl.h>
-#include <VtsHalHidlTargetTestBase.h>
-#include <VtsHalHidlTargetTestEnvBase.h>
+#include <gtest/gtest.h>
+#include <hidl/GtestPrinter.h>
+#include <hidl/ServiceManagement.h>
#include <unordered_set>
@@ -37,30 +38,17 @@
using std::unordered_set;
using std::vector;
-// Test environment for Boot HIDL HAL.
-class BootHidlEnvironment : public ::testing::VtsHalHidlTargetTestEnvBase {
- public:
- // get the test environment singleton
- static BootHidlEnvironment* Instance() {
- static BootHidlEnvironment* instance = new BootHidlEnvironment;
- return instance;
+// The main test class for the Boot HIDL HAL.
+class BootHidlTest : public ::testing::TestWithParam<std::string> {
+ public:
+ virtual void SetUp() override {
+ boot = IBootControl::getService(GetParam());
+ ASSERT_NE(boot, nullptr);
}
- virtual void registerTestServices() override { registerTestService<IBootControl>(); }
-};
+ virtual void TearDown() override {}
-// The main test class for the Boot HIDL HAL.
-class BootHidlTest : public ::testing::VtsHalHidlTargetTestBase {
- public:
- virtual void SetUp() override {
- boot = ::testing::VtsHalHidlTargetTestBase::getService<IBootControl>(
- BootHidlEnvironment::Instance()->getServiceName<IBootControl>());
- ASSERT_NE(boot, nullptr);
- }
-
- virtual void TearDown() override {}
-
- sp<IBootControl> boot;
+ sp<IBootControl> boot;
};
auto generate_callback(CommandResult *dest) {
@@ -68,108 +56,105 @@
}
// Sanity check Boot::getNumberSlots().
-TEST_F(BootHidlTest, GetNumberSlots) {
- uint32_t slots = boot->getNumberSlots();
- EXPECT_LE((uint32_t)2, slots);
+TEST_P(BootHidlTest, GetNumberSlots) {
+ uint32_t slots = boot->getNumberSlots();
+ EXPECT_LE((uint32_t)2, slots);
}
// Sanity check Boot::getCurrentSlot().
-TEST_F(BootHidlTest, GetCurrentSlot) {
- Slot curSlot = boot->getCurrentSlot();
- uint32_t slots = boot->getNumberSlots();
- EXPECT_LT(curSlot, slots);
+TEST_P(BootHidlTest, GetCurrentSlot) {
+ Slot curSlot = boot->getCurrentSlot();
+ uint32_t slots = boot->getNumberSlots();
+ EXPECT_LT(curSlot, slots);
}
// Sanity check Boot::markBootSuccessful().
-TEST_F(BootHidlTest, MarkBootSuccessful) {
- CommandResult cr;
- Return<void> result = boot->markBootSuccessful(generate_callback(&cr));
- ASSERT_TRUE(result.isOk());
- if (cr.success) {
- Slot curSlot = boot->getCurrentSlot();
- BoolResult ret = boot->isSlotMarkedSuccessful(curSlot);
- EXPECT_EQ(BoolResult::TRUE, ret);
- }
+TEST_P(BootHidlTest, MarkBootSuccessful) {
+ CommandResult cr;
+ Return<void> result = boot->markBootSuccessful(generate_callback(&cr));
+ ASSERT_TRUE(result.isOk());
+ if (cr.success) {
+ Slot curSlot = boot->getCurrentSlot();
+ BoolResult ret = boot->isSlotMarkedSuccessful(curSlot);
+ EXPECT_EQ(BoolResult::TRUE, ret);
+ }
}
// Sanity check Boot::setActiveBootSlot() on good and bad inputs.
-TEST_F(BootHidlTest, SetActiveBootSlot) {
- for (Slot s = 0; s < 2; s++) {
- CommandResult cr;
- Return<void> result = boot->setActiveBootSlot(s, generate_callback(&cr));
- EXPECT_TRUE(result.isOk());
- }
- {
- // Restore original flags to avoid problems on reboot
- CommandResult cr;
- Return<void> result = boot->markBootSuccessful(generate_callback(&cr));
- EXPECT_TRUE(result.isOk());
- EXPECT_TRUE(cr.success);
- }
- {
- CommandResult cr;
- uint32_t slots = boot->getNumberSlots();
- Return<void> result =
- boot->setActiveBootSlot(slots, generate_callback(&cr));
- ASSERT_TRUE(result.isOk());
- EXPECT_EQ(false, cr.success);
- }
+TEST_P(BootHidlTest, SetActiveBootSlot) {
+ for (Slot s = 0; s < 2; s++) {
+ CommandResult cr;
+ Return<void> result = boot->setActiveBootSlot(s, generate_callback(&cr));
+ EXPECT_TRUE(result.isOk());
+ }
+ {
+ // Restore original flags to avoid problems on reboot
+ CommandResult cr;
+ Return<void> result = boot->markBootSuccessful(generate_callback(&cr));
+ EXPECT_TRUE(result.isOk());
+ EXPECT_TRUE(cr.success);
+ }
+ {
+ CommandResult cr;
+ uint32_t slots = boot->getNumberSlots();
+ Return<void> result = boot->setActiveBootSlot(slots, generate_callback(&cr));
+ ASSERT_TRUE(result.isOk());
+ EXPECT_EQ(false, cr.success);
+ }
}
// Sanity check Boot::setSlotAsUnbootable() on good and bad inputs.
-TEST_F(BootHidlTest, SetSlotAsUnbootable) {
- {
- CommandResult cr;
- Slot curSlot = boot->getCurrentSlot();
- Slot otherSlot = curSlot ? 0 : 1;
- Return<void> result =
- boot->setSlotAsUnbootable(otherSlot, generate_callback(&cr));
- EXPECT_TRUE(result.isOk());
- if (cr.success) {
- EXPECT_EQ(BoolResult::FALSE, boot->isSlotBootable(otherSlot));
+TEST_P(BootHidlTest, SetSlotAsUnbootable) {
+ {
+ CommandResult cr;
+ Slot curSlot = boot->getCurrentSlot();
+ Slot otherSlot = curSlot ? 0 : 1;
+ Return<void> result = boot->setSlotAsUnbootable(otherSlot, generate_callback(&cr));
+ EXPECT_TRUE(result.isOk());
+ if (cr.success) {
+ EXPECT_EQ(BoolResult::FALSE, boot->isSlotBootable(otherSlot));
- // Restore original flags to avoid problems on reboot
- result = boot->setActiveBootSlot(otherSlot, generate_callback(&cr));
- EXPECT_TRUE(result.isOk());
- EXPECT_TRUE(cr.success);
- result = boot->setActiveBootSlot(curSlot, generate_callback(&cr));
- EXPECT_TRUE(result.isOk());
- EXPECT_TRUE(cr.success);
- result = boot->markBootSuccessful(generate_callback(&cr));
- EXPECT_TRUE(result.isOk());
- EXPECT_TRUE(cr.success);
+ // Restore original flags to avoid problems on reboot
+ result = boot->setActiveBootSlot(otherSlot, generate_callback(&cr));
+ EXPECT_TRUE(result.isOk());
+ EXPECT_TRUE(cr.success);
+ result = boot->setActiveBootSlot(curSlot, generate_callback(&cr));
+ EXPECT_TRUE(result.isOk());
+ EXPECT_TRUE(cr.success);
+ result = boot->markBootSuccessful(generate_callback(&cr));
+ EXPECT_TRUE(result.isOk());
+ EXPECT_TRUE(cr.success);
+ }
}
- }
- {
- CommandResult cr;
- uint32_t slots = boot->getNumberSlots();
- Return<void> result =
- boot->setSlotAsUnbootable(slots, generate_callback(&cr));
- EXPECT_TRUE(result.isOk());
- EXPECT_EQ(false, cr.success);
- }
+ {
+ CommandResult cr;
+ uint32_t slots = boot->getNumberSlots();
+ Return<void> result = boot->setSlotAsUnbootable(slots, generate_callback(&cr));
+ EXPECT_TRUE(result.isOk());
+ EXPECT_EQ(false, cr.success);
+ }
}
// Sanity check Boot::isSlotBootable() on good and bad inputs.
-TEST_F(BootHidlTest, IsSlotBootable) {
- for (Slot s = 0; s < 2; s++) {
- EXPECT_NE(BoolResult::INVALID_SLOT, boot->isSlotBootable(s));
- }
- uint32_t slots = boot->getNumberSlots();
- EXPECT_EQ(BoolResult::INVALID_SLOT, boot->isSlotBootable(slots));
+TEST_P(BootHidlTest, IsSlotBootable) {
+ for (Slot s = 0; s < 2; s++) {
+ EXPECT_NE(BoolResult::INVALID_SLOT, boot->isSlotBootable(s));
+ }
+ uint32_t slots = boot->getNumberSlots();
+ EXPECT_EQ(BoolResult::INVALID_SLOT, boot->isSlotBootable(slots));
}
// Sanity check Boot::isSlotMarkedSuccessful() on good and bad inputs.
-TEST_F(BootHidlTest, IsSlotMarkedSuccessful) {
- for (Slot s = 0; s < 2; s++) {
- EXPECT_NE(BoolResult::INVALID_SLOT, boot->isSlotMarkedSuccessful(s));
- }
- uint32_t slots = boot->getNumberSlots();
- EXPECT_EQ(BoolResult::INVALID_SLOT, boot->isSlotMarkedSuccessful(slots));
+TEST_P(BootHidlTest, IsSlotMarkedSuccessful) {
+ for (Slot s = 0; s < 2; s++) {
+ EXPECT_NE(BoolResult::INVALID_SLOT, boot->isSlotMarkedSuccessful(s));
+ }
+ uint32_t slots = boot->getNumberSlots();
+ EXPECT_EQ(BoolResult::INVALID_SLOT, boot->isSlotMarkedSuccessful(slots));
}
// Sanity check Boot::getSuffix() on good and bad inputs.
-TEST_F(BootHidlTest, GetSuffix) {
+TEST_P(BootHidlTest, GetSuffix) {
string suffixStr;
unordered_set<string> suffixes;
auto cb = [&](hidl_string suffix) { suffixStr = suffix.c_str(); };
@@ -191,11 +176,7 @@
}
}
-int main(int argc, char **argv) {
- ::testing::AddGlobalTestEnvironment(BootHidlEnvironment::Instance());
- ::testing::InitGoogleTest(&argc, argv);
- BootHidlEnvironment::Instance()->init(&argc, argv);
- int status = RUN_ALL_TESTS();
- LOG(INFO) << "Test result = " << status;
- return status;
-}
+INSTANTIATE_TEST_SUITE_P(
+ PerInstance, BootHidlTest,
+ testing::ValuesIn(android::hardware::getAllHalInstanceNames(IBootControl::descriptor)),
+ android::hardware::PrintInstanceNameToString);
diff --git a/compatibility_matrices/compatibility_matrix.current.xml b/compatibility_matrices/compatibility_matrix.current.xml
index 34cbe26..541cfc6 100644
--- a/compatibility_matrices/compatibility_matrix.current.xml
+++ b/compatibility_matrices/compatibility_matrix.current.xml
@@ -223,7 +223,7 @@
</hal>
<hal format="hidl" optional="false">
<name>android.hardware.health</name>
- <version>2.0</version>
+ <version>2.1</version>
<interface>
<name>IHealth</name>
<instance>default</instance>
diff --git a/graphics/composer/2.2/utils/vts/RenderEngineVts.cpp b/graphics/composer/2.2/utils/vts/RenderEngineVts.cpp
index d910169..e2f2670 100644
--- a/graphics/composer/2.2/utils/vts/RenderEngineVts.cpp
+++ b/graphics/composer/2.2/utils/vts/RenderEngineVts.cpp
@@ -26,12 +26,11 @@
using mapper::V2_1::IMapper;
using renderengine::DisplaySettings;
using renderengine::LayerSettings;
+using renderengine::RenderEngineCreationArgs;
-TestRenderEngine::TestRenderEngine(common::V1_1::PixelFormat hwcFormat,
- uint32_t renderEngineFeatures) {
- mFormat = hwcFormat;
- mRenderEngine = renderengine::RenderEngine::create(
- static_cast<int32_t>(mFormat), renderEngineFeatures, mMaxFrameBufferAcquireBuffers);
+TestRenderEngine::TestRenderEngine(const RenderEngineCreationArgs& args) {
+ mFormat = static_cast<common::V1_1::PixelFormat>(args.pixelFormat);
+ mRenderEngine = renderengine::RenderEngine::create(args);
}
void TestRenderEngine::setRenderLayers(std::vector<std::shared_ptr<TestLayer>> layers) {
diff --git a/graphics/composer/2.2/utils/vts/include/composer-vts/2.2/RenderEngineVts.h b/graphics/composer/2.2/utils/vts/include/composer-vts/2.2/RenderEngineVts.h
index 0ac5a22..b936cab 100644
--- a/graphics/composer/2.2/utils/vts/include/composer-vts/2.2/RenderEngineVts.h
+++ b/graphics/composer/2.2/utils/vts/include/composer-vts/2.2/RenderEngineVts.h
@@ -35,11 +35,14 @@
using mapper::V2_1::IMapper;
using renderengine::DisplaySettings;
+using renderengine::RenderEngineCreationArgs;
using vts::Gralloc;
class TestRenderEngine {
public:
- TestRenderEngine(common::V1_1::PixelFormat hwcFormat, uint32_t renderEngineFeatures);
+ static constexpr uint32_t sMaxFrameBufferAcquireBuffers = 2;
+
+ TestRenderEngine(const RenderEngineCreationArgs& args);
~TestRenderEngine() = default;
void setRenderLayers(std::vector<std::shared_ptr<TestLayer>> layers);
@@ -51,7 +54,6 @@
void checkColorBuffer(std::vector<V2_2::IComposerClient::Color>& expectedColors);
private:
- static constexpr uint32_t mMaxFrameBufferAcquireBuffers = 2;
common::V1_1::PixelFormat mFormat;
std::vector<renderengine::LayerSettings> mCompositionLayers;
std::unique_ptr<renderengine::RenderEngine> mRenderEngine;
diff --git a/graphics/composer/2.2/vts/functional/VtsHalGraphicsComposerV2_2ReadbackTest.cpp b/graphics/composer/2.2/vts/functional/VtsHalGraphicsComposerV2_2ReadbackTest.cpp
index ade7a38..6a6f7de 100644
--- a/graphics/composer/2.2/vts/functional/VtsHalGraphicsComposerV2_2ReadbackTest.cpp
+++ b/graphics/composer/2.2/vts/functional/VtsHalGraphicsComposerV2_2ReadbackTest.cpp
@@ -103,9 +103,14 @@
ASSERT_NO_FATAL_FAILURE(
mTestRenderEngine = std::unique_ptr<TestRenderEngine>(new TestRenderEngine(
- PixelFormat::RGBA_8888,
- renderengine::RenderEngine::USE_COLOR_MANAGEMENT |
- renderengine::RenderEngine::USE_HIGH_PRIORITY_CONTEXT)));
+ renderengine::RenderEngineCreationArgs::Builder()
+ .setPixelFormat(static_cast<int>(ui::PixelFormat::RGBA_8888))
+ .setImageCacheSize(TestRenderEngine::sMaxFrameBufferAcquireBuffers)
+ .setUseColorManagerment(true)
+ .setEnableProtectedContext(false)
+ .setPrecacheToneMapperShaderOnly(false)
+ .setContextPriority(renderengine::RenderEngine::ContextPriority::HIGH)
+ .build())));
renderengine::DisplaySettings clientCompositionDisplay;
clientCompositionDisplay.physicalDisplay = Rect(mDisplayWidth, mDisplayHeight);
diff --git a/health/2.1/Android.bp b/health/2.1/Android.bp
new file mode 100644
index 0000000..254bfc0
--- /dev/null
+++ b/health/2.1/Android.bp
@@ -0,0 +1,20 @@
+// This file is autogenerated by hidl-gen -Landroidbp.
+
+hidl_interface {
+ name: "android.hardware.health@2.1",
+ root: "android.hardware",
+ vndk: {
+ enabled: true,
+ },
+ srcs: [
+ "types.hal",
+ "IHealth.hal",
+ "IHealthInfoCallback.hal",
+ ],
+ interfaces: [
+ "android.hardware.health@1.0",
+ "android.hardware.health@2.0",
+ "android.hidl.base@1.0",
+ ],
+ gen_java: true,
+}
diff --git a/health/2.1/IHealth.hal b/health/2.1/IHealth.hal
new file mode 100644
index 0000000..8a5152a
--- /dev/null
+++ b/health/2.1/IHealth.hal
@@ -0,0 +1,80 @@
+/*
+ * Copyright (C) 2019 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 android.hardware.health@2.1;
+
+import @2.0::IHealth;
+import @2.0::Result;
+import HealthConfig;
+import HealthInfo;
+import IHealthInfoCallback;
+
+/**
+ * IHealth manages health info and posts events on registered callbacks.
+ *
+ * An implementation of @2.1::IHealth must be able to handle both
+ * @2.0::IHealthInfoCallback and @2.1::IHealthInfoCallback.
+ * - When registerCallback() is called, an implementation must cast the callback
+ * to @2.1::IHealthInfoCallback.
+ * - If the cast is successful, when a health info broadcast is sent, the
+ * implementation must call
+ * @2.1::IHealthInfoCallback.healthInfoChanged_2_1(). All fields introduced
+ * in 2.1 must be set appropriately. The implementation must not call
+ * @2.0::IHealthInfoCallback.healthInfoChanged().
+ * - If the cast is unsuccessful, the implementation must call
+ * @2.0::IHealthInfoCallback.healthInfoChanged().
+ * - When unregisterCallback() is called, from then on, updates must not be sent
+ * through either healthInfoChanged_2_1() or healthInfoChanged().
+ *
+ * Passthrough implementations are not required to send health info to all
+ * callbacks periodically, but they must do so when update() is called.
+ * Binderized implementations must send health info to all callbacks
+ * periodically. The intervals between two notifications must be retrieved from
+ * the passthrough implementation through the getHealthConfig() function.
+ */
+interface IHealth extends @2.0::IHealth {
+ /**
+ * Get configuration of this HAL.
+ *
+ * @return result SUCCESS if successful,
+ * NOT_SUPPORTED if this API is not supported,
+ * UNKNOWN for other errors.
+ * @return config HAL configuration, to be ignored if result is not
+ * SUCCESS.
+ */
+ getHealthConfig() generates (Result result, HealthConfig config);
+
+ /**
+ * Get Health Information.
+ *
+ * @return result SUCCESS if successful,
+ * NOT_SUPPORTED if this API is not supported,
+ * UNKNOWN for other errors.
+ * @return value Health information, to be ignored if result is not
+ * SUCCESS.
+ */
+ getHealthInfo_2_1() generates (Result result, @2.1::HealthInfo value);
+
+ /**
+ * Return whether the screen should be kept on in charger mode.
+ *
+ * @return result SUCCESS if successful,
+ * NOT_SUPPORTED if this API is not supported,
+ * UNKNOWN for other errors.
+ * @return value whether screen should be kept on.
+ */
+ shouldKeepScreenOn() generates (Result result, bool value);
+};
diff --git a/health/2.1/IHealthInfoCallback.hal b/health/2.1/IHealthInfoCallback.hal
new file mode 100644
index 0000000..275f018
--- /dev/null
+++ b/health/2.1/IHealthInfoCallback.hal
@@ -0,0 +1,36 @@
+/*
+ * Copyright (C) 2019 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 android.hardware.health@2.1;
+
+import @2.0::IHealthInfoCallback;
+
+/**
+ * IHealthInfoCallback is the updated callback interface to
+ * {@link IHealth.registerCallback}.
+ *
+ * A @2.1::IHealthInfoCallback must implement healthInfoChanged_2_1(). The
+ * inherited healthInfoChanged() function is never called when the HAL
+ * implementation post events. See documentation on @2.1::IHealth for details.
+ */
+interface IHealthInfoCallback extends @2.0::IHealthInfoCallback {
+ /**
+ * An implementation of IHealth must call healthInfoChanged on all
+ * registered callbacks after health info changes.
+ * @param info the updated HealthInfo
+ */
+ oneway healthInfoChanged_2_1(HealthInfo info);
+};
diff --git a/health/2.1/types.hal b/health/2.1/types.hal
new file mode 100644
index 0000000..efd8d6f
--- /dev/null
+++ b/health/2.1/types.hal
@@ -0,0 +1,109 @@
+/*
+ * Copyright (C) 2017 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 android.hardware.health@2.1;
+
+import @1.0::HealthConfig;
+import @2.0::HealthInfo;
+
+/**
+ * Battery capacity level. This enum provides additional information along side
+ * with the battery capacity.
+ * Clients of this HAL must use this value before inferring it from the
+ * battery capacity.
+ */
+enum BatteryCapacityLevel : int32_t {
+ /**
+ * Battery capacity level is unknown.
+ * Battery capacity level must be set to this value if and only if battery
+ * is not present.
+ */
+ UNKNOWN = 0,
+ /**
+ * Battery is at critical level. The Android framework must schedule a
+ * shutdown when it sees this value from the HAL.
+ */
+ CRITICAL,
+ /**
+ * Battery is low. The Android framework may limit the performance of
+ * the device when it sees this value from the HAL.
+ */
+ LOW,
+ /**
+ * Battery level is normal.
+ */
+ NORMAL,
+ /**
+ * Battery level is high.
+ */
+ HIGH,
+ /**
+ * Battery is full. It must be set to FULL if and only if battery level is
+ * 100.
+ */
+ FULL,
+};
+
+/**
+ * Combined Health Information.
+ */
+struct HealthInfo {
+ /**
+ * V2.0 HealthInfo.
+ * If a member is unsupported, it is filled with:
+ * - 0 (for integers);
+ * - false (for booleans);
+ * - empty string (for strings);
+ * - UNKNOWN (for BatteryStatus and BatteryHealth).
+ */
+ @2.0::HealthInfo legacy;
+
+ /**
+ * Battery capacity level. See BatteryCapacityLevel for more details.
+ */
+ BatteryCapacityLevel batteryCapacityLevel;
+
+ /**
+ * Estimated time to fully charge the device (in seconds).
+ * Value must be 0 if and only if batteryCapacityLevel is FULL or UNKNOWN.
+ * Otherwise, value must be positive.
+ */
+ int64_t batteryChargeTimeToFullNowSeconds;
+
+ /**
+ * Estimated battery full capacity (in microamp hours, uAh).
+ * Value must be 0 if unknown.
+ * Value must be positive if known, and must be between [50%, 120%] of
+ * batteryFullCharge (the designed capacity).
+ */
+ int32_t batteryFullCapacityUah;
+};
+
+/**
+ * Combined configuration of a health HAL implementation.
+ */
+struct HealthConfig {
+ /**
+ * 1.0 version of health config.
+ */
+ @1.0::HealthConfig battery;
+
+ /**
+ * Minimum battery level for charger to reboot into Android (in percent).
+ * Value should be in range [0, 100].
+ */
+ int32_t bootMinCap;
+};
diff --git a/health/2.1/vts/OWNERS b/health/2.1/vts/OWNERS
new file mode 100644
index 0000000..20450ba
--- /dev/null
+++ b/health/2.1/vts/OWNERS
@@ -0,0 +1,3 @@
+elsk@google.com
+hridya@google.com
+sspatil@google.com
diff --git a/health/2.1/vts/functional/Android.bp b/health/2.1/vts/functional/Android.bp
new file mode 100644
index 0000000..5aa873a
--- /dev/null
+++ b/health/2.1/vts/functional/Android.bp
@@ -0,0 +1,29 @@
+//
+// Copyright (C) 2019 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.
+//
+
+cc_test {
+ name: "VtsHalHealthV2_1TargetTest",
+ defaults: ["VtsHalTargetTestDefaults"],
+ srcs: ["VtsHalHealthV2_1TargetTest.cpp"],
+ static_libs: [
+ "libgflags",
+ "libgmock",
+ "android.hardware.health@1.0",
+ "android.hardware.health@2.0",
+ "android.hardware.health@2.1",
+ ],
+ test_suites: ["general-tests"],
+}
diff --git a/health/2.1/vts/functional/VtsHalHealthV2_1TargetTest.cpp b/health/2.1/vts/functional/VtsHalHealthV2_1TargetTest.cpp
new file mode 100644
index 0000000..7df4926
--- /dev/null
+++ b/health/2.1/vts/functional/VtsHalHealthV2_1TargetTest.cpp
@@ -0,0 +1,269 @@
+/*
+ * Copyright (C) 2019 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.
+ */
+
+#define LOG_TAG "health_hidl_hal_test"
+
+#include <mutex>
+#include <set>
+#include <string>
+
+#include <android-base/logging.h>
+#include <android/hardware/health/1.0/types.h>
+#include <android/hardware/health/2.0/types.h>
+#include <android/hardware/health/2.1/IHealth.h>
+#include <android/hardware/health/2.1/IHealthInfoCallback.h>
+#include <android/hardware/health/2.1/types.h>
+#include <gmock/gmock.h>
+#include <gtest/gtest.h>
+#include <hidl/GtestPrinter.h>
+#include <hidl/ServiceManagement.h>
+
+using ::android::hardware::health::V1_0::BatteryStatus;
+using ::android::hardware::health::V2_0::Result;
+using ::testing::AnyOf;
+using ::testing::AssertionFailure;
+using ::testing::AssertionResult;
+using ::testing::AssertionSuccess;
+using namespace std::chrono_literals;
+
+using ::android::hardware::health::V1_0::toString;
+using ::android::hardware::health::V2_0::toString;
+using ::android::hardware::health::V2_1::toString;
+
+// Return expr if it is evaluated to false.
+#define TEST_AND_RETURN(expr) \
+ do { \
+ auto res = (expr); \
+ if (!res) return res; \
+ } while (0)
+
+// Return a descriptive AssertionFailure() if expr is evaluated to false.
+#define TEST_AND_RETURN_FAILURE(expr) \
+ do { \
+ auto res = (expr); \
+ if (!res) { \
+ return AssertionFailure() << #expr " is false"; \
+ } \
+ } while (0)
+
+namespace android {
+namespace hardware {
+namespace health {
+
+namespace V2_0 {
+std::ostream& operator<<(std::ostream& os, const Result& res) {
+ return os << toString(res);
+}
+} // namespace V2_0
+
+namespace V2_1 {
+
+class HealthHidlTest : public testing::TestWithParam<std::string> {
+ public:
+ virtual void SetUp() override {
+ service_ = IHealth::getService(GetParam());
+ ASSERT_NE(nullptr, service_.get()) << "Instance '" << GetParam() << "'' is not available.";
+ }
+
+ sp<IHealth> service_;
+};
+
+class CallbackBase {
+ public:
+ Return<void> healthInfoChangedInternal() {
+ std::lock_guard<std::mutex> lock(mutex_);
+ invoked_ = true;
+ invoked_notify_.notify_all();
+ return Void();
+ }
+ template <typename R, typename P>
+ bool waitInvoke(std::chrono::duration<R, P> duration) {
+ std::unique_lock<std::mutex> lock(mutex_);
+ bool r = invoked_notify_.wait_for(lock, duration, [this] { return this->invoked_; });
+ invoked_ = false;
+ return r;
+ }
+
+ private:
+ std::mutex mutex_;
+ std::condition_variable invoked_notify_;
+ bool invoked_ = false;
+};
+
+class Callback_2_0 : public android::hardware::health::V2_0::IHealthInfoCallback,
+ public CallbackBase {
+ Return<void> healthInfoChanged(const android::hardware::health::V2_0::HealthInfo&) override {
+ return healthInfoChangedInternal();
+ }
+};
+
+class Callback_2_1 : public android::hardware::health::V2_1::IHealthInfoCallback,
+ public CallbackBase {
+ Return<void> healthInfoChanged(const android::hardware::health::V2_0::HealthInfo&) override {
+ ADD_FAILURE() << "android::hardware::health::V2_1::IHealthInfoCallback::healthInfoChanged "
+ << "is called, but it shouldn't be";
+ return Void();
+ }
+ Return<void> healthInfoChanged_2_1(const HealthInfo&) override {
+ return healthInfoChangedInternal();
+ }
+};
+
+template <typename T>
+AssertionResult IsOk(const Return<T>& r) {
+ return r.isOk() ? AssertionSuccess() : (AssertionFailure() << r.description());
+}
+
+// Both IsOk() and Result::SUCCESS
+AssertionResult ResultIsSuccess(const Return<Result>& r) {
+ if (!r.isOk()) {
+ return AssertionFailure() << r.description();
+ }
+ if (static_cast<Result>(r) != Result::SUCCESS) {
+ return AssertionFailure() << toString(static_cast<Result>(r));
+ }
+ return AssertionSuccess();
+}
+
+/**
+ * Test whether callbacks work. Tested functions are IHealth::registerCallback,
+ * unregisterCallback, and update.
+ */
+template <typename Callback>
+AssertionResult TestCallbacks(sp<IHealth> service) {
+ sp<Callback> first = new Callback();
+ sp<Callback> second = new Callback();
+
+ TEST_AND_RETURN(ResultIsSuccess(service->registerCallback(first)));
+ TEST_AND_RETURN(ResultIsSuccess(service->registerCallback(second)));
+
+ // registerCallback may or may not invoke the callback immediately, so the test needs
+ // to wait for the invocation. If the implementation chooses not to invoke the callback
+ // immediately, just wait for some time.
+ first->waitInvoke(200ms);
+ second->waitInvoke(200ms);
+
+ // assert that the first callback is invoked when update is called.
+ TEST_AND_RETURN(ResultIsSuccess(service->update()));
+
+ TEST_AND_RETURN_FAILURE(first->waitInvoke(1s));
+ TEST_AND_RETURN_FAILURE(second->waitInvoke(1s));
+
+ TEST_AND_RETURN(ResultIsSuccess(service->unregisterCallback(first)));
+
+ // clear any potentially pending callbacks result from wakealarm / kernel events
+ // If there is none, just wait for some time.
+ first->waitInvoke(200ms);
+ second->waitInvoke(200ms);
+
+ // assert that the second callback is still invoked even though the first is unregistered.
+ TEST_AND_RETURN(ResultIsSuccess(service->update()));
+
+ TEST_AND_RETURN_FAILURE(!first->waitInvoke(200ms));
+ TEST_AND_RETURN_FAILURE(second->waitInvoke(1s));
+
+ TEST_AND_RETURN(ResultIsSuccess(service->unregisterCallback(second)));
+ return AssertionSuccess();
+}
+
+TEST_P(HealthHidlTest, Callbacks_2_0) {
+ EXPECT_TRUE(TestCallbacks<Callback_2_0>(service_));
+}
+
+TEST_P(HealthHidlTest, Callbacks_2_1) {
+ EXPECT_TRUE(TestCallbacks<Callback_2_1>(service_));
+}
+
+template <typename Callback>
+AssertionResult TestUnregisterNonExistentCallback(sp<IHealth> service) {
+ sp<Callback> callback = new Callback();
+ auto ret = service->unregisterCallback(callback);
+ TEST_AND_RETURN(IsOk(ret));
+ if (static_cast<Result>(ret) != Result::NOT_FOUND) {
+ return AssertionFailure()
+ << "Unregistering non-existent callback should return NOT_FOUND, but returned "
+ << static_cast<Result>(ret);
+ }
+ return AssertionSuccess();
+}
+
+TEST_P(HealthHidlTest, UnregisterNonExistentCallback_2_0) {
+ EXPECT_TRUE(TestUnregisterNonExistentCallback<Callback_2_0>(service_));
+}
+
+TEST_P(HealthHidlTest, UnregisterNonExistentCallback_2_1) {
+ EXPECT_TRUE(TestUnregisterNonExistentCallback<Callback_2_1>(service_));
+}
+
+template <typename T>
+AssertionResult IsEnum(T value) {
+ for (auto it : hidl_enum_range<T>()) {
+ if (it == value) {
+ return AssertionSuccess();
+ }
+ }
+
+ return AssertionFailure() << static_cast<std::underlying_type_t<T>>(value) << " is not valid";
+}
+
+/*
+ * Tests the values returned by getHealthInfo() from interface IHealth.
+ */
+TEST_P(HealthHidlTest, getHealthInfo_2_1) {
+ EXPECT_TRUE(IsOk(service_->getHealthInfo_2_1([](auto result, const auto& value) {
+ if (result == Result::NOT_SUPPORTED) {
+ return;
+ }
+ ASSERT_EQ(Result::SUCCESS, result);
+ const auto& legacy = value.legacy.legacy;
+
+ EXPECT_TRUE(IsEnum(value.batteryCapacityLevel)) << " BatteryCapacityLevel";
+ EXPECT_GE(value.batteryChargeTimeToFullNowSeconds, 0);
+
+ EXPECT_GE(value.batteryFullCapacityUah, 0) << "batteryFullCapacityUah is unknown";
+ EXPECT_GE(value.batteryFullCapacityUah, legacy.batteryFullCharge * 0.50);
+ EXPECT_LE(value.batteryFullCapacityUah, legacy.batteryFullCharge * 1.20);
+ })));
+}
+
+TEST_P(HealthHidlTest, getHealthConfig) {
+ EXPECT_TRUE(IsOk(service_->getHealthConfig([](auto result, const auto&) {
+ EXPECT_THAT(result, AnyOf(Result::SUCCESS, Result::NOT_SUPPORTED));
+ })));
+}
+
+TEST_P(HealthHidlTest, shouldKeepScreenOn) {
+ EXPECT_TRUE(IsOk(service_->shouldKeepScreenOn([](auto result, const auto&) {
+ EXPECT_THAT(result, AnyOf(Result::SUCCESS, Result::NOT_SUPPORTED));
+ })));
+}
+
+INSTANTIATE_TEST_SUITE_P(
+ , HealthHidlTest,
+ testing::ValuesIn(android::hardware::getAllHalInstanceNames(IHealth::descriptor)),
+ android::hardware::PrintInstanceNameToString);
+
+} // namespace V2_1
+} // namespace health
+} // namespace hardware
+} // namespace android
+
+int main(int argc, char** argv) {
+ ::testing::InitGoogleTest(&argc, argv);
+ int status = RUN_ALL_TESTS();
+ LOG(INFO) << "Test result = " << status;
+ return status;
+}
diff --git a/keymaster/4.0/vts/functional/keymaster_hidl_hal_test.cpp b/keymaster/4.0/vts/functional/keymaster_hidl_hal_test.cpp
index 0ac7e48..c5acf8c 100644
--- a/keymaster/4.0/vts/functional/keymaster_hidl_hal_test.cpp
+++ b/keymaster/4.0/vts/functional/keymaster_hidl_hal_test.cpp
@@ -4413,6 +4413,35 @@
}
/*
+ * AttestationTest.AttestationApplicationIDLengthProperlyEncoded
+ *
+ * Verifies that the Attestation Application ID software enforced tag has a proper length encoding.
+ * Some implementations break strict encoding rules by encoding a length between 127 and 256 in one
+ * byte. Proper DER encoding specifies that for lengths greather than 127, one byte should be used
+ * to specify how many following bytes will be used to encode the length.
+ */
+TEST_F(AttestationTest, AttestationApplicationIDLengthProperlyEncoded) {
+ auto creation_time = std::chrono::system_clock::now();
+ ASSERT_EQ(ErrorCode::OK, GenerateKey(AuthorizationSetBuilder()
+ .Authorization(TAG_NO_AUTH_REQUIRED)
+ .EcdsaSigningKey(EcCurve::P_256)
+ .Digest(Digest::SHA_2_256)));
+
+ hidl_vec<hidl_vec<uint8_t>> cert_chain;
+ const string app_id(143, 'a');
+ ASSERT_EQ(ErrorCode::OK,
+ AttestKey(AuthorizationSetBuilder()
+ .Authorization(TAG_ATTESTATION_CHALLENGE, HidlBuf("challenge"))
+ .Authorization(TAG_ATTESTATION_APPLICATION_ID, HidlBuf(app_id)),
+ &cert_chain));
+ EXPECT_GE(cert_chain.size(), 2U);
+
+ EXPECT_TRUE(verify_attestation_record("challenge", app_id, //
+ key_characteristics_.softwareEnforced, //
+ key_characteristics_.hardwareEnforced, //
+ SecLevel(), cert_chain[0], creation_time));
+}
+/*
* AttestationTest.AesAttestation
*
* Verifies that attesting to AES keys fails in the expected way.