Merge "Add capabilities to bluetooth HAL service" into pi-dev
diff --git a/automotive/vehicle/2.0/default/impl/vhal_v2_0/DefaultConfig.h b/automotive/vehicle/2.0/default/impl/vhal_v2_0/DefaultConfig.h
index c1c511f..e54de00 100644
--- a/automotive/vehicle/2.0/default/impl/vhal_v2_0/DefaultConfig.h
+++ b/automotive/vehicle/2.0/default/impl/vhal_v2_0/DefaultConfig.h
@@ -429,7 +429,7 @@
{.config = {.prop = toInt(VehicleProperty::AP_POWER_BOOTUP_REASON),
.access = VehiclePropertyAccess::READ,
- .changeMode = VehiclePropertyChangeMode::ON_CHANGE},
+ .changeMode = VehiclePropertyChangeMode::STATIC},
.initialValue = {.int32Values = {toInt(VehicleApPowerBootupReason::USER_POWER_ON)}}},
{
diff --git a/automotive/vehicle/2.0/types.hal b/automotive/vehicle/2.0/types.hal
index 3001213..87daedc 100644
--- a/automotive/vehicle/2.0/types.hal
+++ b/automotive/vehicle/2.0/types.hal
@@ -510,6 +510,7 @@
*
* @change_mode VehiclePropertyChangeMode:ON_CHANGE
* @access VehiclePropertyAccess:READ
+ * @data_enum VehicleTurnSignal
*/
TURN_SIGNAL_STATE = (
0x0408
@@ -522,6 +523,7 @@
*
* @change_mode VehiclePropertyChangeMode:ON_CHANGE
* @access VehiclePropertyAccess:READ
+ * @data_enum VehicleIgnitionState
*/
IGNITION_STATE = (
0x0409
diff --git a/confirmationui/support/include/android/hardware/confirmationui/support/msg_formatting.h b/confirmationui/support/include/android/hardware/confirmationui/support/msg_formatting.h
index 0d03591..6558799 100644
--- a/confirmationui/support/include/android/hardware/confirmationui/support/msg_formatting.h
+++ b/confirmationui/support/include/android/hardware/confirmationui/support/msg_formatting.h
@@ -105,6 +105,7 @@
PromptUserConfirmation,
DeliverSecureInputEvent,
Abort,
+ Vendor,
};
template <Command cmd>
@@ -115,6 +116,7 @@
DECLARE_COMMAND(PromptUserConfirmation);
DECLARE_COMMAND(DeliverSecureInputEvent);
DECLARE_COMMAND(Abort);
+DECLARE_COMMAND(Vendor);
using PromptUserConfirmationMsg = Message<PromptUserConfirmation_t, hidl_string, hidl_vec<uint8_t>,
hidl_string, hidl_vec<UIOption>>;
@@ -166,7 +168,7 @@
}
inline void zero(const volatile uint8_t*, const volatile uint8_t*) {}
// This odd alignment function aligns the stream position to a 4byte and never 8byte boundary
-// It is to accommodate the 4 byte size field which is then followed by 8byte alligned data.
+// It is to accommodate the 4 byte size field which is then followed by 8byte aligned data.
template <typename T>
StreamState<T> unalign(StreamState<T> s) {
uint8_t unalignment = uintptr_t(s.pos_) & 0x3;
diff --git a/current.txt b/current.txt
index fdf17be..c35fa92 100644
--- a/current.txt
+++ b/current.txt
@@ -294,7 +294,7 @@
3b17c1fdfc389e0abe626c37054954b07201127d890c2bc05d47613ec1f4de4f android.hardware.automotive.evs@1.0::types
b3caf524c46a47d67e6453a34419e1881942d059e146cda740502670e9a752c3 android.hardware.automotive.vehicle@2.0::IVehicle
80fb4156fa91ce86e49bd2cabe215078f6b69591d416a09e914532eae6712052 android.hardware.automotive.vehicle@2.0::IVehicleCallback
-442de3a3d3819ff8b8bfe9ec710592ca8af7c16bfdb5eb8911b898b8f12b2bb0 android.hardware.automotive.vehicle@2.0::types
+4ff0dcfb938a5df283eef47de33b4e1284fab73f584cfc0c94e97317bdb7bf26 android.hardware.automotive.vehicle@2.0::types
32cc50cc2a7658ec613c0c2dd2accbf6a05113b749852879e818b8b7b438db19 android.hardware.bluetooth.a2dp@1.0::IBluetoothAudioHost
ff4be64d7992f8bec97dff37f35450e79b3430c61f85f54322ce45bef229dc3b android.hardware.bluetooth.a2dp@1.0::IBluetoothAudioOffload
27f22d2e873e6201f9620cf4d8e2facb25bd0dd30a2b911e441b4600d560fa62 android.hardware.bluetooth.a2dp@1.0::types
diff --git a/neuralnetworks/1.1/vts/functional/VtsHalNeuralnetworksV1_1BasicTest.cpp b/neuralnetworks/1.1/vts/functional/VtsHalNeuralnetworksV1_1BasicTest.cpp
index 17f6744..10591dc 100644
--- a/neuralnetworks/1.1/vts/functional/VtsHalNeuralnetworksV1_1BasicTest.cpp
+++ b/neuralnetworks/1.1/vts/functional/VtsHalNeuralnetworksV1_1BasicTest.cpp
@@ -286,6 +286,169 @@
EXPECT_EQ(ErrorStatus::INVALID_ARGUMENT, executionReturnStatus);
}
+class NeuralnetworksInputsOutputsTest
+ : public NeuralnetworksHidlTest,
+ public ::testing::WithParamInterface<std::tuple<bool, bool>> {
+ protected:
+ virtual void SetUp() { NeuralnetworksHidlTest::SetUp(); }
+ virtual void TearDown() { NeuralnetworksHidlTest::TearDown(); }
+ V1_1::Model createModel(const std::vector<uint32_t>& inputs,
+ const std::vector<uint32_t>& outputs) {
+ // We set up the operands as floating-point with no designated
+ // model inputs and outputs, and then patch type and lifetime
+ // later on in this function.
+
+ std::vector<Operand> operands = {
+ {
+ .type = OperandType::TENSOR_FLOAT32,
+ .dimensions = {1},
+ .numberOfConsumers = 1,
+ .scale = 0.0f,
+ .zeroPoint = 0,
+ .lifetime = OperandLifeTime::TEMPORARY_VARIABLE,
+ .location = {.poolIndex = 0, .offset = 0, .length = 0},
+ },
+ {
+ .type = OperandType::TENSOR_FLOAT32,
+ .dimensions = {1},
+ .numberOfConsumers = 1,
+ .scale = 0.0f,
+ .zeroPoint = 0,
+ .lifetime = OperandLifeTime::TEMPORARY_VARIABLE,
+ .location = {.poolIndex = 0, .offset = 0, .length = 0},
+ },
+ {
+ .type = OperandType::INT32,
+ .dimensions = {},
+ .numberOfConsumers = 1,
+ .scale = 0.0f,
+ .zeroPoint = 0,
+ .lifetime = OperandLifeTime::CONSTANT_COPY,
+ .location = {.poolIndex = 0, .offset = 0, .length = sizeof(int32_t)},
+ },
+ {
+ .type = OperandType::TENSOR_FLOAT32,
+ .dimensions = {1},
+ .numberOfConsumers = 0,
+ .scale = 0.0f,
+ .zeroPoint = 0,
+ .lifetime = OperandLifeTime::TEMPORARY_VARIABLE,
+ .location = {.poolIndex = 0, .offset = 0, .length = 0},
+ },
+ };
+
+ const std::vector<Operation> operations = {{
+ .type = OperationType::ADD, .inputs = {0, 1, 2}, .outputs = {3},
+ }};
+
+ std::vector<uint8_t> operandValues;
+ int32_t activation[1] = {static_cast<int32_t>(FusedActivationFunc::NONE)};
+ operandValues.insert(operandValues.end(), reinterpret_cast<const uint8_t*>(&activation[0]),
+ reinterpret_cast<const uint8_t*>(&activation[1]));
+
+ if (kQuantized) {
+ for (auto& operand : operands) {
+ if (operand.type == OperandType::TENSOR_FLOAT32) {
+ operand.type = OperandType::TENSOR_QUANT8_ASYMM;
+ operand.scale = 1.0f;
+ operand.zeroPoint = 0;
+ }
+ }
+ }
+
+ auto patchLifetime = [&operands](const std::vector<uint32_t>& operandIndexes,
+ OperandLifeTime lifetime) {
+ for (uint32_t index : operandIndexes) {
+ operands[index].lifetime = lifetime;
+ }
+ };
+ if (kInputHasPrecedence) {
+ patchLifetime(outputs, OperandLifeTime::MODEL_OUTPUT);
+ patchLifetime(inputs, OperandLifeTime::MODEL_INPUT);
+ } else {
+ patchLifetime(inputs, OperandLifeTime::MODEL_INPUT);
+ patchLifetime(outputs, OperandLifeTime::MODEL_OUTPUT);
+ }
+
+ return {
+ .operands = operands,
+ .operations = operations,
+ .inputIndexes = inputs,
+ .outputIndexes = outputs,
+ .operandValues = operandValues,
+ .pools = {},
+ };
+ }
+ void check(const std::string& name,
+ bool expectation, // true = success
+ const std::vector<uint32_t>& inputs, const std::vector<uint32_t>& outputs) {
+ SCOPED_TRACE(name + " (HAL calls should " + (expectation ? "succeed" : "fail") + ", " +
+ (kInputHasPrecedence ? "input" : "output") + " precedence, " +
+ (kQuantized ? "quantized" : "float"));
+
+ V1_1::Model model = createModel(inputs, outputs);
+
+ // ensure that getSupportedOperations_1_1() checks model validity
+ ErrorStatus supportedOpsErrorStatus = ErrorStatus::GENERAL_FAILURE;
+ Return<void> supportedOpsReturn = device->getSupportedOperations_1_1(
+ model, [&model, &supportedOpsErrorStatus](ErrorStatus status,
+ const hidl_vec<bool>& supported) {
+ supportedOpsErrorStatus = status;
+ if (status == ErrorStatus::NONE) {
+ ASSERT_EQ(supported.size(), model.operations.size());
+ }
+ });
+ ASSERT_TRUE(supportedOpsReturn.isOk());
+ ASSERT_EQ(supportedOpsErrorStatus,
+ (expectation ? ErrorStatus::NONE : ErrorStatus::INVALID_ARGUMENT));
+
+ // ensure that prepareModel_1_1() checks model validity
+ sp<PreparedModelCallback> preparedModelCallback = new PreparedModelCallback;
+ ASSERT_NE(preparedModelCallback.get(), nullptr);
+ Return<ErrorStatus> prepareLaunchReturn =
+ device->prepareModel_1_1(model, preparedModelCallback);
+ ASSERT_TRUE(prepareLaunchReturn.isOk());
+ ASSERT_TRUE(prepareLaunchReturn == ErrorStatus::NONE ||
+ prepareLaunchReturn == ErrorStatus::INVALID_ARGUMENT);
+ bool preparationOk = (prepareLaunchReturn == ErrorStatus::NONE);
+ if (preparationOk) {
+ preparedModelCallback->wait();
+ preparationOk = (preparedModelCallback->getStatus() == ErrorStatus::NONE);
+ }
+
+ if (preparationOk) {
+ ASSERT_TRUE(expectation);
+ } else {
+ // Preparation can fail for reasons other than an invalid model --
+ // for example, perhaps not all operations are supported, or perhaps
+ // the device hit some kind of capacity limit.
+ bool invalid = prepareLaunchReturn == ErrorStatus::INVALID_ARGUMENT ||
+ preparedModelCallback->getStatus() == ErrorStatus::INVALID_ARGUMENT;
+ ASSERT_NE(expectation, invalid);
+ }
+ }
+
+ // Indicates whether an operand that appears in both the inputs
+ // and outputs vector should have lifetime appropriate for input
+ // rather than for output.
+ const bool kInputHasPrecedence = std::get<0>(GetParam());
+
+ // Indicates whether we should test TENSOR_QUANT8_ASYMM rather
+ // than TENSOR_FLOAT32.
+ const bool kQuantized = std::get<1>(GetParam());
+};
+
+TEST_P(NeuralnetworksInputsOutputsTest, Validate) {
+ check("Ok", true, {0, 1}, {3});
+ check("InputIsOutput", false, {0, 1}, {3, 0});
+ check("OutputIsInput", false, {0, 1, 3}, {3});
+ check("DuplicateInputs", false, {0, 1, 0}, {3});
+ check("DuplicateOutputs", false, {0, 1}, {3, 3});
+}
+
+INSTANTIATE_TEST_CASE_P(Flavor, NeuralnetworksInputsOutputsTest,
+ ::testing::Combine(::testing::Bool(), ::testing::Bool()));
+
} // namespace functional
} // namespace vts
} // namespace V1_1
diff --git a/wifi/1.2/default/tests/wifi_chip_unit_tests.cpp b/wifi/1.2/default/tests/wifi_chip_unit_tests.cpp
index 27c8d60..3928c9a 100644
--- a/wifi/1.2/default/tests/wifi_chip_unit_tests.cpp
+++ b/wifi/1.2/default/tests/wifi_chip_unit_tests.cpp
@@ -146,7 +146,7 @@
} else if (type == IfaceType::STA) {
chip_->createStaIface(
[&iface_name](const WifiStatus& status,
- const sp<IWifiStaIface>& iface) {
+ const sp<V1_0::IWifiStaIface>& iface) {
if (WifiStatusCode::SUCCESS == status.code) {
ASSERT_NE(iface.get(), nullptr);
iface->getName([&iface_name](const WifiStatus& status,
diff --git a/wifi/1.2/default/wifi_legacy_hal.cpp b/wifi/1.2/default/wifi_legacy_hal.cpp
index 84af9c4..c314e64 100644
--- a/wifi/1.2/default/wifi_legacy_hal.cpp
+++ b/wifi/1.2/default/wifi_legacy_hal.cpp
@@ -492,6 +492,28 @@
getIfaceHandle(iface_name), program.data(), program.size());
}
+std::pair<wifi_error, std::vector<uint8_t>>
+WifiLegacyHal::readApfPacketFilterData(const std::string& iface_name) {
+ if (global_func_table_.wifi_read_packet_filter == nullptr) {
+ return {WIFI_ERROR_NOT_SUPPORTED, {}};
+ }
+
+ PacketFilterCapabilities caps;
+ wifi_error status = global_func_table_.wifi_get_packet_filter_capabilities(
+ getIfaceHandle(iface_name), &caps.version, &caps.max_len);
+ if (status != WIFI_SUCCESS) {
+ return {status, {}};
+ }
+
+ // Size the buffer to read the entire program & work memory.
+ std::vector<uint8_t> buffer(caps.max_len);
+
+ status = global_func_table_.wifi_read_packet_filter(
+ getIfaceHandle(iface_name), /*src_offset=*/0, buffer.data(),
+ buffer.size());
+ return {status, move(buffer)};
+}
+
std::pair<wifi_error, wifi_gscan_capabilities>
WifiLegacyHal::getGscanCapabilities(const std::string& iface_name) {
wifi_gscan_capabilities caps;
diff --git a/wifi/1.2/default/wifi_legacy_hal.h b/wifi/1.2/default/wifi_legacy_hal.h
index dedbbf8..60905ab 100644
--- a/wifi/1.2/default/wifi_legacy_hal.h
+++ b/wifi/1.2/default/wifi_legacy_hal.h
@@ -156,7 +156,7 @@
* Class that encapsulates all legacy HAL interactions.
* This class manages the lifetime of the event loop thread used by legacy HAL.
*
- * Note: aThere will only be a single instance of this class created in the Wifi
+ * Note: There will only be a single instance of this class created in the Wifi
* object and will be valid for the lifetime of the process.
*/
class WifiLegacyHal {
@@ -188,6 +188,8 @@
const std::string& iface_name);
wifi_error setPacketFilter(const std::string& iface_name,
const std::vector<uint8_t>& program);
+ std::pair<wifi_error, std::vector<uint8_t>> readApfPacketFilterData(
+ const std::string& iface_name);
// Gscan functions.
std::pair<wifi_error, wifi_gscan_capabilities> getGscanCapabilities(
const std::string& iface_name);
diff --git a/wifi/1.2/default/wifi_sta_iface.cpp b/wifi/1.2/default/wifi_sta_iface.cpp
index 6faf009..ab99daa 100644
--- a/wifi/1.2/default/wifi_sta_iface.cpp
+++ b/wifi/1.2/default/wifi_sta_iface.cpp
@@ -94,6 +94,13 @@
hidl_status_cb, cmd_id, program);
}
+Return<void> WifiStaIface::readApfPacketFilterData(
+ readApfPacketFilterData_cb hidl_status_cb) {
+ return validateAndCall(this, WifiStatusCode::ERROR_WIFI_IFACE_INVALID,
+ &WifiStaIface::readApfPacketFilterDataInternal,
+ hidl_status_cb);
+}
+
Return<void> WifiStaIface::getBackgroundScanCapabilities(
getBackgroundScanCapabilities_cb hidl_status_cb) {
return validateAndCall(this, WifiStatusCode::ERROR_WIFI_IFACE_INVALID,
@@ -297,6 +304,15 @@
return createWifiStatusFromLegacyError(legacy_status);
}
+std::pair<WifiStatus, std::vector<uint8_t>>
+WifiStaIface::readApfPacketFilterDataInternal() {
+ const std::pair<legacy_hal::wifi_error, std::vector<uint8_t>>
+ legacy_status_and_data =
+ legacy_hal_.lock()->readApfPacketFilterData(ifname_);
+ return {createWifiStatusFromLegacyError(legacy_status_and_data.first),
+ std::move(legacy_status_and_data.second)};
+}
+
std::pair<WifiStatus, StaBackgroundScanCapabilities>
WifiStaIface::getBackgroundScanCapabilitiesInternal() {
legacy_hal::wifi_error legacy_status;
diff --git a/wifi/1.2/default/wifi_sta_iface.h b/wifi/1.2/default/wifi_sta_iface.h
index 423365c..a212888 100644
--- a/wifi/1.2/default/wifi_sta_iface.h
+++ b/wifi/1.2/default/wifi_sta_iface.h
@@ -18,8 +18,8 @@
#define WIFI_STA_IFACE_H_
#include <android-base/macros.h>
-#include <android/hardware/wifi/1.0/IWifiStaIface.h>
#include <android/hardware/wifi/1.0/IWifiStaIfaceEventCallback.h>
+#include <android/hardware/wifi/1.2/IWifiStaIface.h>
#include "hidl_callback_util.h"
#include "wifi_legacy_hal.h"
@@ -34,7 +34,7 @@
/**
* HIDL interface object used to control a STA Iface instance.
*/
-class WifiStaIface : public V1_0::IWifiStaIface {
+class WifiStaIface : public V1_2::IWifiStaIface {
public:
WifiStaIface(const std::string& ifname,
const std::weak_ptr<legacy_hal::WifiLegacyHal> legacy_hal);
@@ -56,6 +56,8 @@
Return<void> installApfPacketFilter(
uint32_t cmd_id, const hidl_vec<uint8_t>& program,
installApfPacketFilter_cb hidl_status_cb) override;
+ Return<void> readApfPacketFilterData(
+ readApfPacketFilterData_cb hidl_status_cb) override;
Return<void> getBackgroundScanCapabilities(
getBackgroundScanCapabilities_cb hidl_status_cb) override;
Return<void> getValidFrequenciesForBand(
@@ -113,6 +115,8 @@
getApfPacketFilterCapabilitiesInternal();
WifiStatus installApfPacketFilterInternal(
uint32_t cmd_id, const std::vector<uint8_t>& program);
+ std::pair<WifiStatus, std::vector<uint8_t>>
+ readApfPacketFilterDataInternal();
std::pair<WifiStatus, StaBackgroundScanCapabilities>
getBackgroundScanCapabilitiesInternal();
std::pair<WifiStatus, std::vector<WifiChannelInMhz>>