Merge "Added HAL docs for unsupported LOCATION_CHARACTERIZATION behaviour." into udc-dev
diff --git a/audio/aidl/default/include/core-impl/StreamUsb.h b/audio/aidl/default/include/core-impl/StreamUsb.h
index f1815dd..36e64cb 100644
--- a/audio/aidl/default/include/core-impl/StreamUsb.h
+++ b/audio/aidl/default/include/core-impl/StreamUsb.h
@@ -56,7 +56,7 @@
std::vector<::aidl::android::media::audio::common::AudioDeviceAddress> mConnectedDevices
GUARDED_BY(mLock);
std::vector<std::shared_ptr<alsa_device_proxy>> mAlsaDeviceProxies GUARDED_BY(mLock);
- bool mIsStandby = false;
+ bool mIsStandby = true;
};
class StreamInUsb final : public StreamIn {
diff --git a/audio/aidl/default/usb/ModuleUsb.cpp b/audio/aidl/default/usb/ModuleUsb.cpp
index 80b0a5b..89895bf 100644
--- a/audio/aidl/default/usb/ModuleUsb.cpp
+++ b/audio/aidl/default/usb/ModuleUsb.cpp
@@ -120,7 +120,11 @@
const bool isInput = isUsbInputDeviceType(devicePort.device.type.type);
alsa_device_profile profile;
profile_init(&profile, isInput ? PCM_IN : PCM_OUT);
+ profile.card = alsaAddress[0];
+ profile.device = alsaAddress[1];
if (!profile_read_device_info(&profile)) {
+ LOG(ERROR) << __func__ << ": failed to read device info, card=" << profile.card
+ << ", device=" << profile.device;
return ndk::ScopedAStatus::fromExceptionCode(EX_ILLEGAL_STATE);
}
diff --git a/audio/aidl/default/usb/StreamUsb.cpp b/audio/aidl/default/usb/StreamUsb.cpp
index fbfe0f1..5d1d7fe 100644
--- a/audio/aidl/default/usb/StreamUsb.cpp
+++ b/audio/aidl/default/usb/StreamUsb.cpp
@@ -107,10 +107,13 @@
::android::status_t DriverUsb::transfer(void* buffer, size_t frameCount, size_t* actualFrameCount,
int32_t* latencyMs) {
if (!mConfig.has_value() || mConnectedDevices.empty()) {
+ LOG(ERROR) << __func__ << ": failed, has config: " << mConfig.has_value()
+ << ", has connected devices: " << mConnectedDevices.empty();
return ::android::NO_INIT;
}
if (mIsStandby) {
if (::android::status_t status = exitStandby(); status != ::android::OK) {
+ LOG(ERROR) << __func__ << ": failed to exit standby, status=" << status;
return status;
}
}
@@ -151,6 +154,7 @@
std::vector<std::shared_ptr<alsa_device_proxy>> alsaDeviceProxies;
for (const auto& device : connectedDevices) {
alsa_device_profile profile;
+ profile_init(&profile, mIsInput ? PCM_IN : PCM_OUT);
profile.card = device.get<AudioDeviceAddress::alsa>()[0];
profile.device = device.get<AudioDeviceAddress::alsa>()[1];
if (!profile_read_device_info(&profile)) {
@@ -174,6 +178,11 @@
<< " error=" << err;
return ::android::UNKNOWN_ERROR;
}
+ if (int err = proxy_open(proxy.get()); err != 0) {
+ LOG(ERROR) << __func__ << ": failed to open device, address=" << device.toString()
+ << " error=" << err;
+ return ::android::UNKNOWN_ERROR;
+ }
alsaDeviceProxies.push_back(std::move(proxy));
}
{
diff --git a/audio/aidl/default/usb/UsbAlsaUtils.cpp b/audio/aidl/default/usb/UsbAlsaUtils.cpp
index 3a74c2a..74d9c28 100644
--- a/audio/aidl/default/usb/UsbAlsaUtils.cpp
+++ b/audio/aidl/default/usb/UsbAlsaUtils.cpp
@@ -114,8 +114,8 @@
static const AudioFormatDescToPcmFormatMap formatDescToPcmFormatMap = {
{make_AudioFormatDescription(PcmType::UINT_8_BIT), PCM_FORMAT_S8},
{make_AudioFormatDescription(PcmType::INT_16_BIT), PCM_FORMAT_S16_LE},
- {make_AudioFormatDescription(PcmType::INT_24_BIT), PCM_FORMAT_S24_LE},
- {make_AudioFormatDescription(PcmType::FIXED_Q_8_24), PCM_FORMAT_S24_3LE},
+ {make_AudioFormatDescription(PcmType::FIXED_Q_8_24), PCM_FORMAT_S24_LE},
+ {make_AudioFormatDescription(PcmType::INT_24_BIT), PCM_FORMAT_S24_3LE},
{make_AudioFormatDescription(PcmType::INT_32_BIT), PCM_FORMAT_S32_LE},
{make_AudioFormatDescription(PcmType::FLOAT_32_BIT), PCM_FORMAT_FLOAT_LE},
};
diff --git a/audio/aidl/sounddose/vts/VtsHalSoundDoseFactoryTargetTest.cpp b/audio/aidl/sounddose/vts/VtsHalSoundDoseFactoryTargetTest.cpp
index df35bae..7722ccf 100644
--- a/audio/aidl/sounddose/vts/VtsHalSoundDoseFactoryTargetTest.cpp
+++ b/audio/aidl/sounddose/vts/VtsHalSoundDoseFactoryTargetTest.cpp
@@ -71,6 +71,7 @@
std::shared_ptr<ISoundDoseFactory> soundDoseFactory;
};
+// @VsrTest = VSR-5.5-002.001
TEST_P(SoundDoseFactory, GetSoundDoseForSameModule) {
const std::string module = "primary";
diff --git a/audio/aidl/vts/VtsHalAudioCoreModuleTargetTest.cpp b/audio/aidl/vts/VtsHalAudioCoreModuleTargetTest.cpp
index e790d4f..b720305 100644
--- a/audio/aidl/vts/VtsHalAudioCoreModuleTargetTest.cpp
+++ b/audio/aidl/vts/VtsHalAudioCoreModuleTargetTest.cpp
@@ -3532,6 +3532,7 @@
return ndk::ScopedAStatus::ok();
}
+// @VsrTest = VSR-5.5-002.001
TEST_P(AudioCoreSoundDose, SameInstance) {
if (soundDose == nullptr) {
GTEST_SKIP() << "SoundDose is not supported";
@@ -3543,6 +3544,7 @@
<< "getSoundDose must return the same interface instance across invocations";
}
+// @VsrTest = VSR-5.5-002.001
TEST_P(AudioCoreSoundDose, GetSetOutputRs2UpperBound) {
if (soundDose == nullptr) {
GTEST_SKIP() << "SoundDose is not supported";
@@ -3557,6 +3559,7 @@
EXPECT_TRUE(isSupported) << "Getting/Setting RS2 upper bound must be supported";
}
+// @VsrTest = VSR-5.5-002.001
TEST_P(AudioCoreSoundDose, CheckDefaultRs2UpperBound) {
if (soundDose == nullptr) {
GTEST_SKIP() << "SoundDose is not supported";
@@ -3567,6 +3570,7 @@
EXPECT_EQ(rs2Value, ISoundDose::DEFAULT_MAX_RS2);
}
+// @VsrTest = VSR-5.5-002.001
TEST_P(AudioCoreSoundDose, RegisterSoundDoseCallbackTwiceThrowsException) {
if (soundDose == nullptr) {
GTEST_SKIP() << "SoundDose is not supported";
@@ -3577,6 +3581,7 @@
<< "Registering sound dose callback twice should throw EX_ILLEGAL_STATE";
}
+// @VsrTest = VSR-5.5-002.001
TEST_P(AudioCoreSoundDose, RegisterSoundDoseNullCallbackThrowsException) {
if (soundDose == nullptr) {
GTEST_SKIP() << "SoundDose is not supported";
diff --git a/automotive/audiocontrol/aidl/default/audiocontrol-default.xml b/automotive/audiocontrol/aidl/default/audiocontrol-default.xml
index 3536bb9..95cd7f0 100644
--- a/automotive/audiocontrol/aidl/default/audiocontrol-default.xml
+++ b/automotive/audiocontrol/aidl/default/audiocontrol-default.xml
@@ -1,7 +1,7 @@
<manifest version="2.0" type="device">
<hal format="aidl">
<name>android.hardware.automotive.audiocontrol</name>
- <version>2</version>
+ <version>3</version>
<fqname>IAudioControl/default</fqname>
</hal>
</manifest>
diff --git a/automotive/remoteaccess/aidl_api/android.hardware.automotive.remoteaccess/current/android/hardware/automotive/remoteaccess/IRemoteAccess.aidl b/automotive/remoteaccess/aidl_api/android.hardware.automotive.remoteaccess/current/android/hardware/automotive/remoteaccess/IRemoteAccess.aidl
index 9b6eb2f..b0935c2 100644
--- a/automotive/remoteaccess/aidl_api/android.hardware.automotive.remoteaccess/current/android/hardware/automotive/remoteaccess/IRemoteAccess.aidl
+++ b/automotive/remoteaccess/aidl_api/android.hardware.automotive.remoteaccess/current/android/hardware/automotive/remoteaccess/IRemoteAccess.aidl
@@ -34,8 +34,9 @@
package android.hardware.automotive.remoteaccess;
@VintfStability
interface IRemoteAccess {
- String getDeviceId();
+ String getVehicleId();
String getWakeupServiceName();
+ String getProcessorId();
void setRemoteTaskCallback(android.hardware.automotive.remoteaccess.IRemoteTaskCallback callback);
void clearRemoteTaskCallback();
void notifyApStateChange(in android.hardware.automotive.remoteaccess.ApState state);
diff --git a/automotive/remoteaccess/android/hardware/automotive/remoteaccess/IRemoteAccess.aidl b/automotive/remoteaccess/android/hardware/automotive/remoteaccess/IRemoteAccess.aidl
index a198b03..0f4125f 100644
--- a/automotive/remoteaccess/android/hardware/automotive/remoteaccess/IRemoteAccess.aidl
+++ b/automotive/remoteaccess/android/hardware/automotive/remoteaccess/IRemoteAccess.aidl
@@ -28,19 +28,19 @@
@VintfStability
interface IRemoteAccess {
/**
- * Gets a unique device ID that could be recognized by wake up server.
+ * Gets a unique vehicle ID that could be recognized by wake up server.
*
- * This device ID is provisioned during car production and is registered
+ * <p>This vehicle ID is provisioned during car production and is registered
* with the wake up server.
*
- * @return a unique device ID.
+ * @return a unique vehicle ID.
*/
- String getDeviceId();
+ String getVehicleId();
/**
* Gets the name for the remote wakeup server.
*
- * This name will be provided to remote task server during registration
+ * <p>This name will be provided to remote task server during registration
* and used by remote task server to find the remote wakeup server to
* use for waking up the device. This name must be pre-negotiated between
* the remote wakeup server/client and the remote task server/client and
@@ -51,6 +51,17 @@
String getWakeupServiceName();
/**
+ * Gets a unique processor ID that could be recognized by wake up client.
+ *
+ * <p>This processor ID is used to identify each processor in the vehicle.
+ * The wake up client which handles many processors determines which
+ * processor to wake up from the processor ID.
+ *
+ * <p> The processor ID must be unique in the vehicle.
+ */
+ String getProcessorId();
+
+ /**
* Sets a callback to be called when a remote task is requested.
*
* @param callback A callback to be called when a remote task is requested.
diff --git a/automotive/remoteaccess/hal/default/include/RemoteAccessService.h b/automotive/remoteaccess/hal/default/include/RemoteAccessService.h
index 74c2af4..5cfca61 100644
--- a/automotive/remoteaccess/hal/default/include/RemoteAccessService.h
+++ b/automotive/remoteaccess/hal/default/include/RemoteAccessService.h
@@ -62,7 +62,9 @@
~RemoteAccessService();
- ndk::ScopedAStatus getDeviceId(std::string* deviceId) override;
+ ndk::ScopedAStatus getVehicleId(std::string* vehicleId) override;
+
+ ndk::ScopedAStatus getProcessorId(std::string* processorId) override;
ndk::ScopedAStatus getWakeupServiceName(std::string* wakeupServiceName) override;
@@ -103,8 +105,8 @@
void runTaskLoop();
void maybeStartTaskLoop();
void maybeStopTaskLoop();
- ndk::ScopedAStatus getDeviceIdWithClient(
- android::frameworks::automotive::vhal::IVhalClient& client, std::string* deviceId);
+ ndk::ScopedAStatus getVehicleIdWithClient(
+ android::frameworks::automotive::vhal::IVhalClient& client, std::string* vehicleId);
void setRetryWaitInMs(size_t retryWaitInMs) { mRetryWaitInMs = retryWaitInMs; }
void dumpHelp(int fd);
diff --git a/automotive/remoteaccess/hal/default/src/RemoteAccessService.cpp b/automotive/remoteaccess/hal/default/src/RemoteAccessService.cpp
index 4be30a2..d944593 100644
--- a/automotive/remoteaccess/hal/default/src/RemoteAccessService.cpp
+++ b/automotive/remoteaccess/hal/default/src/RemoteAccessService.cpp
@@ -48,11 +48,12 @@
using ::ndk::ScopedAStatus;
const std::string WAKEUP_SERVICE_NAME = "com.google.vehicle.wakeup";
+const std::string PROCESSOR_ID = "application_processor";
constexpr char COMMAND_SET_AP_STATE[] = "--set-ap-state";
constexpr char COMMAND_START_DEBUG_CALLBACK[] = "--start-debug-callback";
constexpr char COMMAND_STOP_DEBUG_CALLBACK[] = "--stop-debug-callback";
constexpr char COMMAND_SHOW_TASK[] = "--show-task";
-constexpr char COMMAND_GET_DEVICE_ID[] = "--get-device-id";
+constexpr char COMMAND_GET_VEHICLE_ID[] = "--get-vehicle-id";
std::vector<uint8_t> stringToBytes(const std::string& s) {
const char* data = s.data();
@@ -176,23 +177,23 @@
}
}
-ScopedAStatus RemoteAccessService::getDeviceId(std::string* deviceId) {
+ScopedAStatus RemoteAccessService::getVehicleId(std::string* vehicleId) {
#ifndef FUZZING_BUILD_MODE_UNSAFE_FOR_PRODUCTION
auto vhalClient = IVhalClient::tryCreate();
if (vhalClient == nullptr) {
ALOGE("Failed to connect to VHAL");
return ScopedAStatus::fromServiceSpecificErrorWithMessage(
- /*errorCode=*/0, "Failed to connect to VHAL to get device ID");
+ /*errorCode=*/0, "Failed to connect to VHAL to get vehicle ID");
}
- return getDeviceIdWithClient(*vhalClient.get(), deviceId);
+ return getVehicleIdWithClient(*vhalClient.get(), vehicleId);
#else
// Don't use VHAL client in fuzzing since IPC is not allowed.
return ScopedAStatus::ok();
#endif
}
-ScopedAStatus RemoteAccessService::getDeviceIdWithClient(IVhalClient& vhalClient,
- std::string* deviceId) {
+ScopedAStatus RemoteAccessService::getVehicleIdWithClient(IVhalClient& vhalClient,
+ std::string* vehicleId) {
auto result = vhalClient.getValueSync(
*vhalClient.createHalPropValue(toInt(VehicleProperty::INFO_VIN)));
if (!result.ok()) {
@@ -200,7 +201,12 @@
/*errorCode=*/0,
("failed to get INFO_VIN from VHAL: " + result.error().message()).c_str());
}
- *deviceId = (*result)->getStringValue();
+ *vehicleId = (*result)->getStringValue();
+ return ScopedAStatus::ok();
+}
+
+ScopedAStatus RemoteAccessService::getProcessorId(std::string* processorId) {
+ *processorId = PROCESSOR_ID;
return ScopedAStatus::ok();
}
@@ -252,8 +258,8 @@
COMMAND_START_DEBUG_CALLBACK +
" Start a debug callback that will record the received tasks\n" +
COMMAND_STOP_DEBUG_CALLBACK + " Stop the debug callback\n" + COMMAND_SHOW_TASK +
- " Show tasks received by debug callback\n" + COMMAND_GET_DEVICE_ID +
- " Get device id\n")
+ " Show tasks received by debug callback\n" + COMMAND_GET_VEHICLE_ID +
+ " Get vehicle id\n")
.c_str());
}
@@ -316,13 +322,13 @@
dprintf(fd, "Debug callback is not currently used, use \"%s\" first.\n",
COMMAND_START_DEBUG_CALLBACK);
}
- } else if (!strcmp(args[0], COMMAND_GET_DEVICE_ID)) {
- std::string deviceId;
- auto status = getDeviceId(&deviceId);
+ } else if (!strcmp(args[0], COMMAND_GET_VEHICLE_ID)) {
+ std::string vehicleId;
+ auto status = getVehicleId(&vehicleId);
if (!status.isOk()) {
- dprintErrorStatus(fd, "Failed to get device ID", status);
+ dprintErrorStatus(fd, "Failed to get vehicle ID", status);
} else {
- dprintf(fd, "Device Id: %s\n", deviceId.c_str());
+ dprintf(fd, "Vehicle Id: %s\n", vehicleId.c_str());
}
} else {
dumpHelp(fd);
diff --git a/automotive/remoteaccess/hal/default/test/RemoteAccessServiceUnitTest.cpp b/automotive/remoteaccess/hal/default/test/RemoteAccessServiceUnitTest.cpp
index 8c4fa08..c5afd63 100644
--- a/automotive/remoteaccess/hal/default/test/RemoteAccessServiceUnitTest.cpp
+++ b/automotive/remoteaccess/hal/default/test/RemoteAccessServiceUnitTest.cpp
@@ -187,8 +187,8 @@
void setRetryWaitInMs(size_t retryWaitInMs) { mService->setRetryWaitInMs(retryWaitInMs); }
- ScopedAStatus getDeviceIdWithClient(IVhalClient& vhalClient, std::string* deviceId) {
- return mService->getDeviceIdWithClient(vhalClient, deviceId);
+ ScopedAStatus getVehicleIdWithClient(IVhalClient& vhalClient, std::string* vehicleId) {
+ return mService->getVehicleIdWithClient(vhalClient, vehicleId);
}
private:
@@ -358,13 +358,13 @@
std::this_thread::sleep_for(std::chrono::milliseconds(150));
}
-TEST_F(RemoteAccessServiceUnitTest, testGetDeviceId) {
- std::string deviceId;
+TEST_F(RemoteAccessServiceUnitTest, testGetVehicleId) {
+ std::string vehicleId;
FakeVhalClient vhalClient;
- ASSERT_TRUE(getDeviceIdWithClient(vhalClient, &deviceId).isOk());
- ASSERT_EQ(deviceId, kTestVin);
+ ASSERT_TRUE(getVehicleIdWithClient(vhalClient, &vehicleId).isOk());
+ ASSERT_EQ(vehicleId, kTestVin);
}
} // namespace remoteaccess
diff --git a/automotive/vehicle/2.0/default/impl/vhal_v2_0/tests/DefaultVhalImpl_test.cpp b/automotive/vehicle/2.0/default/impl/vhal_v2_0/tests/DefaultVhalImpl_test.cpp
index b5026a6..edd4484 100644
--- a/automotive/vehicle/2.0/default/impl/vhal_v2_0/tests/DefaultVhalImpl_test.cpp
+++ b/automotive/vehicle/2.0/default/impl/vhal_v2_0/tests/DefaultVhalImpl_test.cpp
@@ -756,8 +756,9 @@
// Clear existing events.
mEventQueue.flush();
std::this_thread::sleep_for(std::chrono::milliseconds(500));
- // There should be no new events generated.
- EXPECT_EQ((size_t)0, mEventQueue.flush().size());
+ // Technically there should be no new events generated, however, there might still be one event
+ // in the queue while we are stopping the generator.
+ EXPECT_LE(mEventQueue.flush().size(), 1u);
}
std::string getTestFilePath(const char* filename) {
diff --git a/automotive/vehicle/aidl/impl/default_config/config/DefaultProperties.json b/automotive/vehicle/aidl/impl/default_config/config/DefaultProperties.json
index 28790e2..ae36290 100644
--- a/automotive/vehicle/aidl/impl/default_config/config/DefaultProperties.json
+++ b/automotive/vehicle/aidl/impl/default_config/config/DefaultProperties.json
@@ -2371,7 +2371,7 @@
66.19999694824219,
"VehicleUnit::FAHRENHEIT",
19.0,
- 66.5
+ 66.0
]
}
},
diff --git a/automotive/vehicle/aidl/impl/fake_impl/hardware/include/FakeVehicleHardware.h b/automotive/vehicle/aidl/impl/fake_impl/hardware/include/FakeVehicleHardware.h
index 6fd2367..7b74092 100644
--- a/automotive/vehicle/aidl/impl/fake_impl/hardware/include/FakeVehicleHardware.h
+++ b/automotive/vehicle/aidl/impl/fake_impl/hardware/include/FakeVehicleHardware.h
@@ -178,6 +178,13 @@
void eventFromVehicleBus(
const aidl::android::hardware::automotive::vehicle::VehiclePropValue& value);
+ int getHvacTempNumIncrements(int requestedTemp, int minTemp, int maxTemp, int increment);
+ void updateHvacTemperatureValueSuggestionInput(
+ const std::vector<int>& hvacTemperatureSetConfigArray,
+ std::vector<float>* hvacTemperatureValueSuggestionInput);
+ VhalResult<void> setHvacTemperatureValueSuggestion(
+ const aidl::android::hardware::automotive::vehicle::VehiclePropValue&
+ hvacTemperatureValueSuggestion);
VhalResult<void> maybeSetSpecialValue(
const aidl::android::hardware::automotive::vehicle::VehiclePropValue& value,
bool* isSpecialValue);
diff --git a/automotive/vehicle/aidl/impl/fake_impl/hardware/src/FakeVehicleHardware.cpp b/automotive/vehicle/aidl/impl/fake_impl/hardware/src/FakeVehicleHardware.cpp
index 78c21e9..4544389 100644
--- a/automotive/vehicle/aidl/impl/fake_impl/hardware/src/FakeVehicleHardware.cpp
+++ b/automotive/vehicle/aidl/impl/fake_impl/hardware/src/FakeVehicleHardware.cpp
@@ -67,6 +67,7 @@
using ::aidl::android::hardware::automotive::vehicle::VehiclePropertyStatus;
using ::aidl::android::hardware::automotive::vehicle::VehiclePropertyType;
using ::aidl::android::hardware::automotive::vehicle::VehiclePropValue;
+using ::aidl::android::hardware::automotive::vehicle::VehicleUnit;
using ::android::base::EqualsIgnoreCase;
using ::android::base::Error;
@@ -298,6 +299,94 @@
return {};
}
+int FakeVehicleHardware::getHvacTempNumIncrements(int requestedTemp, int minTemp, int maxTemp,
+ int increment) {
+ requestedTemp = std::max(requestedTemp, minTemp);
+ requestedTemp = std::min(requestedTemp, maxTemp);
+ int numIncrements = (requestedTemp - minTemp) / increment;
+ return numIncrements;
+}
+
+void FakeVehicleHardware::updateHvacTemperatureValueSuggestionInput(
+ const std::vector<int>& hvacTemperatureSetConfigArray,
+ std::vector<float>* hvacTemperatureValueSuggestionInput) {
+ int minTempInCelsius = hvacTemperatureSetConfigArray[0];
+ int maxTempInCelsius = hvacTemperatureSetConfigArray[1];
+ int incrementInCelsius = hvacTemperatureSetConfigArray[2];
+
+ int minTempInFahrenheit = hvacTemperatureSetConfigArray[3];
+ int maxTempInFahrenheit = hvacTemperatureSetConfigArray[4];
+ int incrementInFahrenheit = hvacTemperatureSetConfigArray[5];
+
+ // The HVAC_TEMPERATURE_SET config array values are temperature values that have been multiplied
+ // by 10 and converted to integers. Therefore, requestedTemp must also be multiplied by 10 and
+ // converted to an integer in order for them to be the same units.
+ int requestedTemp = static_cast<int>((*hvacTemperatureValueSuggestionInput)[0] * 10.0f);
+ int numIncrements =
+ (*hvacTemperatureValueSuggestionInput)[1] == toInt(VehicleUnit::CELSIUS)
+ ? getHvacTempNumIncrements(requestedTemp, minTempInCelsius, maxTempInCelsius,
+ incrementInCelsius)
+ : getHvacTempNumIncrements(requestedTemp, minTempInFahrenheit,
+ maxTempInFahrenheit, incrementInFahrenheit);
+
+ int suggestedTempInCelsius = minTempInCelsius + incrementInCelsius * numIncrements;
+ int suggestedTempInFahrenheit = minTempInFahrenheit + incrementInFahrenheit * numIncrements;
+ // HVAC_TEMPERATURE_VALUE_SUGGESTION specifies the temperature values to be in the original
+ // floating point form so we divide by 10 and convert to float.
+ (*hvacTemperatureValueSuggestionInput)[2] = static_cast<float>(suggestedTempInCelsius) / 10.0f;
+ (*hvacTemperatureValueSuggestionInput)[3] =
+ static_cast<float>(suggestedTempInFahrenheit) / 10.0f;
+}
+
+VhalResult<void> FakeVehicleHardware::setHvacTemperatureValueSuggestion(
+ const VehiclePropValue& hvacTemperatureValueSuggestion) {
+ auto hvacTemperatureSetConfigResult =
+ mServerSidePropStore->getConfig(toInt(VehicleProperty::HVAC_TEMPERATURE_SET));
+
+ if (!hvacTemperatureSetConfigResult.ok()) {
+ return StatusError(getErrorCode(hvacTemperatureSetConfigResult)) << StringPrintf(
+ "Failed to set HVAC_TEMPERATURE_VALUE_SUGGESTION because"
+ " HVAC_TEMPERATURE_SET could not be retrieved. Error: %s",
+ getErrorMsg(hvacTemperatureSetConfigResult).c_str());
+ }
+
+ const auto& originalInput = hvacTemperatureValueSuggestion.value.floatValues;
+ if (originalInput.size() != 4) {
+ return StatusError(StatusCode::INVALID_ARG) << StringPrintf(
+ "Failed to set HVAC_TEMPERATURE_VALUE_SUGGESTION because float"
+ " array value is not size 4.");
+ }
+
+ bool isTemperatureUnitSpecified = originalInput[1] == toInt(VehicleUnit::CELSIUS) ||
+ originalInput[1] == toInt(VehicleUnit::FAHRENHEIT);
+ if (!isTemperatureUnitSpecified) {
+ return StatusError(StatusCode::INVALID_ARG) << StringPrintf(
+ "Failed to set HVAC_TEMPERATURE_VALUE_SUGGESTION because float"
+ " value at index 1 is not any of %d or %d, which corresponds to"
+ " VehicleUnit#CELSIUS and VehicleUnit#FAHRENHEIT respectively.",
+ toInt(VehicleUnit::CELSIUS), toInt(VehicleUnit::FAHRENHEIT));
+ }
+
+ auto updatedValue = mValuePool->obtain(hvacTemperatureValueSuggestion);
+ const auto& hvacTemperatureSetConfigArray = hvacTemperatureSetConfigResult.value()->configArray;
+ auto& hvacTemperatureValueSuggestionInput = updatedValue->value.floatValues;
+
+ updateHvacTemperatureValueSuggestionInput(hvacTemperatureSetConfigArray,
+ &hvacTemperatureValueSuggestionInput);
+
+ updatedValue->timestamp = elapsedRealtimeNano();
+ auto writeResult = mServerSidePropStore->writeValue(std::move(updatedValue),
+ /* updateStatus = */ true,
+ VehiclePropertyStore::EventMode::ALWAYS);
+ if (!writeResult.ok()) {
+ return StatusError(getErrorCode(writeResult))
+ << StringPrintf("failed to write value into property store, error: %s",
+ getErrorMsg(writeResult).c_str());
+ }
+
+ return {};
+}
+
bool FakeVehicleHardware::isHvacPropAndHvacNotAvailable(int32_t propId, int32_t areaId) const {
std::unordered_set<int32_t> powerProps(std::begin(HVAC_POWER_PROPERTIES),
std::end(HVAC_POWER_PROPERTIES));
@@ -491,6 +580,9 @@
case VENDOR_PROPERTY_ID:
*isSpecialValue = true;
return StatusError((StatusCode)VENDOR_ERROR_CODE);
+ case toInt(VehicleProperty::HVAC_TEMPERATURE_VALUE_SUGGESTION):
+ *isSpecialValue = true;
+ return setHvacTemperatureValueSuggestion(value);
#ifdef ENABLE_VEHICLE_HAL_TEST_PROPERTIES
case toInt(VehicleProperty::CLUSTER_REPORT_STATE):
diff --git a/automotive/vehicle/aidl/impl/fake_impl/hardware/test/FakeVehicleHardwareTest.cpp b/automotive/vehicle/aidl/impl/fake_impl/hardware/test/FakeVehicleHardwareTest.cpp
index 93a63ad..a50b4ad 100644
--- a/automotive/vehicle/aidl/impl/fake_impl/hardware/test/FakeVehicleHardwareTest.cpp
+++ b/automotive/vehicle/aidl/impl/fake_impl/hardware/test/FakeVehicleHardwareTest.cpp
@@ -57,6 +57,7 @@
using ::aidl::android::hardware::automotive::vehicle::VehicleProperty;
using ::aidl::android::hardware::automotive::vehicle::VehiclePropertyStatus;
using ::aidl::android::hardware::automotive::vehicle::VehiclePropValue;
+using ::aidl::android::hardware::automotive::vehicle::VehicleUnit;
using ::android::base::expected;
using ::android::base::ScopedLockAssertion;
using ::android::base::StringPrintf;
@@ -2242,6 +2243,359 @@
}
}
+TEST_F(FakeVehicleHardwareTest, testSetHvacTemperatureValueSuggestion) {
+ float CELSIUS = static_cast<float>(toInt(VehicleUnit::CELSIUS));
+ float FAHRENHEIT = static_cast<float>(toInt(VehicleUnit::FAHRENHEIT));
+
+ VehiclePropValue floatArraySizeFour = {
+ .prop = toInt(VehicleProperty::HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {0, CELSIUS, 0, 0},
+ };
+ StatusCode status = setValue(floatArraySizeFour);
+ EXPECT_EQ(status, StatusCode::OK);
+
+ VehiclePropValue floatArraySizeZero = {
+ .prop = toInt(VehicleProperty::HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ };
+ status = setValue(floatArraySizeZero);
+ EXPECT_EQ(status, StatusCode::INVALID_ARG);
+
+ VehiclePropValue floatArraySizeFive = {
+ .prop = toInt(VehicleProperty::HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {0, CELSIUS, 0, 0, 0},
+ };
+ status = setValue(floatArraySizeFive);
+ EXPECT_EQ(status, StatusCode::INVALID_ARG);
+
+ VehiclePropValue invalidUnit = {
+ .prop = toInt(VehicleProperty::HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {0, 0, 0, 0},
+ };
+ status = setValue(floatArraySizeFive);
+ EXPECT_EQ(status, StatusCode::INVALID_ARG);
+ clearChangedProperties();
+
+ // Config array values from HVAC_TEMPERATURE_SET in DefaultProperties.json
+ auto configs = getHardware()->getAllPropertyConfigs();
+ VehiclePropConfig* hvacTemperatureSetConfig = nullptr;
+ for (auto& config : configs) {
+ if (config.prop == toInt(VehicleProperty::HVAC_TEMPERATURE_SET)) {
+ hvacTemperatureSetConfig = &config;
+ break;
+ }
+ }
+ EXPECT_NE(hvacTemperatureSetConfig, nullptr);
+
+ auto& hvacTemperatureSetConfigArray = hvacTemperatureSetConfig->configArray;
+ // The HVAC_TEMPERATURE_SET config array values are temperature values that have been multiplied
+ // by 10 and converted to integers. HVAC_TEMPERATURE_VALUE_SUGGESTION specifies the temperature
+ // values to be in the original floating point form so we divide by 10 and convert to float.
+ float minTempInCelsius = hvacTemperatureSetConfigArray[0] / 10.0f;
+ float maxTempInCelsius = hvacTemperatureSetConfigArray[1] / 10.0f;
+ float incrementInCelsius = hvacTemperatureSetConfigArray[2] / 10.0f;
+ float minTempInFahrenheit = hvacTemperatureSetConfigArray[3] / 10.0f;
+ float maxTempInFahrenheit = hvacTemperatureSetConfigArray[4] / 10.0f;
+ float incrementInFahrenheit = hvacTemperatureSetConfigArray[5] / 10.0f;
+
+ auto testCases = {
+ SetSpecialValueTestCase{
+ .name = "min_celsius_temperature",
+ .valuesToSet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {minTempInCelsius, CELSIUS, 0, 0},
+ },
+ },
+ .expectedValuesToGet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {minTempInCelsius, CELSIUS,
+ minTempInCelsius,
+ minTempInFahrenheit},
+ },
+ },
+ },
+ SetSpecialValueTestCase{
+ .name = "min_fahrenheit_temperature",
+ .valuesToSet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {minTempInFahrenheit, FAHRENHEIT,
+ 0, 0},
+ },
+ },
+ .expectedValuesToGet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {minTempInFahrenheit, FAHRENHEIT,
+ minTempInCelsius,
+ minTempInFahrenheit},
+ },
+ },
+ },
+ SetSpecialValueTestCase{
+ .name = "max_celsius_temperature",
+ .valuesToSet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {maxTempInCelsius, CELSIUS, 0, 0},
+ },
+ },
+ .expectedValuesToGet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {maxTempInCelsius, CELSIUS,
+ maxTempInCelsius,
+ maxTempInFahrenheit},
+ },
+ },
+ },
+ SetSpecialValueTestCase{
+ .name = "max_fahrenheit_temperature",
+ .valuesToSet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {maxTempInFahrenheit, FAHRENHEIT,
+ 0, 0},
+ },
+ },
+ .expectedValuesToGet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {maxTempInFahrenheit, FAHRENHEIT,
+ maxTempInCelsius,
+ maxTempInFahrenheit},
+ },
+ },
+ },
+ SetSpecialValueTestCase{
+ .name = "below_min_celsius_temperature",
+ .valuesToSet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {minTempInCelsius - 1, CELSIUS, 0,
+ 0},
+ },
+ },
+ .expectedValuesToGet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {minTempInCelsius - 1, CELSIUS,
+ minTempInCelsius,
+ minTempInFahrenheit},
+ },
+ },
+ },
+ SetSpecialValueTestCase{
+ .name = "below_min_fahrenheit_temperature",
+ .valuesToSet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {minTempInFahrenheit - 1,
+ FAHRENHEIT, 0, 0},
+ },
+ },
+ .expectedValuesToGet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {minTempInFahrenheit - 1,
+ FAHRENHEIT, minTempInCelsius,
+ minTempInFahrenheit},
+ },
+ },
+ },
+ SetSpecialValueTestCase{
+ .name = "above_max_celsius_temperature",
+ .valuesToSet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {maxTempInCelsius + 1, CELSIUS, 0,
+ 0},
+ },
+ },
+ .expectedValuesToGet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {maxTempInCelsius + 1, CELSIUS,
+ maxTempInCelsius,
+ maxTempInFahrenheit},
+ },
+ },
+ },
+ SetSpecialValueTestCase{
+ .name = "above_max_fahrenheit_temperature",
+ .valuesToSet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {maxTempInFahrenheit + 1,
+ FAHRENHEIT, 0, 0},
+ },
+ },
+ .expectedValuesToGet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {maxTempInFahrenheit + 1,
+ FAHRENHEIT, maxTempInCelsius,
+ maxTempInFahrenheit},
+ },
+ },
+ },
+ SetSpecialValueTestCase{
+ .name = "inbetween_value_celsius",
+ .valuesToSet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {minTempInCelsius +
+ incrementInCelsius * 2.5f,
+ CELSIUS, 0, 0},
+ },
+ },
+ .expectedValuesToGet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues =
+ {minTempInCelsius + incrementInCelsius * 2.5f,
+ CELSIUS,
+ minTempInCelsius + incrementInCelsius * 2,
+ minTempInFahrenheit +
+ incrementInFahrenheit * 2},
+ },
+ },
+ },
+ SetSpecialValueTestCase{
+ .name = "inbetween_value_fahrenheit",
+ .valuesToSet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues = {minTempInFahrenheit +
+ incrementInFahrenheit *
+ 2.5f,
+ FAHRENHEIT, 0, 0},
+ },
+ },
+ .expectedValuesToGet =
+ {
+ VehiclePropValue{
+ .prop = toInt(
+ VehicleProperty::
+ HVAC_TEMPERATURE_VALUE_SUGGESTION),
+ .areaId = HVAC_ALL,
+ .value.floatValues =
+ {minTempInFahrenheit +
+ incrementInFahrenheit * 2.5f,
+ FAHRENHEIT,
+ minTempInCelsius + incrementInCelsius * 2,
+ minTempInFahrenheit +
+ incrementInFahrenheit * 2},
+ },
+ },
+ },
+ };
+
+ for (auto& tc : testCases) {
+ StatusCode status = setValue(tc.valuesToSet[0]);
+ EXPECT_EQ(status, StatusCode::OK);
+
+ auto events = getChangedProperties();
+ EXPECT_EQ(events.size(), static_cast<size_t>(1));
+ events[0].timestamp = 0;
+
+ EXPECT_EQ(events[0], (tc.expectedValuesToGet[0]))
+ << "Failed Test: " << tc.name << "\n"
+ << "Received - prop: " << events[0].prop << ", areaId: " << events[0].areaId
+ << ", floatValues: {" << events[0].value.floatValues[0] << ", "
+ << events[0].value.floatValues[1] << ", " << events[0].value.floatValues[2] << ", "
+ << events[0].value.floatValues[3] << "}\n"
+ << "Expected - prop: " << tc.expectedValuesToGet[0].prop
+ << ", areaId: " << tc.expectedValuesToGet[0].areaId << ", floatValues: {"
+ << tc.expectedValuesToGet[0].value.floatValues[0] << ", "
+ << tc.expectedValuesToGet[0].value.floatValues[1] << ", "
+ << tc.expectedValuesToGet[0].value.floatValues[2] << ", "
+ << tc.expectedValuesToGet[0].value.floatValues[3] << "}\n";
+ clearChangedProperties();
+ }
+}
+
} // namespace fake
} // namespace vehicle
} // namespace automotive
diff --git a/automotive/vehicle/aidl/impl/vhal/vhal-default-service.xml b/automotive/vehicle/aidl/impl/vhal/vhal-default-service.xml
index 4d587ee..9834cdb 100644
--- a/automotive/vehicle/aidl/impl/vhal/vhal-default-service.xml
+++ b/automotive/vehicle/aidl/impl/vhal/vhal-default-service.xml
@@ -1,7 +1,7 @@
<manifest version="1.0" type="device">
<hal format="aidl">
<name>android.hardware.automotive.vehicle</name>
- <version>1</version>
+ <version>2</version>
<fqname>IVehicle/default</fqname>
</hal>
</manifest>
diff --git a/automotive/vehicle/aidl_property/android/hardware/automotive/vehicle/VehicleHvacFanDirection.aidl b/automotive/vehicle/aidl_property/android/hardware/automotive/vehicle/VehicleHvacFanDirection.aidl
index fa5d711..f5b77de 100644
--- a/automotive/vehicle/aidl_property/android/hardware/automotive/vehicle/VehicleHvacFanDirection.aidl
+++ b/automotive/vehicle/aidl_property/android/hardware/automotive/vehicle/VehicleHvacFanDirection.aidl
@@ -29,6 +29,9 @@
* FACE_AND_FLOOR = FACE | FLOOR
*/
FACE_AND_FLOOR = 0x3,
+ /**
+ * DEFROST may also be described as the windshield fan direction.
+ */
DEFROST = 0x4,
/**
* DEFROST_AND_FLOOR = DEFROST | FLOOR
diff --git a/automotive/vehicle/aidl_property/android/hardware/automotive/vehicle/VehicleProperty.aidl b/automotive/vehicle/aidl_property/android/hardware/automotive/vehicle/VehicleProperty.aidl
index a778bc1..f729405 100644
--- a/automotive/vehicle/aidl_property/android/hardware/automotive/vehicle/VehicleProperty.aidl
+++ b/automotive/vehicle/aidl_property/android/hardware/automotive/vehicle/VehicleProperty.aidl
@@ -4059,7 +4059,10 @@
*
* For the global area ID (0), the VehicleAreaConfig#supportedEnumValues array must be defined
* unless all states of CruiseControlState are supported. Any unsupported commands sent through
- * this property should return StatusCode.INVALID_ARG.
+ * this property must return StatusCode#INVALID_ARG.
+ *
+ * When this property is not available because CC is disabled (i.e. CRUISE_CONTROL_ENABLED is
+ * false), this property must return StatusCode#NOT_AVAILABLE_DISABLED.
*
* @change_mode VehiclePropertyChangeMode.ON_CHANGE
* @access VehiclePropertyAccess.WRITE
@@ -4077,8 +4080,8 @@
* The maxFloatValue represents the upper bound of the target speed.
* The minFloatValue represents the lower bound of the target speed.
*
- * When this property is not available (for example when CRUISE_CONTROL_ENABLED is false), it
- * should return StatusCode.NOT_AVAILABLE_DISABLED.
+ * When this property is not available because CC is disabled (i.e. CRUISE_CONTROL_ENABLED is
+ * false), this property must return StatusCode#NOT_AVAILABLE_DISABLED.
*
* @change_mode VehiclePropertyChangeMode.ON_CHANGE
* @access VehiclePropertyAccess.READ
@@ -4100,7 +4103,8 @@
* ascending order. All values must be positive. If the property is writable, all values must be
* writable.
*
- * Writing to this property when it is not available should return StatusCode.NOT_AVAILABLE.
+ * When this property is not available because CC is disabled (i.e. CRUISE_CONTROL_ENABLED is
+ * false), this property must return StatusCode#NOT_AVAILABLE_DISABLED.
*
* @change_mode VehiclePropertyChangeMode.ON_CHANGE
* @access VehiclePropertyAccess.READ_WRITE
@@ -4124,6 +4128,9 @@
* vehicle is too far away for the sensor to detect), this property should return
* StatusCode.NOT_AVAILABLE.
*
+ * When this property is not available because CC is disabled (i.e. CRUISE_CONTROL_ENABLED is
+ * false), this property must return StatusCode#NOT_AVAILABLE_DISABLED.
+ *
* @change_mode VehiclePropertyChangeMode.CONTINUOUS
* @access VehiclePropertyAccess.READ
* @unit VehicleUnit:MILLIMETER
diff --git a/broadcastradio/aidl/android/hardware/broadcastradio/AmFmRegionConfig.aidl b/broadcastradio/aidl/android/hardware/broadcastradio/AmFmRegionConfig.aidl
index a3086c6..f4c6fd3 100644
--- a/broadcastradio/aidl/android/hardware/broadcastradio/AmFmRegionConfig.aidl
+++ b/broadcastradio/aidl/android/hardware/broadcastradio/AmFmRegionConfig.aidl
@@ -73,14 +73,15 @@
/**
* De-emphasis filter supported/configured.
*
- * It is a bitset of de-emphasis values (DEEMPHASIS_D50 and DEEMPHASIS_D75).
+ * It can be a combination of de-emphasis values ({@link #DEEMPHASIS_D50} and
+ * {@link #DEEMPHASIS_D75}).
*/
int fmDeemphasis;
/**
* RDS/RBDS variant supported/configured.
*
- * It is a bitset of RDS values (RDS and RBDS).
+ * It can be a combination of RDS values ({@link #RDS} and {@link #RBDS}).
*/
int fmRds;
}
diff --git a/broadcastradio/aidl/android/hardware/broadcastradio/ProgramInfo.aidl b/broadcastradio/aidl/android/hardware/broadcastradio/ProgramInfo.aidl
index d650239..7632c81 100644
--- a/broadcastradio/aidl/android/hardware/broadcastradio/ProgramInfo.aidl
+++ b/broadcastradio/aidl/android/hardware/broadcastradio/ProgramInfo.aidl
@@ -150,6 +150,10 @@
/**
* Program flags.
+ *
+ * It can be a combination of {@link #FLAG_LIVE}, {@link #FLAG_MUTED},
+ * {@link #FLAG_TRAFFIC_PROGRAM}, {@link #FLAG_TRAFFIC_ANNOUNCEMENT},
+ * {@link #FLAG_TUNABLE}, and {@link #FLAG_STEREO}.
*/
int infoFlags;
diff --git a/broadcastradio/aidl/android/hardware/broadcastradio/ProgramSelector.aidl b/broadcastradio/aidl/android/hardware/broadcastradio/ProgramSelector.aidl
index 93b0e12..71b824b 100644
--- a/broadcastradio/aidl/android/hardware/broadcastradio/ProgramSelector.aidl
+++ b/broadcastradio/aidl/android/hardware/broadcastradio/ProgramSelector.aidl
@@ -51,8 +51,7 @@
* - analogue AM/FM: AMFM_FREQUENCY_KHZ;
* - FM RDS: RDS_PI;
* - HD Radio: HD_STATION_ID_EXT;
- * - DAB/DMB: DAB_SID_EXT (when used, DAB_ENSEMBLE and DAB_FREQUENCY_KHZ
- * must present in secondaryIds);
+ * - DAB/DMB: DAB_SID_EXT;
* - Digital Radio Mondiale: DRMO_SERVICE_ID;
* - SiriusXM: SXM_SERVICE_ID;
* - vendor-specific: VENDOR_START..VENDOR_END.
@@ -63,13 +62,16 @@
* Secondary program identifiers.
*
* These identifiers are supplementary and can speed up tuning process,
- * but the primary ID must be sufficient (i.e. RDS PI is enough to select
+ * but the primary ID should be sufficient (i.e. RDS PI is enough to select
* a station from the list after a full band scan).
*
* Two selectors with different secondary IDs, but the same primary ID are
* considered equal. In particular, secondary IDs array may get updated for
* an entry on the program list (ie. when a better frequency for a given
* station is found).
+ *
+ * If DAB_SID_EXT is used as primaryId, using DAB_ENSEMBLE or DAB_FREQUENCY_KHZ
+ * as secondray identifiers can uniquely identify the DAB station.
*/
ProgramIdentifier[] secondaryIds;
}
diff --git a/broadcastradio/aidl/default/BroadcastRadio.cpp b/broadcastradio/aidl/default/BroadcastRadio.cpp
index 36520fb..c0c475a 100644
--- a/broadcastradio/aidl/default/BroadcastRadio.cpp
+++ b/broadcastradio/aidl/default/BroadcastRadio.cpp
@@ -589,10 +589,11 @@
}
ProgramSelector sel = {};
if (isDab) {
- if (numArgs != 5) {
+ if (numArgs != 5 && numArgs != 3) {
dprintf(fd,
"Invalid number of arguments: please provide "
- "--tune dab <SID> <ENSEMBLE> <FREQUENCY>\n");
+ "--tune dab <SID> <ENSEMBLE> <FREQUENCY> or "
+ "--tune dab <SID>\n");
return STATUS_BAD_VALUE;
}
int sid;
@@ -600,17 +601,21 @@
dprintf(fd, "Non-integer sid provided with tune: %s\n", args[2]);
return STATUS_BAD_VALUE;
}
- int ensemble;
- if (!utils::parseArgInt(string(args[3]), &ensemble)) {
- dprintf(fd, "Non-integer ensemble provided with tune: %s\n", args[3]);
- return STATUS_BAD_VALUE;
+ if (numArgs == 3) {
+ sel = utils::makeSelectorDab(sid);
+ } else {
+ int ensemble;
+ if (!utils::parseArgInt(string(args[3]), &ensemble)) {
+ dprintf(fd, "Non-integer ensemble provided with tune: %s\n", args[3]);
+ return STATUS_BAD_VALUE;
+ }
+ int freq;
+ if (!utils::parseArgInt(string(args[4]), &freq)) {
+ dprintf(fd, "Non-integer frequency provided with tune: %s\n", args[4]);
+ return STATUS_BAD_VALUE;
+ }
+ sel = utils::makeSelectorDab(sid, ensemble, freq);
}
- int freq;
- if (!utils::parseArgInt(string(args[4]), &freq)) {
- dprintf(fd, "Non-integer frequency provided with tune: %s\n", args[4]);
- return STATUS_BAD_VALUE;
- }
- sel = utils::makeSelectorDab(sid, ensemble, freq);
} else {
if (numArgs != 3) {
dprintf(fd, "Invalid number of arguments: please provide --tune amfm <FREQUENCY>\n");
diff --git a/broadcastradio/common/utilsaidl/Utils.cpp b/broadcastradio/common/utilsaidl/Utils.cpp
index ad82366..0551bad 100644
--- a/broadcastradio/common/utilsaidl/Utils.cpp
+++ b/broadcastradio/common/utilsaidl/Utils.cpp
@@ -136,9 +136,18 @@
return getHdSubchannel(b) == 0 &&
haveEqualIds(a, b, IdentifierType::AMFM_FREQUENCY_KHZ);
case IdentifierType::DAB_SID_EXT:
- return haveEqualIds(a, b, IdentifierType::DAB_SID_EXT) &&
- haveEqualIds(a, b, IdentifierType::DAB_ENSEMBLE) &&
- haveEqualIds(a, b, IdentifierType::DAB_FREQUENCY_KHZ);
+ if (!haveEqualIds(a, b, IdentifierType::DAB_SID_EXT)) {
+ return false;
+ }
+ if (hasId(a, IdentifierType::DAB_ENSEMBLE) &&
+ !haveEqualIds(a, b, IdentifierType::DAB_ENSEMBLE)) {
+ return false;
+ }
+ if (hasId(a, IdentifierType::DAB_FREQUENCY_KHZ) &&
+ !haveEqualIds(a, b, IdentifierType::DAB_FREQUENCY_KHZ)) {
+ return false;
+ }
+ return true;
case IdentifierType::DRMO_SERVICE_ID:
return haveEqualIds(a, b, IdentifierType::DRMO_SERVICE_ID);
case IdentifierType::SXM_SERVICE_ID:
@@ -289,25 +298,7 @@
sel.primaryId.type > IdentifierType::VENDOR_END)) {
return false;
}
- if (!isValid(sel.primaryId)) {
- return false;
- }
-
- bool isDab = sel.primaryId.type == IdentifierType::DAB_SID_EXT;
- bool hasDabEnsemble = false;
- bool hasDabFrequency = false;
- for (auto it = sel.secondaryIds.begin(); it != sel.secondaryIds.end(); it++) {
- if (!isValid(*it)) {
- return false;
- }
- if (isDab && it->type == IdentifierType::DAB_ENSEMBLE) {
- hasDabEnsemble = true;
- }
- if (isDab && it->type == IdentifierType::DAB_FREQUENCY_KHZ) {
- hasDabFrequency = true;
- }
- }
- return !isDab || (hasDabEnsemble && hasDabFrequency);
+ return isValid(sel.primaryId);
}
ProgramIdentifier makeIdentifier(IdentifierType type, int64_t value) {
@@ -320,6 +311,12 @@
return sel;
}
+ProgramSelector makeSelectorDab(int64_t sidExt) {
+ ProgramSelector sel = {};
+ sel.primaryId = makeIdentifier(IdentifierType::DAB_SID_EXT, sidExt);
+ return sel;
+}
+
ProgramSelector makeSelectorDab(int64_t sidExt, int32_t ensemble, int64_t freq) {
ProgramSelector sel = {};
sel.primaryId = makeIdentifier(IdentifierType::DAB_SID_EXT, sidExt);
diff --git a/broadcastradio/common/utilsaidl/include/broadcastradio-utils-aidl/Utils.h b/broadcastradio/common/utilsaidl/include/broadcastradio-utils-aidl/Utils.h
index beebd03..ad075f2 100644
--- a/broadcastradio/common/utilsaidl/include/broadcastradio-utils-aidl/Utils.h
+++ b/broadcastradio/common/utilsaidl/include/broadcastradio-utils-aidl/Utils.h
@@ -138,6 +138,7 @@
ProgramIdentifier makeIdentifier(IdentifierType type, int64_t value);
ProgramSelector makeSelectorAmfm(int32_t frequency);
+ProgramSelector makeSelectorDab(int64_t sidExt);
ProgramSelector makeSelectorDab(int64_t sidExt, int32_t ensemble, int64_t freq);
bool satisfies(const ProgramFilter& filter, const ProgramSelector& sel);
diff --git a/camera/provider/aidl/vts/VtsAidlHalCameraProvider_TargetTest.cpp b/camera/provider/aidl/vts/VtsAidlHalCameraProvider_TargetTest.cpp
index 50fb052..a755d57 100644
--- a/camera/provider/aidl/vts/VtsAidlHalCameraProvider_TargetTest.cpp
+++ b/camera/provider/aidl/vts/VtsAidlHalCameraProvider_TargetTest.cpp
@@ -2025,16 +2025,7 @@
}
TEST_P(CameraAidlTest, process8BitColorSpaceRequests) {
- static int profiles[] = {
- ColorSpaceNamed::BT709,
- ColorSpaceNamed::DCI_P3,
- ColorSpaceNamed::DISPLAY_P3,
- ColorSpaceNamed::EXTENDED_SRGB,
- ColorSpaceNamed::LINEAR_EXTENDED_SRGB,
- ColorSpaceNamed::NTSC_1953,
- ColorSpaceNamed::SMPTE_C,
- ColorSpaceNamed::SRGB
- };
+ static int profiles[] = {ColorSpaceNamed::DISPLAY_P3, ColorSpaceNamed::SRGB};
for (int32_t i = 0; i < sizeof(profiles) / sizeof(profiles[0]); i++) {
processColorSpaceRequest(static_cast<RequestAvailableColorSpaceProfilesMap>(profiles[i]),
@@ -2059,10 +2050,10 @@
ANDROID_REQUEST_AVAILABLE_DYNAMIC_RANGE_PROFILES_MAP_DOLBY_VISION_8B_HDR_OEM_PO
};
- // Process all dynamic range profiles with BT2020
+ // Process all dynamic range profiles with BT2020_HLG
for (int32_t i = 0; i < sizeof(dynamicRangeProfiles) / sizeof(dynamicRangeProfiles[0]); i++) {
processColorSpaceRequest(
- static_cast<RequestAvailableColorSpaceProfilesMap>(ColorSpaceNamed::BT2020),
+ static_cast<RequestAvailableColorSpaceProfilesMap>(ColorSpaceNamed::BT2020_HLG),
static_cast<RequestAvailableDynamicRangeProfilesMap>(dynamicRangeProfiles[i]));
}
}
@@ -3051,6 +3042,47 @@
configureStreamUseCaseInternal(previewStreamThreshold);
}
+// Validate the integrity of stream configuration metadata
+TEST_P(CameraAidlTest, validateStreamConfigurations) {
+ std::vector<std::string> cameraDeviceNames = getCameraDeviceNames(mProvider);
+ std::vector<AvailableStream> outputStreams;
+
+ const int32_t scalerSizesTag = ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS;
+ const int32_t scalerMinFrameDurationsTag = ANDROID_SCALER_AVAILABLE_MIN_FRAME_DURATIONS;
+ const int32_t scalerStallDurationsTag = ANDROID_SCALER_AVAILABLE_STALL_DURATIONS;
+
+ for (const auto& name : cameraDeviceNames) {
+ CameraMetadata meta;
+ std::shared_ptr<ICameraDevice> cameraDevice;
+
+ openEmptyDeviceSession(name, mProvider, &mSession /*out*/, &meta /*out*/,
+ &cameraDevice /*out*/);
+ camera_metadata_t* staticMeta = reinterpret_cast<camera_metadata_t*>(meta.metadata.data());
+
+ if (is10BitDynamicRangeCapable(staticMeta)) {
+ std::vector<std::tuple<size_t, size_t>> supportedP010Sizes, supportedBlobSizes;
+
+ getSupportedSizes(staticMeta, scalerSizesTag, HAL_PIXEL_FORMAT_BLOB,
+ &supportedBlobSizes);
+ getSupportedSizes(staticMeta, scalerSizesTag, HAL_PIXEL_FORMAT_YCBCR_P010,
+ &supportedP010Sizes);
+ ASSERT_FALSE(supportedP010Sizes.empty());
+
+ std::vector<int64_t> blobMinDurations, blobStallDurations;
+ getSupportedDurations(staticMeta, scalerMinFrameDurationsTag, HAL_PIXEL_FORMAT_BLOB,
+ supportedP010Sizes, &blobMinDurations);
+ getSupportedDurations(staticMeta, scalerStallDurationsTag, HAL_PIXEL_FORMAT_BLOB,
+ supportedP010Sizes, &blobStallDurations);
+ ASSERT_FALSE(blobStallDurations.empty());
+ ASSERT_FALSE(blobMinDurations.empty());
+ ASSERT_EQ(supportedP010Sizes.size(), blobMinDurations.size());
+ ASSERT_EQ(blobMinDurations.size(), blobStallDurations.size());
+ }
+
+ // Validate other aspects of stream configuration metadata...
+ }
+}
+
GTEST_ALLOW_UNINSTANTIATED_PARAMETERIZED_TEST(CameraAidlTest);
INSTANTIATE_TEST_SUITE_P(
PerInstance, CameraAidlTest,
diff --git a/camera/provider/aidl/vts/camera_aidl_test.cpp b/camera/provider/aidl/vts/camera_aidl_test.cpp
index 64507fe..058770e 100644
--- a/camera/provider/aidl/vts/camera_aidl_test.cpp
+++ b/camera/provider/aidl/vts/camera_aidl_test.cpp
@@ -3085,6 +3085,10 @@
return "CIE_XYZ";
case ColorSpaceNamed::CIE_LAB:
return "CIE_LAB";
+ case ColorSpaceNamed::BT2020_HLG:
+ return "BT2020_HLG";
+ case ColorSpaceNamed::BT2020_PQ:
+ return "BT2020_PQ";
default:
return "INVALID";
}
@@ -3703,3 +3707,48 @@
ASSERT_TRUE(ret.isOk());
}
}
+
+void CameraAidlTest::getSupportedSizes(const camera_metadata_t* ch, uint32_t tag, int32_t format,
+ std::vector<std::tuple<size_t, size_t>>* sizes /*out*/) {
+ if (sizes == nullptr) {
+ return;
+ }
+
+ camera_metadata_ro_entry entry;
+ int retcode = find_camera_metadata_ro_entry(ch, tag, &entry);
+ if ((0 == retcode) && (entry.count > 0)) {
+ // Scaler entry contains 4 elements (format, width, height, type)
+ for (size_t i = 0; i < entry.count; i += 4) {
+ if ((entry.data.i32[i] == format) &&
+ (entry.data.i32[i + 3] == ANDROID_SCALER_AVAILABLE_STREAM_CONFIGURATIONS_OUTPUT)) {
+ sizes->push_back(std::make_tuple(entry.data.i32[i + 1], entry.data.i32[i + 2]));
+ }
+ }
+ }
+}
+
+void CameraAidlTest::getSupportedDurations(const camera_metadata_t* ch, uint32_t tag,
+ int32_t format,
+ const std::vector<std::tuple<size_t, size_t>>& sizes,
+ std::vector<int64_t>* durations /*out*/) {
+ if (durations == nullptr) {
+ return;
+ }
+
+ camera_metadata_ro_entry entry;
+ int retcode = find_camera_metadata_ro_entry(ch, tag, &entry);
+ if ((0 == retcode) && (entry.count > 0)) {
+ // Duration entry contains 4 elements (format, width, height, duration)
+ for (const auto& size : sizes) {
+ int64_t width = std::get<0>(size);
+ int64_t height = std::get<1>(size);
+ for (size_t i = 0; i < entry.count; i += 4) {
+ if ((entry.data.i64[i] == format) && (entry.data.i64[i + 1] == width) &&
+ (entry.data.i64[i + 2] == height)) {
+ durations->push_back(entry.data.i64[i + 3]);
+ break;
+ }
+ }
+ }
+ }
+}
diff --git a/camera/provider/aidl/vts/camera_aidl_test.h b/camera/provider/aidl/vts/camera_aidl_test.h
index f13d6b2..4b4c039 100644
--- a/camera/provider/aidl/vts/camera_aidl_test.h
+++ b/camera/provider/aidl/vts/camera_aidl_test.h
@@ -145,7 +145,9 @@
ACES,
ACESCG,
CIE_XYZ,
- CIE_LAB
+ CIE_LAB,
+ BT2020_HLG,
+ BT2020_PQ
};
struct AvailableZSLInputOutput {
@@ -418,6 +420,13 @@
bool supportsCroppedRawUseCase(const camera_metadata_t *staticMeta);
bool isPerFrameControl(const camera_metadata_t* staticMeta);
+ void getSupportedSizes(const camera_metadata_t* ch, uint32_t tag, int32_t format,
+ std::vector<std::tuple<size_t, size_t>>* sizes /*out*/);
+
+ void getSupportedDurations(const camera_metadata_t* ch, uint32_t tag, int32_t format,
+ const std::vector<std::tuple<size_t, size_t>>& sizes,
+ std::vector<int64_t>* durations /*out*/);
+
protected:
// In-flight queue for tracking completion of capture requests.
struct InFlightRequest {
diff --git a/compatibility_matrices/compatibility_matrix.8.xml b/compatibility_matrices/compatibility_matrix.8.xml
index c58f559..6def4b8 100644
--- a/compatibility_matrices/compatibility_matrix.8.xml
+++ b/compatibility_matrices/compatibility_matrix.8.xml
@@ -62,7 +62,7 @@
</hal>
<hal format="aidl" optional="true">
<name>android.hardware.automotive.audiocontrol</name>
- <version>2</version>
+ <version>2-3</version>
<interface>
<name>IAudioControl</name>
<instance>default</instance>
@@ -103,6 +103,7 @@
</hal>
<hal format="aidl" optional="true">
<name>android.hardware.automotive.vehicle</name>
+ <version>1-2</version>
<interface>
<name>IVehicle</name>
<instance>default</instance>
diff --git a/graphics/composer/aidl/vts/VtsHalGraphicsComposer3_TargetTest.cpp b/graphics/composer/aidl/vts/VtsHalGraphicsComposer3_TargetTest.cpp
index 746330b..323554c 100644
--- a/graphics/composer/aidl/vts/VtsHalGraphicsComposer3_TargetTest.cpp
+++ b/graphics/composer/aidl/vts/VtsHalGraphicsComposer3_TargetTest.cpp
@@ -118,6 +118,12 @@
[&](const Capability& activeCapability) { return activeCapability == capability; });
}
+ int getInterfaceVersion() {
+ const auto& [versionStatus, version] = mComposerClient->getInterfaceVersion();
+ EXPECT_TRUE(versionStatus.isOk());
+ return version;
+ }
+
const VtsDisplay& getPrimaryDisplay() const { return mDisplays[0]; }
int64_t getPrimaryDisplayId() const { return getPrimaryDisplay().getDisplayId(); }
@@ -874,9 +880,7 @@
}
TEST_P(GraphicsComposerAidlTest, GetOverlaySupport) {
- const auto& [versionStatus, version] = mComposerClient->getInterfaceVersion();
- ASSERT_TRUE(versionStatus.isOk());
- if (version == 1) {
+ if (getInterfaceVersion() <= 1) {
GTEST_SUCCEED() << "Device does not support the new API for overlay support";
return;
}
@@ -2290,6 +2294,11 @@
}
TEST_P(GraphicsComposerAidlCommandTest, SetRefreshRateChangedCallbackDebug_Unsupported) {
+ if (getInterfaceVersion() <= 1) {
+ GTEST_SUCCEED() << "Capability::REFRESH_RATE_CHANGED_CALLBACK_DEBUG is "
+ "not supported on older version of the service";
+ return;
+ }
if (!hasCapability(Capability::REFRESH_RATE_CHANGED_CALLBACK_DEBUG)) {
auto status = mComposerClient->setRefreshRateChangedCallbackDebugEnabled(
getPrimaryDisplayId(), /*enabled*/ true);
@@ -2306,6 +2315,11 @@
}
TEST_P(GraphicsComposerAidlCommandTest, SetRefreshRateChangedCallbackDebug_Enabled) {
+ if (getInterfaceVersion() <= 1) {
+ GTEST_SUCCEED() << "Capability::REFRESH_RATE_CHANGED_CALLBACK_DEBUG is "
+ "not supported on older version of the service";
+ return;
+ }
if (!hasCapability(Capability::REFRESH_RATE_CHANGED_CALLBACK_DEBUG)) {
GTEST_SUCCEED() << "Capability::REFRESH_RATE_CHANGED_CALLBACK_DEBUG is not supported";
return;
@@ -2335,6 +2349,11 @@
TEST_P(GraphicsComposerAidlCommandTest,
SetRefreshRateChangedCallbackDebugEnabled_noCallbackWhenIdle) {
+ if (getInterfaceVersion() <= 1) {
+ GTEST_SUCCEED() << "Capability::REFRESH_RATE_CHANGED_CALLBACK_DEBUG is "
+ "not supported on older version of the service";
+ return;
+ }
if (!hasCapability(Capability::REFRESH_RATE_CHANGED_CALLBACK_DEBUG)) {
GTEST_SUCCEED() << "Capability::REFRESH_RATE_CHANGED_CALLBACK_DEBUG is not supported";
return;
@@ -2392,6 +2411,11 @@
TEST_P(GraphicsComposerAidlCommandTest,
SetRefreshRateChangedCallbackDebugEnabled_SetActiveConfigWithConstraints) {
+ if (getInterfaceVersion() <= 1) {
+ GTEST_SUCCEED() << "Capability::REFRESH_RATE_CHANGED_CALLBACK_DEBUG is "
+ "not supported on older version of the service";
+ return;
+ }
if (!hasCapability(Capability::REFRESH_RATE_CHANGED_CALLBACK_DEBUG)) {
GTEST_SUCCEED() << "Capability::REFRESH_RATE_CHANGED_CALLBACK_DEBUG is not supported";
return;
@@ -2514,9 +2538,7 @@
* Capability::SKIP_VALIDATE has been deprecated and should not be enabled.
*/
TEST_P(GraphicsComposerAidlCommandTest, SkipValidateDeprecatedTest) {
- const auto& [versionStatus, version] = mComposerClient->getInterfaceVersion();
- ASSERT_TRUE(versionStatus.isOk());
- if (version <= 1) {
+ if (getInterfaceVersion() <= 1) {
GTEST_SUCCEED() << "HAL at version 1 or lower can contain Capability::SKIP_VALIDATE.";
return;
}
diff --git a/health/aidl/vts/functional/VtsHalHealthTargetTest.cpp b/health/aidl/vts/functional/VtsHalHealthTargetTest.cpp
index 69d4789..783ce11 100644
--- a/health/aidl/vts/functional/VtsHalHealthTargetTest.cpp
+++ b/health/aidl/vts/functional/VtsHalHealthTargetTest.cpp
@@ -257,7 +257,7 @@
BatteryChargingPolicy value;
/* set ChargingPolicy*/
- status = health->setChargingPolicy(static_cast<BatteryChargingPolicy>(2)); // LONG_LIFE
+ status = health->setChargingPolicy(BatteryChargingPolicy::LONG_LIFE);
ASSERT_THAT(status, AnyOf(IsOk(), ExceptionIs(EX_UNSUPPORTED_OPERATION)));
if (!status.isOk()) return;
@@ -265,7 +265,9 @@
status = health->getChargingPolicy(&value);
ASSERT_THAT(status, AnyOf(IsOk(), ExceptionIs(EX_UNSUPPORTED_OPERATION)));
if (!status.isOk()) return;
- ASSERT_THAT(static_cast<int>(value), Eq(2));
+ // the result of getChargingPolicy will be one of default(1), ADAPTIVE_AON(2)
+ // ADAPTIVE_AC(3) or LONG_LIFE(4). default(1) means NOT_SUPPORT
+ ASSERT_THAT(static_cast<int>(value), AnyOf(Eq(1), Eq(4)));
}
MATCHER(IsValidHealthData, "") {
diff --git a/neuralnetworks/aidl/vts/functional/GeneratedTestHarness.cpp b/neuralnetworks/aidl/vts/functional/GeneratedTestHarness.cpp
index dcf8451..e344458 100644
--- a/neuralnetworks/aidl/vts/functional/GeneratedTestHarness.cpp
+++ b/neuralnetworks/aidl/vts/functional/GeneratedTestHarness.cpp
@@ -736,8 +736,8 @@
// If a sync fence is returned, try start another run waiting for the sync
// fence.
if (testConfig.reusable) {
- ret = execution->executeFenced(waitFor, kNoDeadline, kNoDuration,
- &executionResult);
+ // Nothing to do because at most one execution may occur on a reusable
+ // execution object at any given time.
} else if (testConfig.useConfig) {
ret = preparedModel->executeFencedWithConfig(
request, waitFor,
diff --git a/radio/1.5/vts/functional/radio_hidl_hal_api.cpp b/radio/1.5/vts/functional/radio_hidl_hal_api.cpp
index 5539b9c..316c308 100644
--- a/radio/1.5/vts/functional/radio_hidl_hal_api.cpp
+++ b/radio/1.5/vts/functional/radio_hidl_hal_api.cpp
@@ -565,9 +565,9 @@
serial = GetRandomSerialNumber();
::android::hardware::radio::V1_5::RadioAccessSpecifier::Bands band17;
- band17.eutranBands() = {::android::hardware::radio::V1_5::EutranBands::BAND_17};
+ band17.eutranBands({::android::hardware::radio::V1_5::EutranBands::BAND_17});
::android::hardware::radio::V1_5::RadioAccessSpecifier::Bands band20;
- band20.eutranBands() = {::android::hardware::radio::V1_5::EutranBands::BAND_20};
+ band20.eutranBands({::android::hardware::radio::V1_5::EutranBands::BAND_20});
::android::hardware::radio::V1_5::RadioAccessSpecifier specifier17 = {
.radioAccessNetwork = ::android::hardware::radio::V1_5::RadioAccessNetworks::EUTRAN,
.bands = band17,
diff --git a/secure_element/aidl/android/hardware/secure_element/ISecureElement.aidl b/secure_element/aidl/android/hardware/secure_element/ISecureElement.aidl
index 8c0dd6d..800494a 100644
--- a/secure_element/aidl/android/hardware/secure_element/ISecureElement.aidl
+++ b/secure_element/aidl/android/hardware/secure_element/ISecureElement.aidl
@@ -117,6 +117,9 @@
* closed by this operation.
* HAL service must send onStateChange() with connected equal to true
* after resetting and all the re-initialization has been successfully completed.
+ *
+ * @throws ServiceSpecificException on error with the following code:
+ * - FAILED if the service was unable to reset the secure element.
*/
void reset();
diff --git a/secure_element/aidl/vts/VtsHalSecureElementTargetTest.cpp b/secure_element/aidl/vts/VtsHalSecureElementTargetTest.cpp
index 0925a21..839a4ff 100644
--- a/secure_element/aidl/vts/VtsHalSecureElementTargetTest.cpp
+++ b/secure_element/aidl/vts/VtsHalSecureElementTargetTest.cpp
@@ -284,14 +284,21 @@
TEST_P(SecureElementAidl, transmit) {
std::vector<uint8_t> response;
+ LogicalChannelResponse logical_channel_response;
- // transmit called after init shall succeed.
- // Note: no channel is opened for this test and the transmit
- // response will have the status SW_LOGICAL_CHANNEL_NOT_SUPPORTED.
- // The transmit response shall be larger than 2 bytes as it includes the
- // status code.
- EXPECT_OK(secure_element_->transmit(kDataApdu, &response));
- EXPECT_GE(response.size(), 2u);
+ // Note: no channel is opened for this test
+ // transmit() will return an empty response with the error
+ // code CHANNEL_NOT_AVAILABLE when the SE cannot be
+ // communicated with.
+ EXPECT_ERR(secure_element_->transmit(kDataApdu, &response));
+
+ EXPECT_OK(secure_element_->openLogicalChannel(kSelectableAid, 0x00, &logical_channel_response));
+ EXPECT_GE(logical_channel_response.selectResponse.size(), 2u);
+ EXPECT_GE(logical_channel_response.channelNumber, 1u);
+ EXPECT_LE(logical_channel_response.channelNumber, 19u);
+
+ // transmit called on the logical channel should succeed.
+ EXPECT_EQ(transmit(logical_channel_response.channelNumber), 0x9000);
}
GTEST_ALLOW_UNINSTANTIATED_PARAMETERIZED_TEST(SecureElementAidl);
diff --git a/security/keymint/support/remote_prov_utils.cpp b/security/keymint/support/remote_prov_utils.cpp
index 086ee79..7214234 100644
--- a/security/keymint/support/remote_prov_utils.cpp
+++ b/security/keymint/support/remote_prov_utils.cpp
@@ -22,6 +22,7 @@
#include "aidl/android/hardware/security/keymint/IRemotelyProvisionedComponent.h"
#include <aidl/android/hardware/security/keymint/RpcHardwareInfo.h>
+#include <android-base/macros.h>
#include <android-base/properties.h>
#include <cppbor.h>
#include <hwtrust/hwtrust.h>
@@ -43,6 +44,7 @@
constexpr int32_t kBccPayloadSubjPubKey = -4670552;
constexpr int32_t kBccPayloadKeyUsage = -4670553;
constexpr int kP256AffinePointSize = 32;
+constexpr uint32_t kNumTeeDeviceInfoEntries = 14;
using EC_KEY_Ptr = bssl::UniquePtr<EC_KEY>;
using EVP_PKEY_Ptr = bssl::UniquePtr<EVP_PKEY>;
@@ -388,6 +390,11 @@
return entryName + " has an invalid value.\n";
}
+bool isTeeDeviceInfo(const cppbor::Map& devInfo) {
+ return devInfo.get("security_level") && devInfo.get("security_level")->asTstr() &&
+ devInfo.get("security_level")->asTstr()->value() == "tee";
+}
+
ErrMsgOr<std::unique_ptr<cppbor::Map>> parseAndValidateDeviceInfo(
const std::vector<uint8_t>& deviceInfoBytes, IRemotelyProvisionedComponent* provisionable,
bool isFactory) {
@@ -396,6 +403,21 @@
const cppbor::Array kValidSecurityLevels = {"tee", "strongbox"};
const cppbor::Array kValidAttIdStates = {"locked", "open"};
const cppbor::Array kValidFused = {0, 1};
+ constexpr std::array<std::string_view, kNumTeeDeviceInfoEntries> kDeviceInfoKeys = {
+ "brand",
+ "manufacturer",
+ "product",
+ "model",
+ "device",
+ "vb_state",
+ "bootloader_state",
+ "vbmeta_digest",
+ "os_version",
+ "system_patch_level",
+ "boot_patch_level",
+ "vendor_patch_level",
+ "security_level",
+ "fused"};
struct AttestationIdEntry {
const char* id;
@@ -439,20 +461,48 @@
}
std::string error;
+ std::string tmp;
+ std::set<std::string_view> previousKeys;
switch (info.versionNumber) {
case 3:
+ if (isTeeDeviceInfo(*parsed) && parsed->size() != kNumTeeDeviceInfoEntries) {
+ error += fmt::format(
+ "Err: Incorrect number of device info entries. Expected {} but got"
+ "{}\n",
+ kNumTeeDeviceInfoEntries, parsed->size());
+ }
+ // TEE IRPC instances require all entries to be present in DeviceInfo. Non-TEE instances
+ // may omit `os_version`
+ if (!isTeeDeviceInfo(*parsed) && (parsed->size() != kNumTeeDeviceInfoEntries ||
+ parsed->size() != kNumTeeDeviceInfoEntries - 1)) {
+ error += fmt::format(
+ "Err: Incorrect number of device info entries. Expected {} or {} but got"
+ "{}\n",
+ kNumTeeDeviceInfoEntries - 1, kNumTeeDeviceInfoEntries, parsed->size());
+ }
+ for (auto& [key, _] : *parsed) {
+ const std::string& keyValue = key->asTstr()->value();
+ if (!previousKeys.insert(keyValue).second) {
+ error += "Err: Duplicate device info entry: <" + keyValue + ">,\n";
+ }
+ if (std::find(kDeviceInfoKeys.begin(), kDeviceInfoKeys.end(), keyValue) ==
+ kDeviceInfoKeys.end()) {
+ error += "Err: Unrecognized key entry: <" + key->asTstr()->value() + ">,\n";
+ }
+ }
+ FALLTHROUGH_INTENDED;
case 2:
for (const auto& entry : kAttestationIdEntrySet) {
- error += checkMapEntry(isFactory && !entry.alwaysValidate, *parsed, cppbor::TSTR,
- entry.id);
+ tmp = checkMapEntry(isFactory && !entry.alwaysValidate, *parsed, cppbor::TSTR,
+ entry.id);
}
- if (!error.empty()) {
- return error +
- "Attestation IDs are missing or malprovisioned. If this test is being\n"
- "run against an early proto or EVT build, this error is probably WAI\n"
- "and indicates that Device IDs were not provisioned in the factory. If\n"
- "this error is returned on a DVT or later build revision, then\n"
- "something is likely wrong with the factory provisioning process.";
+ if (!tmp.empty()) {
+ error += tmp +
+ "Attestation IDs are missing or malprovisioned. If this test is being\n"
+ "run against an early proto or EVT build, this error is probably WAI\n"
+ "and indicates that Device IDs were not provisioned in the factory. If\n"
+ "this error is returned on a DVT or later build revision, then\n"
+ "something is likely wrong with the factory provisioning process.";
}
// TODO: Refactor the KeyMint code that validates these fields and include it here.
error += checkMapEntry(isFactory, *parsed, cppbor::TSTR, "vb_state", kValidVbStates);
@@ -465,8 +515,7 @@
error += checkMapEntry(isFactory, *parsed, cppbor::UINT, "fused", kValidFused);
error += checkMapEntry(isFactory, *parsed, cppbor::TSTR, "security_level",
kValidSecurityLevels);
- if (parsed->get("security_level") && parsed->get("security_level")->asTstr() &&
- parsed->get("security_level")->asTstr()->value() == "tee") {
+ if (isTeeDeviceInfo(*parsed)) {
error += checkMapEntry(isFactory, *parsed, cppbor::TSTR, "os_version");
}
break;
diff --git a/tests/extension/vibrator/aidl/Android.bp b/tests/extension/vibrator/aidl/Android.bp
index 20df5bb..0306dca 100644
--- a/tests/extension/vibrator/aidl/Android.bp
+++ b/tests/extension/vibrator/aidl/Android.bp
@@ -38,5 +38,11 @@
enabled: false,
},
},
- versions: ["1"],
+ frozen: true,
+ versions_with_info: [
+ {
+ version: "1",
+ imports: ["android.hardware.vibrator-V2"],
+ },
+ ],
}
diff --git a/tests/extension/vibrator/aidl/default/Android.bp b/tests/extension/vibrator/aidl/default/Android.bp
index 0f3895f..5e156af 100644
--- a/tests/extension/vibrator/aidl/default/Android.bp
+++ b/tests/extension/vibrator/aidl/default/Android.bp
@@ -29,6 +29,6 @@
"libbase",
"libbinder_ndk",
"android.hardware.vibrator-V2-ndk",
- "android.hardware.tests.extension.vibrator-V2-ndk",
+ "android.hardware.tests.extension.vibrator-V1-ndk",
],
}
diff --git a/wifi/1.6/default/Android.bp b/wifi/1.6/default/Android.bp
index 0f98e71..6038e36 100644
--- a/wifi/1.6/default/Android.bp
+++ b/wifi/1.6/default/Android.bp
@@ -26,6 +26,7 @@
"hidl_feature_disable_ap", // WIFI_HIDL_FEATURE_DISABLE_AP
"hidl_feature_disable_ap_mac_randomization", // WIFI_HIDL_FEATURE_DISABLE_AP_MAC_RANDOMIZATION
"avoid_iface_reset_mac_change", // WIFI_AVOID_IFACE_RESET_MAC_CHANGE
+ "wifi_skip_state_toggle_off_on_for_nan", // WIFI_SKIP_STATE_TOGGLE_OFF_ON_FOR_NAN
],
value_variables: [
"hal_interface_combinations", // WIFI_HAL_INTERFACE_COMBINATIONS
@@ -53,6 +54,9 @@
avoid_iface_reset_mac_change: {
cppflags: ["-DWIFI_AVOID_IFACE_RESET_MAC_CHANGE"],
},
+ wifi_skip_state_toggle_off_on_for_nan: {
+ cppflags: ["-DWIFI_SKIP_STATE_TOGGLE_OFF_ON_FOR_NAN"],
+ },
hal_interface_combinations: {
cppflags: ["-DWIFI_HAL_INTERFACE_COMBINATIONS=%s"],
},
diff --git a/wifi/1.6/default/wifi_nan_iface.cpp b/wifi/1.6/default/wifi_nan_iface.cpp
index ac2ebc9..4c61ba7 100644
--- a/wifi/1.6/default/wifi_nan_iface.cpp
+++ b/wifi/1.6/default/wifi_nan_iface.cpp
@@ -453,6 +453,7 @@
// Register for iface state toggle events.
iface_util::IfaceEventHandlers event_handlers = {};
+#ifndef WIFI_SKIP_STATE_TOGGLE_OFF_ON_FOR_NAN
event_handlers.on_state_toggle_off_on = [weak_ptr_this](const std::string& /* iface_name */) {
const auto shared_ptr_this = weak_ptr_this.promote();
if (!shared_ptr_this.get() || !shared_ptr_this->isValid()) {
@@ -467,6 +468,7 @@
}
}
};
+#endif
iface_util_.lock()->registerIfaceEventHandlers(ifname_, event_handlers);
}
diff --git a/wifi/aidl/default/Android.bp b/wifi/aidl/default/Android.bp
index 441d461..91d609d 100644
--- a/wifi/aidl/default/Android.bp
+++ b/wifi/aidl/default/Android.bp
@@ -26,6 +26,7 @@
"hidl_feature_disable_ap", // WIFI_HIDL_FEATURE_DISABLE_AP
"hidl_feature_disable_ap_mac_randomization", // WIFI_HIDL_FEATURE_DISABLE_AP_MAC_RANDOMIZATION
"avoid_iface_reset_mac_change", // WIFI_AVOID_IFACE_RESET_MAC_CHANGE
+ "wifi_skip_state_toggle_off_on_for_nan", // WIFI_SKIP_STATE_TOGGLE_OFF_ON_FOR_NAN
],
value_variables: [
"hal_interface_combinations", // WIFI_HAL_INTERFACE_COMBINATIONS
@@ -53,6 +54,9 @@
avoid_iface_reset_mac_change: {
cppflags: ["-DWIFI_AVOID_IFACE_RESET_MAC_CHANGE"],
},
+ wifi_skip_state_toggle_off_on_for_nan: {
+ cppflags: ["-DWIFI_SKIP_STATE_TOGGLE_OFF_ON_FOR_NAN"],
+ },
hal_interface_combinations: {
cppflags: ["-DWIFI_HAL_INTERFACE_COMBINATIONS=%s"],
},
diff --git a/wifi/aidl/default/wifi_nan_iface.cpp b/wifi/aidl/default/wifi_nan_iface.cpp
index 8e3a191..cefe7f7 100644
--- a/wifi/aidl/default/wifi_nan_iface.cpp
+++ b/wifi/aidl/default/wifi_nan_iface.cpp
@@ -623,6 +623,7 @@
// Register for iface state toggle events.
iface_util::IfaceEventHandlers event_handlers = {};
+#ifndef WIFI_SKIP_STATE_TOGGLE_OFF_ON_FOR_NAN
event_handlers.on_state_toggle_off_on = [weak_ptr_this](const std::string& /* iface_name */) {
const auto shared_ptr_this = weak_ptr_this.lock();
if (!shared_ptr_this.get() || !shared_ptr_this->isValid()) {
@@ -637,6 +638,7 @@
}
}
};
+#endif
iface_util_.lock()->registerIfaceEventHandlers(ifname_, event_handlers);
}
diff --git a/wifi/supplicant/aidl/android/hardware/wifi/supplicant/INonStandardCertCallback.aidl b/wifi/supplicant/aidl/android/hardware/wifi/supplicant/INonStandardCertCallback.aidl
index 2f9e528..2e11c76 100644
--- a/wifi/supplicant/aidl/android/hardware/wifi/supplicant/INonStandardCertCallback.aidl
+++ b/wifi/supplicant/aidl/android/hardware/wifi/supplicant/INonStandardCertCallback.aidl
@@ -18,7 +18,8 @@
/**
* Callback to allow supplicant to retrieve non-standard certificate types
- * from the client.
+ * from the framework. Certificates can be stored in the framework using
+ * the WifiKeystore#put system API.
*
* Must be registered by the client at initialization, so that
* supplicant can call into the client to retrieve any values.