Merge "Add support to blacklist IRNSS in HAL 2.1"
diff --git a/audio/common/6.0/types.hal b/audio/common/6.0/types.hal
index 0c97c36..fa2f3a9 100644
--- a/audio/common/6.0/types.hal
+++ b/audio/common/6.0/types.hal
@@ -156,6 +156,11 @@
@export(name="audio_session_t", value_prefix="AUDIO_SESSION_")
enum AudioSessionConsts : int32_t {
/**
+ * Session for effects attached to a particular sink or source audio device
+ * (e.g an effect only applied to a speaker)
+ */
+ DEVICE = -2,
+ /**
* Session for effects attached to a particular output stream
* (value must be less than 0)
*/
diff --git a/audio/effect/all-versions/default/Effect.cpp b/audio/effect/all-versions/default/Effect.cpp
index e11e123..406a571 100644
--- a/audio/effect/all-versions/default/Effect.cpp
+++ b/audio/effect/all-versions/default/Effect.cpp
@@ -709,7 +709,10 @@
#elif MAJOR_VERSION >= 6
// No need to join the processing thread, it is part of the API contract that the client
// must finish processing before closing the effect.
- return analyzeStatus("EffectRelease", "", sContextCallFunction, EffectRelease(mHandle));
+ Result retval =
+ analyzeStatus("EffectRelease", "", sContextCallFunction, EffectRelease(mHandle));
+ EffectMap::getInstance().remove(mHandle);
+ return retval;
#endif
}
diff --git a/automotive/can/1.0/default/service.cpp b/automotive/can/1.0/default/service.cpp
index 7ef44fc..ebc2f8c 100644
--- a/automotive/can/1.0/default/service.cpp
+++ b/automotive/can/1.0/default/service.cpp
@@ -32,8 +32,8 @@
configureRpcThreadpool(16, true);
LOG(DEBUG) << "CAN controller service starting...";
- CanController canController;
- if (canController.registerAsService("socketcan") != OK) {
+ sp<CanController> canController(new CanController);
+ if (canController->registerAsService("socketcan") != OK) {
LOG(FATAL) << "Failed to register CAN controller";
return;
}
diff --git a/automotive/occupant_awareness/aidl/Android.bp b/automotive/occupant_awareness/aidl/Android.bp
new file mode 100644
index 0000000..6e9e8aa
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/Android.bp
@@ -0,0 +1,13 @@
+aidl_interface {
+ name: "android.hardware.automotive.occupant_awareness",
+ vendor_available: true,
+ srcs: [
+ "android/hardware/automotive/occupant_awareness/*.aidl",
+ ],
+ stability: "vintf",
+ backend: {
+ java: {
+ enabled: false,
+ },
+ }
+}
diff --git a/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/ConfidenceLevel.aidl b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/ConfidenceLevel.aidl
new file mode 100644
index 0000000..8597ddb
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/ConfidenceLevel.aidl
@@ -0,0 +1,40 @@
+/*
+ * 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.automotive.occupant_awareness;
+
+@VintfStability
+@Backing(type="byte")
+enum ConfidenceLevel {
+ /**
+ * No prediction could be made.
+ */
+ NONE,
+ /**
+ * Best-guess, low-confidence prediction. Predictions exceeding this threshold are adequate
+ * for non-critical applications.
+ */
+ LOW,
+ /**
+ * High-confidence prediction. Predictions exceeding this threshold are adequate for
+ * applications that require reliable predictions.
+ */
+ HIGH,
+ /**
+ * Highest confidence rate achievable.
+ */
+ MAX,
+}
diff --git a/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/DriverMonitoringDetection.aidl b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/DriverMonitoringDetection.aidl
new file mode 100644
index 0000000..f5cc9d5
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/DriverMonitoringDetection.aidl
@@ -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.automotive.occupant_awareness;
+
+import android.hardware.automotive.occupant_awareness.ConfidenceLevel;
+
+@VintfStability
+parcelable DriverMonitoringDetection {
+ /*
+ * Confidence of the computed attention data.
+ */
+ ConfidenceLevel confidenceScore;
+ /*
+ * Is the driver currently looking on-road?
+ */
+ boolean isLookingOnRoad;
+ /*
+ * Duration the driver has been looking on or off road, in milliseconds.
+ */
+ long gazeDurationMillis;
+}
+
diff --git a/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/GazeDetection.aidl b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/GazeDetection.aidl
new file mode 100644
index 0000000..fc36e13
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/GazeDetection.aidl
@@ -0,0 +1,57 @@
+/*
+ * 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.automotive.occupant_awareness;
+
+import android.hardware.automotive.occupant_awareness.VehicleRegion;
+import android.hardware.automotive.occupant_awareness.ConfidenceLevel;
+
+@VintfStability
+parcelable GazeDetection {
+ /*
+ * Confidence level for the gaze detection.
+ */
+ ConfidenceLevel gazeConfidence;
+ /*
+ * Head position, in millimeters. The vehicle coordinate system is specified in the cabin space
+ * configuration. headPosition is double[3] array.
+ */
+ double[] headPosition;
+ /*
+ * Unit vector for the head pose direction. The vehicle coordinate system is specified in the
+ * cabin space configuration. headAngleUnitVector is double[3] array.
+ */
+ double[] headAngleUnitVector;
+ /*
+ * Unit vector for the gaze direction. The vehicle coordinate system is specified in the cabin
+ * space configuration. gazeAngleUnitVector is double[3] array.
+ */
+ double[] gazeAngleUnitVector;
+ /*
+ * Current gaze target.
+ */
+ VehicleRegion gazeTarget;
+ /*
+ * Custom gaze target string. This only need to be populated when gazeTarget is CUSTOM_TARGET.
+ * Vendors should use "com.vendor_name.target_name" format to avoid name collision with other
+ * vendors.
+ */
+ String customGazeTarget;
+ /*
+ * Duration that the subject has been looking at the current gaze target in milliseconds.
+ */
+ long timeOnTargetMillis;
+}
diff --git a/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/IOccupantAwareness.aidl b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/IOccupantAwareness.aidl
new file mode 100644
index 0000000..1df0bda
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/IOccupantAwareness.aidl
@@ -0,0 +1,88 @@
+/*
+ * 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.automotive.occupant_awareness;
+
+import android.hardware.automotive.occupant_awareness.OccupantAwarenessStatus;
+import android.hardware.automotive.occupant_awareness.Role;
+import android.hardware.automotive.occupant_awareness.IOccupantAwarenessClientCallback;
+import android.hardware.automotive.occupant_awareness.OccupantDetections;
+
+@VintfStability
+interface IOccupantAwareness {
+ /*
+ * System not able to generate any occupancy awareness.
+ */
+ const int CAP_NONE = 0;
+ /*
+ * System is able to detect the presence of humans.
+ */
+ const int CAP_PRESENCE_DETECTION = 1 << 0;
+ /*
+ * System is able to detect the gaze of humans.
+ */
+ const int CAP_GAZE_DETECTION = 1 << 1;
+ /*
+ * System is able to compute the attention details of humans.
+ */
+ const int CAP_DRIVER_MONITORING_DETECTION = 1 << 2;
+
+ /**
+ * Starts the occupant awareness detection system. This is a non-blocking function call.
+ * Once system is ready, state will be modified. State update can be inrquired using callback
+ * or getState() function.
+ * @return status is the current system state.
+ */
+ OccupantAwarenessStatus startDetection();
+
+ /**
+ * Stops the occupant awareness detection system. This is a non-blocking function call.
+ * Once system is reset, state will be modified. State update can be inrquired using callback
+ * or getState() function.
+ * @return status is the current system state.
+ */
+ OccupantAwarenessStatus stopDetection();
+
+ /**
+ * Returns list of Awareness Capability supported for the given type of occupants.
+ *
+ * @param out Bitwise OR of supported capabilities (CAP_* mask).
+ */
+ int getCapabilityForRole(in Role occupantRole);
+
+ /**
+ * Inquires the current state of the occupant awareness system.
+ * @param occupantRole specifies the role of occupants of interest.
+ * @param detectionCapability specifies a single detection capability (CAP_* ) of interest.
+ *
+ * @return status is the current system state.
+ */
+ OccupantAwarenessStatus getState(in Role occupantRole, in int detectionCapability);
+
+ /**
+ * Registers a callback for data streaming. Only single callback is supported. setCallback()
+ * should replace existing callback with new callback.
+ * @return: returns ok if successful.
+ */
+ void setCallback(in IOccupantAwarenessClientCallback callback);
+
+ /**
+ * Returns the most recent set of detections.
+ * @param OccupantDetections output detections.
+ * @return returns ok if successful.
+ */
+ void getLatestDetection(out OccupantDetections detections);
+}
diff --git a/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/IOccupantAwarenessClientCallback.aidl b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/IOccupantAwarenessClientCallback.aidl
new file mode 100644
index 0000000..69f7b0b
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/IOccupantAwarenessClientCallback.aidl
@@ -0,0 +1,38 @@
+/*
+ * 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.automotive.occupant_awareness;
+
+import android.hardware.automotive.occupant_awareness.OccupantAwarenessStatus;
+import android.hardware.automotive.occupant_awareness.OccupantDetections;
+
+@VintfStability
+interface IOccupantAwarenessClientCallback {
+ /**
+ * A callback invoked when the system status changes.
+ *
+ * @param detectionFlags The detection subsystem(s) whose status has changed.
+ * @param status The new system status.
+ */
+ oneway void onSystemStatusChanged(in int detectionFlags, in OccupantAwarenessStatus status);
+
+ /**
+ * A callback invoked when a new set of detections are available.
+ *
+ * @param detections Occupant detections.
+ */
+ oneway void onDetectionEvent(in OccupantDetections detections);
+}
diff --git a/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/OccupantAwarenessStatus.aidl b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/OccupantAwarenessStatus.aidl
new file mode 100644
index 0000000..6a3453d
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/OccupantAwarenessStatus.aidl
@@ -0,0 +1,41 @@
+/*
+ * 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.automotive.occupant_awareness;
+
+@VintfStability
+@Backing(type="byte")
+enum OccupantAwarenessStatus {
+ /*
+ * System is online and ready to serve requests.
+ */
+ READY = 0,
+ /**
+ * Detection is not supported in this vehicle due to a permanent lack of capabilities. Clients
+ * need not retry.
+ */
+ NOT_SUPPORTED = 1,
+ /*
+ * The system has not yet been initialized. No requests can be served until the
+ * initialization process completes. This state does not indicate any error and
+ * clients should retry later.
+ */
+ NOT_INITIALIZED = 2,
+ /*
+ * A permanent failure has occurred. No detections will be provided.
+ */
+ FAILURE = 3,
+}
diff --git a/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/OccupantDetection.aidl b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/OccupantDetection.aidl
new file mode 100644
index 0000000..47ca35a
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/OccupantDetection.aidl
@@ -0,0 +1,50 @@
+/*
+ * 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.automotive.occupant_awareness;
+
+import android.hardware.automotive.occupant_awareness.Role;
+import android.hardware.automotive.occupant_awareness.PresenceDetection;
+import android.hardware.automotive.occupant_awareness.GazeDetection;
+import android.hardware.automotive.occupant_awareness.DriverMonitoringDetection;
+
+/*
+ * A complete detection for a single occupant in the vehicle. Includes data about the subject's
+ * presence in the vehicle, gaze and attention.
+ */
+ @VintfStability
+parcelable OccupantDetection {
+ /*
+ * Role of the occupant (e.g., driver, passenger).
+ */
+ Role role;
+ /*
+ * Occupant presence state for a single occupant.
+ * If the vector is empty, no data could be generated.
+ */
+ PresenceDetection[] presenceData;
+ /*
+ * Gaze data for a single occupant.
+ * If the vector is empty, no data could be generated.
+ */
+ GazeDetection[] gazeData;
+ /*
+ * Attention data for a single occupant.
+ * If the vector is empty, no data could be generated.
+ */
+ DriverMonitoringDetection[] attentionData;
+}
+
diff --git a/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/OccupantDetections.aidl b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/OccupantDetections.aidl
new file mode 100644
index 0000000..e8f6621
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/OccupantDetections.aidl
@@ -0,0 +1,34 @@
+/*
+ * 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.automotive.occupant_awareness;
+
+import android.hardware.automotive.occupant_awareness.OccupantDetection;
+
+@VintfStability
+parcelable OccupantDetections {
+ /**
+ * Timestamp that the underlying source image was captured, in milliseconds since Jan 1, 1970
+ * (Unix time).
+ */
+ long timeStampMillis;
+ /**
+ * A vector of detections for all occupants in the vehicle. One OccupantDetection will be
+ * generated per detected face.
+ */
+ OccupantDetection[] detections;
+}
+
diff --git a/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/PresenceDetection.aidl b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/PresenceDetection.aidl
new file mode 100644
index 0000000..a018106
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/PresenceDetection.aidl
@@ -0,0 +1,31 @@
+/*
+ * 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.automotive.occupant_awareness;
+
+@VintfStability
+parcelable PresenceDetection {
+ /*
+ * Boolean representing whether an occupant was detected.
+ */
+ boolean isOccupantDetected;
+ /**
+ * Duration that a particular occupant has been continuously
+ * detected, in milliseconds. Will be zero duration if the occupant is not
+ * currently detected.
+ */
+ long detectionDurationMillis;
+}
diff --git a/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/Role.aidl b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/Role.aidl
new file mode 100644
index 0000000..42e86ad
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/Role.aidl
@@ -0,0 +1,83 @@
+/*
+ * 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.automotive.occupant_awareness;
+
+@VintfStability
+@Backing(type="int")
+enum Role {
+ /*
+ * All valid role(s) must have at least 1 bit set.
+ */
+ INVALID = 0,
+ /*
+ * System could not determine role for this occupant.
+ */
+ UNKNOWN = 1 << 0,
+ /*
+ * Occupants that the system detects as front seat passengers.
+ */
+ FRONT_PASSENGER = 1 << 1,
+ /*
+ * Occupants that the system detects as driver(s).
+ */
+ DRIVER = 1 << 2,
+ /*
+ * Occupants on left seat of row 2.
+ */
+ ROW_2_PASSENGER_LEFT = 1 << 3,
+ /*
+ * Occupants on center seat of row 2.
+ */
+ ROW_2_PASSENGER_CENTER = 1 << 4,
+ /*
+ * Occupants on right seat of row 2.
+ */
+ ROW_2_PASSENGER_RIGHT = 1 << 5,
+ /*
+ * Occupants on left seat of row 3.
+ */
+ ROW_3_PASSENGER_LEFT = 1 << 6,
+ /*
+ * Occupants on center seat of row 3.
+ */
+ ROW_3_PASSENGER_CENTER = 1 << 7,
+ /*
+ * Occupants on right seat of row 3.
+ */
+ ROW_3_PASSENGER_RIGHT = 1 << 8,
+
+ /*
+ * Occupants that the system detects as front seat occupant.
+ * FRONT_OCCUPANTS = DRIVER | FRONT_PASSENGER
+ */
+ FRONT_OCCUPANTS = 1 << 1 | 1 << 2,
+ /*
+ * Occupants of row 2.
+ * ROW_2_OCCUPANTS = ROW_2_PASSENGER_LEFT | ROW_2_PASSENGER_CENTER | ROW_2_PASSENGER_RIGHT
+ */
+ ROW_2_OCCUPANTS = 1 << 3 | 1 << 4 | 1 << 5,
+ /*
+ * Occupants of row 3.
+ * ROW_3_OCCUPANTS = ROW_3_PASSENGER_LEFT | ROW_3_PASSENGER_CENTER | ROW_3_PASSENGER_RIGHT
+ */
+ ROW_3_OCCUPANTS = 1 << 6 | 1 << 7 | 1 << 8,
+ /*
+ * All the occupants in the vehicle.
+ * ALL_OCCUPANTS = UNKNOWN | FRONT_OCCUPANTS | ROW_2_OCCUPANTS | ROW_3_OCCUPANTS
+ */
+ ALL_OCCUPANTS = 0x1FF,
+}
diff --git a/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/VehicleRegion.aidl b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/VehicleRegion.aidl
new file mode 100644
index 0000000..9ee9d52
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/android/hardware/automotive/occupant_awareness/VehicleRegion.aidl
@@ -0,0 +1,39 @@
+/*
+ * 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.automotive.occupant_awareness;
+
+@VintfStability
+@Backing(type="int")
+enum VehicleRegion {
+ /*
+ * List of targets in the car.
+ */
+ UNKNOWN = 0,
+ INSTRUMENT_CLUSTER = 1,
+ REAR_VIEW_MIRROR = 2,
+ LEFT_SIDE_MIRROR = 3,
+ RIGHT_SIDE_MIRROR = 4,
+ FORWARD_ROADWAY = 5,
+ LEFT_ROADWAY = 6,
+ RIGHT_ROADWAY = 7,
+ HEAD_UNIT_DISPLAY = 8,
+ /*
+ * Vendors can use this value along with customGazeTarget string to uniquely identify their
+ * custom region.
+ */
+ CUSTOM_TARGET = 200,
+}
diff --git a/automotive/occupant_awareness/aidl/default/Android.bp b/automotive/occupant_awareness/aidl/default/Android.bp
new file mode 100644
index 0000000..1b2fba2
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/default/Android.bp
@@ -0,0 +1,32 @@
+/*
+ * 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_binary {
+ name: "android.hardware.automotive.occupant_awareness@1.0-service",
+ init_rc: ["android.hardware.automotive.occupant_awareness@1.0-service.rc"],
+ relative_install_path: "hw",
+ vendor: true,
+ srcs: [
+ "service.cpp",
+ "OccupantAwareness.cpp",
+ ],
+ shared_libs: [
+ "libbase",
+ "libbinder_ndk",
+ "libutils",
+ "android.hardware.automotive.occupant_awareness-ndk_platform",
+ ],
+}
diff --git a/automotive/occupant_awareness/aidl/default/OccupantAwareness.cpp b/automotive/occupant_awareness/aidl/default/OccupantAwareness.cpp
new file mode 100644
index 0000000..a156075
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/default/OccupantAwareness.cpp
@@ -0,0 +1,122 @@
+/*
+ * 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.
+ */
+
+#include "OccupantAwareness.h"
+
+namespace android {
+namespace hardware {
+namespace automotive {
+namespace occupant_awareness {
+namespace V1_0 {
+namespace implementation {
+
+using ndk::ScopedAStatus;
+
+static const int32_t kAllCapabilities = OccupantAwareness::CAP_PRESENCE_DETECTION |
+ OccupantAwareness::CAP_GAZE_DETECTION |
+ OccupantAwareness::CAP_DRIVER_MONITORING_DETECTION;
+
+ScopedAStatus OccupantAwareness::startDetection(OccupantAwarenessStatus* status) {
+ std::lock_guard<std::mutex> lock(mMutex);
+ if (mStatus != OccupantAwarenessStatus::NOT_SUPPORTED) {
+ mStatus = OccupantAwarenessStatus::NOT_SUPPORTED;
+ if (mCallback) {
+ mCallback->onSystemStatusChanged(kAllCapabilities,
+ OccupantAwarenessStatus::NOT_SUPPORTED);
+ }
+ }
+ *status = mStatus;
+ return ScopedAStatus::ok();
+}
+
+ScopedAStatus OccupantAwareness::stopDetection(OccupantAwarenessStatus* status) {
+ std::lock_guard<std::mutex> lock(mMutex);
+ if (mStatus != OccupantAwarenessStatus::NOT_INITIALIZED) {
+ mStatus = OccupantAwarenessStatus::NOT_INITIALIZED;
+ if (mCallback) {
+ mCallback->onSystemStatusChanged(kAllCapabilities,
+ OccupantAwarenessStatus::NOT_INITIALIZED);
+ }
+ }
+ *status = mStatus;
+ return ScopedAStatus::ok();
+}
+
+ScopedAStatus OccupantAwareness::getCapabilityForRole(Role occupantRole, int32_t* capabilities) {
+ if (!isValidRole(occupantRole)) {
+ return ScopedAStatus::fromExceptionCode(EX_TRANSACTION_FAILED);
+ }
+
+ // No awareness capability for default HAL.
+ *capabilities = 0;
+ return ScopedAStatus::ok();
+}
+
+ScopedAStatus OccupantAwareness::getState(Role occupantRole, int detectionCapability,
+ OccupantAwarenessStatus* status) {
+ if (!isValidRole(occupantRole)) {
+ return ScopedAStatus::fromExceptionCode(EX_TRANSACTION_FAILED);
+ }
+
+ if (!isValidDetectionCapabilities(detectionCapability) ||
+ !isSingularCapability(detectionCapability)) {
+ return ScopedAStatus::fromExceptionCode(EX_TRANSACTION_FAILED);
+ }
+
+ std::lock_guard<std::mutex> lock(mMutex);
+ *status = mStatus;
+ return ScopedAStatus::ok();
+}
+
+ScopedAStatus OccupantAwareness::setCallback(
+ const std::shared_ptr<IOccupantAwarenessClientCallback>& callback) {
+ if (callback == nullptr) {
+ return ScopedAStatus::fromExceptionCode(EX_TRANSACTION_FAILED);
+ }
+
+ std::lock_guard<std::mutex> lock(mMutex);
+ mCallback = callback;
+ return ScopedAStatus::ok();
+}
+
+ScopedAStatus OccupantAwareness::getLatestDetection(OccupantDetections* detections) {
+ // No detection generated for default hal.
+ (void)detections;
+ return ScopedAStatus::fromExceptionCode(EX_TRANSACTION_FAILED);
+}
+
+bool OccupantAwareness::isValidRole(Role occupantRole) {
+ int intVal = static_cast<int>(occupantRole);
+ int allOccupants = static_cast<int>(Role::ALL_OCCUPANTS);
+ return (occupantRole != Role::INVALID) && ((intVal & (~allOccupants)) == 0);
+}
+
+bool OccupantAwareness::isValidDetectionCapabilities(int detectionCapabilities) {
+ return (detectionCapabilities != CAP_NONE) &&
+ ((detectionCapabilities & (~kAllCapabilities)) == 0);
+}
+
+bool OccupantAwareness::isSingularCapability(int detectionCapability) {
+ // Check whether the value is 0, or the value has only one bit set.
+ return (detectionCapability & (detectionCapability - 1)) == 0;
+}
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace occupant_awareness
+} // namespace automotive
+} // namespace hardware
+} // namespace android
diff --git a/automotive/occupant_awareness/aidl/default/OccupantAwareness.h b/automotive/occupant_awareness/aidl/default/OccupantAwareness.h
new file mode 100644
index 0000000..ac51aa4
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/default/OccupantAwareness.h
@@ -0,0 +1,67 @@
+/*
+ * 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.
+ */
+
+#pragma once
+#include <aidl/android/hardware/automotive/occupant_awareness/BnOccupantAwareness.h>
+#include <aidl/android/hardware/automotive/occupant_awareness/BnOccupantAwarenessClientCallback.h>
+#include <utils/StrongPointer.h>
+
+namespace android {
+namespace hardware {
+namespace automotive {
+namespace occupant_awareness {
+namespace V1_0 {
+namespace implementation {
+
+using ::aidl::android::hardware::automotive::occupant_awareness::BnOccupantAwareness;
+using ::aidl::android::hardware::automotive::occupant_awareness::IOccupantAwarenessClientCallback;
+using ::aidl::android::hardware::automotive::occupant_awareness::OccupantAwarenessStatus;
+using ::aidl::android::hardware::automotive::occupant_awareness::OccupantDetections;
+using ::aidl::android::hardware::automotive::occupant_awareness::Role;
+
+/**
+ * The default HAL mimics a system which has no Occupant awareness capability. The hal does not
+ * do any useful work, and returns appropriate failure code / status.
+ **/
+class OccupantAwareness : public BnOccupantAwareness {
+ public:
+ // Methods from ::android::hardware::automotive::occupant_awareness::IOccupantAwareness
+ // follow.
+ ndk::ScopedAStatus startDetection(OccupantAwarenessStatus* status) override;
+ ndk::ScopedAStatus stopDetection(OccupantAwarenessStatus* status) override;
+ ndk::ScopedAStatus getCapabilityForRole(Role occupantRole, int32_t* capabilities) override;
+ ndk::ScopedAStatus getState(Role occupantRole, int detectionCapability,
+ OccupantAwarenessStatus* status) override;
+ ndk::ScopedAStatus setCallback(
+ const std::shared_ptr<IOccupantAwarenessClientCallback>& callback) override;
+ ndk::ScopedAStatus getLatestDetection(OccupantDetections* detections) override;
+
+ private:
+ bool isValidRole(Role occupantRole);
+ bool isValidDetectionCapabilities(int detectionCapabilities);
+ bool isSingularCapability(int detectionCapability);
+
+ std::mutex mMutex;
+ std::shared_ptr<IOccupantAwarenessClientCallback> mCallback = nullptr;
+ OccupantAwarenessStatus mStatus = OccupantAwarenessStatus::NOT_INITIALIZED;
+};
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace occupant_awareness
+} // namespace automotive
+} // namespace hardware
+} // namespace android
diff --git a/automotive/occupant_awareness/aidl/default/android.hardware.automotive.occupant_awareness@1.0-service.rc b/automotive/occupant_awareness/aidl/default/android.hardware.automotive.occupant_awareness@1.0-service.rc
new file mode 100644
index 0000000..35d5bca
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/default/android.hardware.automotive.occupant_awareness@1.0-service.rc
@@ -0,0 +1,4 @@
+service hal_occupant_awareness_default /vendor/bin/hw/android.hardware.automotive.occupant_awareness@1.0-service
+ class hal
+ user system
+ group system
diff --git a/automotive/occupant_awareness/aidl/default/service.cpp b/automotive/occupant_awareness/aidl/default/service.cpp
new file mode 100644
index 0000000..44960fb
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/default/service.cpp
@@ -0,0 +1,55 @@
+/*
+ * Copyright (C) 2016 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 "android.hardware.automotive.occupant_awareness@1.0-service"
+
+#include <unistd.h>
+
+#include <android-base/logging.h>
+#include <android/binder_manager.h>
+#include <android/binder_process.h>
+
+#include "OccupantAwareness.h"
+
+using ::aidl::android::hardware::automotive::occupant_awareness::IOccupantAwareness;
+using ::android::hardware::automotive::occupant_awareness::V1_0::implementation::OccupantAwareness;
+using ::ndk::ScopedAStatus;
+using ::ndk::SharedRefBase;
+
+const static char kOccupantAwarenessServiceName[] = "default";
+
+int main() {
+ ABinderProcess_setThreadPoolMaxThreadCount(0);
+ LOG(INFO) << "Occupant Awareness service is starting";
+ std::shared_ptr<OccupantAwareness> occupantAwareness = SharedRefBase::make<OccupantAwareness>();
+
+ const std::string instance =
+ std::string() + IOccupantAwareness::descriptor + "/" + kOccupantAwarenessServiceName;
+
+ binder_status_t status =
+ AServiceManager_addService(occupantAwareness->asBinder().get(), instance.c_str());
+ if (status == STATUS_OK) {
+ LOG(INFO) << "Service " << kOccupantAwarenessServiceName << " is ready";
+ ABinderProcess_joinThreadPool();
+ } else {
+ LOG(ERROR) << "Could not register service " << kOccupantAwarenessServiceName
+ << ", status: " << status;
+ }
+
+ // In normal operation, we don't expect the thread pool to exit.
+ LOG(ERROR) << "Occupant Awareness service is shutting down";
+ return 1;
+}
diff --git a/automotive/occupant_awareness/aidl/mock/Android.bp b/automotive/occupant_awareness/aidl/mock/Android.bp
new file mode 100644
index 0000000..4b30866
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/mock/Android.bp
@@ -0,0 +1,32 @@
+/*
+ * 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_binary {
+ name: "android.hardware.automotive.occupant_awareness@1.0-service_mock",
+ relative_install_path: "hw",
+ vendor: true,
+ srcs: [
+ "service.cpp",
+ "OccupantAwareness.cpp",
+ "DetectionGenerator.cpp",
+ ],
+ shared_libs: [
+ "libbase",
+ "libbinder_ndk",
+ "libutils",
+ "android.hardware.automotive.occupant_awareness-ndk_platform",
+ ],
+}
diff --git a/automotive/occupant_awareness/aidl/mock/DetectionGenerator.cpp b/automotive/occupant_awareness/aidl/mock/DetectionGenerator.cpp
new file mode 100644
index 0000000..79d4dbc
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/mock/DetectionGenerator.cpp
@@ -0,0 +1,71 @@
+/*
+ * 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.
+ */
+
+#include <utils/SystemClock.h>
+
+#include "DetectionGenerator.h"
+
+namespace android {
+namespace hardware {
+namespace automotive {
+namespace occupant_awareness {
+namespace V1_0 {
+namespace implementation {
+
+using ::aidl::android::hardware::automotive::occupant_awareness::ConfidenceLevel;
+using ::aidl::android::hardware::automotive::occupant_awareness::DriverMonitoringDetection;
+using ::aidl::android::hardware::automotive::occupant_awareness::OccupantDetection;
+using ::aidl::android::hardware::automotive::occupant_awareness::PresenceDetection;
+
+static int64_t kNanoSecondsPerMilliSecond = 1000 * 1000;
+
+OccupantDetections DetectionGenerator::GetNextDetections() {
+ OccupantDetections detections;
+ detections.timeStampMillis = android::elapsedRealtimeNano() / kNanoSecondsPerMilliSecond;
+ int remainingRoles = getSupportedRoles();
+ while (remainingRoles) {
+ int currentRole = remainingRoles & (~(remainingRoles - 1));
+ remainingRoles = remainingRoles & (remainingRoles - 1);
+
+ OccupantDetection occupantDetection;
+ occupantDetection.role = static_cast<Role>(currentRole);
+
+ // Add presence detection object for this occupant.
+ PresenceDetection presenceDetection;
+ presenceDetection.isOccupantDetected = true;
+ presenceDetection.detectionDurationMillis = detections.timeStampMillis;
+ occupantDetection.presenceData.emplace_back(presenceDetection);
+
+ if (occupantDetection.role == Role::DRIVER) {
+ // Add driver monitoring detection object for this occupant.
+ DriverMonitoringDetection driverMonitoringDetection;
+ driverMonitoringDetection.confidenceScore = ConfidenceLevel::HIGH;
+ driverMonitoringDetection.isLookingOnRoad = 0;
+ driverMonitoringDetection.gazeDurationMillis = detections.timeStampMillis;
+ occupantDetection.attentionData.emplace_back(driverMonitoringDetection);
+ }
+
+ detections.detections.emplace_back(occupantDetection);
+ }
+ return detections;
+}
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace occupant_awareness
+} // namespace automotive
+} // namespace hardware
+} // namespace android
diff --git a/automotive/occupant_awareness/aidl/mock/DetectionGenerator.h b/automotive/occupant_awareness/aidl/mock/DetectionGenerator.h
new file mode 100644
index 0000000..0884685
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/mock/DetectionGenerator.h
@@ -0,0 +1,50 @@
+/*
+ * 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.
+ */
+
+#pragma once
+
+#include <aidl/android/hardware/automotive/occupant_awareness/BnOccupantAwareness.h>
+
+namespace android {
+namespace hardware {
+namespace automotive {
+namespace occupant_awareness {
+namespace V1_0 {
+namespace implementation {
+
+using ::aidl::android::hardware::automotive::occupant_awareness::BnOccupantAwareness;
+using ::aidl::android::hardware::automotive::occupant_awareness::OccupantDetections;
+using ::aidl::android::hardware::automotive::occupant_awareness::Role;
+
+class DetectionGenerator {
+ public:
+ static int getSupportedRoles() {
+ return static_cast<int>(Role::DRIVER) | static_cast<int>(Role::FRONT_PASSENGER);
+ }
+ static int getSupportedCapabilities() {
+ return static_cast<int>(BnOccupantAwareness::CAP_PRESENCE_DETECTION) |
+ static_cast<int>(BnOccupantAwareness::CAP_DRIVER_MONITORING_DETECTION);
+ }
+
+ OccupantDetections GetNextDetections();
+};
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace occupant_awareness
+} // namespace automotive
+} // namespace hardware
+} // namespace android
diff --git a/automotive/occupant_awareness/aidl/mock/OccupantAwareness.cpp b/automotive/occupant_awareness/aidl/mock/OccupantAwareness.cpp
new file mode 100644
index 0000000..910760a
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/mock/OccupantAwareness.cpp
@@ -0,0 +1,176 @@
+/*
+ * 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.
+ */
+
+#include <utils/SystemClock.h>
+
+#include "OccupantAwareness.h"
+
+namespace android {
+namespace hardware {
+namespace automotive {
+namespace occupant_awareness {
+namespace V1_0 {
+namespace implementation {
+
+using ndk::ScopedAStatus;
+
+static const int32_t kAllCapabilities = OccupantAwareness::CAP_PRESENCE_DETECTION |
+ OccupantAwareness::CAP_GAZE_DETECTION |
+ OccupantAwareness::CAP_DRIVER_MONITORING_DETECTION;
+
+constexpr int64_t kNanoSecondsPerMilliSecond = 1000 * 1000;
+
+ScopedAStatus OccupantAwareness::startDetection(OccupantAwarenessStatus* status) {
+ std::lock_guard<std::mutex> lock(mMutex);
+ if (mStatus != OccupantAwarenessStatus::NOT_INITIALIZED) {
+ return ScopedAStatus::fromExceptionCode(EX_TRANSACTION_FAILED);
+ }
+
+ mStatus = OccupantAwarenessStatus::READY;
+ mWorkerThread = std::thread(startWorkerThread, this);
+ if (mCallback) {
+ mCallback->onSystemStatusChanged(kAllCapabilities, mStatus);
+ }
+
+ *status = mStatus;
+ return ScopedAStatus::ok();
+}
+
+ScopedAStatus OccupantAwareness::stopDetection(OccupantAwarenessStatus* status) {
+ std::lock_guard<std::mutex> lock(mMutex);
+ if (mStatus != OccupantAwarenessStatus::READY) {
+ return ScopedAStatus::fromExceptionCode(EX_TRANSACTION_FAILED);
+ }
+
+ mStatus = OccupantAwarenessStatus::NOT_INITIALIZED;
+ mWorkerThread.join();
+ if (mCallback) {
+ mCallback->onSystemStatusChanged(kAllCapabilities, mStatus);
+ }
+
+ *status = mStatus;
+ return ScopedAStatus::ok();
+}
+
+ScopedAStatus OccupantAwareness::getCapabilityForRole(Role occupantRole, int32_t* capabilities) {
+ if (!isValidRole(occupantRole)) {
+ return ScopedAStatus::fromExceptionCode(EX_TRANSACTION_FAILED);
+ }
+
+ int intVal = static_cast<int>(occupantRole);
+ if ((intVal & DetectionGenerator::getSupportedRoles()) == intVal) {
+ int capabilities_ = DetectionGenerator::getSupportedCapabilities();
+ if (occupantRole != Role::DRIVER) {
+ capabilities_ &= ~CAP_DRIVER_MONITORING_DETECTION;
+ }
+ *capabilities = capabilities_;
+ } else {
+ *capabilities = 0;
+ }
+
+ return ScopedAStatus::ok();
+}
+
+ScopedAStatus OccupantAwareness::getState(Role occupantRole, int detectionCapability,
+ OccupantAwarenessStatus* status) {
+ if (!isValidRole(occupantRole)) {
+ return ScopedAStatus::fromExceptionCode(EX_TRANSACTION_FAILED);
+ }
+
+ if (!isValidDetectionCapabilities(detectionCapability) ||
+ !isSingularCapability(detectionCapability)) {
+ return ScopedAStatus::fromExceptionCode(EX_TRANSACTION_FAILED);
+ }
+
+ int roleVal = static_cast<int>(occupantRole);
+
+ if (((roleVal & DetectionGenerator::getSupportedRoles()) != roleVal) ||
+ ((detectionCapability & DetectionGenerator::getSupportedCapabilities()) !=
+ detectionCapability)) {
+ *status = OccupantAwarenessStatus::NOT_SUPPORTED;
+ return ScopedAStatus::ok();
+ }
+
+ std::lock_guard<std::mutex> lock(mMutex);
+ *status = mStatus;
+ return ScopedAStatus::ok();
+}
+
+ScopedAStatus OccupantAwareness::setCallback(
+ const std::shared_ptr<IOccupantAwarenessClientCallback>& callback) {
+ if (callback == nullptr) {
+ return ScopedAStatus::fromExceptionCode(EX_TRANSACTION_FAILED);
+ }
+
+ std::lock_guard<std::mutex> lock(mMutex);
+ mCallback = callback;
+ return ScopedAStatus::ok();
+}
+
+ScopedAStatus OccupantAwareness::getLatestDetection(OccupantDetections* detections) {
+ std::lock_guard<std::mutex> lock(mMutex);
+
+ if (mStatus != OccupantAwarenessStatus::READY) {
+ return ScopedAStatus::fromExceptionCode(EX_TRANSACTION_FAILED);
+ }
+
+ *detections = mLatestDetections;
+ return ScopedAStatus::ok();
+}
+
+bool OccupantAwareness::isValidRole(Role occupantRole) {
+ int intVal = static_cast<int>(occupantRole);
+ int allOccupants = static_cast<int>(Role::ALL_OCCUPANTS);
+ return (occupantRole != Role::INVALID) && ((intVal & (~allOccupants)) == 0);
+}
+
+bool OccupantAwareness::isValidDetectionCapabilities(int detectionCapabilities) {
+ return (detectionCapabilities != OccupantAwareness::CAP_NONE) &&
+ ((detectionCapabilities & (~kAllCapabilities)) == 0);
+}
+
+bool OccupantAwareness::isSingularCapability(int detectionCapability) {
+ // Check whether the value is 0, or the value has only one bit set.
+ return (detectionCapability & (detectionCapability - 1)) == 0;
+}
+
+void OccupantAwareness::startWorkerThread(OccupantAwareness* occupantAwareness) {
+ occupantAwareness->workerThreadFunction();
+}
+
+void OccupantAwareness::workerThreadFunction() {
+ bool isFirstDetection = true;
+ int64_t prevDetectionTimeMs;
+ while (mStatus == OccupantAwarenessStatus::READY) {
+ int64_t currentTimeMs = android::elapsedRealtimeNano() / kNanoSecondsPerMilliSecond;
+ if ((isFirstDetection) || (currentTimeMs - prevDetectionTimeMs > mDetectionDurationMs)) {
+ std::lock_guard<std::mutex> lock(mMutex);
+ mLatestDetections = mGenerator.GetNextDetections();
+ if (mCallback != nullptr) {
+ mCallback->onDetectionEvent(mLatestDetections);
+ }
+ isFirstDetection = false;
+ prevDetectionTimeMs = currentTimeMs;
+ }
+ }
+}
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace occupant_awareness
+} // namespace automotive
+} // namespace hardware
+} // namespace android
diff --git a/automotive/occupant_awareness/aidl/mock/OccupantAwareness.h b/automotive/occupant_awareness/aidl/mock/OccupantAwareness.h
new file mode 100644
index 0000000..c5f6dd6
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/mock/OccupantAwareness.h
@@ -0,0 +1,83 @@
+/*
+ * 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.
+ */
+
+#pragma once
+
+#include <thread>
+
+#include <aidl/android/hardware/automotive/occupant_awareness/BnOccupantAwareness.h>
+#include <aidl/android/hardware/automotive/occupant_awareness/BnOccupantAwarenessClientCallback.h>
+#include <utils/StrongPointer.h>
+
+#include "DetectionGenerator.h"
+
+namespace android {
+namespace hardware {
+namespace automotive {
+namespace occupant_awareness {
+namespace V1_0 {
+namespace implementation {
+
+using ::aidl::android::hardware::automotive::occupant_awareness::BnOccupantAwareness;
+using ::aidl::android::hardware::automotive::occupant_awareness::IOccupantAwarenessClientCallback;
+using ::aidl::android::hardware::automotive::occupant_awareness::OccupantAwarenessStatus;
+using ::aidl::android::hardware::automotive::occupant_awareness::OccupantDetections;
+using ::aidl::android::hardware::automotive::occupant_awareness::Role;
+
+/**
+ * The mock HAL can detect presence of Driver and front passenger, and driver awareness detection
+ * for driver.
+ **/
+class OccupantAwareness : public BnOccupantAwareness {
+ public:
+ // Methods from ::android::hardware::automotive::occupant_awareness::IOccupantAwareness
+ // follow.
+ ndk::ScopedAStatus startDetection(OccupantAwarenessStatus* status) override;
+ ndk::ScopedAStatus stopDetection(OccupantAwarenessStatus* status) override;
+ ndk::ScopedAStatus getCapabilityForRole(Role occupantRole, int32_t* capabilities) override;
+ ndk::ScopedAStatus getState(Role occupantRole, int detectionCapability,
+ OccupantAwarenessStatus* status) override;
+ ndk::ScopedAStatus setCallback(
+ const std::shared_ptr<IOccupantAwarenessClientCallback>& callback) override;
+ ndk::ScopedAStatus getLatestDetection(OccupantDetections* detections) override;
+
+ private:
+ bool isValidRole(Role occupantRole);
+ bool isValidDetectionCapabilities(int detectionCapabilities);
+ bool isSingularCapability(int detectionCapability);
+
+ void workerThreadFunction();
+ static void startWorkerThread(OccupantAwareness* occupantAwareness);
+
+ std::mutex mMutex;
+ std::shared_ptr<IOccupantAwarenessClientCallback> mCallback = nullptr;
+ OccupantAwarenessStatus mStatus = OccupantAwarenessStatus::NOT_INITIALIZED;
+
+ OccupantDetections mLatestDetections;
+ std::thread mWorkerThread;
+
+ DetectionGenerator mGenerator;
+
+ // Generate a new detection every 1ms.
+ const int64_t mDetectionDurationMs = 1;
+};
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace occupant_awareness
+} // namespace automotive
+} // namespace hardware
+} // namespace android
diff --git a/automotive/occupant_awareness/aidl/mock/service.cpp b/automotive/occupant_awareness/aidl/mock/service.cpp
new file mode 100644
index 0000000..d8860df
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/mock/service.cpp
@@ -0,0 +1,55 @@
+/*
+ * Copyright (C) 2016 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 "android.hardware.automotive.occupant_awareness@1.0-service_mock"
+
+#include <unistd.h>
+
+#include <android-base/logging.h>
+#include <android/binder_manager.h>
+#include <android/binder_process.h>
+
+#include "OccupantAwareness.h"
+
+using ::aidl::android::hardware::automotive::occupant_awareness::IOccupantAwareness;
+using ::android::hardware::automotive::occupant_awareness::V1_0::implementation::OccupantAwareness;
+using ::ndk::ScopedAStatus;
+using ::ndk::SharedRefBase;
+
+const static char kOccupantAwarenessServiceName[] = "default";
+
+int main() {
+ ABinderProcess_setThreadPoolMaxThreadCount(0);
+ LOG(INFO) << "Occupant Awareness service is starting";
+ std::shared_ptr<OccupantAwareness> occupantAwareness = SharedRefBase::make<OccupantAwareness>();
+
+ const std::string instance =
+ std::string() + IOccupantAwareness::descriptor + "/" + kOccupantAwarenessServiceName;
+
+ binder_status_t status =
+ AServiceManager_addService(occupantAwareness->asBinder().get(), instance.c_str());
+ if (status == STATUS_OK) {
+ LOG(INFO) << "Service " << kOccupantAwarenessServiceName << " is ready";
+ ABinderProcess_joinThreadPool();
+ } else {
+ LOG(ERROR) << "Could not register service " << kOccupantAwarenessServiceName
+ << ", status: " << status;
+ }
+
+ // In normal operation, we don't expect the thread pool to exit.
+ LOG(ERROR) << "Occupant Awareness service is shutting down";
+ return 1;
+}
diff --git a/automotive/occupant_awareness/aidl/vts/functional/Android.bp b/automotive/occupant_awareness/aidl/vts/functional/Android.bp
new file mode 100644
index 0000000..1256b69
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/vts/functional/Android.bp
@@ -0,0 +1,17 @@
+cc_test {
+ name: "VtsHalOccupantAwarenessV1_0TargetTest",
+ defaults: [
+ "VtsHalTargetTestDefaults",
+ "use_libaidlvintf_gtest_helper_static",
+ ],
+ srcs: ["VtsHalOccupantAwarenessV1_0TargetTest.cpp"],
+ shared_libs: [
+ "libbinder",
+ ],
+ static_libs: [
+ "android.hardware.automotive.occupant_awareness-cpp",
+ ],
+ test_suites: [
+ "vts-core",
+ ],
+}
diff --git a/automotive/occupant_awareness/aidl/vts/functional/VtsHalOccupantAwarenessV1_0TargetTest.cpp b/automotive/occupant_awareness/aidl/vts/functional/VtsHalOccupantAwarenessV1_0TargetTest.cpp
new file mode 100644
index 0000000..c431f9d
--- /dev/null
+++ b/automotive/occupant_awareness/aidl/vts/functional/VtsHalOccupantAwarenessV1_0TargetTest.cpp
@@ -0,0 +1,203 @@
+/*
+ * 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 "**** HAL log ****"
+
+#include <aidl/Gtest.h>
+#include <aidl/Vintf.h>
+#include <android-base/logging.h>
+#include <android/hardware/automotive/occupant_awareness/BnOccupantAwarenessClientCallback.h>
+#include <android/hardware/automotive/occupant_awareness/IOccupantAwareness.h>
+#include <binder/IServiceManager.h>
+#include <binder/ProcessState.h>
+#include <gtest/gtest.h>
+
+#include <chrono>
+#include <future>
+#include <vector>
+
+using namespace android::hardware::automotive::occupant_awareness;
+using android::hardware::automotive::occupant_awareness::IOccupantAwareness;
+
+using android::ProcessState;
+using android::sp;
+using android::String16;
+using android::binder::Status;
+
+constexpr auto kTimeout = std::chrono::seconds(3);
+
+#define EXPECT_OK(ret) ASSERT_TRUE((ret).isOk())
+
+class OccupantAwarenessCallback : public BnOccupantAwarenessClientCallback {
+ public:
+ OccupantAwarenessCallback(const std::function<void(int, OccupantAwarenessStatus)>& callback)
+ : mCallback(callback) {}
+ Status onSystemStatusChanged(int detectionFlags, OccupantAwarenessStatus status) override {
+ mCallback(detectionFlags, status);
+ return Status::ok();
+ }
+
+ Status onDetectionEvent(const OccupantDetections& detections) override {
+ (void)detections;
+ return Status::ok();
+ }
+
+ private:
+ std::function<void(int, OccupantAwarenessStatus)> mCallback;
+};
+
+class OccupantAwarenessAidl : public testing::TestWithParam<std::string> {
+ public:
+ virtual void SetUp() override {
+ mOccupantAwarenessService =
+ android::waitForDeclaredService<IOccupantAwareness>(String16(GetParam().c_str()));
+ ASSERT_NE(mOccupantAwarenessService, nullptr);
+ }
+
+ sp<IOccupantAwareness> mOccupantAwarenessService;
+};
+
+// Test that startDetection() returns within the timeout.
+TEST_P(OccupantAwarenessAidl, StartDetectionTest) {
+ auto start = std::chrono::system_clock::now();
+ OccupantAwarenessStatus occupantAwarenessStatus;
+ Status status = mOccupantAwarenessService->startDetection(&occupantAwarenessStatus);
+ auto elapsed = std::chrono::system_clock::now() - start;
+ EXPECT_OK(status);
+ ASSERT_LE(elapsed, kTimeout);
+
+ EXPECT_OK(mOccupantAwarenessService->stopDetection(&occupantAwarenessStatus));
+}
+
+// Test that getCapabilityForRole() returns supported capabilities for the role. The test only
+// verifies that the IPC call returns successfully and does not verify the supported capabilities.
+TEST_P(OccupantAwarenessAidl, GetCapabilityTest) {
+ std::vector<Role> rolesToTest = {Role::FRONT_PASSENGER, Role::DRIVER,
+ Role::ROW_2_PASSENGER_LEFT, Role::ROW_2_PASSENGER_CENTER,
+ Role::ROW_2_PASSENGER_RIGHT, Role::ROW_3_PASSENGER_LEFT,
+ Role::ROW_3_PASSENGER_CENTER, Role::ROW_3_PASSENGER_RIGHT,
+ Role::FRONT_OCCUPANTS, Role::ROW_2_OCCUPANTS,
+ Role::ROW_3_OCCUPANTS, Role::ALL_OCCUPANTS};
+
+ for (auto role : rolesToTest) {
+ int32_t capabilities;
+ EXPECT_OK(mOccupantAwarenessService->getCapabilityForRole(role, &capabilities));
+ }
+}
+
+// Test that getCapabilityForRole() returns failure when arguments are invalid.
+TEST_P(OccupantAwarenessAidl, GetCapabilityFailureTest) {
+ int32_t capabilities;
+ EXPECT_FALSE(
+ mOccupantAwarenessService->getCapabilityForRole(Role::INVALID, &capabilities).isOk());
+
+ Role invalidRole = static_cast<Role>(static_cast<int>(Role::ALL_OCCUPANTS) + 1);
+ EXPECT_FALSE(
+ mOccupantAwarenessService->getCapabilityForRole(invalidRole, &capabilities).isOk());
+}
+
+// Test that getState() returns within the timeout. The test do not attempt to verify the state, but
+// only checks that the IPC call returns successfully.
+TEST_P(OccupantAwarenessAidl, GetStateTest) {
+ std::vector<Role> rolesToTest = {Role::FRONT_PASSENGER, Role::DRIVER,
+ Role::ROW_2_PASSENGER_LEFT, Role::ROW_2_PASSENGER_CENTER,
+ Role::ROW_2_PASSENGER_RIGHT, Role::ROW_3_PASSENGER_LEFT,
+ Role::ROW_3_PASSENGER_CENTER, Role::ROW_3_PASSENGER_RIGHT,
+ Role::FRONT_OCCUPANTS, Role::ROW_2_OCCUPANTS,
+ Role::ROW_3_OCCUPANTS, Role::ALL_OCCUPANTS};
+
+ std::vector<int> detectionCapabilities = {IOccupantAwareness::CAP_PRESENCE_DETECTION,
+ IOccupantAwareness::CAP_GAZE_DETECTION,
+ IOccupantAwareness::CAP_DRIVER_MONITORING_DETECTION};
+
+ for (auto role : rolesToTest) {
+ for (auto detectionCapability : detectionCapabilities) {
+ OccupantAwarenessStatus oasStatus;
+ EXPECT_OK(mOccupantAwarenessService->getState(role, detectionCapability, &oasStatus));
+ }
+ }
+}
+
+// Test that getState() returns failure with invalid args.
+TEST_P(OccupantAwarenessAidl, GetStateFailureTest) {
+ // Verify that getState() returns error when role is invalid (0).
+ OccupantAwarenessStatus oasStatus;
+ EXPECT_FALSE(mOccupantAwarenessService
+ ->getState(Role::INVALID, IOccupantAwareness::CAP_PRESENCE_DETECTION,
+ &oasStatus)
+ .isOk());
+
+ // Verify that getState() returns error when role is invalid (invalid flag).
+ int invalidRole = static_cast<int>(Role::ALL_OCCUPANTS) + 1;
+ EXPECT_FALSE(mOccupantAwarenessService
+ ->getState(static_cast<Role>(invalidRole),
+ IOccupantAwareness::CAP_PRESENCE_DETECTION, &oasStatus)
+ .isOk());
+
+ // Verify that getState() returns error when capability is invalid (none).
+ EXPECT_FALSE(mOccupantAwarenessService
+ ->getState(Role::FRONT_PASSENGER, IOccupantAwareness::CAP_NONE, &oasStatus)
+ .isOk());
+
+ // Verify that getState() returns error when capability is invalid (invalid flag).
+ int invalidDetectionFlags = 0x10;
+ EXPECT_FALSE(mOccupantAwarenessService
+ ->getState(Role::FRONT_PASSENGER, invalidDetectionFlags, &oasStatus)
+ .isOk());
+}
+
+// Test that setCallback() returns within the timeout.
+TEST_P(OccupantAwarenessAidl, SetCallbackTest) {
+ sp<OccupantAwarenessCallback> callback =
+ new OccupantAwarenessCallback([](int detectionFlags, OccupantAwarenessStatus status) {
+ (void)detectionFlags;
+ (void)status;
+ });
+ auto start = std::chrono::system_clock::now();
+ Status status = mOccupantAwarenessService->setCallback(callback);
+ auto elapsed = std::chrono::system_clock::now() - start;
+ EXPECT_OK(status);
+ ASSERT_LE(elapsed, kTimeout);
+}
+
+// Test that setCallback() returns failure with invalid args.
+TEST_P(OccupantAwarenessAidl, SetCallbackFailureTest) {
+ sp<OccupantAwarenessCallback> callback = nullptr;
+ Status status = mOccupantAwarenessService->setCallback(callback);
+ EXPECT_FALSE(status.isOk());
+}
+
+// Test that getLatestDetection() returns within the timeout.
+TEST_P(OccupantAwarenessAidl, GetLatestDetectionTest) {
+ auto start = std::chrono::system_clock::now();
+ OccupantDetections detections;
+ // Do not check status here, since error status is returned when no detection is present.
+ (void)mOccupantAwarenessService->getLatestDetection(&detections);
+ auto elapsed = std::chrono::system_clock::now() - start;
+ ASSERT_LE(elapsed, kTimeout);
+}
+
+INSTANTIATE_TEST_SUITE_P(
+ InstantiationName, OccupantAwarenessAidl,
+ testing::ValuesIn(android::getAidlHalInstanceNames(IOccupantAwareness::descriptor)),
+ android::PrintInstanceNameToString);
+
+int main(int argc, char** argv) {
+ ::testing::InitGoogleTest(&argc, argv);
+ ProcessState::self()->setThreadPoolMaxThreadCount(1);
+ ProcessState::self()->startThreadPool();
+ return RUN_ALL_TESTS();
+}
diff --git a/broadcastradio/1.1/default/service.cpp b/broadcastradio/1.1/default/service.cpp
index f8af0b7..29dc76f 100644
--- a/broadcastradio/1.1/default/service.cpp
+++ b/broadcastradio/1.1/default/service.cpp
@@ -20,6 +20,7 @@
#include "BroadcastRadioFactory.h"
+using android::sp;
using android::hardware::configureRpcThreadpool;
using android::hardware::joinRpcThreadpool;
using android::hardware::broadcastradio::V1_1::implementation::BroadcastRadioFactory;
@@ -27,8 +28,8 @@
int main(int /* argc */, char** /* argv */) {
configureRpcThreadpool(4, true);
- BroadcastRadioFactory broadcastRadioFactory;
- auto status = broadcastRadioFactory.registerAsService();
+ sp<BroadcastRadioFactory> broadcastRadioFactory(new BroadcastRadioFactory());
+ auto status = broadcastRadioFactory->registerAsService();
CHECK_EQ(status, android::OK) << "Failed to register Broadcast Radio HAL implementation";
joinRpcThreadpool();
diff --git a/broadcastradio/2.0/default/service.cpp b/broadcastradio/2.0/default/service.cpp
index 349aba2..bd746fd 100644
--- a/broadcastradio/2.0/default/service.cpp
+++ b/broadcastradio/2.0/default/service.cpp
@@ -19,6 +19,7 @@
#include "BroadcastRadio.h"
#include "VirtualRadio.h"
+using android::sp;
using android::hardware::configureRpcThreadpool;
using android::hardware::joinRpcThreadpool;
using android::hardware::broadcastradio::V2_0::implementation::BroadcastRadio;
@@ -30,13 +31,13 @@
android::base::SetMinimumLogSeverity(android::base::VERBOSE);
configureRpcThreadpool(4, true);
- BroadcastRadio broadcastRadio(gAmFmRadio);
- auto amFmStatus = broadcastRadio.registerAsService("amfm");
+ sp<BroadcastRadio> broadcastRadio(new BroadcastRadio(gAmFmRadio));
+ auto amFmStatus = broadcastRadio->registerAsService("amfm");
CHECK_EQ(amFmStatus, android::OK)
<< "Failed to register Broadcast Radio AM/FM HAL implementation";
- BroadcastRadio dabRadio(gDabRadio);
- auto dabStatus = dabRadio.registerAsService("dab");
+ sp<BroadcastRadio> dabRadio(new BroadcastRadio(gDabRadio));
+ auto dabStatus = dabRadio->registerAsService("dab");
CHECK_EQ(dabStatus, android::OK) << "Failed to register Broadcast Radio DAB HAL implementation";
joinRpcThreadpool();
diff --git a/compatibility_matrices/compatibility_matrix.current.xml b/compatibility_matrices/compatibility_matrix.current.xml
index aecc4e0..8abbd48 100644
--- a/compatibility_matrices/compatibility_matrix.current.xml
+++ b/compatibility_matrices/compatibility_matrix.current.xml
@@ -49,6 +49,13 @@
<instance>default</instance>
</interface>
</hal>
+ <hal format="aidl" optional="true">
+ <name>android.hardware.automotive.occupant_awareness</name>
+ <interface>
+ <name>IOccupantAwareness</name>
+ <instance>default</instance>
+ </interface>
+ </hal>
<hal format="hidl" optional="true">
<name>android.hardware.automotive.vehicle</name>
<version>2.0</version>
diff --git a/current.txt b/current.txt
index 19a3c0f..c716c54 100644
--- a/current.txt
+++ b/current.txt
@@ -585,6 +585,30 @@
fd65298e1e09e0e3c781ab18305920d757dbe55a3b459ce17814ec5cf6dfee99 android.hardware.wifi@1.0::IWifiP2pIface
# HALs released in Android R
+e966a3437d6a98d9d9e14e9d672088771716031900c0deb55a0946c751a03a44 android.hardware.audio@6.0::types
+2736c59abaccacac407ebe80c5e48d446edf015051d05632fb679ba471779e6e android.hardware.audio@6.0::IDevice
+2402876cbc23c0de3690a665eca84fd3857d1808dba5cad25ce272f81ecef8c9 android.hardware.audio@6.0::IDevicesFactory
+bca5379d5065e2e08b6ad7308ffc8a71a972fc0698bec678ea32eea786d01cb5 android.hardware.audio@6.0::IPrimaryDevice
+7318b521ea12fdd4b6e3f381085c71784c810d1ec7a8d701ec2250f3f86712e4 android.hardware.audio@6.0::IStream
+2df5d5866b37776f25079c0e54b54350a2abe4e025a59c9e02a7d3abe8ca00e8 android.hardware.audio@6.0::IStreamIn
+78e4138cc8307c11fc777c3bd376e581ba4ba48196b05ca1d7cdfa515c87b48a android.hardware.audio@6.0::IStreamOut
+997fdaad7a9d17ee7e01feb7031a753e2365e72ad30b11d950e9183fabdf3844 android.hardware.audio@6.0::IStreamOutCallback
+0b291ebd7e94dd1cfaadd41a8b9a80bc9389bbb76f5ad5b3df94db5fe7faea9d android.hardware.audio.common@6.0::types
+817930d58412d662cb45e641c50cb62c727e4a3e3ffe7029a53cad9677b97d58 android.hardware.audio.effect@6.0::types
+525bec6b44f1103869c269a128d51b8dccd73af5340ba863c8886c68357c7faf android.hardware.audio.effect@6.0::IAcousticEchoCancelerEffect
+8d76bbe3719d051a8e9a1dcf9244f37f5b0a491feb249fa48391edf7cb4f3131 android.hardware.audio.effect@6.0::IAutomaticGainControlEffect
+461b1114cb35d89f87e5694e0792ba53c112a7fa9a14d9b95188cf9c4764be23 android.hardware.audio.effect@6.0::IBassBoostEffect
+8bc597d166e07e9eba633267fc2872c4c53d13d3f0025b778c98e13324a165de android.hardware.audio.effect@6.0::IDownmixEffect
+9ee022c81e79da6051fde0836c1c1c4d5414e0c9a6cccc0ce17a90346ceb1391 android.hardware.audio.effect@6.0::IEffect
+75c99a70577d543359910a0b378bcbf5a0d6076712e58e6864cd8803f76c8684 android.hardware.audio.effect@6.0::IEffectBufferProviderCallback
+5910bdd600fc6501a67233a9a3f4f21dda86af08c05497322712600131d1fa8f android.hardware.audio.effect@6.0::IEffectsFactory
+dd377f404a8e71f6191d295e10067db629b0f0c28e594af906f2bea5d87fe2cc android.hardware.audio.effect@6.0::IEnvironmentalReverbEffect
+455e085e136767302ec34d02b51a085c310e79bf500b76dda7c96a7f3637f11a android.hardware.audio.effect@6.0::IEqualizerEffect
+24b5e107a0cbd2b322f764a4d5f7fb8b5d8c337a060b9a4a26b9af050c57b5d0 android.hardware.audio.effect@6.0::ILoudnessEnhancerEffect
+4aae0a13f53a8ce20fad372de2d1d864a0bae194b0f1b1d2c090367af8615af2 android.hardware.audio.effect@6.0::INoiseSuppressionEffect
+5237c42d3913ef569f07bec802568084b615155d05a7951e75085da54856508c android.hardware.audio.effect@6.0::IPresetReverbEffect
+282193799d60bff27a84c65a36218c1e7d8f582f5828e2e059383d1b90aa56bd android.hardware.audio.effect@6.0::IVirtualizerEffect
+0868e00f7c5ee16723bda1a8f57099763d04100ae7126a1c2d3a9a87c844a7e8 android.hardware.audio.effect@6.0::IVisualizerEffect
79e115c8f8970b8b914bafc66df5425e065fda4dcda97222966ef12451d2a1cc android.hardware.bluetooth@1.1::IBluetoothHci
40ab2c6866c18d32baf6e49e3053949e79601f56963a791e93e68b9ee18f718d android.hardware.bluetooth@1.1::IBluetoothHciCallbacks
07d0a252b2d8fa35887908a996ba395cf392968395fc30afab791f46e0c22a52 android.hardware.boot@1.1::IBootControl
@@ -618,8 +642,8 @@
619fc9839ec6e369cfa9b28e3e9412e6885720ff8f9b5750c1b6ffb905120391 android.hardware.wifi.supplicant@1.3::ISupplicantStaIfaceCallback
c9273429fcf98d797d3bb07fdba6f1be95bf960f9255cde169fd1ca4db85f856 android.hardware.wifi.supplicant@1.3::ISupplicantStaNetwork
9b0a3ab6f4f74b971ed094426d8a443e29b512ff03e1ab50c07156396cdb2483 android.hardware.wifi.supplicant@1.3::types
-35cd6586225912718c599421606d69260707e43732d874f2064e28de45c87fac android.hardware.radio@1.5::types
-3f1e2410d9bed4e7d41c6a589fe3a7943bc904b0066e40e0199a7c58427ac4e9 android.hardware.radio@1.5::IRadio
+eaf870a7439838c66127a74e1896c4a2346979c116eb1931785ebb4d353230ae android.hardware.radio@1.5::types
+584001c25a16e3a29d496cff28dee690833cd2bda5376febe01cecd476ce876f android.hardware.radio@1.5::IRadio
3afac66f21a33bc9c4b80481c7d5540038348651d9a7d8af64ea13610af138da android.hardware.radio@1.5::IRadioIndication
caf00e0d942b77b17d7061b38de11e5b19e1da90d4818434cb4916ba89e30686 android.hardware.radio@1.5::IRadioResponse
55f0a15642869ec98a55ea0a5ac049d3e1a6245ff7750deb6bcb7182057eee83 android.hardware.radio.config@1.3::types
diff --git a/gnss/1.1/vts/functional/gnss_hal_test.cpp b/gnss/1.1/vts/functional/gnss_hal_test.cpp
index 2c8a7b1..b87f558 100644
--- a/gnss/1.1/vts/functional/gnss_hal_test.cpp
+++ b/gnss/1.1/vts/functional/gnss_hal_test.cpp
@@ -175,6 +175,48 @@
return hasGnssHalVersion_1_1 && !hasGnssHalVersion_2_0;
}
+GnssConstellationType GnssHalTest::startLocationAndGetNonGpsConstellation() {
+ const int kLocationsToAwait = 3;
+
+ gnss_cb_->location_cbq_.reset();
+ StartAndCheckLocations(kLocationsToAwait);
+ const int location_called_count = gnss_cb_->location_cbq_.calledCount();
+
+ // Tolerate 1 less sv status to handle edge cases in reporting.
+ int sv_status_cbq_size = gnss_cb_->sv_status_cbq_.size();
+ EXPECT_GE(sv_status_cbq_size + 1, kLocationsToAwait);
+ ALOGD("Observed %d GnssSvStatus, while awaiting %d Locations (%d received)", sv_status_cbq_size,
+ kLocationsToAwait, location_called_count);
+
+ // Find first non-GPS constellation to blacklist
+ const int kGnssSvStatusTimeout = 2;
+ GnssConstellationType constellation_to_blacklist = GnssConstellationType::UNKNOWN;
+ for (int i = 0; i < sv_status_cbq_size; ++i) {
+ IGnssCallback::GnssSvStatus gnss_sv_status;
+ gnss_cb_->sv_status_cbq_.retrieve(gnss_sv_status, kGnssSvStatusTimeout);
+ for (uint32_t iSv = 0; iSv < gnss_sv_status.numSvs; iSv++) {
+ const auto& gnss_sv = gnss_sv_status.gnssSvList[iSv];
+ if ((gnss_sv.svFlag & IGnssCallback::GnssSvFlags::USED_IN_FIX) &&
+ (gnss_sv.constellation != GnssConstellationType::UNKNOWN) &&
+ (gnss_sv.constellation != GnssConstellationType::GPS)) {
+ // found a non-GPS constellation
+ constellation_to_blacklist = gnss_sv.constellation;
+ break;
+ }
+ }
+ if (constellation_to_blacklist != GnssConstellationType::UNKNOWN) {
+ break;
+ }
+ }
+
+ if (constellation_to_blacklist == GnssConstellationType::UNKNOWN) {
+ ALOGI("No non-GPS constellations found, constellation blacklist test less effective.");
+ // Proceed functionally to blacklist something.
+ constellation_to_blacklist = GnssConstellationType::GLONASS;
+ }
+ return constellation_to_blacklist;
+}
+
GnssHalTest::GnssCallback::GnssCallback()
: info_cbq_("system_info"),
name_cbq_("name"),
diff --git a/gnss/1.1/vts/functional/gnss_hal_test.h b/gnss/1.1/vts/functional/gnss_hal_test.h
index 169cd62..b0e52be 100644
--- a/gnss/1.1/vts/functional/gnss_hal_test.h
+++ b/gnss/1.1/vts/functional/gnss_hal_test.h
@@ -28,6 +28,7 @@
using android::hardware::gnss::V1_0::GnssLocation;
using android::hardware::gnss::common::GnssCallbackEventQueue;
+using android::hardware::gnss::V1_0::GnssConstellationType;
using android::hardware::gnss::V1_0::GnssLocationFlags;
using android::hardware::gnss::V1_1::IGnss;
using android::hardware::gnss::V1_1::IGnssCallback;
@@ -139,6 +140,16 @@
*/
bool IsGnssHalVersion_1_1() const;
+ /*
+ * startLocationAndGetNonGpsConstellation:
+ * 1. Start location
+ * 2. Find and return first non-GPS constellation
+ *
+ * Note that location is not stopped in this method. The client should call
+ * StopAndClearLocations() after the call.
+ */
+ GnssConstellationType startLocationAndGetNonGpsConstellation();
+
sp<IGnss> gnss_hal_; // GNSS HAL to call into
sp<GnssCallback> gnss_cb_; // Primary callback interface
};
diff --git a/gnss/1.1/vts/functional/gnss_hal_test_cases.cpp b/gnss/1.1/vts/functional/gnss_hal_test_cases.cpp
index 79da84a..afba61f 100644
--- a/gnss/1.1/vts/functional/gnss_hal_test_cases.cpp
+++ b/gnss/1.1/vts/functional/gnss_hal_test_cases.cpp
@@ -352,7 +352,7 @@
}
/*
- * BlacklistConstellation:
+ * BlacklistConstellationWithLocationOff:
*
* 1) Turns on location, waits for 3 locations, ensuring they are valid, and checks corresponding
* GnssStatus for any non-GPS constellations.
@@ -361,50 +361,19 @@
* GnssStatus does not use any constellation but GPS.
* 4a & b) Clean up by turning off location, and send in empty blacklist.
*/
-TEST_P(GnssHalTest, BlacklistConstellation) {
+TEST_P(GnssHalTest, BlacklistConstellationWithLocationOff) {
if (!IsGnssHalVersion_1_1()) {
ALOGI("Test BlacklistConstellation skipped. GNSS HAL version is greater than 1.1.");
return;
}
const int kLocationsToAwait = 3;
-
- gnss_cb_->location_cbq_.reset();
- StartAndCheckLocations(kLocationsToAwait);
- const int location_called_count = gnss_cb_->location_cbq_.calledCount();
-
- // Tolerate 1 less sv status to handle edge cases in reporting.
- int sv_status_cbq_size = gnss_cb_->sv_status_cbq_.size();
- EXPECT_GE(sv_status_cbq_size + 1, kLocationsToAwait);
- ALOGD("Observed %d GnssSvStatus, while awaiting %d Locations (%d received)", sv_status_cbq_size,
- kLocationsToAwait, location_called_count);
-
// Find first non-GPS constellation to blacklist
- const int kGnssSvStatusTimeout = 2;
- GnssConstellationType constellation_to_blacklist = GnssConstellationType::UNKNOWN;
- for (int i = 0; i < sv_status_cbq_size; ++i) {
- IGnssCallback::GnssSvStatus gnss_sv_status;
- gnss_cb_->sv_status_cbq_.retrieve(gnss_sv_status, kGnssSvStatusTimeout);
- for (uint32_t iSv = 0; iSv < gnss_sv_status.numSvs; iSv++) {
- const auto& gnss_sv = gnss_sv_status.gnssSvList[iSv];
- if ((gnss_sv.svFlag & IGnssCallback::GnssSvFlags::USED_IN_FIX) &&
- (gnss_sv.constellation != GnssConstellationType::UNKNOWN) &&
- (gnss_sv.constellation != GnssConstellationType::GPS)) {
- // found a non-GPS constellation
- constellation_to_blacklist = gnss_sv.constellation;
- break;
- }
- }
- if (constellation_to_blacklist != GnssConstellationType::UNKNOWN) {
- break;
- }
- }
+ GnssConstellationType constellation_to_blacklist = startLocationAndGetNonGpsConstellation();
- if (constellation_to_blacklist == GnssConstellationType::UNKNOWN) {
- ALOGI("No non-GPS constellations found, constellation blacklist test less effective.");
- // Proceed functionally to blacklist something.
- constellation_to_blacklist = GnssConstellationType::GLONASS;
- }
+ // Turns off location
+ StopAndClearLocations();
+
IGnssConfiguration::BlacklistedSource source_to_blacklist;
source_to_blacklist.constellation = constellation_to_blacklist;
source_to_blacklist.svid = 0; // documented wildcard for all satellites in this constellation
@@ -418,6 +387,7 @@
sources.resize(1);
sources[0] = source_to_blacklist;
+ // setBlacklist when location is off.
auto result = gnss_configuration_hal->setBlacklist(sources);
ASSERT_TRUE(result.isOk());
EXPECT_TRUE(result);
@@ -429,10 +399,82 @@
StartAndCheckLocations(kLocationsToAwait);
// Tolerate 1 less sv status to handle edge cases in reporting.
- sv_status_cbq_size = gnss_cb_->sv_status_cbq_.size();
+ int sv_status_cbq_size = gnss_cb_->sv_status_cbq_.size();
EXPECT_GE(sv_status_cbq_size + 1, kLocationsToAwait);
ALOGD("Observed %d GnssSvStatus, while awaiting %d Locations", sv_status_cbq_size,
kLocationsToAwait);
+ const int kGnssSvStatusTimeout = 2;
+ for (int i = 0; i < sv_status_cbq_size; ++i) {
+ IGnssCallback::GnssSvStatus gnss_sv_status;
+ gnss_cb_->sv_status_cbq_.retrieve(gnss_sv_status, kGnssSvStatusTimeout);
+ for (uint32_t iSv = 0; iSv < gnss_sv_status.numSvs; iSv++) {
+ const auto& gnss_sv = gnss_sv_status.gnssSvList[iSv];
+ EXPECT_FALSE((gnss_sv.constellation == source_to_blacklist.constellation) &&
+ (gnss_sv.svFlag & IGnssCallback::GnssSvFlags::USED_IN_FIX));
+ }
+ }
+
+ // clean up
+ StopAndClearLocations();
+ sources.resize(0);
+ result = gnss_configuration_hal->setBlacklist(sources);
+ ASSERT_TRUE(result.isOk());
+ EXPECT_TRUE(result);
+}
+
+/*
+ * BlacklistConstellationWithLocationOn:
+ *
+ * 1) Turns on location, waits for 3 locations, ensuring they are valid, and checks corresponding
+ * GnssStatus for any non-GPS constellations.
+ * 2a & b) Turns off location, and blacklist first non-GPS constellations.
+ * 3) Restart location, wait for 3 locations, ensuring they are valid, and checks corresponding
+ * GnssStatus does not use any constellation but GPS.
+ * 4a & b) Clean up by turning off location, and send in empty blacklist.
+ */
+TEST_P(GnssHalTest, BlacklistConstellationWithLocationOn) {
+ if (!IsGnssHalVersion_1_1()) {
+ ALOGI("Test BlacklistConstellation skipped. GNSS HAL version is greater than 1.1.");
+ return;
+ }
+
+ const int kLocationsToAwait = 3;
+ // Find first non-GPS constellation to blacklist
+ GnssConstellationType constellation_to_blacklist = startLocationAndGetNonGpsConstellation();
+
+ IGnssConfiguration::BlacklistedSource source_to_blacklist;
+ source_to_blacklist.constellation = constellation_to_blacklist;
+ source_to_blacklist.svid = 0; // documented wildcard for all satellites in this constellation
+
+ auto gnss_configuration_hal_return = gnss_hal_->getExtensionGnssConfiguration_1_1();
+ ASSERT_TRUE(gnss_configuration_hal_return.isOk());
+ sp<IGnssConfiguration> gnss_configuration_hal = gnss_configuration_hal_return;
+ ASSERT_NE(gnss_configuration_hal, nullptr);
+
+ hidl_vec<IGnssConfiguration::BlacklistedSource> sources;
+ sources.resize(1);
+ sources[0] = source_to_blacklist;
+
+ // setBlacklist when location is still on
+ auto result = gnss_configuration_hal->setBlacklist(sources);
+ ASSERT_TRUE(result.isOk());
+ EXPECT_TRUE(result);
+
+ // Turns off location
+ StopAndClearLocations();
+
+ // retry and ensure constellation not used
+ gnss_cb_->sv_status_cbq_.reset();
+
+ gnss_cb_->location_cbq_.reset();
+ StartAndCheckLocations(kLocationsToAwait);
+
+ // Tolerate 1 less sv status to handle edge cases in reporting.
+ int sv_status_cbq_size = gnss_cb_->sv_status_cbq_.size();
+ EXPECT_GE(sv_status_cbq_size + 1, kLocationsToAwait);
+ ALOGD("Observed %d GnssSvStatus, while awaiting %d Locations", sv_status_cbq_size,
+ kLocationsToAwait);
+ const int kGnssSvStatusTimeout = 2;
for (int i = 0; i < sv_status_cbq_size; ++i) {
IGnssCallback::GnssSvStatus gnss_sv_status;
gnss_cb_->sv_status_cbq_.retrieve(gnss_sv_status, kGnssSvStatusTimeout);
diff --git a/graphics/composer/2.3/utils/vts/include/composer-vts/2.3/ComposerVts.h b/graphics/composer/2.3/utils/vts/include/composer-vts/2.3/ComposerVts.h
index 0d4e5b8..e5ac842 100644
--- a/graphics/composer/2.3/utils/vts/include/composer-vts/2.3/ComposerVts.h
+++ b/graphics/composer/2.3/utils/vts/include/composer-vts/2.3/ComposerVts.h
@@ -49,12 +49,10 @@
public:
Composer();
explicit Composer(const std::string& name);
+ explicit Composer(const sp<IComposer>& composer);
std::unique_ptr<ComposerClient> createClient();
- protected:
- explicit Composer(const sp<IComposer>& composer);
-
private:
const sp<IComposer> mComposer;
};
diff --git a/graphics/composer/2.3/vts/functional/Android.bp b/graphics/composer/2.3/vts/functional/Android.bp
index b729062..fa4823e 100644
--- a/graphics/composer/2.3/vts/functional/Android.bp
+++ b/graphics/composer/2.3/vts/functional/Android.bp
@@ -49,4 +49,6 @@
"android.hardware.graphics.composer@2.2-command-buffer",
"android.hardware.graphics.composer@2.3-command-buffer",
],
+ disable_framework: true,
+ test_suites: ["general-tests", "vts-core"],
}
diff --git a/graphics/composer/2.3/vts/functional/VtsHalGraphicsComposerV2_3TargetTest.cpp b/graphics/composer/2.3/vts/functional/VtsHalGraphicsComposerV2_3TargetTest.cpp
index dafe587..94766af 100644
--- a/graphics/composer/2.3/vts/functional/VtsHalGraphicsComposerV2_3TargetTest.cpp
+++ b/graphics/composer/2.3/vts/functional/VtsHalGraphicsComposerV2_3TargetTest.cpp
@@ -18,13 +18,15 @@
#include <algorithm>
-#include <VtsHalHidlTargetTestBase.h>
#include <android-base/logging.h>
#include <android/hardware/graphics/mapper/2.0/IMapper.h>
#include <composer-command-buffer/2.3/ComposerCommandBuffer.h>
#include <composer-vts/2.1/GraphicsComposerCallback.h>
#include <composer-vts/2.1/TestCommandReader.h>
#include <composer-vts/2.3/ComposerVts.h>
+#include <gtest/gtest.h>
+#include <hidl/GtestPrinter.h>
+#include <hidl/ServiceManagement.h>
#include <mapper-vts/2.0/MapperVts.h>
namespace android {
@@ -43,29 +45,11 @@
using mapper::V2_0::IMapper;
using V2_2::vts::Gralloc;
-// Test environment for graphics.composer
-class GraphicsComposerHidlEnvironment : public ::testing::VtsHalHidlTargetTestEnvBase {
- public:
- // get the test environment singleton
- static GraphicsComposerHidlEnvironment* Instance() {
- static GraphicsComposerHidlEnvironment* instance = new GraphicsComposerHidlEnvironment;
- return instance;
- }
-
- virtual void registerTestServices() override { registerTestService<IComposer>(); }
-
- private:
- GraphicsComposerHidlEnvironment() {}
-
- GTEST_DISALLOW_COPY_AND_ASSIGN_(GraphicsComposerHidlEnvironment);
-};
-
-class GraphicsComposerHidlTest : public ::testing::VtsHalHidlTargetTestBase {
- protected:
+class GraphicsComposerHidlTest : public ::testing::TestWithParam<std::string> {
+ protected:
void SetUp() override {
ASSERT_NO_FATAL_FAILURE(
- mComposer = std::make_unique<Composer>(
- GraphicsComposerHidlEnvironment::Instance()->getServiceName<IComposer>()));
+ mComposer = std::make_unique<Composer>(IComposer::getService(GetParam())));
ASSERT_NO_FATAL_FAILURE(mComposerClient = mComposer->createClient());
mComposerCallback = new V2_1::vts::GraphicsComposerCallback;
@@ -175,7 +159,7 @@
*
* TODO: Check that ports are unique for multiple displays.
*/
-TEST_F(GraphicsComposerHidlTest, GetDisplayIdentificationData) {
+TEST_P(GraphicsComposerHidlTest, GetDisplayIdentificationData) {
uint8_t port0;
std::vector<uint8_t> data0;
if (mComposerClient->getDisplayIdentificationData(mPrimaryDisplay, &port0, &data0)) {
@@ -193,7 +177,7 @@
/**
* Test IComposerClient::Command::SET_LAYER_PER_FRAME_METADATA.
*/
-TEST_F(GraphicsComposerHidlCommandTest, SET_LAYER_PER_FRAME_METADATA) {
+TEST_P(GraphicsComposerHidlCommandTest, SET_LAYER_PER_FRAME_METADATA) {
Layer layer;
ASSERT_NO_FATAL_FAILURE(layer =
mComposerClient->createLayer(mPrimaryDisplay, kBufferSlotCount));
@@ -244,7 +228,7 @@
/**
* Test IComposerClient::getHdrCapabilities_2_3
*/
-TEST_F(GraphicsComposerHidlTest, GetHdrCapabilities_2_3) {
+TEST_P(GraphicsComposerHidlTest, GetHdrCapabilities_2_3) {
float maxLuminance;
float maxAverageLuminance;
float minLuminance;
@@ -256,7 +240,7 @@
/**
* Test IComposerClient::getPerFrameMetadataKeys_2_3
*/
-TEST_F(GraphicsComposerHidlTest, GetPerFrameMetadataKeys_2_3) {
+TEST_P(GraphicsComposerHidlTest, GetPerFrameMetadataKeys_2_3) {
std::vector<IComposerClient::PerFrameMetadataKey> keys;
mComposerClient->getRaw()->getPerFrameMetadataKeys_2_3(
mPrimaryDisplay, [&](const auto tmpError, const auto outKeys) {
@@ -270,7 +254,7 @@
/**
* TestIComposerClient::getReadbackBufferAttributes_2_3
*/
-TEST_F(GraphicsComposerHidlTest, GetReadbackBufferAttributes_2_3) {
+TEST_P(GraphicsComposerHidlTest, GetReadbackBufferAttributes_2_3) {
Dataspace dataspace;
PixelFormat pixelFormat;
@@ -288,7 +272,7 @@
/**
* Test IComposerClient::getClientTargetSupport_2_3
*/
-TEST_F(GraphicsComposerHidlTest, GetClientTargetSupport_2_3) {
+TEST_P(GraphicsComposerHidlTest, GetClientTargetSupport_2_3) {
std::vector<V2_1::Config> configs = mComposerClient->getDisplayConfigs(mPrimaryDisplay);
for (auto config : configs) {
int32_t width = mComposerClient->getDisplayAttribute(mPrimaryDisplay, config,
@@ -311,7 +295,7 @@
* Error::BAD_DISPLAY when passed in an invalid display handle
*/
-TEST_F(GraphicsComposerHidlTest, GetClientTargetSupport_2_3BadDisplay) {
+TEST_P(GraphicsComposerHidlTest, GetClientTargetSupport_2_3BadDisplay) {
std::vector<V2_1::Config> configs = mComposerClient->getDisplayConfigs(mPrimaryDisplay);
for (auto config : configs) {
int32_t width = mComposerClient->getDisplayAttribute(mPrimaryDisplay, config,
@@ -333,7 +317,7 @@
/**
* Test IComposerClient::getRenderIntents_2_3
*/
-TEST_F(GraphicsComposerHidlTest, GetRenderIntents_2_3) {
+TEST_P(GraphicsComposerHidlTest, GetRenderIntents_2_3) {
std::vector<ColorMode> modes = mComposerClient->getColorModes_2_3(mPrimaryDisplay);
for (auto mode : modes) {
std::vector<RenderIntent> intents =
@@ -363,7 +347,7 @@
* Test that IComposerClient::getRenderIntents_2_3 returns Error::BAD_DISPLAY when
* passed an invalid display handle
*/
-TEST_F(GraphicsComposerHidlTest, GetRenderIntents_2_3BadDisplay) {
+TEST_P(GraphicsComposerHidlTest, GetRenderIntents_2_3BadDisplay) {
std::vector<ColorMode> modes = mComposerClient->getColorModes_2_3(mPrimaryDisplay);
for (auto mode : modes) {
mComposerClient->getRaw()->getRenderIntents_2_3(
@@ -378,7 +362,7 @@
* Test that IComposerClient::getRenderIntents_2_3 returns Error::BAD_PARAMETER when
* pased either an invalid Color mode or an invalid Render Intent
*/
-TEST_F(GraphicsComposerHidlTest, GetRenderIntents_2_3BadParameter) {
+TEST_P(GraphicsComposerHidlTest, GetRenderIntents_2_3BadParameter) {
mComposerClient->getRaw()->getRenderIntents_2_3(
mPrimaryDisplay, static_cast<ColorMode>(-1),
[&](const auto& tmpError, const auto&) { EXPECT_EQ(Error::BAD_PARAMETER, tmpError); });
@@ -387,7 +371,7 @@
/**
* IComposerClient::getColorModes_2_3
*/
-TEST_F(GraphicsComposerHidlTest, GetColorModes_2_3) {
+TEST_P(GraphicsComposerHidlTest, GetColorModes_2_3) {
std::vector<ColorMode> colorModes = mComposerClient->getColorModes_2_3(mPrimaryDisplay);
auto native = std::find(colorModes.cbegin(), colorModes.cend(), ColorMode::NATIVE);
@@ -400,7 +384,7 @@
* Test that IComposerClient::getColorModes_2_3 returns Error::BAD_DISPLAY when
* passed an invalid display handle
*/
-TEST_F(GraphicsComposerHidlTest, GetColorMode_2_3BadDisplay) {
+TEST_P(GraphicsComposerHidlTest, GetColorMode_2_3BadDisplay) {
mComposerClient->getRaw()->getColorModes_2_3(
mInvalidDisplayId,
[&](const auto& tmpError, const auto&) { ASSERT_EQ(Error::BAD_DISPLAY, tmpError); });
@@ -409,7 +393,7 @@
/**
* IComposerClient::setColorMode_2_3
*/
-TEST_F(GraphicsComposerHidlTest, SetColorMode_2_3) {
+TEST_P(GraphicsComposerHidlTest, SetColorMode_2_3) {
std::vector<ColorMode> colorModes = mComposerClient->getColorModes_2_3(mPrimaryDisplay);
for (auto mode : colorModes) {
std::vector<RenderIntent> intents =
@@ -430,7 +414,7 @@
* Test that IComposerClient::setColorMode_2_3 returns an Error::BAD_DISPLAY
* when passed an invalid display handle
*/
-TEST_F(GraphicsComposerHidlTest, SetColorMode_2_3BadDisplay) {
+TEST_P(GraphicsComposerHidlTest, SetColorMode_2_3BadDisplay) {
Error error = mComposerClient->getRaw()->setColorMode_2_3(mInvalidDisplayId, ColorMode::NATIVE,
RenderIntent::COLORIMETRIC);
@@ -443,7 +427,7 @@
* Test that IComposerClient::setColorMode_2_3 returns Error::BAD_PARAMETER when
* passed an invalid Color mode or an invalid render intent
*/
-TEST_F(GraphicsComposerHidlTest, SetColorMode_2_3BadParameter) {
+TEST_P(GraphicsComposerHidlTest, SetColorMode_2_3BadParameter) {
Error colorModeError = mComposerClient->getRaw()->setColorMode_2_3(
mPrimaryDisplay, static_cast<ColorMode>(-1), RenderIntent::COLORIMETRIC);
EXPECT_EQ(Error::BAD_PARAMETER, colorModeError);
@@ -458,7 +442,7 @@
* TODO Add color to the layer, use matrix to keep only red component,
* and check.
*/
-TEST_F(GraphicsComposerHidlTest, SetLayerColorTransform) {
+TEST_P(GraphicsComposerHidlTest, SetLayerColorTransform) {
Layer layer;
ASSERT_NO_FATAL_FAILURE(layer =
mComposerClient->createLayer(mPrimaryDisplay, kBufferSlotCount));
@@ -485,7 +469,7 @@
}
}
-TEST_F(GraphicsComposerHidlTest, GetDisplayedContentSamplingAttributes) {
+TEST_P(GraphicsComposerHidlTest, GetDisplayedContentSamplingAttributes) {
int constexpr invalid = -1;
auto format = static_cast<PixelFormat>(invalid);
auto dataspace = static_cast<Dataspace>(invalid);
@@ -505,7 +489,7 @@
static_cast<hidl_bitfield<IComposerClient::FormatColorComponent>>(invalid));
};
-TEST_F(GraphicsComposerHidlTest, SetDisplayedContentSamplingEnabled) {
+TEST_P(GraphicsComposerHidlTest, SetDisplayedContentSamplingEnabled) {
auto const maxFrames = 10;
auto const enableAllComponents = 0;
auto error = mComposerClient->setDisplayedContentSamplingEnabled(
@@ -523,7 +507,7 @@
EXPECT_EQ(error, Error::NONE);
}
-TEST_F(GraphicsComposerHidlTest, GetDisplayedContentSample) {
+TEST_P(GraphicsComposerHidlTest, GetDisplayedContentSample) {
int constexpr invalid = -1;
auto format = static_cast<PixelFormat>(invalid);
auto dataspace = static_cast<Dataspace>(invalid);
@@ -558,7 +542,7 @@
* getDisplayCapabilities is required in composer 2.3
* Test some constraints.
*/
-TEST_F(GraphicsComposerHidlTest, getDisplayCapabilitiesBasic) {
+TEST_P(GraphicsComposerHidlTest, getDisplayCapabilitiesBasic) {
std::vector<IComposerClient::DisplayCapability> capabilities;
const auto error = mComposerClient->getDisplayCapabilities(mPrimaryDisplay, &capabilities);
ASSERT_EQ(Error::NONE, error);
@@ -572,13 +556,13 @@
EXPECT_EQ(mComposerClient->getDisplayBrightnessSupport(mPrimaryDisplay), hasBrightnessSupport);
}
-TEST_F(GraphicsComposerHidlTest, getDisplayCapabilitiesBadDisplay) {
+TEST_P(GraphicsComposerHidlTest, getDisplayCapabilitiesBadDisplay) {
std::vector<IComposerClient::DisplayCapability> capabilities;
const auto error = mComposerClient->getDisplayCapabilities(mInvalidDisplayId, &capabilities);
EXPECT_EQ(Error::BAD_DISPLAY, error);
}
-TEST_F(GraphicsComposerHidlTest, SetLayerPerFrameMetadataBlobs) {
+TEST_P(GraphicsComposerHidlTest, SetLayerPerFrameMetadataBlobs) {
Layer layer;
ASSERT_NO_FATAL_FAILURE(layer =
mComposerClient->createLayer(mPrimaryDisplay, kBufferSlotCount));
@@ -604,7 +588,7 @@
/*
* Test that if brightness operations are supported, setDisplayBrightness works as expected.
*/
-TEST_F(GraphicsComposerHidlTest, setDisplayBrightness) {
+TEST_P(GraphicsComposerHidlTest, setDisplayBrightness) {
std::vector<IComposerClient::DisplayCapability> capabilities;
const auto error = mComposerClient->getDisplayCapabilities(mPrimaryDisplay, &capabilities);
ASSERT_EQ(Error::NONE, error);
@@ -627,6 +611,16 @@
EXPECT_EQ(mComposerClient->setDisplayBrightness(mPrimaryDisplay, -2.0f), Error::BAD_PARAMETER);
}
+INSTANTIATE_TEST_SUITE_P(
+ PerInstance, GraphicsComposerHidlTest,
+ testing::ValuesIn(android::hardware::getAllHalInstanceNames(IComposer::descriptor)),
+ android::hardware::PrintInstanceNameToString);
+
+INSTANTIATE_TEST_SUITE_P(
+ PerInstance, GraphicsComposerHidlCommandTest,
+ testing::ValuesIn(android::hardware::getAllHalInstanceNames(IComposer::descriptor)),
+ android::hardware::PrintInstanceNameToString);
+
} // namespace
} // namespace vts
} // namespace V2_3
@@ -634,12 +628,3 @@
} // namespace graphics
} // namespace hardware
} // namespace android
-
-int main(int argc, char** argv) {
- using android::hardware::graphics::composer::V2_3::vts::GraphicsComposerHidlEnvironment;
- ::testing::AddGlobalTestEnvironment(GraphicsComposerHidlEnvironment::Instance());
- ::testing::InitGoogleTest(&argc, argv);
- GraphicsComposerHidlEnvironment::Instance()->init(&argc, argv);
- int status = RUN_ALL_TESTS();
- return status;
-}
diff --git a/graphics/mapper/4.0/IMapper.hal b/graphics/mapper/4.0/IMapper.hal
index 298f31e..03dfef1 100644
--- a/graphics/mapper/4.0/IMapper.hal
+++ b/graphics/mapper/4.0/IMapper.hal
@@ -56,6 +56,12 @@
* BufferUsage.
*/
bitfield<BufferUsage> usage;
+
+ /**
+ * The size in bytes of the reserved region associated with the buffer.
+ * See getReservedRegion for more information.
+ */
+ uint64_t reservedSize;
};
struct Rect {
@@ -71,9 +77,10 @@
*
* Since the buffer descriptor fully describes a buffer, any device
* dependent or device independent checks must be performed here whenever
- * possible. Specifically, when layered buffers are not supported, this
- * function must return `UNSUPPORTED` if `description.layers` is great than
- * 1.
+ * possible. When layered buffers are not supported, this function must
+ * return `UNSUPPORTED` if `description.layers` is great than 1. This
+ * function may return `UNSUPPORTED` if `description.reservedSize` is
+ * larger than a page.
*
* @param description Attributes of the descriptor.
* @return error Error status of the call, which may be
@@ -259,6 +266,50 @@
unlock(pointer buffer) generates (Error error, handle releaseFence);
/**
+ * Flushes the contents of a locked buffer.
+ *
+ * This function flushes the CPUs caches for the range of all the buffer's
+ * planes and metadata. This should behave similarly to unlock() except the
+ * buffer should remain mapped to the CPU.
+ *
+ * The client is still responsible for calling unlock() when it is done
+ * with all CPU accesses to the buffer.
+ *
+ * If non-CPU blocks are simultaneously writing the buffer, the locked
+ * copy should still be flushed but what happens is undefined except that
+ * it should not cause any crashes.
+ *
+ * @param buffer Buffer to flush.
+ * @return error Error status of the call, which may be
+ * - `NONE` upon success.
+ * - `BAD_BUFFER` if the buffer is invalid or not locked.
+ * @return releaseFence Handle containing a file descriptor referring to a
+ * sync fence object. The sync fence object will be signaled when the
+ * mapper has completed any pending work. @p releaseFence may be an
+ * empty fence.
+ */
+ flushLockedBuffer(pointer buffer) generates (Error error, handle releaseFence);
+
+ /**
+ * Rereads the contents of a locked buffer.
+ *
+ * This should fetch the most recent copy of the locked buffer.
+ *
+ * It may reread locked copies of the buffer in other processes.
+ *
+ * The client is still responsible for calling unlock() when it is done
+ * with all CPU accesses to the buffer.
+ *
+ * @param buffer Buffer to reread.
+ * @return error Error status of the call, which may be
+ * - `NONE` upon success.
+ * - `BAD_BUFFER` if the buffer is invalid or not locked.
+ * - `NO_RESOURCES` if the buffer cannot be reread at this time. Note
+ * that rereading may succeed at a later time.
+ */
+ rereadLockedBuffer(pointer buffer) generates(Error error);
+
+ /**
* Test whether the given BufferDescriptorInfo is allocatable.
*
* If this function returns true, it means that a buffer with the given
@@ -560,5 +611,35 @@
*/
dumpBuffers()
generates (Error error, vec<BufferDump> bufferDumps);
+
+ /**
+ * Returns the region of shared memory associated with the buffer that is
+ * reserved for client use.
+ *
+ * The shared memory may be allocated from any shared memory allocator.
+ * The shared memory must be CPU-accessible and virtually contiguous. The
+ * starting address must be word-aligned.
+ *
+ * This function may only be called after importBuffer() has been called by the
+ * client. The reserved region must remain accessible until freeBuffer() has
+ * been called. After freeBuffer() has been called, the client must not access
+ * the reserved region.
+ *
+ * This reserved memory may be used in future versions of Android to
+ * help clients implement backwards compatible features without requiring
+ * IAllocator/IMapper updates.
+ *
+ * @param buffer Imported buffer handle.
+ * @return error Error status of the call, which may be
+ * - `NONE` upon success.
+ * - `BAD_BUFFER` if the buffer is invalid.
+ * @return reservedRegion CPU-accessible pointer to the reserved region
+ * @return reservedSize the size of the reservedRegion that was requested
+ * in the BufferDescriptorInfo.
+ */
+ getReservedRegion(pointer buffer)
+ generates (Error error,
+ pointer reservedRegion,
+ uint64_t reservedSize);
};
diff --git a/graphics/mapper/4.0/utils/vts/MapperVts.cpp b/graphics/mapper/4.0/utils/vts/MapperVts.cpp
index 8073e69..c317ed2 100644
--- a/graphics/mapper/4.0/utils/vts/MapperVts.cpp
+++ b/graphics/mapper/4.0/utils/vts/MapperVts.cpp
@@ -246,6 +246,34 @@
return releaseFence;
}
+int Gralloc::flushLockedBuffer(const native_handle_t* bufferHandle) {
+ auto buffer = const_cast<native_handle_t*>(bufferHandle);
+
+ int releaseFence = -1;
+ mMapper->flushLockedBuffer(buffer, [&](const auto& tmpError, const auto& tmpReleaseFence) {
+ ASSERT_EQ(Error::NONE, tmpError) << "failed to flush locked buffer " << buffer;
+
+ auto fenceHandle = tmpReleaseFence.getNativeHandle();
+ if (fenceHandle) {
+ ASSERT_EQ(0, fenceHandle->numInts) << "invalid fence handle " << fenceHandle;
+ if (fenceHandle->numFds == 1) {
+ releaseFence = dup(fenceHandle->data[0]);
+ ASSERT_LT(0, releaseFence) << "failed to dup fence fd";
+ } else {
+ ASSERT_EQ(0, fenceHandle->numFds) << " invalid fence handle " << fenceHandle;
+ }
+ }
+ });
+
+ return releaseFence;
+}
+
+void Gralloc::rereadLockedBuffer(const native_handle_t* bufferHandle) {
+ auto buffer = const_cast<native_handle_t*>(bufferHandle);
+
+ ASSERT_EQ(Error::NONE, mMapper->rereadLockedBuffer(buffer));
+}
+
bool Gralloc::validateBufferSize(const native_handle_t* bufferHandle,
const IMapper::BufferDescriptorInfo& descriptorInfo,
uint32_t stride) {
@@ -310,6 +338,19 @@
return err;
}
+Error Gralloc::getReservedRegion(const native_handle_t* bufferHandle, void** outReservedRegion,
+ uint64_t* outReservedSize) {
+ Error err;
+ mMapper->getReservedRegion(
+ const_cast<native_handle_t*>(bufferHandle),
+ [&](const auto& tmpError, const auto& tmpReservedRegion, const auto& tmpReservedSize) {
+ err = tmpError;
+ *outReservedRegion = tmpReservedRegion;
+ *outReservedSize = tmpReservedSize;
+ });
+ return err;
+}
+
} // namespace vts
} // namespace V4_0
} // namespace mapper
diff --git a/graphics/mapper/4.0/utils/vts/include/mapper-vts/4.0/MapperVts.h b/graphics/mapper/4.0/utils/vts/include/mapper-vts/4.0/MapperVts.h
index 6251e66..eed043f 100644
--- a/graphics/mapper/4.0/utils/vts/include/mapper-vts/4.0/MapperVts.h
+++ b/graphics/mapper/4.0/utils/vts/include/mapper-vts/4.0/MapperVts.h
@@ -73,6 +73,9 @@
const IMapper::Rect& accessRegion, int acquireFence);
int unlock(const native_handle_t* bufferHandle);
+ int flushLockedBuffer(const native_handle_t* bufferHandle);
+ void rereadLockedBuffer(const native_handle_t* bufferHandle);
+
bool validateBufferSize(const native_handle_t* bufferHandle,
const IMapper::BufferDescriptorInfo& descriptorInfo, uint32_t stride);
void getTransportSize(const native_handle_t* bufferHandle, uint32_t* outNumFds,
@@ -90,6 +93,9 @@
const IMapper::MetadataType& metadataType,
hidl_vec<uint8_t>* outVec);
+ Error getReservedRegion(const native_handle_t* bufferHandle, void** outReservedRegion,
+ uint64_t* outReservedSize);
+
private:
void init(const std::string& allocatorServiceName, const std::string& mapperServiceName);
diff --git a/graphics/mapper/4.0/vts/functional/Android.bp b/graphics/mapper/4.0/vts/functional/Android.bp
index a8030ab..506026d 100644
--- a/graphics/mapper/4.0/vts/functional/Android.bp
+++ b/graphics/mapper/4.0/vts/functional/Android.bp
@@ -20,6 +20,7 @@
srcs: ["VtsHalGraphicsMapperV4_0TargetTest.cpp"],
static_libs: [
"android.hardware.graphics.mapper@4.0-vts",
+ "libsync",
],
shared_libs: [
"android.hardware.graphics.allocator@4.0",
diff --git a/graphics/mapper/4.0/vts/functional/VtsHalGraphicsMapperV4_0TargetTest.cpp b/graphics/mapper/4.0/vts/functional/VtsHalGraphicsMapperV4_0TargetTest.cpp
index d63b078..347eca6 100644
--- a/graphics/mapper/4.0/vts/functional/VtsHalGraphicsMapperV4_0TargetTest.cpp
+++ b/graphics/mapper/4.0/vts/functional/VtsHalGraphicsMapperV4_0TargetTest.cpp
@@ -16,6 +16,7 @@
#define LOG_TAG "VtsHalGraphicsMapperV4_0TargetTest"
+#include <unistd.h>
#include <chrono>
#include <thread>
#include <vector>
@@ -24,6 +25,7 @@
#include <VtsHalHidlTargetTestBase.h>
#include <android-base/logging.h>
+#include <android/sync.h>
#include <gralloctypes/Gralloc4.h>
#include <mapper-vts/4.0/MapperVts.h>
#include <system/graphics.h>
@@ -82,6 +84,7 @@
mDummyDescriptorInfo.format = PixelFormat::RGBA_8888;
mDummyDescriptorInfo.usage =
static_cast<uint64_t>(BufferUsage::CPU_WRITE_OFTEN | BufferUsage::CPU_READ_OFTEN);
+ mDummyDescriptorInfo.reservedSize = 0;
}
void TearDown() override {}
@@ -273,6 +276,24 @@
ASSERT_NE(nullptr, outYCbCr->cr);
}
+ void fillRGBA8888(uint8_t* data, uint32_t height, size_t strideInBytes, size_t widthInBytes,
+ uint32_t seed = 0) {
+ for (uint32_t y = 0; y < height; y++) {
+ memset(data, y + seed, widthInBytes);
+ data += strideInBytes;
+ }
+ }
+
+ void verifyRGBA8888(uint8_t* data, uint32_t height, size_t strideInBytes, size_t widthInBytes,
+ uint32_t seed = 0) {
+ for (uint32_t y = 0; y < height; y++) {
+ for (size_t i = 0; i < widthInBytes; i++) {
+ EXPECT_EQ(static_cast<uint8_t>(y + seed), data[i]);
+ }
+ data += strideInBytes;
+ }
+ }
+
std::unique_ptr<Gralloc> mGralloc;
IMapper::BufferDescriptorInfo mDummyDescriptorInfo{};
static const std::set<StandardMetadataType> sRequiredMetadataTypes;
@@ -529,25 +550,14 @@
data = static_cast<uint8_t*>(mGralloc->lock(bufferHandle, info.usage, region, fence)));
// RGBA_8888
- size_t strideInBytes = stride * 4;
- size_t writeInBytes = info.width * 4;
-
- for (uint32_t y = 0; y < info.height; y++) {
- memset(data, y, writeInBytes);
- data += strideInBytes;
- }
+ fillRGBA8888(data, info.height, stride * 4, info.width * 4);
ASSERT_NO_FATAL_FAILURE(fence = mGralloc->unlock(bufferHandle));
// lock again for reading
ASSERT_NO_FATAL_FAILURE(
data = static_cast<uint8_t*>(mGralloc->lock(bufferHandle, info.usage, region, fence)));
- for (uint32_t y = 0; y < info.height; y++) {
- for (size_t i = 0; i < writeInBytes; i++) {
- EXPECT_EQ(static_cast<uint8_t>(y), data[i]);
- }
- data += strideInBytes;
- }
+ ASSERT_NO_FATAL_FAILURE(verifyRGBA8888(data, info.height, stride * 4, info.width * 4));
ASSERT_NO_FATAL_FAILURE(fence = mGralloc->unlock(bufferHandle));
if (fence >= 0) {
@@ -706,6 +716,75 @@
}
/**
+ * Test IMapper::flush and IMapper::reread.
+ */
+TEST_F(GraphicsMapperHidlTest, FlushRereadBasic) {
+ const auto& info = mDummyDescriptorInfo;
+
+ const native_handle_t* rawHandle;
+ uint32_t stride;
+ ASSERT_NO_FATAL_FAILURE(
+ rawHandle = mGralloc->allocate(mDummyDescriptorInfo, false, false, &stride));
+
+ const native_handle_t* writeBufferHandle;
+ const native_handle_t* readBufferHandle;
+ ASSERT_NO_FATAL_FAILURE(writeBufferHandle = mGralloc->importBuffer(rawHandle));
+ ASSERT_NO_FATAL_FAILURE(readBufferHandle = mGralloc->importBuffer(rawHandle));
+
+ // lock buffer for writing
+ const IMapper::Rect region{0, 0, static_cast<int32_t>(info.width),
+ static_cast<int32_t>(info.height)};
+ uint8_t* writeData;
+ ASSERT_NO_FATAL_FAILURE(
+ writeData = static_cast<uint8_t*>(mGralloc->lock(
+ writeBufferHandle, static_cast<uint64_t>(BufferUsage::CPU_WRITE_OFTEN), region,
+ -1)));
+
+ uint8_t* readData;
+ ASSERT_NO_FATAL_FAILURE(
+ readData = static_cast<uint8_t*>(mGralloc->lock(
+ readBufferHandle, static_cast<uint64_t>(BufferUsage::CPU_READ_OFTEN), region,
+ -1)));
+
+ fillRGBA8888(writeData, info.height, stride * 4, info.width * 4);
+
+ int fence;
+ ASSERT_NO_FATAL_FAILURE(fence = mGralloc->flushLockedBuffer(writeBufferHandle));
+ ASSERT_EQ(0, sync_wait(fence, 3500));
+ close(fence);
+
+ ASSERT_NO_FATAL_FAILURE(mGralloc->rereadLockedBuffer(readBufferHandle));
+
+ ASSERT_NO_FATAL_FAILURE(verifyRGBA8888(readData, info.height, stride * 4, info.width * 4));
+
+ ASSERT_NO_FATAL_FAILURE(fence = mGralloc->unlock(readBufferHandle));
+ if (fence >= 0) {
+ close(fence);
+ }
+ ASSERT_NO_FATAL_FAILURE(fence = mGralloc->unlock(writeBufferHandle));
+ if (fence >= 0) {
+ close(fence);
+ }
+}
+
+/**
+ * Test IMapper::flushLockedBuffer with bad buffer
+ */
+TEST_F(GraphicsMapperHidlTest, FlushLockedBufferBadBuffer) {
+ ASSERT_NO_FATAL_FAILURE(mGralloc->getMapper()->flushLockedBuffer(
+ nullptr, [&](const auto& tmpError, const auto& /*tmpReleaseFence*/) {
+ ASSERT_EQ(Error::BAD_BUFFER, tmpError);
+ }));
+}
+
+/**
+ * Test IMapper::rereadLockedBuffer with bad buffer
+ */
+TEST_F(GraphicsMapperHidlTest, RereadLockedBufferBadBuffer) {
+ ASSERT_EQ(Error::BAD_BUFFER, mGralloc->getMapper()->rereadLockedBuffer(nullptr));
+}
+
+/**
* Test IMapper::isSupported with required format RGBA_8888
*/
TEST_F(GraphicsMapperHidlTest, IsSupportedRGBA8888) {
@@ -1821,6 +1900,124 @@
}
}
+/**
+ * Test IMapper::getReservedRegion()
+ */
+TEST_F(GraphicsMapperHidlTest, GetReservedRegion) {
+ const native_handle_t* bufferHandle = nullptr;
+ auto info = mDummyDescriptorInfo;
+
+ const int pageSize = getpagesize();
+ ASSERT_GE(0, pageSize);
+ std::vector<uint64_t> requestedReservedSizes{1, 10, 333, static_cast<uint64_t>(pageSize) / 2,
+ static_cast<uint64_t>(pageSize)};
+
+ for (auto requestedReservedSize : requestedReservedSizes) {
+ info.reservedSize = requestedReservedSize;
+
+ ASSERT_NO_FATAL_FAILURE(bufferHandle = mGralloc->allocate(info, true));
+
+ void* reservedRegion = nullptr;
+ uint64_t reservedSize = 0;
+ ASSERT_EQ(Error::NONE,
+ mGralloc->getReservedRegion(bufferHandle, &reservedRegion, &reservedSize));
+ ASSERT_NE(nullptr, reservedRegion);
+ ASSERT_EQ(requestedReservedSize, reservedSize);
+
+ uint8_t testValue = 1;
+ memset(reservedRegion, testValue, reservedSize);
+ for (uint64_t i = 0; i < reservedSize; i++) {
+ ASSERT_EQ(testValue, static_cast<uint8_t*>(reservedRegion)[i]);
+ }
+ }
+}
+
+/**
+ * Test IMapper::getReservedRegion() request over a page
+ */
+TEST_F(GraphicsMapperHidlTest, GetLargeReservedRegion) {
+ const native_handle_t* bufferHandle = nullptr;
+ auto info = mDummyDescriptorInfo;
+
+ const int pageSize = getpagesize();
+ ASSERT_GE(0, pageSize);
+ std::vector<uint64_t> requestedReservedSizes{static_cast<uint64_t>(pageSize) * 2,
+ static_cast<uint64_t>(pageSize) * 10,
+ static_cast<uint64_t>(pageSize) * 1000};
+
+ for (auto requestedReservedSize : requestedReservedSizes) {
+ info.reservedSize = requestedReservedSize;
+
+ BufferDescriptor descriptor;
+ ASSERT_NO_FATAL_FAILURE(descriptor = mGralloc->createDescriptor(info));
+
+ Error err;
+ mGralloc->getAllocator()->allocate(
+ descriptor, 1,
+ [&](const auto& tmpError, const auto&, const auto&) { err = tmpError; });
+ if (err == Error::UNSUPPORTED) {
+ continue;
+ }
+ ASSERT_EQ(Error::NONE, err);
+
+ void* reservedRegion = nullptr;
+ uint64_t reservedSize = 0;
+ err = mGralloc->getReservedRegion(bufferHandle, &reservedRegion, &reservedSize);
+
+ ASSERT_EQ(Error::NONE, err);
+ ASSERT_NE(nullptr, reservedRegion);
+ ASSERT_EQ(requestedReservedSize, reservedSize);
+ }
+}
+
+/**
+ * Test IMapper::getReservedRegion() across multiple mappers
+ */
+TEST_F(GraphicsMapperHidlTest, GetReservedRegionMultiple) {
+ const native_handle_t* bufferHandle = nullptr;
+ auto info = mDummyDescriptorInfo;
+
+ const int pageSize = getpagesize();
+ ASSERT_GE(0, pageSize);
+ info.reservedSize = pageSize;
+
+ ASSERT_NO_FATAL_FAILURE(bufferHandle = mGralloc->allocate(info, true));
+
+ void* reservedRegion1 = nullptr;
+ uint64_t reservedSize1 = 0;
+ ASSERT_EQ(Error::NONE,
+ mGralloc->getReservedRegion(bufferHandle, &reservedRegion1, &reservedSize1));
+ ASSERT_NE(nullptr, reservedRegion1);
+ ASSERT_EQ(info.reservedSize, reservedSize1);
+
+ std::unique_ptr<Gralloc> anotherGralloc;
+ ASSERT_NO_FATAL_FAILURE(
+ anotherGralloc = std::make_unique<Gralloc>(
+ GraphicsMapperHidlEnvironment::Instance()->getServiceName<IAllocator>(),
+ GraphicsMapperHidlEnvironment::Instance()->getServiceName<IMapper>()));
+
+ void* reservedRegion2 = nullptr;
+ uint64_t reservedSize2 = 0;
+ ASSERT_EQ(Error::NONE,
+ mGralloc->getReservedRegion(bufferHandle, &reservedRegion2, &reservedSize2));
+ ASSERT_EQ(reservedRegion1, reservedRegion2);
+ ASSERT_EQ(reservedSize1, reservedSize2);
+}
+
+/**
+ * Test IMapper::getReservedRegion() with a bad buffer
+ */
+TEST_F(GraphicsMapperHidlTest, GetReservedRegionBadBuffer) {
+ const native_handle_t* bufferHandle = nullptr;
+
+ void* reservedRegion = nullptr;
+ uint64_t reservedSize = 0;
+ ASSERT_EQ(Error::BAD_BUFFER,
+ mGralloc->getReservedRegion(bufferHandle, &reservedRegion, &reservedSize));
+ ASSERT_EQ(nullptr, reservedRegion);
+ ASSERT_EQ(0, reservedSize);
+}
+
} // namespace
} // namespace vts
} // namespace V4_0
diff --git a/health/1.0/default/Android.bp b/health/1.0/default/Android.bp
index 049e393..7581335 100644
--- a/health/1.0/default/Android.bp
+++ b/health/1.0/default/Android.bp
@@ -18,3 +18,55 @@
}
+cc_library_static {
+ name: "android.hardware.health@1.0-impl-helper",
+ vendor: true,
+ srcs: ["Health.cpp"],
+
+ header_libs: [
+ "libbase_headers",
+ "libhealthd_headers",
+ ],
+
+ shared_libs: [
+ "libcutils",
+ "libhidlbase",
+ "liblog",
+ "libutils",
+ "android.hardware.health@1.0",
+ ],
+
+ static_libs: [
+ "android.hardware.health@1.0-convert",
+ ],
+}
+
+cc_library_shared {
+ name: "android.hardware.health@1.0-impl",
+ vendor: true,
+ relative_install_path: "hw",
+
+ static_libs: [
+ "android.hardware.health@1.0-impl-helper",
+ "android.hardware.health@1.0-convert",
+ "libhealthd.default",
+ ],
+}
+
+cc_binary {
+ name: "android.hardware.health@1.0-service",
+ vendor: true,
+ relative_install_path: "hw",
+ init_rc: ["android.hardware.health@1.0-service.rc"],
+ srcs: ["HealthService.cpp"],
+
+ shared_libs: [
+ "liblog",
+ "libcutils",
+ "libdl",
+ "libbase",
+ "libutils",
+ "libhidlbase",
+ "android.hardware.health@1.0",
+ ],
+}
diff --git a/health/1.0/default/Android.mk b/health/1.0/default/Android.mk
deleted file mode 100644
index bbf37af..0000000
--- a/health/1.0/default/Android.mk
+++ /dev/null
@@ -1,45 +0,0 @@
-LOCAL_PATH := $(call my-dir)
-
-include $(CLEAR_VARS)
-LOCAL_MODULE := android.hardware.health@1.0-impl
-LOCAL_PROPRIETARY_MODULE := true
-LOCAL_MODULE_RELATIVE_PATH := hw
-LOCAL_C_INCLUDES := system/core/base/include
-LOCAL_SRC_FILES := \
- Health.cpp \
-
-LOCAL_HEADER_LIBRARIES := libhealthd_headers
-
-LOCAL_SHARED_LIBRARIES := \
- libcutils \
- libhidlbase \
- liblog \
- libutils \
- android.hardware.health@1.0 \
-
-LOCAL_STATIC_LIBRARIES := android.hardware.health@1.0-convert
-
-LOCAL_HAL_STATIC_LIBRARIES := libhealthd
-
-include $(BUILD_SHARED_LIBRARY)
-
-include $(CLEAR_VARS)
-LOCAL_PROPRIETARY_MODULE := true
-LOCAL_MODULE_RELATIVE_PATH := hw
-LOCAL_MODULE := android.hardware.health@1.0-service
-LOCAL_INIT_RC := android.hardware.health@1.0-service.rc
-LOCAL_SRC_FILES := \
- HealthService.cpp \
-
-LOCAL_SHARED_LIBRARIES := \
- liblog \
- libcutils \
- libdl \
- libbase \
- libutils \
- libhidlbase \
- android.hardware.health@1.0 \
-
-include $(BUILD_EXECUTABLE)
-
-include $(call first-makefiles-under,$(LOCAL_PATH))
diff --git a/health/1.0/default/README.md b/health/1.0/default/README.md
new file mode 100644
index 0000000..1ded7de
--- /dev/null
+++ b/health/1.0/default/README.md
@@ -0,0 +1,66 @@
+# Implement the 2.1 HAL instead!
+
+It is strongly recommended that you implement the 2.1 HAL directly. See
+`hardware/interfaces/health/2.1/README.md` for more details.
+
+# Implement Health 1.0 HAL
+
+1. Install common binderized service. The binderized service `dlopen()`s
+ passthrough implementations on the device, so there is no need to write
+ your own.
+
+ ```mk
+ # Install default binderized implementation to vendor.
+ PRODUCT_PACKAGES += android.hardware.health@1.0-service
+ ```
+
+1. Add proper VINTF manifest entry to your device manifest. Example:
+
+ ```xml
+ <hal format="hidl">
+ <name>android.hardware.health</name>
+ <transport>hwbinder</transport>
+ <version>1.0</version>
+ <interface>
+ <name>IHealth</name>
+ <instance>default</instance>
+ </interface>
+ </hal>
+ ```
+
+1. Install the proper passthrough implemetation.
+
+ 1. If you want to use the default implementation (with default `libhealthd`),
+ add the following to `device.mk`:
+
+ ```mk
+ PRODUCT_PACKAGES += \
+ android.hardware.health@1.0-impl
+ ```
+
+ 1. Otherwise, if you have a customized `libhealthd.<board>`:
+
+ 1. Define your passthrough implementation. Example (replace `<device>`
+ and `<board>` accordingly):
+
+ ```bp
+ cc_library_shared {
+ name: "android.hardware.health@1.0-impl-<device>",
+ vendor: true,
+ relative_install_path: "hw",
+
+ static_libs: [
+ "android.hardware.health@1.0-impl-helper",
+ "android.hardware.health@1.0-convert",
+ "libhealthd.<board>",
+ ],
+ }
+ ```
+
+ 1. Add to `device.mk`.
+
+ ```
+ PRODUCT_PACKAGES += android.hardware.health@1.0-impl-<device>
+ ```
+
+ 1. Define appropriate SELinux permissions.
diff --git a/neuralnetworks/1.2/vts/functional/GeneratedTestHarness.cpp b/neuralnetworks/1.2/vts/functional/GeneratedTestHarness.cpp
index c1bf494..4909214 100644
--- a/neuralnetworks/1.2/vts/functional/GeneratedTestHarness.cpp
+++ b/neuralnetworks/1.2/vts/functional/GeneratedTestHarness.cpp
@@ -29,13 +29,14 @@
#include <android/hardware/neuralnetworks/1.2/IPreparedModelCallback.h>
#include <android/hidl/allocator/1.0/IAllocator.h>
#include <android/hidl/memory/1.0/IMemory.h>
+#include <gtest/gtest.h>
#include <hidlmemory/mapping.h>
-#include <gtest/gtest.h>
#include <algorithm>
#include <chrono>
#include <iostream>
#include <numeric>
+#include <vector>
#include "1.0/Utils.h"
#include "1.2/Callbacks.h"
@@ -333,9 +334,9 @@
void EvaluatePreparedModel(const sp<IPreparedModel>& preparedModel, const TestModel& testModel,
bool testDynamicOutputShape) {
- std::initializer_list<OutputType> outputTypesList;
- std::initializer_list<MeasureTiming> measureTimingList;
- std::initializer_list<Executor> executorList;
+ std::vector<OutputType> outputTypesList;
+ std::vector<MeasureTiming> measureTimingList;
+ std::vector<Executor> executorList;
if (testDynamicOutputShape) {
outputTypesList = {OutputType::UNSPECIFIED, OutputType::INSUFFICIENT};
diff --git a/neuralnetworks/1.3/vts/functional/GeneratedTestHarness.cpp b/neuralnetworks/1.3/vts/functional/GeneratedTestHarness.cpp
index 3e947f5..f61240e 100644
--- a/neuralnetworks/1.3/vts/functional/GeneratedTestHarness.cpp
+++ b/neuralnetworks/1.3/vts/functional/GeneratedTestHarness.cpp
@@ -34,13 +34,14 @@
#include <android/hardware/neuralnetworks/1.3/types.h>
#include <android/hidl/allocator/1.0/IAllocator.h>
#include <android/hidl/memory/1.0/IMemory.h>
+#include <gtest/gtest.h>
#include <hidlmemory/mapping.h>
-#include <gtest/gtest.h>
#include <algorithm>
#include <chrono>
#include <iostream>
#include <numeric>
+#include <vector>
#include "1.0/Utils.h"
#include "1.2/Callbacks.h"
@@ -368,9 +369,9 @@
void EvaluatePreparedModel(const sp<IPreparedModel>& preparedModel, const TestModel& testModel,
TestKind testKind) {
- std::initializer_list<OutputType> outputTypesList;
- std::initializer_list<MeasureTiming> measureTimingList;
- std::initializer_list<Executor> executorList;
+ std::vector<OutputType> outputTypesList;
+ std::vector<MeasureTiming> measureTimingList;
+ std::vector<Executor> executorList;
switch (testKind) {
case TestKind::GENERAL: {
@@ -403,11 +404,9 @@
const TestModel& testModel,
const sp<IPreparedModel>& preparedCoupledModel,
const TestModel& coupledModel) {
- std::initializer_list<OutputType> outputTypesList = {OutputType::FULLY_SPECIFIED};
- std::initializer_list<MeasureTiming> measureTimingList = {MeasureTiming::NO,
- MeasureTiming::YES};
- std::initializer_list<Executor> executorList = {Executor::ASYNC, Executor::SYNC,
- Executor::BURST};
+ const std::vector<OutputType> outputTypesList = {OutputType::FULLY_SPECIFIED};
+ const std::vector<MeasureTiming> measureTimingList = {MeasureTiming::NO, MeasureTiming::YES};
+ const std::vector<Executor> executorList = {Executor::ASYNC, Executor::SYNC, Executor::BURST};
for (const OutputType outputType : outputTypesList) {
for (const MeasureTiming measureTiming : measureTimingList) {
diff --git a/radio/1.5/IRadio.hal b/radio/1.5/IRadio.hal
index 6d422be..aa93ef3 100644
--- a/radio/1.5/IRadio.hal
+++ b/radio/1.5/IRadio.hal
@@ -42,16 +42,20 @@
* -EUTRAN - RSRP/RSRQ/RSSNR
* -NGRAN - SSRSRP/SSRSRQ/SSSINR
*
- * Note: Reporting criteria must be individually set for each RAN. For any unset reporting
- * criteria, the value is implementation-defined.
+ * Note: Reporting criteria must be individually set for each RAN. For each RAN, if none of
+ * reporting criteria of any measurement is set enabled
+ * (see @1.5::SignalThresholdInfo.isEnabled), the reporting criteria for this RAN is
+ * implementation-defined. For each RAN, if any of reporting criteria of any measure is set
+ * enabled, the reporting criteria of the other measures in this RAN are set disabled
+ * (see @1.5::SignalThresholdInfo.isEnabled) until they are set enabled.
*
* Response callback is
* IRadioResponse.setSignalStrengthReportingCriteriaResponse_1_5()
*
* @param serial Serial number of request.
* @param signalThresholdInfo Signal threshold info including the threshold values,
- * hysteresisDb, and hysteresisMs. See @1.5::SignalThresholdInfo
- * for details.
+ * hysteresisDb, hysteresisMs and isEnabled.
+ * See @1.5::SignalThresholdInfo for details.
* @param accessNetwork The type of network for which to apply these thresholds.
*/
oneway setSignalStrengthReportingCriteria_1_5(int32_t serial,
diff --git a/radio/1.5/types.hal b/radio/1.5/types.hal
index 664ddc4..04a9bcf 100644
--- a/radio/1.5/types.hal
+++ b/radio/1.5/types.hal
@@ -113,6 +113,15 @@
* A vector size of 0 disables the use of thresholds for reporting.
*/
vec<int32_t> thresholds;
+
+ /**
+ * Indicates whether the reporting criteria of the corresponding measurement is enabled
+ * (isEnabled==true) or disabled (isEnabled==false).
+ *
+ * If enabled, modem must trigger the report based on the criteria.
+ * If disabled, modem must not trigger the report based on the criteria.
+ */
+ bool isEnabled;
};
enum AccessNetwork : @1.4::AccessNetwork {
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 4df5b14..6bf8170 100644
--- a/radio/1.5/vts/functional/radio_hidl_hal_api.cpp
+++ b/radio/1.5/vts/functional/radio_hidl_hal_api.cpp
@@ -29,6 +29,7 @@
signalThresholdInfo.hysteresisMs = 5000;
signalThresholdInfo.hysteresisDb = 10; // hysteresisDb too large given threshold list deltas
signalThresholdInfo.thresholds = {-109, -103, -97, -89};
+ signalThresholdInfo.isEnabled = true;
Return<void> res = radio_v1_5->setSignalStrengthReportingCriteria_1_5(
serial, signalThresholdInfo, ::android::hardware::radio::V1_5::AccessNetwork::GERAN);
@@ -52,6 +53,7 @@
signalThresholdInfo.signalMeasurement = SignalMeasurementType::RSSI;
signalThresholdInfo.hysteresisMs = 0;
signalThresholdInfo.hysteresisDb = 0;
+ signalThresholdInfo.isEnabled = true;
Return<void> res = radio_v1_5->setSignalStrengthReportingCriteria_1_5(
serial, signalThresholdInfo, ::android::hardware::radio::V1_5::AccessNetwork::GERAN);
@@ -76,6 +78,7 @@
signalThresholdInfo.hysteresisMs = 5000;
signalThresholdInfo.hysteresisDb = 2;
signalThresholdInfo.thresholds = {-109, -103, -97, -89};
+ signalThresholdInfo.isEnabled = true;
Return<void> res = radio_v1_5->setSignalStrengthReportingCriteria_1_5(
serial, signalThresholdInfo, ::android::hardware::radio::V1_5::AccessNetwork::GERAN);
@@ -100,6 +103,7 @@
signalThresholdInfo.hysteresisMs = 5000;
signalThresholdInfo.hysteresisDb = 2;
signalThresholdInfo.thresholds = {-110, -97, -73, -49, -25};
+ signalThresholdInfo.isEnabled = true;
Return<void> res = radio_v1_5->setSignalStrengthReportingCriteria_1_5(
serial, signalThresholdInfo, ::android::hardware::radio::V1_5::AccessNetwork::UTRAN);
@@ -124,6 +128,7 @@
signalThresholdInfo.hysteresisMs = 5000;
signalThresholdInfo.hysteresisDb = 2;
signalThresholdInfo.thresholds = {-128, -108, -88, -68};
+ signalThresholdInfo.isEnabled = true;
Return<void> res = radio_v1_5->setSignalStrengthReportingCriteria_1_5(
serial, signalThresholdInfo, ::android::hardware::radio::V1_5::AccessNetwork::EUTRAN);
@@ -148,6 +153,7 @@
signalThresholdInfo.hysteresisMs = 5000;
signalThresholdInfo.hysteresisDb = 2;
signalThresholdInfo.thresholds = {-27, -20, -13, -6};
+ signalThresholdInfo.isEnabled = true;
Return<void> res = radio_v1_5->setSignalStrengthReportingCriteria_1_5(
serial, signalThresholdInfo, ::android::hardware::radio::V1_5::AccessNetwork::EUTRAN);
@@ -172,6 +178,7 @@
signalThresholdInfo.hysteresisMs = 5000;
signalThresholdInfo.hysteresisDb = 2;
signalThresholdInfo.thresholds = {-10, 0, 10, 20};
+ signalThresholdInfo.isEnabled = true;
Return<void> res = radio_v1_5->setSignalStrengthReportingCriteria_1_5(
serial, signalThresholdInfo, ::android::hardware::radio::V1_5::AccessNetwork::EUTRAN);
@@ -192,6 +199,7 @@
signalThresholdInfo.hysteresisMs = 5000;
signalThresholdInfo.hysteresisDb = 2;
signalThresholdInfo.thresholds = {-105, -90, -75, -65};
+ signalThresholdInfo.isEnabled = true;
Return<void> res = radio_v1_5->setSignalStrengthReportingCriteria_1_5(
serial, signalThresholdInfo, ::android::hardware::radio::V1_5::AccessNetwork::CDMA2000);
@@ -216,6 +224,7 @@
signalThresholdInfo.hysteresisMs = 5000;
signalThresholdInfo.hysteresisDb = 0;
signalThresholdInfo.thresholds = {-105, -90, -75, -65};
+ signalThresholdInfo.isEnabled = true;
Return<void> res = radio_v1_5->setSignalStrengthReportingCriteria_1_5(
serial, signalThresholdInfo, ::android::hardware::radio::V1_5::AccessNetwork::NGRAN);
@@ -240,6 +249,7 @@
signalThresholdInfo.hysteresisMs = 5000;
signalThresholdInfo.hysteresisDb = 0;
signalThresholdInfo.thresholds = {-15, -10, -5, -4};
+ signalThresholdInfo.isEnabled = true;
Return<void> res = radio_v1_5->setSignalStrengthReportingCriteria_1_5(
serial, signalThresholdInfo, ::android::hardware::radio::V1_5::AccessNetwork::NGRAN);
@@ -254,6 +264,27 @@
}
/*
+ * Test IRadio.setSignalStrengthReportingCriteria_1_5() for EUTRAN
+ */
+TEST_F(RadioHidlTest_v1_5, setSignalStrengthReportingCriteria_1_5_Disable_RSSNR) {
+ serial = GetRandomSerialNumber();
+
+ ::android::hardware::radio::V1_5::SignalThresholdInfo signalThresholdInfo;
+ signalThresholdInfo.signalMeasurement = SignalMeasurementType::RSSNR;
+ signalThresholdInfo.hysteresisMs = 5000;
+ signalThresholdInfo.hysteresisDb = 2;
+ signalThresholdInfo.thresholds = {-10, 0, 10, 20};
+ signalThresholdInfo.isEnabled = false;
+
+ Return<void> res = radio_v1_5->setSignalStrengthReportingCriteria_1_5(
+ serial, signalThresholdInfo, ::android::hardware::radio::V1_5::AccessNetwork::EUTRAN);
+ ASSERT_OK(res);
+ EXPECT_EQ(std::cv_status::no_timeout, wait());
+ EXPECT_EQ(RadioResponseType::SOLICITED, radioRsp_v1_5->rspInfo.type);
+ EXPECT_EQ(serial, radioRsp_v1_5->rspInfo.serial);
+}
+
+/*
* Test IRadio.setSignalStrengthReportingCriteria_1_5() for NGRAN_SSSINR
*/
TEST_F(RadioHidlTest_v1_5, setSignalStrengthReportingCriteria_1_5_NGRAN_SSSINR) {
@@ -264,6 +295,7 @@
signalThresholdInfo.hysteresisMs = 5000;
signalThresholdInfo.hysteresisDb = 0;
signalThresholdInfo.thresholds = {-10, 3, 16, 18};
+ signalThresholdInfo.isEnabled = true;
Return<void> res = radio_v1_5->setSignalStrengthReportingCriteria_1_5(
serial, signalThresholdInfo, ::android::hardware::radio::V1_5::AccessNetwork::NGRAN);
diff --git a/wifi/1.4/Android.bp b/wifi/1.4/Android.bp
index 5750e42..e63b1eb 100644
--- a/wifi/1.4/Android.bp
+++ b/wifi/1.4/Android.bp
@@ -11,6 +11,7 @@
"IWifi.hal",
"IWifiApIface.hal",
"IWifiChip.hal",
+ "IWifiChipEventCallback.hal",
"IWifiRttController.hal",
"IWifiRttControllerEventCallback.hal",
"IWifiStaIface.hal",
diff --git a/wifi/1.4/IWifiChip.hal b/wifi/1.4/IWifiChip.hal
index d269427..de5a64e 100644
--- a/wifi/1.4/IWifiChip.hal
+++ b/wifi/1.4/IWifiChip.hal
@@ -19,6 +19,7 @@
import @1.0::WifiStatus;
import @1.0::IWifiIface;
import @1.3::IWifiChip;
+import IWifiChipEventCallback;
import IWifiRttController;
/**
@@ -26,6 +27,22 @@
*/
interface IWifiChip extends @1.3::IWifiChip {
/**
+ * Requests notifications of significant events on this chip. Multiple calls
+ * to this must register multiple callbacks each of which must receive all
+ * events.
+ *
+ * @param callback An instance of the |IWifiChipEventCallback| HIDL interface
+ * object.
+ * @return status WifiStatus of the operation.
+ * Possible status codes:
+ * |WifiStatusCode.SUCCESS|,
+ * |WifiStatusCode.ERROR_NOT_SUPPORTED|,
+ * |WifiStatusCode.ERROR_WIFI_CHIP_INVALID|
+ */
+ registerEventCallback_1_4(IWifiChipEventCallback callback)
+ generates (WifiStatus status);
+
+ /**
* Create a RTTController instance.
*
* RTT controller can be either:
diff --git a/wifi/1.4/IWifiChipEventCallback.hal b/wifi/1.4/IWifiChipEventCallback.hal
new file mode 100644
index 0000000..ecd0a44
--- /dev/null
+++ b/wifi/1.4/IWifiChipEventCallback.hal
@@ -0,0 +1,65 @@
+/*
+ * Copyright 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.wifi@1.4;
+
+import @1.2::IWifiChipEventCallback;
+import WifiBand;
+
+/**
+ * Wifi chip event callbacks.
+ */
+interface IWifiChipEventCallback extends @1.2::IWifiChipEventCallback {
+ /**
+ * Struct describing the state of each hardware radio chain (hardware MAC)
+ * on the device.
+ */
+ struct RadioModeInfo {
+ /**
+ * Identifier for this radio chain. This is vendor dependent & used
+ * only for debugging purposes.
+ */
+ uint32_t radioId;
+ /**
+ * List of bands on which this radio chain is operating.
+ * Can be one of:
+ * a) WifiBand.BAND_24GHZ => 2.4Ghz.
+ * b) WifiBand.BAND_5GHZ => 5Ghz.
+ * c) WifiBand.BAND_24GHZ_5GHZ = 2.4Ghz + 5Ghz (Radio is time sharing
+ * across the 2 bands).
+ * d) WifiBand.BAND_6GHZ => 6Ghz.
+ * e) WifiBand.BAND_5GHZ_6GHZ => 5Ghz + 6Ghz (Radio is time sharing
+ * across the 2 bands).
+ * f) WifiBand.BAND_24GHZ_5GHZ_6GHZ => 2.4Ghz + 5Ghz + 6Ghz (Radio is
+ * time sharing across the 3 bands).
+ */
+ WifiBand bandInfo;
+ /** List of interfaces on this radio chain (hardware MAC). */
+ vec<IfaceInfo> ifaceInfos;
+ };
+
+ /**
+ * Asynchronous callback indicating a radio mode change.
+ * Radio mode change could be a result of:
+ * a) Bringing up concurrent interfaces (For ex: STA + AP).
+ * b) Change in operating band of one of the concurrent interfaces (For ex:
+ * STA connection moved from 2.4G to 5G)
+ *
+ * @param radioModeInfos List of RadioModeInfo structures for each
+ * radio chain (hardware MAC) on the device.
+ */
+ oneway onRadioModeChange_1_4(vec<RadioModeInfo> radioModeInfos);
+};
diff --git a/wifi/1.4/default/hidl_struct_util.cpp b/wifi/1.4/default/hidl_struct_util.cpp
index 6eeb642..35c6839 100644
--- a/wifi/1.4/default/hidl_struct_util.cpp
+++ b/wifi/1.4/default/hidl_struct_util.cpp
@@ -316,7 +316,7 @@
bool convertLegacyWifiMacInfoToHidl(
const legacy_hal::WifiMacInfo& legacy_mac_info,
- V1_2::IWifiChipEventCallback::RadioModeInfo* hidl_radio_mode_info) {
+ IWifiChipEventCallback::RadioModeInfo* hidl_radio_mode_info) {
if (!hidl_radio_mode_info) {
return false;
}
@@ -325,8 +325,17 @@
hidl_radio_mode_info->radioId = legacy_mac_info.wlan_mac_id;
// Convert from bitmask of bands in the legacy HAL to enum value in
// the HIDL interface.
- if (legacy_mac_info.mac_band & legacy_hal::WLAN_MAC_2_4_BAND &&
- legacy_mac_info.mac_band & legacy_hal::WLAN_MAC_5_0_BAND) {
+ if (legacy_mac_info.mac_band & legacy_hal::WLAN_MAC_6_0_BAND &&
+ legacy_mac_info.mac_band & legacy_hal::WLAN_MAC_5_0_BAND &&
+ legacy_mac_info.mac_band & legacy_hal::WLAN_MAC_2_4_BAND) {
+ hidl_radio_mode_info->bandInfo = WifiBand::BAND_24GHZ_5GHZ_6GHZ;
+ } else if (legacy_mac_info.mac_band & legacy_hal::WLAN_MAC_6_0_BAND &&
+ legacy_mac_info.mac_band & legacy_hal::WLAN_MAC_5_0_BAND) {
+ hidl_radio_mode_info->bandInfo = WifiBand::BAND_5GHZ_6GHZ;
+ } else if (legacy_mac_info.mac_band & legacy_hal::WLAN_MAC_6_0_BAND) {
+ hidl_radio_mode_info->bandInfo = WifiBand::BAND_6GHZ;
+ } else if (legacy_mac_info.mac_band & legacy_hal::WLAN_MAC_2_4_BAND &&
+ legacy_mac_info.mac_band & legacy_hal::WLAN_MAC_5_0_BAND) {
hidl_radio_mode_info->bandInfo = WifiBand::BAND_24GHZ_5GHZ;
} else if (legacy_mac_info.mac_band & legacy_hal::WLAN_MAC_2_4_BAND) {
hidl_radio_mode_info->bandInfo = WifiBand::BAND_24GHZ;
@@ -348,15 +357,14 @@
bool convertLegacyWifiMacInfosToHidl(
const std::vector<legacy_hal::WifiMacInfo>& legacy_mac_infos,
- std::vector<V1_2::IWifiChipEventCallback::RadioModeInfo>*
- hidl_radio_mode_infos) {
+ std::vector<IWifiChipEventCallback::RadioModeInfo>* hidl_radio_mode_infos) {
if (!hidl_radio_mode_infos) {
return false;
}
*hidl_radio_mode_infos = {};
for (const auto& legacy_mac_info : legacy_mac_infos) {
- V1_2::IWifiChipEventCallback::RadioModeInfo hidl_radio_mode_info;
+ IWifiChipEventCallback::RadioModeInfo hidl_radio_mode_info;
if (!convertLegacyWifiMacInfoToHidl(legacy_mac_info,
&hidl_radio_mode_info)) {
return false;
@@ -449,21 +457,21 @@
return true;
}
-legacy_hal::wifi_band convertHidlWifiBandToLegacy(WifiBand band) {
+legacy_hal::wifi_band convertHidlWifiBandToLegacy(V1_0::WifiBand band) {
switch (band) {
- case WifiBand::BAND_UNSPECIFIED:
+ case V1_0::WifiBand::BAND_UNSPECIFIED:
return legacy_hal::WIFI_BAND_UNSPECIFIED;
- case WifiBand::BAND_24GHZ:
+ case V1_0::WifiBand::BAND_24GHZ:
return legacy_hal::WIFI_BAND_BG;
- case WifiBand::BAND_5GHZ:
+ case V1_0::WifiBand::BAND_5GHZ:
return legacy_hal::WIFI_BAND_A;
- case WifiBand::BAND_5GHZ_DFS:
+ case V1_0::WifiBand::BAND_5GHZ_DFS:
return legacy_hal::WIFI_BAND_A_DFS;
- case WifiBand::BAND_5GHZ_WITH_DFS:
+ case V1_0::WifiBand::BAND_5GHZ_WITH_DFS:
return legacy_hal::WIFI_BAND_A_WITH_DFS;
- case WifiBand::BAND_24GHZ_5GHZ:
+ case V1_0::WifiBand::BAND_24GHZ_5GHZ:
return legacy_hal::WIFI_BAND_ABG;
- case WifiBand::BAND_24GHZ_5GHZ_WITH_DFS:
+ case V1_0::WifiBand::BAND_24GHZ_5GHZ_WITH_DFS:
return legacy_hal::WIFI_BAND_ABG_WITH_DFS;
};
CHECK(false);
diff --git a/wifi/1.4/default/hidl_struct_util.h b/wifi/1.4/default/hidl_struct_util.h
index cfaa4ad..987891b 100644
--- a/wifi/1.4/default/hidl_struct_util.h
+++ b/wifi/1.4/default/hidl_struct_util.h
@@ -21,10 +21,10 @@
#include <android/hardware/wifi/1.0/IWifiChip.h>
#include <android/hardware/wifi/1.0/types.h>
-#include <android/hardware/wifi/1.2/IWifiChipEventCallback.h>
#include <android/hardware/wifi/1.2/types.h>
#include <android/hardware/wifi/1.3/IWifiChip.h>
#include <android/hardware/wifi/1.3/types.h>
+#include <android/hardware/wifi/1.4/IWifiChipEventCallback.h>
#include <android/hardware/wifi/1.4/IWifiStaIface.h>
#include <android/hardware/wifi/1.4/types.h>
@@ -65,8 +65,7 @@
V1_2::IWifiChip::TxPowerScenario hidl_scenario);
bool convertLegacyWifiMacInfosToHidl(
const std::vector<legacy_hal::WifiMacInfo>& legacy_mac_infos,
- std::vector<V1_2::IWifiChipEventCallback::RadioModeInfo>*
- hidl_radio_mode_infos);
+ std::vector<IWifiChipEventCallback::RadioModeInfo>* hidl_radio_mode_infos);
// STA iface conversion methods.
bool convertLegacyFeaturesToHidlStaCapabilities(
@@ -78,7 +77,7 @@
bool convertLegacyGscanCapabilitiesToHidl(
const legacy_hal::wifi_gscan_capabilities& legacy_caps,
StaBackgroundScanCapabilities* hidl_caps);
-legacy_hal::wifi_band convertHidlWifiBandToLegacy(WifiBand band);
+legacy_hal::wifi_band convertHidlWifiBandToLegacy(V1_0::WifiBand band);
bool convertHidlGscanParamsToLegacy(
const StaBackgroundScanParameters& hidl_scan_params,
legacy_hal::wifi_scan_cmd_params* legacy_scan_params);
diff --git a/wifi/1.4/default/tests/hidl_struct_util_unit_tests.cpp b/wifi/1.4/default/tests/hidl_struct_util_unit_tests.cpp
index 14a1504..b71d549 100644
--- a/wifi/1.4/default/tests/hidl_struct_util_unit_tests.cpp
+++ b/wifi/1.4/default/tests/hidl_struct_util_unit_tests.cpp
@@ -55,8 +55,7 @@
legacy_mac_info1.iface_infos.push_back(legacy_iface_info2);
legacy_mac_infos.push_back(legacy_mac_info1);
- std::vector<V1_2::IWifiChipEventCallback::RadioModeInfo>
- hidl_radio_mode_infos;
+ std::vector<IWifiChipEventCallback::RadioModeInfo> hidl_radio_mode_infos;
ASSERT_TRUE(hidl_struct_util::convertLegacyWifiMacInfosToHidl(
legacy_mac_infos, &hidl_radio_mode_infos));
@@ -90,20 +89,18 @@
legacy_mac_info2.iface_infos.push_back(legacy_iface_info2);
legacy_mac_infos.push_back(legacy_mac_info2);
- std::vector<V1_2::IWifiChipEventCallback::RadioModeInfo>
- hidl_radio_mode_infos;
+ std::vector<IWifiChipEventCallback::RadioModeInfo> hidl_radio_mode_infos;
ASSERT_TRUE(hidl_struct_util::convertLegacyWifiMacInfosToHidl(
legacy_mac_infos, &hidl_radio_mode_infos));
ASSERT_EQ(2u, hidl_radio_mode_infos.size());
// Find mac info 1.
- const auto hidl_radio_mode_info1 =
- std::find_if(hidl_radio_mode_infos.begin(), hidl_radio_mode_infos.end(),
- [&legacy_mac_info1](
- const V1_2::IWifiChipEventCallback::RadioModeInfo& x) {
- return x.radioId == legacy_mac_info1.wlan_mac_id;
- });
+ const auto hidl_radio_mode_info1 = std::find_if(
+ hidl_radio_mode_infos.begin(), hidl_radio_mode_infos.end(),
+ [&legacy_mac_info1](const IWifiChipEventCallback::RadioModeInfo& x) {
+ return x.radioId == legacy_mac_info1.wlan_mac_id;
+ });
ASSERT_NE(hidl_radio_mode_infos.end(), hidl_radio_mode_info1);
EXPECT_EQ(WifiBand::BAND_5GHZ, hidl_radio_mode_info1->bandInfo);
ASSERT_EQ(1u, hidl_radio_mode_info1->ifaceInfos.size());
@@ -113,12 +110,11 @@
hidl_iface_info1.channel);
// Find mac info 2.
- const auto hidl_radio_mode_info2 =
- std::find_if(hidl_radio_mode_infos.begin(), hidl_radio_mode_infos.end(),
- [&legacy_mac_info2](
- const V1_2::IWifiChipEventCallback::RadioModeInfo& x) {
- return x.radioId == legacy_mac_info2.wlan_mac_id;
- });
+ const auto hidl_radio_mode_info2 = std::find_if(
+ hidl_radio_mode_infos.begin(), hidl_radio_mode_infos.end(),
+ [&legacy_mac_info2](const IWifiChipEventCallback::RadioModeInfo& x) {
+ return x.radioId == legacy_mac_info2.wlan_mac_id;
+ });
ASSERT_NE(hidl_radio_mode_infos.end(), hidl_radio_mode_info2);
EXPECT_EQ(WifiBand::BAND_24GHZ, hidl_radio_mode_info2->bandInfo);
ASSERT_EQ(1u, hidl_radio_mode_info2->ifaceInfos.size());
diff --git a/wifi/1.4/default/wifi_ap_iface.cpp b/wifi/1.4/default/wifi_ap_iface.cpp
index e677f19..8777a4c 100644
--- a/wifi/1.4/default/wifi_ap_iface.cpp
+++ b/wifi/1.4/default/wifi_ap_iface.cpp
@@ -64,7 +64,7 @@
}
Return<void> WifiApIface::getValidFrequenciesForBand(
- WifiBand band, getValidFrequenciesForBand_cb hidl_status_cb) {
+ V1_0::WifiBand band, getValidFrequenciesForBand_cb hidl_status_cb) {
return validateAndCall(this, WifiStatusCode::ERROR_WIFI_IFACE_INVALID,
&WifiApIface::getValidFrequenciesForBandInternal,
hidl_status_cb, band);
@@ -100,7 +100,7 @@
}
std::pair<WifiStatus, std::vector<WifiChannelInMhz>>
-WifiApIface::getValidFrequenciesForBandInternal(WifiBand band) {
+WifiApIface::getValidFrequenciesForBandInternal(V1_0::WifiBand band) {
static_assert(sizeof(WifiChannelInMhz) == sizeof(uint32_t),
"Size mismatch");
legacy_hal::wifi_error legacy_status;
diff --git a/wifi/1.4/default/wifi_ap_iface.h b/wifi/1.4/default/wifi_ap_iface.h
index 4f3438c..bf16d5e 100644
--- a/wifi/1.4/default/wifi_ap_iface.h
+++ b/wifi/1.4/default/wifi_ap_iface.h
@@ -49,7 +49,8 @@
Return<void> setCountryCode(const hidl_array<int8_t, 2>& code,
setCountryCode_cb hidl_status_cb) override;
Return<void> getValidFrequenciesForBand(
- WifiBand band, getValidFrequenciesForBand_cb hidl_status_cb) override;
+ V1_0::WifiBand band,
+ getValidFrequenciesForBand_cb hidl_status_cb) override;
Return<void> setMacAddress(const hidl_array<uint8_t, 6>& mac,
setMacAddress_cb hidl_status_cb) override;
Return<void> getFactoryMacAddress(
@@ -61,7 +62,7 @@
std::pair<WifiStatus, IfaceType> getTypeInternal();
WifiStatus setCountryCodeInternal(const std::array<int8_t, 2>& code);
std::pair<WifiStatus, std::vector<WifiChannelInMhz>>
- getValidFrequenciesForBandInternal(WifiBand band);
+ getValidFrequenciesForBandInternal(V1_0::WifiBand band);
WifiStatus setMacAddressInternal(const std::array<uint8_t, 6>& mac);
std::pair<WifiStatus, std::array<uint8_t, 6>>
getFactoryMacAddressInternal();
diff --git a/wifi/1.4/default/wifi_chip.cpp b/wifi/1.4/default/wifi_chip.cpp
index 40f73b5..2b015d3 100644
--- a/wifi/1.4/default/wifi_chip.cpp
+++ b/wifi/1.4/default/wifi_chip.cpp
@@ -341,7 +341,7 @@
bool WifiChip::isValid() { return is_valid_; }
-std::set<sp<V1_2::IWifiChipEventCallback>> WifiChip::getEventCallbacks() {
+std::set<sp<IWifiChipEventCallback>> WifiChip::getEventCallbacks() {
return event_cb_handler_.getCallbacks();
}
@@ -628,6 +628,14 @@
hidl_status_cb, bound_iface);
}
+Return<void> WifiChip::registerEventCallback_1_4(
+ const sp<IWifiChipEventCallback>& event_callback,
+ registerEventCallback_cb hidl_status_cb) {
+ return validateAndCall(this, WifiStatusCode::ERROR_WIFI_CHIP_INVALID,
+ &WifiChip::registerEventCallbackInternal_1_4,
+ hidl_status_cb, event_callback);
+}
+
void WifiChip::invalidateAndRemoveAllIfaces() {
invalidateAndClearAll(ap_ifaces_);
invalidateAndClearAll(nan_ifaces_);
@@ -1125,11 +1133,9 @@
}
WifiStatus WifiChip::registerEventCallbackInternal_1_2(
- const sp<V1_2::IWifiChipEventCallback>& event_callback) {
- if (!event_cb_handler_.addCallback(event_callback)) {
- return createWifiStatus(WifiStatusCode::ERROR_UNKNOWN);
- }
- return createWifiStatus(WifiStatusCode::SUCCESS);
+ const sp<V1_2::IWifiChipEventCallback>& /* event_callback */) {
+ // Deprecated support for this callback.
+ return createWifiStatus(WifiStatusCode::ERROR_NOT_SUPPORTED);
}
WifiStatus WifiChip::selectTxPowerScenarioInternal_1_2(
@@ -1179,6 +1185,14 @@
return {createWifiStatus(WifiStatusCode::SUCCESS), rtt};
}
+WifiStatus WifiChip::registerEventCallbackInternal_1_4(
+ const sp<IWifiChipEventCallback>& event_callback) {
+ if (!event_cb_handler_.addCallback(event_callback)) {
+ return createWifiStatus(WifiStatusCode::ERROR_UNKNOWN);
+ }
+ return createWifiStatus(WifiStatusCode::SUCCESS);
+}
+
WifiStatus WifiChip::handleChipConfiguration(
/* NONNULL */ std::unique_lock<std::recursive_mutex>* lock,
ChipModeId mode_id) {
@@ -1281,7 +1295,7 @@
LOG(ERROR) << "Callback invoked on an invalid object";
return;
}
- std::vector<V1_2::IWifiChipEventCallback::RadioModeInfo>
+ std::vector<IWifiChipEventCallback::RadioModeInfo>
hidl_radio_mode_infos;
if (!hidl_struct_util::convertLegacyWifiMacInfosToHidl(
mac_infos, &hidl_radio_mode_infos)) {
@@ -1289,9 +1303,9 @@
return;
}
for (const auto& callback : shared_ptr_this->getEventCallbacks()) {
- if (!callback->onRadioModeChange(hidl_radio_mode_infos)
+ if (!callback->onRadioModeChange_1_4(hidl_radio_mode_infos)
.isOk()) {
- LOG(ERROR) << "Failed to invoke onRadioModeChange"
+ LOG(ERROR) << "Failed to invoke onRadioModeChange_1_4"
<< " callback on: " << toString(callback);
}
}
diff --git a/wifi/1.4/default/wifi_chip.h b/wifi/1.4/default/wifi_chip.h
index 3bf1847..c76eabf 100644
--- a/wifi/1.4/default/wifi_chip.h
+++ b/wifi/1.4/default/wifi_chip.h
@@ -71,7 +71,7 @@
// marked valid before processing them.
void invalidate();
bool isValid();
- std::set<sp<V1_2::IWifiChipEventCallback>> getEventCallbacks();
+ std::set<sp<IWifiChipEventCallback>> getEventCallbacks();
// HIDL methods exposed.
Return<void> getId(getId_cb hidl_status_cb) override;
@@ -156,6 +156,9 @@
Return<void> createRttController_1_4(
const sp<IWifiIface>& bound_iface,
createRttController_1_4_cb hidl_status_cb) override;
+ Return<void> registerEventCallback_1_4(
+ const sp<IWifiChipEventCallback>& event_callback,
+ registerEventCallback_1_4_cb hidl_status_cb) override;
private:
void invalidateAndRemoveAllIfaces();
@@ -223,6 +226,9 @@
std::pair<WifiStatus, uint32_t> getCapabilitiesInternal_1_3();
std::pair<WifiStatus, sp<IWifiRttController>>
createRttControllerInternal_1_4(const sp<IWifiIface>& bound_iface);
+ WifiStatus registerEventCallbackInternal_1_4(
+ const sp<IWifiChipEventCallback>& event_callback);
+
WifiStatus handleChipConfiguration(
std::unique_lock<std::recursive_mutex>* lock, ChipModeId mode_id);
WifiStatus registerDebugRingBufferCallback();
@@ -271,7 +277,7 @@
// registration mechanism. Use this to check if we have already
// registered a callback.
bool debug_ring_buffer_cb_registered_;
- hidl_callback_util::HidlCallbackHandler<V1_2::IWifiChipEventCallback>
+ hidl_callback_util::HidlCallbackHandler<IWifiChipEventCallback>
event_cb_handler_;
DISALLOW_COPY_AND_ASSIGN(WifiChip);
diff --git a/wifi/1.4/default/wifi_sta_iface.cpp b/wifi/1.4/default/wifi_sta_iface.cpp
index 8e1ada1..68c989d 100644
--- a/wifi/1.4/default/wifi_sta_iface.cpp
+++ b/wifi/1.4/default/wifi_sta_iface.cpp
@@ -113,7 +113,7 @@
}
Return<void> WifiStaIface::getValidFrequenciesForBand(
- WifiBand band, getValidFrequenciesForBand_cb hidl_status_cb) {
+ V1_0::WifiBand band, getValidFrequenciesForBand_cb hidl_status_cb) {
return validateAndCall(this, WifiStatusCode::ERROR_WIFI_IFACE_INVALID,
&WifiStaIface::getValidFrequenciesForBandInternal,
hidl_status_cb, band);
@@ -344,7 +344,7 @@
}
std::pair<WifiStatus, std::vector<WifiChannelInMhz>>
-WifiStaIface::getValidFrequenciesForBandInternal(WifiBand band) {
+WifiStaIface::getValidFrequenciesForBandInternal(V1_0::WifiBand band) {
static_assert(sizeof(WifiChannelInMhz) == sizeof(uint32_t),
"Size mismatch");
legacy_hal::wifi_error legacy_status;
diff --git a/wifi/1.4/default/wifi_sta_iface.h b/wifi/1.4/default/wifi_sta_iface.h
index ccf234f..e85e39d 100644
--- a/wifi/1.4/default/wifi_sta_iface.h
+++ b/wifi/1.4/default/wifi_sta_iface.h
@@ -63,7 +63,8 @@
Return<void> getBackgroundScanCapabilities(
getBackgroundScanCapabilities_cb hidl_status_cb) override;
Return<void> getValidFrequenciesForBand(
- WifiBand band, getValidFrequenciesForBand_cb hidl_status_cb) override;
+ V1_0::WifiBand band,
+ getValidFrequenciesForBand_cb hidl_status_cb) override;
Return<void> startBackgroundScan(
uint32_t cmd_id, const StaBackgroundScanParameters& params,
startBackgroundScan_cb hidl_status_cb) override;
@@ -130,7 +131,7 @@
std::pair<WifiStatus, StaBackgroundScanCapabilities>
getBackgroundScanCapabilitiesInternal();
std::pair<WifiStatus, std::vector<WifiChannelInMhz>>
- getValidFrequenciesForBandInternal(WifiBand band);
+ getValidFrequenciesForBandInternal(V1_0::WifiBand band);
WifiStatus startBackgroundScanInternal(
uint32_t cmd_id, const StaBackgroundScanParameters& params);
WifiStatus stopBackgroundScanInternal(uint32_t cmd_id);
diff --git a/wifi/1.4/types.hal b/wifi/1.4/types.hal
index 232e26f..0db0c2c 100644
--- a/wifi/1.4/types.hal
+++ b/wifi/1.4/types.hal
@@ -26,6 +26,7 @@
import @1.0::RttType;
import @1.0::TimeSpanInPs;
import @1.0::TimeStampInUs;
+import @1.0::WifiBand;
import @1.0::WifiChannelInfo;
import @1.0::WifiChannelWidthInMhz;
import @1.0::WifiInformationElement;
@@ -33,6 +34,28 @@
import @1.0::WifiRatePreamble;
/**
+ * Wifi bands defined in 80211 spec.
+ */
+enum WifiBand : @1.0::WifiBand {
+ /**
+ * 6 GHz.
+ */
+ BAND_6GHZ = 8,
+ /**
+ * 5 GHz no DFS + 6 GHz.
+ */
+ BAND_5GHZ_6GHZ = 10,
+ /**
+ * 2.4 GHz + 5 GHz no DFS + 6 GHz.
+ */
+ BAND_24GHZ_5GHZ_6GHZ = 11,
+ /**
+ * 2.4 GHz + 5 GHz with DFS + 6 GHz.
+ */
+ BAND_24GHZ_5GHZ_WITH_DFS_6GHZ = 15
+};
+
+/**
* Wifi Rate Preamble
*/
enum WifiRatePreamble : @1.0::WifiRatePreamble {
diff --git a/wifi/1.4/vts/functional/Android.bp b/wifi/1.4/vts/functional/Android.bp
index c71b319..f3be25d 100644
--- a/wifi/1.4/vts/functional/Android.bp
+++ b/wifi/1.4/vts/functional/Android.bp
@@ -21,6 +21,7 @@
srcs: [
"VtsHalWifiV1_4TargetTest.cpp",
"wifi_ap_iface_hidl_test.cpp",
+ "wifi_chip_hidl_test.cpp"
],
static_libs: [
"VtsHalWifiV1_0TargetTestUtil",
diff --git a/wifi/1.4/vts/functional/wifi_chip_hidl_test.cpp b/wifi/1.4/vts/functional/wifi_chip_hidl_test.cpp
new file mode 100644
index 0000000..8ca5214
--- /dev/null
+++ b/wifi/1.4/vts/functional/wifi_chip_hidl_test.cpp
@@ -0,0 +1,135 @@
+/*
+ * 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.
+ */
+
+#include <VtsHalHidlTargetCallbackBase.h>
+#include <android-base/logging.h>
+
+#undef NAN // NAN is defined in bionic/libc/include/math.h:38
+
+#include <android/hardware/wifi/1.4/IWifi.h>
+#include <android/hardware/wifi/1.4/IWifiChip.h>
+#include <android/hardware/wifi/1.4/IWifiChipEventCallback.h>
+#include <gtest/gtest.h>
+#include <hidl/GtestPrinter.h>
+#include <hidl/ServiceManagement.h>
+
+#include "wifi_hidl_call_util.h"
+#include "wifi_hidl_test_utils.h"
+
+using ::android::sp;
+using ::android::hardware::hidl_string;
+using ::android::hardware::hidl_vec;
+using ::android::hardware::Return;
+using ::android::hardware::Void;
+using ::android::hardware::wifi::V1_0::IfaceType;
+using ::android::hardware::wifi::V1_0::WifiDebugRingBufferStatus;
+using ::android::hardware::wifi::V1_0::WifiStatus;
+using ::android::hardware::wifi::V1_0::WifiStatusCode;
+using ::android::hardware::wifi::V1_4::IWifiChip;
+using ::android::hardware::wifi::V1_4::IWifiChipEventCallback;
+
+/**
+ * Fixture to use for all Wifi chip HIDL interface tests.
+ */
+class WifiChipHidlTest : public ::testing::TestWithParam<std::string> {
+ public:
+ virtual void SetUp() override {
+ wifi_chip_ = IWifiChip::castFrom(getWifiChip(GetInstanceName()));
+ ASSERT_NE(nullptr, wifi_chip_.get());
+ }
+
+ virtual void TearDown() override { stopWifi(GetInstanceName()); }
+
+ // A simple test implementation of WifiChipEventCallback.
+ class WifiChipEventCallback
+ : public ::testing::VtsHalHidlTargetCallbackBase<WifiChipHidlTest>,
+ public IWifiChipEventCallback {
+ public:
+ WifiChipEventCallback(){};
+
+ virtual ~WifiChipEventCallback() = default;
+
+ Return<void> onChipReconfigured(uint32_t modeId __unused) {
+ return Void();
+ };
+
+ Return<void> onChipReconfigureFailure(
+ const WifiStatus& status __unused) {
+ return Void();
+ };
+
+ Return<void> onIfaceAdded(IfaceType type __unused,
+ const hidl_string& name __unused) {
+ return Void();
+ };
+
+ Return<void> onIfaceRemoved(IfaceType type __unused,
+ const hidl_string& name __unused) {
+ return Void();
+ };
+
+ Return<void> onDebugRingBufferDataAvailable(
+ const WifiDebugRingBufferStatus& status __unused,
+ const hidl_vec<uint8_t>& data __unused) {
+ return Void();
+ };
+
+ Return<void> onDebugErrorAlert(int32_t errorCode __unused,
+ const hidl_vec<uint8_t>& debugData
+ __unused) {
+ return Void();
+ };
+
+ Return<void> onRadioModeChange(
+ const hidl_vec<::android::hardware::wifi::V1_2::
+ IWifiChipEventCallback::RadioModeInfo>&
+ radioModeInfos __unused) {
+ return Void();
+ };
+
+ Return<void> onRadioModeChange_1_4(
+ const hidl_vec<RadioModeInfo>& radioModeInfos __unused) {
+ return Void();
+ };
+ };
+
+ protected:
+ sp<IWifiChip> wifi_chip_;
+
+ private:
+ std::string GetInstanceName() { return GetParam(); }
+};
+
+/*
+ * registerEventCallback_1_4
+ * This test case tests the registerEventCallback_1_4() API which registers
+ * a call back function with the hal implementation
+ *
+ * Note: it is not feasible to test the invocation of the call back function
+ * since event is triggered internally in the HAL implementation, and can not be
+ * triggered from the test case
+ */
+TEST_P(WifiChipHidlTest, registerEventCallback_1_4) {
+ sp<WifiChipEventCallback> wifiChipEventCallback =
+ new WifiChipEventCallback();
+ const auto& status = HIDL_INVOKE(wifi_chip_, registerEventCallback_1_4,
+ wifiChipEventCallback);
+
+ if (status.code != WifiStatusCode::SUCCESS) {
+ EXPECT_EQ(WifiStatusCode::ERROR_NOT_SUPPORTED, status.code);
+ return;
+ }
+}