Merge "Revert "add NFC component_type""
diff --git a/Android.bp b/Android.bp
index 2ef4e4c..dca108d 100644
--- a/Android.bp
+++ b/Android.bp
@@ -4,8 +4,13 @@
"audio/common/2.0",
"audio/effect/2.0",
"benchmarks/msgq/1.0",
+ "biometrics/fingerprint/2.1",
+ "gnss/1.0",
+ "bluetooth/1.0",
"graphics/allocator/2.0",
"graphics/allocator/2.0/default",
+ "graphics/composer/2.1",
+ "graphics/composer/2.1/default",
"graphics/mapper/2.0",
"graphics/mapper/2.0/default",
"light/2.0",
@@ -16,16 +21,24 @@
"power/1.0",
"power/1.0/default",
"radio/1.0",
+ "sensors/1.0",
+ "sensors/1.0/default",
"soundtrigger/2.0",
"tests/bar/1.0",
+ "tests/bar/1.0/default",
"tests/baz/1.0",
"tests/expression/1.0",
"tests/foo/1.0",
+ "tests/foo/1.0/default",
"tests/libhwbinder/1.0",
"tests/msgq/1.0",
"tests/pointer/1.0",
+ "tests/pointer/1.0/default",
+ "thermal/1.0",
+ "thermal/1.0/default",
"vehicle/2.0",
"vibrator/1.0",
+ "vibrator/1.0/default",
"wifi/1.0",
"wifi/supplicant/1.0",
]
diff --git a/benchmarks/msgq/1.0/IBenchmarkMsgQ.hal b/benchmarks/msgq/1.0/IBenchmarkMsgQ.hal
index 2e50335..3af0b71 100644
--- a/benchmarks/msgq/1.0/IBenchmarkMsgQ.hal
+++ b/benchmarks/msgq/1.0/IBenchmarkMsgQ.hal
@@ -20,36 +20,37 @@
/*
* This method requests the service to set up Synchronous read/write
* wait-free FMQ with the client as reader.
- * @return ret Will be 0 if the setup is successful.
+ * @return ret Will be true if the setup was successful, false otherwise.
* @return mqDescIn This structure describes the FMQ that was set up
* by the service. Client can use it to set up the FMQ at its end.
*/
configureClientInboxSyncReadWrite()
- generates(int32_t ret, MQDescriptorSync mqDescIn);
+ generates(bool ret, MQDescriptorSync mqDescIn);
/*
* This method requests the service to set up Synchronous read/write
* wait-free FMQ with the client as writer.
- * @return Will be 0 if the setup is successful.
+ * @return ret Will be true if the setup was successful, false otherwise.
* @return mqDescOut This structure describes the FMQ that was set up
* by the service. Client can use it to set up the FMQ at its end.
*/
configureClientOutboxSyncReadWrite()
- generates(int32_t ret, MQDescriptorSync mqDescOut);
+ generates(bool ret, MQDescriptorSync mqDescOut);
/*
* This method request the service to write into the FMQ.
* @param count Number to messages to write.
- * @ret Number of messages succesfully written.
+ * @return ret Will be true if the write operation was successful,
+ * false otherwise.
*/
- requestWrite(int32_t count) generates (int32_t ret);
+ requestWrite(int32_t count) generates (bool ret);
/*
* This method request the service to read from the FMQ.
* @param count Number to messages to read.
- * @ret Number of messages succesfully read.
+ * @ret Will be true if the read operation was successful, false otherwise.
*/
- requestRead(int32_t count) generates (int32_t ret);
+ requestRead(int32_t count) generates (bool ret);
/*
* This method kicks off a benchmarking experiment where
diff --git a/biometrics/fingerprint/2.1/Android.bp b/biometrics/fingerprint/2.1/Android.bp
new file mode 100644
index 0000000..77b41b8
--- /dev/null
+++ b/biometrics/fingerprint/2.1/Android.bp
@@ -0,0 +1,54 @@
+// This file is autogenerated by hidl-gen. Do not edit manually.
+
+genrule {
+ name: "android.hardware.biometrics.fingerprint@2.1_genc++",
+ tool: "hidl-gen",
+ cmd: "$tool -o $genDir -Lc++ -randroid.hardware:hardware/interfaces android.hardware.biometrics.fingerprint@2.1",
+ srcs: [
+ "types.hal",
+ "IBiometricsFingerprint.hal",
+ "IBiometricsFingerprintClientCallback.hal",
+ ],
+ out: [
+ "android/hardware/biometrics/fingerprint/2.1/types.cpp",
+ "android/hardware/biometrics/fingerprint/2.1/BiometricsFingerprintAll.cpp",
+ "android/hardware/biometrics/fingerprint/2.1/BiometricsFingerprintClientCallbackAll.cpp",
+ ],
+}
+
+genrule {
+ name: "android.hardware.biometrics.fingerprint@2.1_genc++_headers",
+ tool: "hidl-gen",
+ cmd: "$tool -o $genDir -Lc++ -randroid.hardware:hardware/interfaces android.hardware.biometrics.fingerprint@2.1",
+ srcs: [
+ "types.hal",
+ "IBiometricsFingerprint.hal",
+ "IBiometricsFingerprintClientCallback.hal",
+ ],
+ out: [
+ "android/hardware/biometrics/fingerprint/2.1/types.h",
+ "android/hardware/biometrics/fingerprint/2.1/IBiometricsFingerprint.h",
+ "android/hardware/biometrics/fingerprint/2.1/IHwBiometricsFingerprint.h",
+ "android/hardware/biometrics/fingerprint/2.1/BnBiometricsFingerprint.h",
+ "android/hardware/biometrics/fingerprint/2.1/BpBiometricsFingerprint.h",
+ "android/hardware/biometrics/fingerprint/2.1/BsBiometricsFingerprint.h",
+ "android/hardware/biometrics/fingerprint/2.1/IBiometricsFingerprintClientCallback.h",
+ "android/hardware/biometrics/fingerprint/2.1/IHwBiometricsFingerprintClientCallback.h",
+ "android/hardware/biometrics/fingerprint/2.1/BnBiometricsFingerprintClientCallback.h",
+ "android/hardware/biometrics/fingerprint/2.1/BpBiometricsFingerprintClientCallback.h",
+ "android/hardware/biometrics/fingerprint/2.1/BsBiometricsFingerprintClientCallback.h",
+ ],
+}
+
+cc_library_shared {
+ name: "android.hardware.biometrics.fingerprint@2.1",
+ generated_sources: ["android.hardware.biometrics.fingerprint@2.1_genc++"],
+ generated_headers: ["android.hardware.biometrics.fingerprint@2.1_genc++_headers"],
+ export_generated_headers: ["android.hardware.biometrics.fingerprint@2.1_genc++_headers"],
+ shared_libs: [
+ "libhidl",
+ "libhwbinder",
+ "libutils",
+ "libcutils",
+ ],
+}
diff --git a/biometrics/fingerprint/2.1/IBiometricsFingerprint.hal b/biometrics/fingerprint/2.1/IBiometricsFingerprint.hal
new file mode 100644
index 0000000..a9c3190
--- /dev/null
+++ b/biometrics/fingerprint/2.1/IBiometricsFingerprint.hal
@@ -0,0 +1,157 @@
+/*
+ * 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.
+ */
+
+package android.hardware.biometrics.fingerprint@2.1;
+
+interface IBiometricsFingerprint {
+ /*
+ * Fingerprint pre-enroll enroll request:
+ * Generates a unique token to upper layers to indicate the start of
+ * an enrollment transaction. pre-enroll and post-enroll specify
+ * a pin/password cleared time window where enrollment is allowed.
+ * Pre-enroll only generates a challenge, a full hardwareAuthToken is
+ * generated by trustzone after verifying a pin/password/swipe. This is to
+ * ensure adding a new fingerprint template was preceded by some kind of
+ * credential confirmation (e.g. device password).
+ *
+ * @return 0 if function failed, a uint64_t of challenge otherwise.
+ */
+ @callflow(next={"enroll", "postEnroll"})
+ preEnroll() generates (uint64_t authChallenge);
+
+ /*
+ * Fingerprint enroll request:
+ * Switches the HAL state machine to collect and store a new fingerprint
+ * template. Switches back as soon as enroll is complete, signalled by
+ * (fingerprintMsg.type == FINGERPRINT_TEMPLATE_ENROLLING &&
+ * fingerprintMsg.data.enroll.samplesRemaining == 0)
+ * or after timeoutSec seconds.
+ * The fingerprint template must be assigned to the group gid.
+ *
+ * @param hat a valid Hardware Authentication Token (HAT), generated
+ * as a result of a preEnroll() call.
+ * @param gid a framework defined fingerprint set (group) id.
+ * @param timeoutSec a timeout in seconds.
+ *
+ * @return isOk indicates if the request is accepted.
+ * @return debugErrno is a value the framework logs in case isOk == false.
+ *
+ * A notify() function may be called with a more detailed error structure.
+ */
+ @callflow(next={"cancel", "enroll", "postEnroll", "remove"})
+ enroll(HwAuthToken hat, uint32_t gid, uint32_t timeoutSec)
+ generates (bool isOk, int32_t debugErrno);
+
+ /*
+ * Finishes the enroll operation and invalidates the preEnroll() generated
+ * challenge. This must be called at the end of a multi-finger enrollment
+ * session to indicate that no more fingers may be added.
+ *
+ * @return isOk indicates if the request is accepted.
+ * @return debugErrno is a value the framework logs in case isOk == false.
+ */
+ @callflow(next={"authenticate", "setActiveGroup", "enumerate", "remove"})
+ postEnroll() generates (bool isOk, int32_t debugErrno);
+
+ /*
+ * getAuthenticatorId:
+ * Returns a token associated with the current fingerprint set. This value
+ * must change whenever a new fingerprint is enrolled, thus creating a new
+ * fingerprint set.
+ *
+ * @return getAuthenticatorIdRet current authenticator id, 0 if function
+ * failed.
+ */
+ @callflow(next={"authenticate"})
+ getAuthenticatorId() generates (uint64_t AuthenticatorId);
+
+ /*
+ * Cancel pending enroll or authenticate, sending FINGERPRINT_ERROR_CANCELED
+ * to all running clients. Switches the HAL state machine back to the idle
+ * state. Unlike enrollDone() doesn't invalidate the preEnroll() challenge.
+ *
+ * @return isOk indicates if the request is accepted.
+ * @return debugErrno is a value the framework logs in case isOk == false.
+ */
+ @callflow(next={"authenticate", "enroll", "enumerate", "remove",
+ "setActiveGroup"})
+ cancel() generates (bool isOk, int32_t debugErrno);
+
+ /*
+ * Enumerate all the fingerprint templates found in the directory set by
+ * setActiveGroup():
+ * For each template found a notify() must be called with:
+ * fingerprintMsg.type == FINGERPRINT_TEMPLATE_ENUMERATED
+ * fingerprintMsg.data.enumerated.finger indicating a template id
+ * fingerprintMsg.data.enumerated.remainingTemplates indicating how many more
+ * enumeration messages to expect.
+ *
+ * @return isOk indicates if the request is accepted.
+ * @return debugErrno is a value the framework logs in case isOk == false.
+ */
+ @callflow(next={"remove", "enroll", "authenticate", "setActiveGroup"})
+ enumerate() generates (bool isOk, int32_t debugErrno);
+
+ /*
+ * Fingerprint remove request:
+ * Deletes fingerprint template(s).
+ * Works only within the path set by setActiveGroup().
+ * For each template found a notify() must be called with:
+ * fingerprintMsg.type == FINGERPRINT_TEMPLATE_REMOVED
+ * fingerprintMsg.data.removed.finger indicating the template id deleted
+ * fingerprintMsg.data.removed.remainingTemplates indicating how many more
+ * templates must be deleted by this operation.
+ *
+ * @param gid group id must match the last group set by setActiveGroup().
+ * @param fid template id to delete or 0 to delete all templates within the
+ * current group.
+ *
+ * @return isOk indicates if the request is accepted.
+ * @return debugErrno is a value the framework logs in case isOk == false.
+ */
+ @callflow(next={"enumerate", "authenticate", "cancel", "getAuthenticatorId",
+ "setActiveGroup"})
+ remove(uint32_t gid, uint32_t fid) generates (bool isOk, int32_t debugErrno);
+
+ /*
+ * Restricts the HAL operation to a set of fingerprints belonging to a group
+ * provided. The caller must provide a path to a storage location within the
+ * user's data directory.
+ *
+ * @param gid the fingerprint group (set) id.
+ * @param storePath filesystem path to the template storage directory.
+ *
+ * @return isOk indicates if the request is accepted.
+ * @return debugErrno is a value the framework logs in case isOk == false.
+ */
+ @callflow(next={"authenticate", "preEnroll", "enumerate", "remove"})
+ @entry
+ setActiveGroup(uint32_t gid, string storePath)
+ generates (bool isOk, int32_t debugErrno);
+
+ /*
+ * Authenticates an operation identifed by operationId
+ *
+ * @param operationId operation id.
+ * @param gid fingerprint group id.
+ *
+ * @return isOk indicates if the request is accepted.
+ * @return debugErrno is a value the framework logs in case isOk == false.
+ */
+ @callflow(next={"cancel", "preEnroll", "remove"})
+ authenticate(uint64_t operationId, uint32_t gid)
+ generates (bool isOk, int32_t debugErrno);
+};
diff --git a/biometrics/fingerprint/2.1/IBiometricsFingerprintClientCallback.hal b/biometrics/fingerprint/2.1/IBiometricsFingerprintClientCallback.hal
new file mode 100644
index 0000000..365e905
--- /dev/null
+++ b/biometrics/fingerprint/2.1/IBiometricsFingerprintClientCallback.hal
@@ -0,0 +1,27 @@
+/*
+ * 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.
+ */
+
+package android.hardware.biometrics.fingerprint@2.1;
+
+interface IBiometricsFingerprintClientCallback {
+ /* This function is the response chanel for all messages
+ * coming from the fingerprint HAL to the framework
+ *
+ * @param msg a union of message structures identified by
+ * FingerprintMsg.type
+ */
+ oneway notify(FingerprintMsg msg);
+};
diff --git a/biometrics/fingerprint/2.1/types.hal b/biometrics/fingerprint/2.1/types.hal
new file mode 100644
index 0000000..cf68c04
--- /dev/null
+++ b/biometrics/fingerprint/2.1/types.hal
@@ -0,0 +1,148 @@
+/*
+ * 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.
+ */
+
+package android.hardware.biometrics.fingerprint@2.1;
+
+/*
+ * Fingerprint errors are meant to tell the framework to terminate the current
+ * operation and ask for the user to correct the situation. These will almost
+ * always result in messaging and user interaction to correct the problem.
+ *
+ * For example, ERROR_CANCELED should follow any acquisition message that
+ * results in a situation where the current operation can't continue without
+ * user interaction. For example, if the sensor is dirty during enrollment and
+ * no further enrollment progress can be made, send ACQUIRED_IMAGER_DIRTY
+ * followed by ERROR_CANCELED.
+ */
+enum FingerprintError : int32_t {
+ /* The hardware has an error that can't be resolved. */
+ ERROR_HW_UNAVAILABLE = 1,
+ /* Bad data; operation can't continue */
+ ERROR_UNABLE_TO_PROCESS = 2,
+ /* The operation has timed out waiting for user input. */
+ ERROR_TIMEOUT = 3,
+ /* No space available to store a template */
+ ERROR_NO_SPACE = 4,
+ /* The current operation has been canceled */
+ ERROR_CANCELED = 5,
+ /* Unable to remove a template */
+ ERROR_UNABLE_TO_REMOVE = 6,
+};
+
+/*
+ * Fingerprint acquisition info is meant as feedback for the current operation.
+ * Anything but ACQUIRED_GOOD must be shown to the user as feedback on how to
+ * take action on the current operation. For example, ACQUIRED_IMAGER_DIRTY may
+ * be used to tell the user to clean the sensor if it is detected to be dirty.
+ * If this causes the current operation to fail, an additional ERROR_CANCELED
+ * must be sent to stop the operation in progress (e.g. enrollment).
+ * In general, these messages will result in a "Try again" message.
+ */
+enum FingerprintAcquiredInfo : int32_t {
+ ACQUIRED_GOOD = 0,
+ /* sensor needs more data, i.e. longer swipe. */
+ ACQUIRED_PARTIAL = 1,
+ /* image doesn't contain enough detail for recognition*/
+ ACQUIRED_INSUFFICIENT = 2,
+ /* sensor needs to be cleaned */
+ ACQUIRED_IMAGER_DIRTY = 3,
+ /* mostly swipe-type sensors; not enough data collected */
+ ACQUIRED_TOO_SLOW = 4,
+ /* vendor-specific acquisition messages start here */
+ ACQUIRED_TOO_FAST = 5,
+ ACQUIRED_VENDOR_BASE = 1000,
+};
+
+/* TODO import from keymaster HIDL when available */
+enum HwAuthenticatorType : uint32_t {
+ HW_AUTH_NONE = 0,
+ HW_AUTH_PASSWORD = 1,
+ HW_AUTH_FINGERPRINT = 2,
+ HW_AUTH_ANY = 0xffffffff,
+};
+
+/* TODO import from keymaster HIDL when available */
+struct HwAuthToken {
+ uint8_t version;
+ uint64_t challenge;
+ uint64_t userId;
+ uint64_t authenticatorId;
+ uint32_t authenticatorType;
+ uint64_t timestamp;
+ uint8_t[32] hmac;
+};
+
+struct FingerprintFingerId {
+ /* Group ID */
+ uint32_t gid;
+ /* Fingerprint template ID */
+ uint32_t fid;
+};
+
+struct FingerprintEnroll {
+ /* Template ID */
+ FingerprintFingerId finger;
+ /* samplesRemaining goes from N (no data collected, but N scans needed)
+ * to 0 (no more data is needed to build a template). */
+ uint32_t samplesRemaining;
+ /* Vendor specific message. Used for user guidance */
+ uint64_t msg;
+};
+
+struct FingerprintIterator {
+ /* Template ID */
+ FingerprintFingerId finger;
+ /* How many templates remain to iterate through */
+ uint32_t remainingTemplates;
+};
+
+typedef FingerprintIterator FingerprintEnumerated;
+typedef FingerprintIterator FingerprintRemoved;
+
+struct FingerprintAcquired {
+ /* information about the image */
+ FingerprintAcquiredInfo acquiredInfo;
+};
+
+struct FingerprintAuthenticated {
+ /* Matched template ID */
+ FingerprintFingerId finger;
+ /* Authentication result from the keymaster */
+ HwAuthToken hat;
+};
+
+/* Run time type identification for the notify() call payload. */
+enum FingerprintMsgType : int32_t {
+ ERROR = -1,
+ ACQUIRED = 1,
+ TEMPLATE_ENROLLING = 3,
+ TEMPLATE_REMOVED = 4,
+ AUTHENTICATED = 5,
+ TEMPLATE_ENUMERATING = 6,
+};
+
+struct FingerprintMsg {
+ /* Selects the payload below */
+ FingerprintMsgType type;
+ union data {
+ FingerprintError error;
+ FingerprintEnroll enroll;
+ FingerprintEnumerated enumerated;
+ FingerprintRemoved removed;
+ FingerprintAcquired acquired;
+ FingerprintAuthenticated authenticated;
+ };
+};
diff --git a/bluetooth/1.0/Android.bp b/bluetooth/1.0/Android.bp
new file mode 100644
index 0000000..c5f898d
--- /dev/null
+++ b/bluetooth/1.0/Android.bp
@@ -0,0 +1,54 @@
+// This file is autogenerated by hidl-gen. Do not edit manually.
+
+genrule {
+ name: "android.hardware.bluetooth@1.0_genc++",
+ tool: "hidl-gen",
+ cmd: "$tool -o $genDir -Lc++ -randroid.hardware:hardware/interfaces android.hardware.bluetooth@1.0",
+ srcs: [
+ "types.hal",
+ "IBluetoothHci.hal",
+ "IBluetoothHciCallbacks.hal",
+ ],
+ out: [
+ "android/hardware/bluetooth/1.0/types.cpp",
+ "android/hardware/bluetooth/1.0/BluetoothHciAll.cpp",
+ "android/hardware/bluetooth/1.0/BluetoothHciCallbacksAll.cpp",
+ ],
+}
+
+genrule {
+ name: "android.hardware.bluetooth@1.0_genc++_headers",
+ tool: "hidl-gen",
+ cmd: "$tool -o $genDir -Lc++ -randroid.hardware:hardware/interfaces android.hardware.bluetooth@1.0",
+ srcs: [
+ "types.hal",
+ "IBluetoothHci.hal",
+ "IBluetoothHciCallbacks.hal",
+ ],
+ out: [
+ "android/hardware/bluetooth/1.0/types.h",
+ "android/hardware/bluetooth/1.0/IBluetoothHci.h",
+ "android/hardware/bluetooth/1.0/IHwBluetoothHci.h",
+ "android/hardware/bluetooth/1.0/BnBluetoothHci.h",
+ "android/hardware/bluetooth/1.0/BpBluetoothHci.h",
+ "android/hardware/bluetooth/1.0/BsBluetoothHci.h",
+ "android/hardware/bluetooth/1.0/IBluetoothHciCallbacks.h",
+ "android/hardware/bluetooth/1.0/IHwBluetoothHciCallbacks.h",
+ "android/hardware/bluetooth/1.0/BnBluetoothHciCallbacks.h",
+ "android/hardware/bluetooth/1.0/BpBluetoothHciCallbacks.h",
+ "android/hardware/bluetooth/1.0/BsBluetoothHciCallbacks.h",
+ ],
+}
+
+cc_library_shared {
+ name: "android.hardware.bluetooth@1.0",
+ generated_sources: ["android.hardware.bluetooth@1.0_genc++"],
+ generated_headers: ["android.hardware.bluetooth@1.0_genc++_headers"],
+ export_generated_headers: ["android.hardware.bluetooth@1.0_genc++_headers"],
+ shared_libs: [
+ "libhidl",
+ "libhwbinder",
+ "libutils",
+ "libcutils",
+ ],
+}
diff --git a/bluetooth/1.0/Android.mk b/bluetooth/1.0/Android.mk
new file mode 100644
index 0000000..7100765
--- /dev/null
+++ b/bluetooth/1.0/Android.mk
@@ -0,0 +1,144 @@
+# This file is autogenerated by hidl-gen. Do not edit manually.
+
+LOCAL_PATH := $(call my-dir)
+
+################################################################################
+
+include $(CLEAR_VARS)
+LOCAL_MODULE := android.hardware.bluetooth@1.0-java
+LOCAL_MODULE_CLASS := JAVA_LIBRARIES
+
+intermediates := $(local-generated-sources-dir)
+
+HIDL := $(HOST_OUT_EXECUTABLES)/hidl-gen$(HOST_EXECUTABLE_SUFFIX)
+
+#
+# Build types.hal (Status)
+#
+GEN := $(intermediates)/android/hardware/bluetooth/1.0/Status.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.bluetooth@1.0::types.Status
+
+$(GEN): $(LOCAL_PATH)/types.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+
+#
+# Build IBluetoothHci.hal
+#
+GEN := $(intermediates)/android/hardware/bluetooth/1.0/IBluetoothHci.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/IBluetoothHci.hal
+$(GEN): PRIVATE_DEPS += $(LOCAL_PATH)/IBluetoothHciCallbacks.hal
+$(GEN): $(LOCAL_PATH)/IBluetoothHciCallbacks.hal
+$(GEN): PRIVATE_DEPS += $(LOCAL_PATH)/types.hal
+$(GEN): $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.bluetooth@1.0::IBluetoothHci
+
+$(GEN): $(LOCAL_PATH)/IBluetoothHci.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+
+#
+# Build IBluetoothHciCallbacks.hal
+#
+GEN := $(intermediates)/android/hardware/bluetooth/1.0/IBluetoothHciCallbacks.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/IBluetoothHciCallbacks.hal
+$(GEN): PRIVATE_DEPS += $(LOCAL_PATH)/types.hal
+$(GEN): $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.bluetooth@1.0::IBluetoothHciCallbacks
+
+$(GEN): $(LOCAL_PATH)/IBluetoothHciCallbacks.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+include $(BUILD_JAVA_LIBRARY)
+
+
+################################################################################
+
+include $(CLEAR_VARS)
+LOCAL_MODULE := android.hardware.bluetooth@1.0-java-static
+LOCAL_MODULE_CLASS := JAVA_LIBRARIES
+
+intermediates := $(local-generated-sources-dir)
+
+HIDL := $(HOST_OUT_EXECUTABLES)/hidl-gen$(HOST_EXECUTABLE_SUFFIX)
+
+#
+# Build types.hal (Status)
+#
+GEN := $(intermediates)/android/hardware/bluetooth/1.0/Status.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.bluetooth@1.0::types.Status
+
+$(GEN): $(LOCAL_PATH)/types.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+
+#
+# Build IBluetoothHci.hal
+#
+GEN := $(intermediates)/android/hardware/bluetooth/1.0/IBluetoothHci.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/IBluetoothHci.hal
+$(GEN): PRIVATE_DEPS += $(LOCAL_PATH)/IBluetoothHciCallbacks.hal
+$(GEN): $(LOCAL_PATH)/IBluetoothHciCallbacks.hal
+$(GEN): PRIVATE_DEPS += $(LOCAL_PATH)/types.hal
+$(GEN): $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.bluetooth@1.0::IBluetoothHci
+
+$(GEN): $(LOCAL_PATH)/IBluetoothHci.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+
+#
+# Build IBluetoothHciCallbacks.hal
+#
+GEN := $(intermediates)/android/hardware/bluetooth/1.0/IBluetoothHciCallbacks.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/IBluetoothHciCallbacks.hal
+$(GEN): PRIVATE_DEPS += $(LOCAL_PATH)/types.hal
+$(GEN): $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.bluetooth@1.0::IBluetoothHciCallbacks
+
+$(GEN): $(LOCAL_PATH)/IBluetoothHciCallbacks.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+include $(BUILD_STATIC_JAVA_LIBRARY)
+
+
+
+include $(call all-makefiles-under,$(LOCAL_PATH))
diff --git a/bluetooth/1.0/IBluetoothHci.hal b/bluetooth/1.0/IBluetoothHci.hal
new file mode 100644
index 0000000..10cf914
--- /dev/null
+++ b/bluetooth/1.0/IBluetoothHci.hal
@@ -0,0 +1,74 @@
+/*
+ * 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.
+ */
+
+package android.hardware.bluetooth@1.0;
+
+import IBluetoothHciCallbacks;
+
+/*
+ * The Host Controller Interface (HCI) is the layer defined by the Bluetooth
+ * specification between the software that runs on the host and the Bluetooth
+ * controller chip. This boundary is the natural choice for a Hardware
+ * Abstraction Layer (HAL). Dealing only in HCI packets and events simplifies
+ * the stack and abstracts away power management, initialization, and other
+ * implementation-specific details related to the hardware.
+ */
+
+interface IBluetoothHci {
+ /**
+ * Initialize the underlying HCI interface.
+ *
+ * This method should be used to initialize any hardware interfaces
+ * required to communicate with the Bluetooth hardware in the
+ * device.
+ *
+ * @param callback implements IBluetoothHciCallbacks which will
+ * receive callbacks when incoming HCI packets are received
+ * from the controller to be sent to the host.
+ * @return status result of the initialization
+ */
+ initialize(IBluetoothHciCallbacks callback) generates (Status status);
+
+ /**
+ * Send an HCI command (as specified in the Bluetooth Specification
+ * V4.2, Vol 2, Part 5, Section 5.4.1) to the Bluetooth controller.
+ * Commands must be executed in order.
+ *
+ * @param command is the HCI command to be sent
+ */
+ sendHciCommand(HciPacket command);
+
+ /**
+ * Send an HCI ACL data packet (as specified in the Bluetooth Specification
+ * V4.2, Vol 2, Part 5, Section 5.4.2) to the Bluetooth controller.
+ * Packets must be processed in order.
+ * @param data HCI data packet to be sent
+ */
+ sendAclData(HciPacket data);
+
+ /**
+ * Send an SCO data packet (as specified in the Bluetooth Specification
+ * V4.2, Vol 2, Part 5, Section 5.4.3) to the Bluetooth controller.
+ * Packets must be processed in order.
+ * @param data HCI data packet to be sent
+ */
+ sendScoData(HciPacket data);
+
+ /**
+ * Close the HCI interface
+ */
+ close();
+};
diff --git a/bluetooth/1.0/IBluetoothHciCallbacks.hal b/bluetooth/1.0/IBluetoothHciCallbacks.hal
new file mode 100644
index 0000000..afaab6c
--- /dev/null
+++ b/bluetooth/1.0/IBluetoothHciCallbacks.hal
@@ -0,0 +1,39 @@
+/*
+ * 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.
+ */
+
+package android.hardware.bluetooth@1.0;
+
+/* The interface from the Bluetooth Controller to the stack. */
+interface IBluetoothHciCallbacks {
+ /**
+ * This function is invoked when an HCI event is received from the
+ * Bluetooth controller to be forwarded to the Bluetooth stack.
+ * @param event is the HCI event to be sent to the Bluetooth stack.
+ */
+ oneway hciEventReceived(HciPacket event);
+
+ /**
+ * Send an ACL data packet form the controller to the host.
+ * @param data the ACL HCI packet to be passed to the host stack
+ */
+ oneway aclDataReceived(HciPacket data);
+
+ /**
+ * Send a SCO data packet form the controller to the host.
+ * @param data the SCO HCI packet to be passed to the host stack
+ */
+ oneway scoDataReceived(HciPacket data);
+};
diff --git a/bluetooth/1.0/types.hal b/bluetooth/1.0/types.hal
new file mode 100644
index 0000000..5f5570a
--- /dev/null
+++ b/bluetooth/1.0/types.hal
@@ -0,0 +1,29 @@
+/*
+ * 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.
+ */
+
+package android.hardware.bluetooth@1.0;
+
+enum Status : int32_t {
+ SUCCESS,
+ TRANSPORT_ERROR,
+ INITIALIZATION_ERROR,
+ UNKNOWN
+};
+
+/**
+ * HCI packets are transmitted as a vector of type uint8_t.
+ */
+typedef vec<uint8_t> HciPacket;
diff --git a/gnss/1.0/Android.bp b/gnss/1.0/Android.bp
new file mode 100644
index 0000000..a97531d
--- /dev/null
+++ b/gnss/1.0/Android.bp
@@ -0,0 +1,174 @@
+// This file is autogenerated by hidl-gen. Do not edit manually.
+
+genrule {
+ name: "android.hardware.gnss@1.0_genc++",
+ tool: "hidl-gen",
+ cmd: "$tool -o $genDir -Lc++ -randroid.hardware:hardware/interfaces android.hardware.gnss@1.0",
+ srcs: [
+ "types.hal",
+ "IAGnss.hal",
+ "IAGnssCallback.hal",
+ "IAGnssRil.hal",
+ "IAGnssRilCallback.hal",
+ "IGnss.hal",
+ "IGnssCallback.hal",
+ "IGnssDebug.hal",
+ "IGnssGeofenceCallback.hal",
+ "IGnssGeofencing.hal",
+ "IGnssMeasurement.hal",
+ "IGnssMeasurementCallback.hal",
+ "IGnssNavigationMessage.hal",
+ "IGnssNavigationMessageCallback.hal",
+ "IGnssNi.hal",
+ "IGnssNiCallback.hal",
+ "IGnssXtra.hal",
+ "IGnssXtraCallback.hal",
+ ],
+ out: [
+ "android/hardware/gnss/1.0/types.cpp",
+ "android/hardware/gnss/1.0/AGnssAll.cpp",
+ "android/hardware/gnss/1.0/AGnssCallbackAll.cpp",
+ "android/hardware/gnss/1.0/AGnssRilAll.cpp",
+ "android/hardware/gnss/1.0/AGnssRilCallbackAll.cpp",
+ "android/hardware/gnss/1.0/GnssAll.cpp",
+ "android/hardware/gnss/1.0/GnssCallbackAll.cpp",
+ "android/hardware/gnss/1.0/GnssDebugAll.cpp",
+ "android/hardware/gnss/1.0/GnssGeofenceCallbackAll.cpp",
+ "android/hardware/gnss/1.0/GnssGeofencingAll.cpp",
+ "android/hardware/gnss/1.0/GnssMeasurementAll.cpp",
+ "android/hardware/gnss/1.0/GnssMeasurementCallbackAll.cpp",
+ "android/hardware/gnss/1.0/GnssNavigationMessageAll.cpp",
+ "android/hardware/gnss/1.0/GnssNavigationMessageCallbackAll.cpp",
+ "android/hardware/gnss/1.0/GnssNiAll.cpp",
+ "android/hardware/gnss/1.0/GnssNiCallbackAll.cpp",
+ "android/hardware/gnss/1.0/GnssXtraAll.cpp",
+ "android/hardware/gnss/1.0/GnssXtraCallbackAll.cpp",
+ ],
+}
+
+genrule {
+ name: "android.hardware.gnss@1.0_genc++_headers",
+ tool: "hidl-gen",
+ cmd: "$tool -o $genDir -Lc++ -randroid.hardware:hardware/interfaces android.hardware.gnss@1.0",
+ srcs: [
+ "types.hal",
+ "IAGnss.hal",
+ "IAGnssCallback.hal",
+ "IAGnssRil.hal",
+ "IAGnssRilCallback.hal",
+ "IGnss.hal",
+ "IGnssCallback.hal",
+ "IGnssDebug.hal",
+ "IGnssGeofenceCallback.hal",
+ "IGnssGeofencing.hal",
+ "IGnssMeasurement.hal",
+ "IGnssMeasurementCallback.hal",
+ "IGnssNavigationMessage.hal",
+ "IGnssNavigationMessageCallback.hal",
+ "IGnssNi.hal",
+ "IGnssNiCallback.hal",
+ "IGnssXtra.hal",
+ "IGnssXtraCallback.hal",
+ ],
+ out: [
+ "android/hardware/gnss/1.0/types.h",
+ "android/hardware/gnss/1.0/IAGnss.h",
+ "android/hardware/gnss/1.0/IHwAGnss.h",
+ "android/hardware/gnss/1.0/BnAGnss.h",
+ "android/hardware/gnss/1.0/BpAGnss.h",
+ "android/hardware/gnss/1.0/BsAGnss.h",
+ "android/hardware/gnss/1.0/IAGnssCallback.h",
+ "android/hardware/gnss/1.0/IHwAGnssCallback.h",
+ "android/hardware/gnss/1.0/BnAGnssCallback.h",
+ "android/hardware/gnss/1.0/BpAGnssCallback.h",
+ "android/hardware/gnss/1.0/BsAGnssCallback.h",
+ "android/hardware/gnss/1.0/IAGnssRil.h",
+ "android/hardware/gnss/1.0/IHwAGnssRil.h",
+ "android/hardware/gnss/1.0/BnAGnssRil.h",
+ "android/hardware/gnss/1.0/BpAGnssRil.h",
+ "android/hardware/gnss/1.0/BsAGnssRil.h",
+ "android/hardware/gnss/1.0/IAGnssRilCallback.h",
+ "android/hardware/gnss/1.0/IHwAGnssRilCallback.h",
+ "android/hardware/gnss/1.0/BnAGnssRilCallback.h",
+ "android/hardware/gnss/1.0/BpAGnssRilCallback.h",
+ "android/hardware/gnss/1.0/BsAGnssRilCallback.h",
+ "android/hardware/gnss/1.0/IGnss.h",
+ "android/hardware/gnss/1.0/IHwGnss.h",
+ "android/hardware/gnss/1.0/BnGnss.h",
+ "android/hardware/gnss/1.0/BpGnss.h",
+ "android/hardware/gnss/1.0/BsGnss.h",
+ "android/hardware/gnss/1.0/IGnssCallback.h",
+ "android/hardware/gnss/1.0/IHwGnssCallback.h",
+ "android/hardware/gnss/1.0/BnGnssCallback.h",
+ "android/hardware/gnss/1.0/BpGnssCallback.h",
+ "android/hardware/gnss/1.0/BsGnssCallback.h",
+ "android/hardware/gnss/1.0/IGnssDebug.h",
+ "android/hardware/gnss/1.0/IHwGnssDebug.h",
+ "android/hardware/gnss/1.0/BnGnssDebug.h",
+ "android/hardware/gnss/1.0/BpGnssDebug.h",
+ "android/hardware/gnss/1.0/BsGnssDebug.h",
+ "android/hardware/gnss/1.0/IGnssGeofenceCallback.h",
+ "android/hardware/gnss/1.0/IHwGnssGeofenceCallback.h",
+ "android/hardware/gnss/1.0/BnGnssGeofenceCallback.h",
+ "android/hardware/gnss/1.0/BpGnssGeofenceCallback.h",
+ "android/hardware/gnss/1.0/BsGnssGeofenceCallback.h",
+ "android/hardware/gnss/1.0/IGnssGeofencing.h",
+ "android/hardware/gnss/1.0/IHwGnssGeofencing.h",
+ "android/hardware/gnss/1.0/BnGnssGeofencing.h",
+ "android/hardware/gnss/1.0/BpGnssGeofencing.h",
+ "android/hardware/gnss/1.0/BsGnssGeofencing.h",
+ "android/hardware/gnss/1.0/IGnssMeasurement.h",
+ "android/hardware/gnss/1.0/IHwGnssMeasurement.h",
+ "android/hardware/gnss/1.0/BnGnssMeasurement.h",
+ "android/hardware/gnss/1.0/BpGnssMeasurement.h",
+ "android/hardware/gnss/1.0/BsGnssMeasurement.h",
+ "android/hardware/gnss/1.0/IGnssMeasurementCallback.h",
+ "android/hardware/gnss/1.0/IHwGnssMeasurementCallback.h",
+ "android/hardware/gnss/1.0/BnGnssMeasurementCallback.h",
+ "android/hardware/gnss/1.0/BpGnssMeasurementCallback.h",
+ "android/hardware/gnss/1.0/BsGnssMeasurementCallback.h",
+ "android/hardware/gnss/1.0/IGnssNavigationMessage.h",
+ "android/hardware/gnss/1.0/IHwGnssNavigationMessage.h",
+ "android/hardware/gnss/1.0/BnGnssNavigationMessage.h",
+ "android/hardware/gnss/1.0/BpGnssNavigationMessage.h",
+ "android/hardware/gnss/1.0/BsGnssNavigationMessage.h",
+ "android/hardware/gnss/1.0/IGnssNavigationMessageCallback.h",
+ "android/hardware/gnss/1.0/IHwGnssNavigationMessageCallback.h",
+ "android/hardware/gnss/1.0/BnGnssNavigationMessageCallback.h",
+ "android/hardware/gnss/1.0/BpGnssNavigationMessageCallback.h",
+ "android/hardware/gnss/1.0/BsGnssNavigationMessageCallback.h",
+ "android/hardware/gnss/1.0/IGnssNi.h",
+ "android/hardware/gnss/1.0/IHwGnssNi.h",
+ "android/hardware/gnss/1.0/BnGnssNi.h",
+ "android/hardware/gnss/1.0/BpGnssNi.h",
+ "android/hardware/gnss/1.0/BsGnssNi.h",
+ "android/hardware/gnss/1.0/IGnssNiCallback.h",
+ "android/hardware/gnss/1.0/IHwGnssNiCallback.h",
+ "android/hardware/gnss/1.0/BnGnssNiCallback.h",
+ "android/hardware/gnss/1.0/BpGnssNiCallback.h",
+ "android/hardware/gnss/1.0/BsGnssNiCallback.h",
+ "android/hardware/gnss/1.0/IGnssXtra.h",
+ "android/hardware/gnss/1.0/IHwGnssXtra.h",
+ "android/hardware/gnss/1.0/BnGnssXtra.h",
+ "android/hardware/gnss/1.0/BpGnssXtra.h",
+ "android/hardware/gnss/1.0/BsGnssXtra.h",
+ "android/hardware/gnss/1.0/IGnssXtraCallback.h",
+ "android/hardware/gnss/1.0/IHwGnssXtraCallback.h",
+ "android/hardware/gnss/1.0/BnGnssXtraCallback.h",
+ "android/hardware/gnss/1.0/BpGnssXtraCallback.h",
+ "android/hardware/gnss/1.0/BsGnssXtraCallback.h",
+ ],
+}
+
+cc_library_shared {
+ name: "android.hardware.gnss@1.0",
+ generated_sources: ["android.hardware.gnss@1.0_genc++"],
+ generated_headers: ["android.hardware.gnss@1.0_genc++_headers"],
+ export_generated_headers: ["android.hardware.gnss@1.0_genc++_headers"],
+ shared_libs: [
+ "libhidl",
+ "libhwbinder",
+ "libutils",
+ "libcutils",
+ ],
+}
diff --git a/gnss/1.0/IAGnss.hal b/gnss/1.0/IAGnss.hal
new file mode 100644
index 0000000..a3172f3
--- /dev/null
+++ b/gnss/1.0/IAGnss.hal
@@ -0,0 +1,77 @@
+/*
+ * 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.
+ */
+
+package android.hardware.gnss@1.0;
+
+import IAGnssCallback;
+
+/*
+ * Extended interface for AGNSS support.
+ */
+interface IAGnss {
+ enum ApnIpType : uint16_t {
+ INVALID = 0,
+ IPV4 = 1,
+ IPV6 = 2,
+ IPV4V6 = 3
+ };
+
+ /*
+ * Opens the AGNSS interface and provides the callback routines to the
+ * implementation of this interface.
+ *
+ * @param callback Handle to the AGNSS status callback interface.
+ */
+ setCallback(IAGnssCallback callback);
+
+ /*
+ * Notifies that the AGNSS data connection has been closed.
+ *
+ * @return success True if the operation is successful.
+ */
+ dataConnClosed() generates (bool success);
+
+ /*
+ * Notifies that a data connection is not available for AGNSS.
+ *
+ * @return success True if the operation is successful.
+ */
+ dataConnFailed() generates (bool success);
+
+ /*
+ * Sets the hostname and port for the AGNSS server.
+ *
+ * @param type Specifies if SUPL or C2K.
+ * @param hostname Hostname of the AGNSS server.
+ * @param port Port number associated with the server.
+ *
+ * @return success True if the operation is successful.
+ */
+ setServer(AGnssType type, string hostname, int32_t port)
+ generates (bool success);
+
+ /*
+ * Notifies that a data connection is available and sets the name of the
+ * APN, and its IP type, to be used for SUPL connections.
+ *
+ * @param apn Access Point Name(follows regular APN naming convention).
+ * @param apnIpType Specifies if SUPL or C2K.
+ *
+ * @return success True if the operation is successful.
+ */
+ dataConnOpenWithApnIpType(string apn, ApnIpType apnIpType)
+ generates (bool success);
+};
diff --git a/gnss/1.0/IAGnssCallback.hal b/gnss/1.0/IAGnssCallback.hal
new file mode 100644
index 0000000..46641be
--- /dev/null
+++ b/gnss/1.0/IAGnssCallback.hal
@@ -0,0 +1,78 @@
+/*
+ * 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.
+ */
+
+package android.hardware.gnss@1.0;
+
+/** Callback structure for the AGNSS interface. */
+interface IAGnssCallback {
+ /** AGNSS type **/
+ enum AGnssType : uint16_t {
+ TYPE_SUPL = 1,
+ TYPE_C2K = 2
+ };
+
+ enum AGnssStatusValue : uint16_t {
+ /** GNSS requests data connection for AGNSS. */
+ REQUEST_AGNSS_DATA_CONN = 1,
+ /** GNSS releases the AGNSS data connection. */
+ RELEASE_AGNSS_DATA_CONN = 2,
+ /** AGNSS data connection initiated */
+ AGNSS_DATA_CONNECTED = 3,
+ /** AGNSS data connection completed */
+ AGNSS_DATA_CONN_DONE = 4,
+ /** AGNSS data connection failed */
+ AGNSS_DATA_CONN_FAILED = 5
+ };
+
+ /*
+ * Represents the status of AGNSS augmented to support IPv4.
+ */
+ struct AGnssStatusIpV4 {
+ AGnssType type;
+ AGnssStatusValue status;
+ /*
+ * 32-bit IPv4 address.
+ */
+ uint32_t ipV4Addr;
+ };
+
+ /*
+ * Represents the status of AGNSS augmented to support IPv6.
+ */
+ struct AGnssStatusIpV6 {
+ AGnssType type;
+ AGnssStatusValue status;
+ /*
+ * 128-bit IPv6 address.
+ */
+ uint8_t[16] ipV6Addr;
+ };
+
+ /*
+ * Callback with AGNSS(IpV4) status information.
+ *
+ * @param status Will be of type AGnssStatusIpV4.
+ */
+ agnssStatusIpV4Cb(AGnssStatusIpV4 status);
+
+ /*
+ * Callback with AGNSS(IpV6) status information.
+ *
+ * @param status Will be of type AGnssStatusIpV6.
+ */
+ agnssStatusIpV6Cb(AGnssStatusIpV6 status);
+
+};
diff --git a/gnss/1.0/IAGnssRil.hal b/gnss/1.0/IAGnssRil.hal
new file mode 100644
index 0000000..fb73498
--- /dev/null
+++ b/gnss/1.0/IAGnssRil.hal
@@ -0,0 +1,151 @@
+/*
+ * 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.
+ */
+
+package android.hardware.gnss@1.0;
+
+import IAGnssRilCallback;
+
+/*
+ * Extended interface for AGNSS RIL support. An Assisted GNSS Radio Interface
+ * Layer interface allows the GNSS chipset to request radio interface layer
+ * information from Android platform. Examples of such information are reference
+ * location, unique subscriber ID, phone number string and network availability changes.
+ */
+interface IAGnssRil {
+ enum SetIDType : uint16_t {
+ NONE = 0,
+ IMSI = 1,
+ MSISDM = 2
+ };
+
+ enum NetworkType : int32_t {
+ MOBILE = 0,
+ WIFI = 1,
+ MMS = 2,
+ SUPL = 3,
+ DUN = 4,
+ HIPRI = 5,
+ WIMAX = 6,
+ };
+
+ enum AGnssRefLocationType {
+ GSM_CELLID = 1,
+ UMTS_CELLID = 2,
+ MAC = 3,
+ LTE_CELLID = 4,
+ };
+
+ /* CellID for 2G, 3G and LTE, used in AGNSS. */
+ struct AGnssRefLocationCellID {
+ AGnssRefLocationType type;
+
+ /* Mobile Country Code. */
+ uint16_t mcc;
+
+ /* Mobile Network Code .*/
+ uint16_t mnc;
+
+ /*
+ * Location Area Code in 2G, 3G and LTE. In 3G lac is discarded. In LTE,
+ * lac is populated with tac, to ensure that we don't break old clients that
+ * might rely in the old (wrong) behavior.
+ */
+ uint16_t lac;
+
+ /* Cell id in 2G. Utran Cell id in 3G. Cell Global Id EUTRA in LTE. */
+ uint32_t cid;
+
+ /* Tracking Area Code in LTE. */
+ uint16_t tac;
+
+ /* Physical Cell id in LTE (not used in 2G and 3G) */
+ uint16_t pcid;
+ };
+
+ struct AGnssRefLocationMac {
+ uint8_t[6] mac;
+ };
+
+ /* Represents ref locations */
+ struct AGnssRefLocation {
+ AGnssRefLocationType type;
+
+ union RefLoc {
+ AGnssRefLocationCellID cellID;
+ AGnssRefLocationMac mac;
+ };
+
+ RefLoc refLocVal;
+ };
+
+ /*
+ * Opens the AGNSS interface and provides the callback routines
+ * to the implementation of this interface.
+ *
+ * @param callback Interface for AGnssRil callbacks.
+ */
+ setCallback(IAGnssRilCallback callback);
+
+ /*
+ * Sets the reference location.
+ *
+ * @param agnssReflocation AGNSS reference location CellID/MAC.
+ */
+ setRefLocation(AGnssRefLocation agnssReflocation);
+
+ /*
+ * Sets the SET ID.
+ *
+ * @param type Must be populated with either IMSI or MSISDN or NONE.
+ * @param setid If type is IMSI then setid is populated with
+ * a string representing the unique Subscriber ID, for example, the IMSI for
+ * a GMS phone. If type is MSISDN, then setid must contain
+ * the phone number string for line 1. For example, the MSISDN for a GSM phone.
+ * If the type is NONE, then the string must be empty.
+ *
+ * @return success True if all parameters were valid and operation was
+ * successful.
+ */
+ setSetId(SetIDType type, string setid) generates (bool success);
+
+ /*
+ * Notify GNSS of network status changes.
+ *
+ * @param connected Indicates whether network connectivity exists and
+ * it is possible to establish connections and pass data.
+ * @param type Indicates the kind of network, for eg. mobile, wifi etc.
+ * @param roaming Indicates whether the device is currently roaming on
+ * this network.
+ *
+ * @return success True is all parameters were valid and operation was
+ * successful.
+ */
+ updateNetworkState(bool connected, NetworkType type, bool roaming)
+ generates (bool success);
+
+ /*
+ * Notify GNSS of network status changes.
+ *
+ * @param available Indicates whether network connectivity is available.
+ * @param apn String containing the Access Point Name.
+ *
+ * @return success True if all parameters were valid and the operation was
+ * successful.
+ * TODO(b/32022567): Add VTS test to validate the format of APN.
+ */
+ updateNetworkAvailability(bool available, string apn) generates (bool success);
+
+};
diff --git a/gnss/1.0/IAGnssRilCallback.hal b/gnss/1.0/IAGnssRilCallback.hal
new file mode 100644
index 0000000..6f29820
--- /dev/null
+++ b/gnss/1.0/IAGnssRilCallback.hal
@@ -0,0 +1,51 @@
+/*
+ * 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.
+ */
+
+package android.hardware.gnss@1.0;
+
+/*
+ * Callback for IAGnssRil interface. Used to request SET ID and
+ * Reference Location.
+ */
+interface IAGnssRilCallback {
+ /* Kinds of SET ID that can be requested */
+ enum ID : uint32_t {
+ IMSI = 1 << 0L,
+ MSISDN = 1 << 1L,
+ };
+
+ /* Kinds of reference location that can be requested. */
+ enum RefLoc : uint32_t {
+ CELLID = 1 << 0L,
+ MAC = 1 << 1L
+ };
+
+ /*
+ * The Hal uses this API to request a SET ID.
+ *
+ * @param setIdflag Specifies the kind of SET ID that is required by the HAL.
+ */
+ requestSetIdCb(ID setIdflag);
+
+ /*
+ * The Hal uses this API to request a reference location.
+ *
+ * @param refLocflag Specifies the kind of reference location that is required
+ * by the HAL.
+ */
+ requestRefLocCb(RefLoc refLocflag);
+
+};
diff --git a/gnss/1.0/IGnss.hal b/gnss/1.0/IGnss.hal
new file mode 100644
index 0000000..bc19e78
--- /dev/null
+++ b/gnss/1.0/IGnss.hal
@@ -0,0 +1,210 @@
+/*
+ * 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.
+ */
+
+package android.hardware.gnss@1.0;
+
+import IAGnss;
+import IAGnssRil;
+import IGnssCallback;
+import IGnssDebug;
+import IGnssMeasurement;
+import IGnssNavigationMessage;
+import IGnssGeofencing;
+import IGnssNi;
+import IGnssXtra;
+
+/* Represents the standard GNSS interface. */
+interface IGnss {
+ /* Requested operational mode for GNSS operation. */
+ enum GnssPositionMode : uint32_t {
+ /** Mode for running GNSS standalone (no assistance). */
+ STANDALONE = 0,
+ /** AGNSS MS-Based mode. */
+ MS_BASED = 1,
+ /*
+ * AGNSS MS-Assisted mode. This mode is not maintained by the platform anymore.
+ * It is strongly recommended to use MS_BASED instead.
+ */
+ MS_ASSISTED = 2,
+ };
+
+ /* Requested recurrence mode for GNSS operation. */
+ enum GnssPositionRecurrence : uint32_t {
+ /** Receive GNSS fixes on a recurring basis at a specified period. */
+ RECURRENCE_PERIODIC = 0,
+ /** Request a single shot GNSS fix. */
+ RECURRENCE_SINGLE = 1
+ };
+
+ /*
+ * Flags used to specify which aiding data to delete when calling
+ * deleteAidingData().
+ */
+ enum GnssAidingData : uint16_t {
+ DELETE_EPHEMERIS = 0x0001,
+ DELETE_ALMANAC = 0x0002,
+ DELETE_POSITION = 0x0004,
+ DELETE_TIME = 0x0008,
+ DELETE_IONO = 0x0010,
+ DELETE_UTC = 0x0020,
+ DELETE_HEALTH = 0x0040,
+ DELETE_SVDIR = 0x0080,
+ DELETE_SVSTEER = 0x0100,
+ DELETE_SADATA = 0x0200,
+ DELETE_RTI = 0x0400,
+ DELETE_CELLDB_INFO = 0x8000,
+ DELETE_ALL = 0xFFFF
+ };
+
+ /*
+ * Opens the interface and provides the callback routines
+ * to the implementation of this interface.
+ *
+ * @param callback Callback interface for IGnss.
+ *
+ * @return success Returns true on success.
+ */
+ setCallback(IGnssCallback callback) generates (bool success);
+
+ /*
+ * Starts navigating.
+ *
+ * @return success Returns true on success.
+ */
+ start() generates (bool success);
+
+ /*
+ * Stops navigating.
+ *
+ * @return success Returns true on success.
+ */
+ stop() generates (bool success);
+
+ /*
+ * Closes the interface.
+ */
+ cleanup();
+
+ /*
+ * Injects the current time.
+ *
+ * @param timeMs This is the UTC time received from the NTP server, its value
+ * is given in milliseconds since January 1, 1970.
+ * @param timeReferenceMs The corresponding value of
+ * SystemClock.elapsedRealtime() from the device when the NTP response was
+ * received in milliseconds.
+ * @param uncertaintyMs Uncertainty associated with the value represented by
+ * time. Represented in milliseconds.
+ *
+ * @return success Returns true if the operation is successful.
+ *
+ injectTime(GnssUtcTime timeMs, int64_t timeReferenceMs, int32_t uncertaintyMs)
+ generates (bool success);
+
+ /*
+ * Injects current location from another location provider (typically cell
+ * ID).
+ *
+ * @param latitudeDegrees Measured in Degrees.
+ * @param longitudeDegrees Measured in Degrees.
+ * @param accuracyMeters Measured in meters.
+ *
+ * @return success Returns true if successful.
+ */
+ injectLocation(double latitudeDegrees, double longitudeDegrees, float accuracyMeters)
+ generates (bool success);
+
+ /*
+ * Specifies that the next call to start will not use the
+ * information defined in the flags. GnssAidingData value of DELETE_ALL is
+ * passed for a cold start.
+ *
+ * @param aidingDataFlags Flags specifying the aiding data to be deleted.
+ */
+ deleteAidingData(GnssAidingData aidingDataFlags);
+
+ /*
+ * @param mode Parameter must be one of MS_BASED or STANDALONE.
+ * It is allowed by the platform (and it is recommended) to fallback to
+ * MS_BASED if MS_ASSISTED is passed in, and MS_BASED is supported.
+ * @recurrence GNSS postion recurrence value, either periodic or single.
+ * @param minIntervalMs Represents the time between fixes in milliseconds.
+ * @param preferredAccuracyMeters Represents the requested fix accuracy in meters.
+ * @param preferredTimeMs Represents the requested time to first fix in milliseconds.
+
+ * @return success Returns true if successful.
+ */
+ setPositionMode(GnssPositionMode mode, GnssPositionRecurrence recurrence,
+ uint32_t minIntervalMs, uint32_t preferredAccuracyMeters,
+ uint32_t preferredTimeMs)
+ generates (bool success);
+
+ /*
+ * This method returns the IAGnssRil Interface.
+ *
+ * @return infc Handle to the IAGnssRil interface.
+ */
+ getExtensionAGnssRil() generates (IAGnssRil infc);
+
+ /*
+ * This method returns the IGnssGeofencing Interface.
+ *
+ * @return infc Handle to the IGnssGeofencing interface.
+ */
+ getExtensionGnssGeofencing() generates(IGnssGeofencing infc);
+
+ /*
+ * This method returns the IAGnss Interface.
+ *
+ * @return infc Handle to the IAGnss interface.
+ */
+ getExtensionAGnss() generates (IAGnss infc);
+
+ /*
+ * This method returns the IGnssNi interface.
+ *
+ * @return infc Handle to the IGnssNi interface.
+ */
+ getExtensionGnssNi() generates (IGnssNi infc);
+
+ /*
+ * This method returns the IGnssMeasurement interface.
+ *
+ * @return infc Handle to the IGnssMeasurement interface.
+ */
+ getExtensionGnssMeasurement() generates (IGnssMeasurement infc);
+
+ /*
+ * This method returns the IGnssNavigationMessage interface.
+ *
+ * @return infc Handle to the IGnssNavigationMessage interface.
+ */
+ getExtensionGnssNavigationMessage() generates (IGnssNavigationMessage infc);
+
+ /*
+ * This method returns the IGnssXtra interface.
+ *
+ * @return infc Handle to the IGnssXtra interface.
+ */
+ getExtensionXtra() generates (IGnssXtra infc);
+
+ /*
+ * This method returns the IGnssDebug interface.
+ *
+ * @return infc Handle to the IGnssDebug interface.
+ */
+ getExtensionGnssDebug() generates (IGnssDebug infc);
+};
diff --git a/gnss/1.0/IGnssCallback.hal b/gnss/1.0/IGnssCallback.hal
new file mode 100644
index 0000000..5234688
--- /dev/null
+++ b/gnss/1.0/IGnssCallback.hal
@@ -0,0 +1,222 @@
+/*
+ * 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.
+ */
+
+package android.hardware.gnss@1.0;
+
+/*
+ * The interface is required for the HAL to communicate certain information
+ * like status and location info back to the platform, the platform implements
+ * the interfaces and passes a handle to the HAL.
+ */
+interface IGnssCallback {
+ /* Flags for the gnssSetCapabilities callback. */
+ enum Capabilities : uint32_t {
+ /*
+ * GNSS HAL schedules fixes for RECURRENCE_PERIODIC mode.
+ * If this is not set, then the framework will use 1000ms for
+ * minInterval and will call start() and stop() to schedule the GNSS.
+ */
+ SCHEDULING = 1 << 0,
+ /** GNSS supports MS-Based AGNSS mode */
+ MSB = 1 << 1,
+ /** GNSS supports MS-Assisted AGNSS mode */
+ MSA = 1 << 2,
+ /** GNSS supports single-shot fixes */
+ SINGLE_SHOT = 1 << 3,
+ /** GNSS supports on demand time injection */
+ ON_DEMAND_TIME = 1 << 4,
+ /** GNSS supports Geofencing */
+ GEOFENCING = 1 << 5,
+ /** GNSS supports Measurements. */
+ MEASUREMENTS = 1 << 6,
+ /** GNSS supports Navigation Messages */
+ NAV_MESSAGES = 1 << 7,
+ };
+
+ /* GNSS status event values. */
+ enum GnssStatusValue : uint16_t {
+ /** GNSS status unknown. */
+ STATUS_NONE = 0,
+ /** GNSS has begun navigating. */
+ SESSION_BEGIN = 1,
+ /** GNSS has stopped navigating. */
+ SESSION_END = 2,
+ /** GNSS has powered on but is not navigating. */
+ ENGINE_ON = 3,
+ /** GNSS is powered off. */
+ ENGINE_OFF = 4
+ };
+
+ /*
+ * Flags that indicate information about the satellite
+ */
+ enum GnssSvFlags : uint8_t {
+ FLAGS_NONE = 0,
+ HAS_EPHEMERIS_DATA = 1 << 0,
+ HAS_ALMANAC_DATA = 1 << 1,
+ USED_IN_FIX = 1 << 2
+ };
+
+ struct GnssSvInfo {
+ /*
+ * Pseudo-random number for the SV, or FCN/OSN number for Glonass. The
+ * distinction is made by looking at constellation field. Values must be
+ * in the range of:
+ *
+ * - GNSS: 1-32
+ * - SBAS: 120-151, 183-192
+ * - GLONASS: 1-24, the orbital slot number (OSN), if known. Or, if not:
+ * 93-106, the frequency channel number (FCN) (-7 to +6) offset by
+ * + 100
+ * i.e. report an FCN of -7 as 93, FCN of 0 as 100, and FCN of +6
+ * as 106.
+ * - QZSS: 193-200
+ * - Galileo: 1-36
+ * - Beidou: 1-37
+ */
+ int16_t svid;
+
+ /*
+ * Defines the constellation of the given SV.
+ */
+ GnssConstellationType constellation;
+
+ /*
+ * Carrier-to-noise density in dB-Hz, typically in the range [0, 63].
+ * It contains the measured C/N0 value for the signal at the antenna port.
+ *
+ * This is a mandatory value.
+ */
+ float cN0Dbhz;
+
+ /** Elevation of SV in degrees. */
+ float elevationDegrees;
+
+ /** Azimuth of SV in degrees. */
+ float azimuthDegrees;
+
+ /*
+ * Contains additional data about the given SV.
+ */
+ GnssSvFlags svFlag;
+ };
+
+ /*
+ * Represents SV status.
+ */
+ struct GnssSvStatus {
+ /*
+ * Number of GNSS SVs currently visible, refers to the SVs stored in sv_list
+ */
+ int32_t numSvs;
+
+ /*
+ * Pointer to an array of SVs information for all GNSS constellations,
+ * except GNSS, which is reported using svList
+ */
+ GnssSvInfo[ConstS32:GNSS_MAX_SVS] gnssSvList;
+
+ };
+
+ /*
+ * Called when a GNSS location is available.
+ *
+ * @param location Location information from HAL.
+ */
+ gnssLocationCb(GnssLocation location);
+
+ /*
+ * Called to communicate the status of the GNSS engine.
+ *
+ * @param status Status information from HAL.
+ */
+ gnssStatusCb(GnssStatusValue status);
+
+ /*
+ * @param svInfo SV status information from HAL.
+ */
+ gnssSvStatusCb(GnssSvStatus svInfo);
+
+ /*
+ * Called when NMEA data is available.
+ * Callback for reporting NMEA sentences.
+ *
+ * @param timestamp Marks the instance of reporting.
+ * @param nmea Follows standard NMEA 0183. Each sentence begins with a '$'
+ * and ends with a carriage return/line feed sequence and can be no longer
+ * than 80 characters of visible text (plus the line terminators). The data
+ * is contained within this single line with data items separated by commas.
+ * The data itself is just ascii text and may extend over multiple sentences
+ * in certain specialized instances but is normally fully contained in one
+ * variable length sentence. The data may vary in the amount of precision
+ * contained in the message. For example time might be indicated to decimal
+ * parts of a second or location may be shown with 3 or even 4 digits after
+ * the decimal point. Programs that read the data must only use the commas
+ * to determine the field boundaries and not depend on column positions.
+ * There is a provision for a checksum at the end of each sentence which may
+ * or may not be checked by the unit that reads the data. The checksum field
+ * consists of a '*' and two hex digits representing an 8 bit exclusive OR
+ * of all characters between, but not including, the '$' and '*'.
+ */
+ gnssNmeaCb(GnssUtcTime timestamp, string nmea);
+
+ /*
+ * Callback to inform framework of the GNSS engine's capabilities.
+ *
+ * @param capabilities Capability parameter is a bit field of
+ * the Capabilities enum.
+ */
+ gnssSetCapabilitesCb(uint32_t capabilities);
+
+ /*
+ * Callback utility for acquiring the GNSS wakelock. This can be used to prevent
+ * the CPU from suspending while handling GNSS events.
+ */
+ gnssAcquireWakelockCb();
+
+ /** Callback utility for releasing the GNSS wakelock. */
+ gnssReleaseWakelockCb();
+
+ /** Callback for requesting NTP time */
+ gnssRequestTimeCb();
+
+ /*
+ * Provides information about how new the underlying GPS/GNSS hardware and
+ * software is.
+ *
+ * This information will be available for Android Test Applications. If a GNSS
+ * HAL does not provide this information, it will be considered "2015 or
+ * earlier".
+ *
+ * If a GNSS HAL does provide this information, then newer years will need to
+ * meet newer CTS standards. E.g. if the date are 2016 or above, then N+ level
+ * GnssMeasurement support will be verified.
+ */
+ struct GnssSystemInfo{
+ /*
+ * year in which the last update was made to the underlying hardware/firmware
+ * used to capture GNSS signals, e.g. 2016
+ */
+ uint16_t yearOfHw;
+ };
+
+ /*
+ * Callback to inform framework of the engine's hardware version information.
+ *
+ * @param info GnssSystemInfo about the GPS/GNSS hardware.
+ */
+ gnssSetSystemInfoCb(GnssSystemInfo info);
+};
diff --git a/gnss/1.0/IGnssDebug.hal b/gnss/1.0/IGnssDebug.hal
new file mode 100644
index 0000000..b0ac69d
--- /dev/null
+++ b/gnss/1.0/IGnssDebug.hal
@@ -0,0 +1,122 @@
+package android.hardware.gnss@1.0;
+
+/* Extended interface for DEBUG support. */
+interface IGnssDebug {
+ enum SatelliteEphemerisType : uint32_t {
+ /* no information is known to the gnss hardware, about this satellite */
+ UNKNOWN,
+ /* this satellite is known to exist */
+ KNOWN,
+ /* this satellite is not known to exist */
+ NONEXISTENT,
+ /* Only Almanac (approximate) location known for this satellite */
+ ALMANAC_ONLY,
+ /* Ephemeris is known from demodulating the signal on device */
+ DEMODULATED,
+ /* Ephemeris has been provided by SUPL */
+ SUPL_PROVIDED,
+ /* Ephemeris has been provided by another server */
+ OTHER_SERVER_PROVIDED,
+ /*
+ * Predicted ephemeris has been provided by a server
+ * (e.g. Xtra, Extended Ephemeris, etc...)
+ */
+ SERVER_PREDICTED,
+ /*
+ * Predicted ephemeris in use, generated locally on the device (e.g. from prior
+ * ephemeris)
+ */
+ LOCALLY_PREDICTED
+ };
+
+ /*
+ * Provides the current best known position from any
+ * source (GNSS or injected assistance).
+ */
+ struct PositionDebug {
+ /*
+ * Validity of the data in this struct. False only if no
+ * latitude/longitude information is known.
+ * /
+ bool valid;
+ /* Latitude expressed in degrees */
+ double latitudeDegrees;
+ /* Longitude expressed in degrees */
+ double longitudeDegrees;
+ /* Altitude above ellipsoid expressed in meters */
+ float altitudeDegrees;
+ /*
+ * estimated horizontal accuracy of position expressed in meters, radial,
+ * 68% confidence.
+ */
+ double accuracyMeters;
+ /*
+ * Time duration before this report that this position information was
+ * valid.
+ */
+ float ageSeconds;
+ };
+
+ /*
+ * Provides the current best known UTC time estimate.
+ */
+ struct TimeDebug {
+ /*
+ * Validity of the data in the struct.
+ * False if current time is unknown.
+ */
+ bool valid;
+ /*
+ * UTC time estimate.
+ */
+ GnssUtcTime timeEstimate;
+ /* 68% error estimate in time. */
+ float timeUncertaintyNs;
+ };
+
+ /*
+ * Provides a single satellite info that has decoded navigation data.
+ */
+ struct SatelliteData {
+ /* Satellite vehicle ID number */
+ int16_t svid;
+ /* Defines the constellation type of the given SV. */
+ GnssConstellationType constellation;
+ /* Defines the ephemeris type of the satellite. */
+ SatelliteEphemerisType ephemerisType;
+ /*
+ * Time duration before this report, that the ephemeris source was last
+ * updated, e.g. latest demodulation, or latest server download.
+ * Set to 0 when ephemerisType is UNKNOWN.
+ */
+ float ephemerisAgeSeconds;
+ };
+
+ /*
+ * Provides a set of debug information that is filled by the GNSS chipset
+ * when the method getDebugData() is invoked.
+ */
+ struct DebugData {
+ /* Current best known position. */
+ PositionDebug position;
+ /* Current best know time estimate */
+ TimeDebug time;
+ /*
+ * Provides a list of the decoded satellite ephemeris.
+ * Should provide a complete list for all constellations device can track,
+ * including GnssConstellationType UNKNOWN.
+ */
+ vec<SatelliteData> satelliteDataArray;
+
+ };
+
+ /*
+ * This methods requests position, time and satellite ephemeris debug information
+ * from the HAL.
+ *
+ * @return ret debugData information from GNSS Hal that contains the current best
+ * known position, best known time estimate and a complete list of
+ * constellations that the device can track.
+ */
+ getDebugData() generates (DebugData debugData);
+};
diff --git a/gnss/1.0/IGnssGeofenceCallback.hal b/gnss/1.0/IGnssGeofenceCallback.hal
new file mode 100644
index 0000000..06eb62a
--- /dev/null
+++ b/gnss/1.0/IGnssGeofenceCallback.hal
@@ -0,0 +1,188 @@
+/*
+ * 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.
+ */
+
+package android.hardware.gnss@1.0;
+
+/*
+ * GNSS Geofence.
+ * There are 3 states associated with a Geofence: Inside, Outside, Unknown.
+ * There are 3 transitions: ENTERED, EXITED, UNCERTAIN.
+ *
+ * An example state diagram with confidence level: 95% and Unknown time limit
+ * set as 30 secs is shown below. (confidence level and Unknown time limit are
+ * explained latter).
+ * ____________________________
+ * | Unknown (30 secs) |
+ * """"""""""""""""""""""""""""
+ * ^ | | ^
+ * UNCERTAIN| |ENTERED EXITED| |UNCERTAIN
+ * | v v |
+ * ________ EXITED _________
+ * | Inside | -----------> | Outside |
+ * | | <----------- | |
+ * """""""" ENTERED """""""""
+ *
+ * Inside state: We are 95% confident that the user is inside the geofence.
+ * Outside state: We are 95% confident that the user is outside the geofence
+ * Unknown state: Rest of the time.
+ *
+ * The Unknown state is better explained with an example:
+ *
+ * __________
+ * | c|
+ * | ___ | _______
+ * | |a| | | b |
+ * | """ | """""""
+ * | |
+ * """"""""""
+ * In the diagram above, "a" and "b" are 2 geofences and "c" is the accuracy
+ * circle reported by the GNSS subsystem. Now with regard to "b", the system is
+ * confident that the user is outside. But with regard to "a" is not confident
+ * whether it is inside or outside the geofence. If the accuracy remains the
+ * same for a sufficient period of time, the UNCERTAIN transition must be
+ * triggered with the state set to Unknown. If the accuracy improves later, an
+ * appropriate transition must be triggered. This "sufficient period of time"
+ * is defined by the parameter in the addGeofenceArea API.
+ * In other words, Unknown state can be interpreted as a state in which the
+ * GNSS subsystem isn't confident enough that the user is either inside or
+ * outside the Geofence. It moves to Unknown state only after the expiry of the
+ * timeout.
+ *
+ * The geofence callback needs to be triggered for the ENTERED and EXITED
+ * transitions, when the GNSS system is confident that the user has entered
+ * (Inside state) or exited (Outside state) the Geofence. An implementation
+ * which uses a value of 95% as the confidence is recommended. The callback
+ * must be triggered only for the transitions requested by the
+ * addGeofenceArea method.
+ *
+ * Even though the diagram and explanation talks about states and transitions,
+ * the callee is only interested in the transistions. The states are mentioned
+ * here for illustrative purposes.
+ *
+ * Startup Scenario: When the device boots up, if an application adds geofences,
+ * and then we get an accurate GNSS location fix, it needs to trigger the
+ * appropriate (ENTERED or EXITED) transition for every Geofence it knows about.
+ * By default, all the Geofences will be in the Unknown state.
+ *
+ * When the GNSS system is unavailable, gnssGeofenceStatusCb must be
+ * called to inform the upper layers of the same. Similarly, when it becomes
+ * available the callback must be called. This is a global state while the
+ * UNKNOWN transition described above is per geofence.
+ *
+ * An important aspect to note is that users of this API (framework), will use
+ * other subsystems like wifi, sensors, cell to handle Unknown case and
+ * hopefully provide a definitive state transition to the third party
+ * application. GNSS Geofence will just be a signal indicating what the GNSS
+ * subsystem knows about the Geofence.
+ *
+ */
+
+interface IGnssGeofenceCallback {
+ enum GeofenceTransition : int32_t {
+ ENTERED = (1 << 0L),
+ EXITED = (1 << 1L),
+ UNCERTAIN = (1 << 2L),
+ };
+
+ enum GeofenceAvailability : int32_t {
+ UNAVAILABLE = (1 << 0L),
+ AVAILABLE = (1 << 1L),
+ };
+
+ enum GeofenceStatus : int32_t {
+ OPERATION_SUCCESS = 0,
+ ERROR_TOO_MANY_GEOFENCES = -100,
+ ERROR_ID_EXISTS = -101,
+ ERROR_ID_UNKNOWN = -102,
+ ERROR_INVALID_TRANSITION = -103,
+ ERROR_GENERIC = -149
+ };
+
+ /*
+ * The callback associated with the geofence transition.
+ * The callback must only be called when the caller is interested in that
+ * particular transition. For instance, if the caller is interested only in
+ * ENTERED transition, then the callback must not be called with the EXITED
+ * transition.
+ *
+ * IMPORTANT: If a transition is triggered resulting in this callback, the
+ * GNSS subsystem will wake up the application processor, if its in suspend
+ * state.
+ *
+ * @param geofenceId The id associated with the addGeofenceArea.
+ * @param location The current GNSS location.
+ * @param transition Can be one of ENTERED, EXITED or UNCERTAIN.
+ * @param timestamp Timestamp when the transition was detected.
+ *
+ */
+ gnssGeofenceTransitionCb(int32_t geofenceId, GnssLocation location,
+ GeofenceTransition transition, GnssUtcTime timestamp);
+
+ /*
+ * The callback associated with the availability of the GNSS system for
+ * geofencing monitoring. If the GNSS system determines that it cannot monitor
+ * geofences because of lack of reliability or unavailability of the GNSS
+ * signals, it will call this callback with UNAVAILABLE parameter.
+ *
+ * @param status - UNAVAILABLE or AVAILABLE.
+ * @param lastLocation - Last known location.
+ */
+ gnssGeofenceStatusCb(GeofenceAvailability status, GnssLocation lastLocation);
+
+ /*
+ * The callback associated with the addGeofence call.
+ *
+ * @param geofenceId Id of the geofence.
+ * @param status Will be OPERATION_SUCCESS if the geofence
+ * add was successful. Will be ERROR_TOO_MANY_GEOFENCES if the
+ * geofence limit has been reached.
+ * Will be ERROR_ID_EXISTS if geofence with id already exists.
+ * Will be ERROR_INVALID_TRANSITION if the monitorTransition contains an
+ * invalid transition.
+ * Will be ERROR_GENERIC for other errors.
+ */
+ gnssGeofenceAddCb(int32_t geofenceId, GeofenceStatus status);
+
+ /*
+ * The callback associated with the removeGeofence call.
+ *
+ * @param geofenceId Id of the geofence.
+ * @param status Will return OPERATION_SUCCESS if successful.
+ * Will be ERROR_ID_UNKNOWN for invalid id and
+ * ERROR_GENERIC for others.
+ */
+ gnssGeofenceRemoveCb(int32_t geofenceId, GeofenceStatus status);
+
+ /*
+ * The callback associated with the pauseGeofence call.
+ *
+ * @param geofenceId Id of the geofence.
+ * @param status Will be OPERATION_SUCCESS if success.
+ * Will be ERROR_ID_UNKNOWN for invalid id. Will be
+ * ERROR_INVALID_TRANSITION when monitorTransitions is invalid.
+ * Will be ERROR_GENERIC for other err errors.
+ */
+ gnssGeofencePauseCb(int32_t geofenceId, GeofenceStatus status);
+
+ /*
+ * The callback associated with the resumeGeofence call.
+ *
+ * @param geofenceId - Id of the geofence.
+ * @param status Will be OPERATION_SUCCESS if successful.
+ * Will be ERROR_ID_UNKNOWN for invalid id and ERROR_GENERIC for others.
+ */
+ gnssGeofenceResumeCb(int32_t geofenceId, GeofenceStatus status);
+};
diff --git a/gnss/1.0/IGnssGeofencing.hal b/gnss/1.0/IGnssGeofencing.hal
new file mode 100644
index 0000000..89301f4
--- /dev/null
+++ b/gnss/1.0/IGnssGeofencing.hal
@@ -0,0 +1,86 @@
+/*
+ * 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.
+ */
+
+package android.hardware.gnss@1.0;
+
+import IGnssGeofenceCallback;
+
+/* Extended interface for GNSS Geofencing support */
+interface IGnssGeofencing {
+ /*
+ * Opens the geofence interface and provides the callback routines
+ * to the HAL.
+ *
+ * @param callback Handle to the IGnssGeofenceCallback interface.
+ */
+ setCallback(IGnssGeofenceCallback callback);
+
+ /*
+ * Add a geofence area. This api currently supports circular geofences.
+ *
+ * @param geofenceId The id for the geofence. If a geofence with this id
+ * already exists, an error value (ERROR_ID_EXISTS) must be returned.
+ * @param latitudeDegrees The latitude(in degrees) for the geofence lastTransition.
+ * @param longtitudeDegrees The longitude(in degrees) for the geofence lastTransition.
+ * @param radiusMeters The radius(in meters) for the geofence lastTransition.
+ * @param lastTransition The current state of the geofence. For example, if
+ * the system already knows that the user is inside the geofence, this will
+ * be set to ENTERED. In most cases, it will be UNCERTAIN.
+ * @param monitorTransitions - Which transitions to monitor. Bitwise OR of
+ * ENTERED, EXITED and UNCERTAIN.
+ * @param notificationResponsivenessMs - Defines the best-effort description
+ * of how soon must the callback be called when the transition associated
+ * with the Geofence is triggered. For instance, if set to 1000 millseconds
+ * with ENTERED, the callback must be called 1000 milliseconds within entering
+ * the geofence. This parameter is defined in milliseconds.
+ * NOTE: This is not to be confused with the rate that the GNSS is polled at.
+ * It is acceptable to dynamically vary the rate of sampling the GNSS for
+ * power-saving reasons; thus the rate of sampling may be faster or slower
+ * than this.
+ * @param unknownTimerMs - The time limit after which the UNCERTAIN transition
+ * must be triggered. This parameter is defined in milliseconds.
+ */
+ addGeofenceArea(int32_t geofenceId, double latitudeDegrees, double longitudeDegrees,
+ double radiusMeters, GeofenceTransition lastTransition,
+ int32_t monitorTransitions, uint32_t notificationResponsivenessMs,
+ uint32_t unknownTimerMs);
+
+ /*
+ * Pause monitoring a particular geofence.
+ *
+ * @param geofenceId The id for the geofence.
+ */
+ pauseGeofence(int32_t geofenceId);
+
+ /*
+ * Resume monitoring a particular geofence.
+ *
+ * @param geofenceId - The id for the geofence.
+ * @param monitorTransitions Specifies which transitions to monitor.
+ * It can be a bitwise OR of ENTERED, EXITED and
+ * UNCERTAIN. This supersedes the value associated
+ * provided in the addGeofenceArea call.
+ */
+ resumeGeofence(int32_t geofenceId, int32_t monitorTransitions);
+
+ /*
+ * Remove a geofence area. After the function returns, no notifications
+ * must be sent.
+ *
+ * @param geofenceId The id of the geofence.
+ */
+ removeGeofenceArea(int32_t geofenceId);
+};
diff --git a/gnss/1.0/IGnssMeasurement.hal b/gnss/1.0/IGnssMeasurement.hal
new file mode 100644
index 0000000..5156b32
--- /dev/null
+++ b/gnss/1.0/IGnssMeasurement.hal
@@ -0,0 +1,57 @@
+/*
+ * 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.
+ */
+
+package android.hardware.gnss@1.0;
+
+import IGnssMeasurementCallback;
+
+/*
+ * Extended interface for GNSS Measurements support.
+ */
+interface IGnssMeasurement {
+ enum GnssMeasurementStatus : int32_t {
+ SUCCESS = 0,
+ ERROR_ALREADY_INIT = -100,
+ ERROR_GENERIC = -101
+ };
+
+ /*
+ * Initializes the interface and registers the callback routines with the HAL.
+ * After a successful call to 'setCallback' the HAL must begin to provide updates at
+ * an average output rate of 1Hz (occasional
+ * intra-measurement time offsets in the range from 0-2000msec can be
+ * tolerated.)
+ *
+ * @param callback Handle to GnssMeasurement callback interface.
+ *
+ * @return initRet Returns SUCCESS if successful.
+ * Returns ERROR_ALREADY_INIT if a callback has already been
+ * registered without a corresponding call to 'close'.
+ * Returns ERROR_GENERIC for any other error. The HAL must
+ * not generate any other updates upon returning this error code.
+ */
+ setCallback(IGnssMeasurementCallback callback) generates (int32_t initRet);
+
+ /*
+ * Stops updates from the HAL, and unregisters the callback routines.
+ * After a call to close(), the previously registered callbacks must be
+ * considered invalid by the HAL.
+ * If close() is invoked without a previous setCallback, this function must perform
+ * no work.
+ */
+ close();
+
+};
diff --git a/gnss/1.0/IGnssMeasurementCallback.hal b/gnss/1.0/IGnssMeasurementCallback.hal
new file mode 100644
index 0000000..3650892
--- /dev/null
+++ b/gnss/1.0/IGnssMeasurementCallback.hal
@@ -0,0 +1,554 @@
+/*
+ * 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.
+ */
+
+package android.hardware.gnss@1.0;
+
+/* The callback interface to report measurements from the HAL. */
+interface IGnssMeasurementCallback {
+ /*
+ * Flags to indicate what fields in GnssClock are valid.
+ */
+ enum GnssClockFlags : uint16_t {
+ /** A valid 'leap second' is stored in the data structure. */
+ HAS_LEAP_SECOND = 1 << 0,
+ /** A valid 'time uncertainty' is stored in the data structure. */
+ HAS_TIME_UNCERTAINTY = 1 << 1,
+ /** A valid 'full bias' is stored in the data structure. */
+ HAS_FULL_BIAS = 1 << 2,
+ /** A valid 'bias' is stored in the data structure. */
+ HAS_BIAS = 1 << 3,
+ /** A valid 'bias uncertainty' is stored in the data structure. */
+ HAS_BIAS_UNCERTAINTY = 1 << 4,
+ /** A valid 'drift' is stored in the data structure. */
+ HAS_DRIFT = 1 << 5,
+ /** A valid 'drift uncertainty' is stored in the data structure. */
+ HAS_DRIFT_UNCERTAINTY = 1 << 6
+ };
+
+ /*
+ * Flags to indicate what fields in GnssMeasurement are valid.
+ */
+ enum GnssMeasurementFlags : uint32_t {
+ /** A valid 'snr' is stored in the data structure. */
+ HAS_SNR = 1 << 0,
+ /** A valid 'carrier frequency' is stored in the data structure. */
+ HAS_CARRIER_FREQUENCY = 1 << 9,
+ /** A valid 'carrier cycles' is stored in the data structure. */
+ HAS_CARRIER_CYCLES = 1 << 10,
+ /** A valid 'carrier phase' is stored in the data structure. */
+ HAS_CARRIER_PHASE = 1 << 11,
+ /** A valid 'carrier phase uncertainty' is stored in the data structure. */
+ HAS_CARRIER_PHASE_UNCERTAINTY = 1 << 12
+ };
+
+ /*
+ * Enumeration of available values for the GNSS Measurement's multipath
+ * indicator.
+ */
+ enum GnssMultipathIndicator : uint8_t {
+ /** The indicator is not available or unknown. */
+ INDICATOR_UNKNOWN = 0,
+ /** The measurement is indicated to be affected by multipath. */
+ INDICATOR_PRESENT = 1,
+ /** The measurement is indicated to be not affected by multipath. */
+ INDICATIOR_NOT_PRESENT = 2
+ };
+
+ /*
+ * Flags indicating the GNSS measurement state.
+ *
+ * The expected behavior here is for GNSS HAL to set all the flags that applies.
+ * For example, if the state for a satellite is only C/A code locked and bit
+ * synchronized, and there is still millisecond ambiguity, the state must be
+ * set as:
+ *
+ * STATE_CODE_LOCK | STATE_BIT_SYNC | STATE_MSEC_AMBIGUOUS
+ *
+ * If GNSS is still searching for a satellite, the corresponding state must be
+ * set to STATE_UNKNOWN(0).
+ */
+ enum GnssMeasurementState : uint32_t {
+ STATE_UNKNOWN = 0,
+ STATE_CODE_LOCK = 1 << 0,
+ STATE_BIT_SYNC = 1 << 1,
+ STATE_SUBFRAME_SYNC = 1 << 2,
+ STATE_TOW_DECODED = 1 << 3,
+ STATE_MSEC_AMBIGUOUS = 1 << 4,
+ STATE_SYMBOL_SYNC = 1 << 5,
+ STATE_GLO_STRING_SYNC = 1 << 6,
+ STATE_GLO_TOD_DECODED = 1 << 7,
+ STATE_BDS_D2_BIT_SYNC = 1 << 8,
+ STATE_BDS_D2_SUBFRAME_SYNC = 1 << 9,
+ STATE_GAL_E1BC_CODE_LOCK = 1 << 10,
+ STATE_GAL_E1C_2ND_CODE_LOCK = 1 << 11,
+ STATE_GAL_E1B_PAGE_SYNC = 1 << 12,
+ STATE_SBAS_SYNC = 1 << 13
+ };
+
+ /*
+ * Flags indicating the Accumulated Delta Range's states.
+ */
+ enum GnssAccumulatedDeltaRangeState : uint16_t {
+ ADR_STATE_UNKNOWN = 0,
+ ADR_STATE_VALID = 1 << 0,
+ ADR_STATE_RESET = 1 << 1,
+ ADR_STATE_CYCLE_SLIP = 1 << 2,
+ };
+
+ /*
+ * Represents an estimate of the GNSS clock time.
+ */
+ struct GnssClock {
+ /*
+ * A set of flags indicating the validity of the fields in this data
+ * structure.
+ */
+ GnssClockFlags gnssClockFlags;
+
+ /*
+ * Leap second data.
+ * The sign of the value is defined by the following equation:
+ * utcTimeNs = timeNs - (fullBiasNs + biasNs) - leapSecond *
+ * 1,000,000,000
+ *
+ * If this data is available, gnssClockFlags must contain
+ * HAS_LEAP_SECOND.
+ */
+ int16_t leapSecond;
+
+ /*
+ * The GNSS receiver internal clock value. This is the local hardware clock
+ * value.
+ *
+ * For local hardware clock, this value is expected to be monotonically
+ * increasing while the hardware clock remains powered on. (For the case of a
+ * HW clock that is not continuously on, see the
+ * hwClockDiscontinuityCount field). The receiver's estimate of GNSS time
+ * can be derived by subtracting the sum of fullBiasNs and biasNs (when
+ * available) from this value.
+ *
+ * This GNSS time must be the best estimate of current GNSS time
+ * that GNSS receiver can achieve.
+ *
+ * Sub-nanosecond accuracy can be provided by means of the 'biasNs' field.
+ * The value contains the timeUncertaintyNs in it.
+ *
+ * This field is mandatory.
+ */
+ int64_t timeNs;
+
+ /*
+ * 1-Sigma uncertainty associated with the clock's time in nanoseconds.
+ * The uncertainty is represented as an absolute (single sided) value.
+ *
+ * If the data is available, gnssClockFlags must contain
+ * HAS_TIME_UNCERTAINTY. Ths value is ideally zero, as the time
+ * 'latched' by timeNs is defined as the reference clock vs. which all
+ * other times (and corresponding uncertainties) are measured.
+ */
+ double timeUncertaintyNs;
+
+ /*
+ * The difference between hardware clock ('time' field) inside GNSS receiver
+ * and the true GNSS time since 0000Z, January 6, 1980, in nanoseconds.
+ *
+ * The sign of the value is defined by the following equation:
+ * local estimate of GNSS time = timeNs - (fullBiasNs + biasNs)
+ *
+ * This value is mandatory if the receiver has estimated GNSS time. If the
+ * computed time is for a non-GNSS constellation, the time offset of that
+ * constellation to GNSS has to be applied to fill this value. The error
+ * estimate for the sum of this and the biasNs is the biasUncertaintyNs,
+ * and the caller is responsible for using this uncertainty (it can be very
+ * large before the GNSS time has been solved for.) If the data is available
+ * gnssClockFlags must contain HAS_FULL_BIAS.
+ */
+ int64_t fullBiasNs;
+
+ /*
+ * Sub-nanosecond bias.
+ * The error estimate for the sum of this and the fullBiasNs is the
+ * biasUncertaintyNs.
+ *
+ * If the data is available gnssClockFlags must contain HAS_BIAS. If GNSS
+ * has computed a position fix. This value is mandatory if the receiver has
+ * estimated GNSS time.
+ */
+ double biasNs;
+
+ /*
+ * 1-Sigma uncertainty associated with the local estimate of GNSS time (clock
+ * bias) in nanoseconds. The uncertainty is represented as an absolute
+ * (single sided) value.
+ *
+ * If the data is available gnssClockFlags must contain
+ * HAS_BIAS_UNCERTAINTY. This value is mandatory if the receiver
+ * has estimated GNSS time.
+ */
+ double biasUncertaintyNs;
+
+ /*
+ * The clock's drift in nanoseconds (per second).
+ *
+ * A positive value means that the frequency is higher than the nominal
+ * frequency, and that the (fullBiasNs + biasNs) is growing more positive
+ * over time.
+ *
+ * The value contains the 'drift uncertainty' in it.
+ * If the data is available gnssClockFlags must contain HAS_DRIFT.
+ *
+ * This value is mandatory if the receiver has estimated GNSS time.
+ */
+ double driftNsps;
+
+ /*
+ * 1-Sigma uncertainty associated with the clock's drift in nanoseconds (per
+ * second).
+ * The uncertainty is represented as an absolute (single sided) value.
+ *
+ * If the data is available gnssClockFlags must contain
+ * HAS_DRIFT_UNCERTAINTY. If GNSS has computed a position fix this
+ * field is mandatory and must be populated.
+ */
+ double driftUncertaintyNsps;
+
+ /*
+ * When there are any discontinuities in the HW clock, this field is
+ * mandatory.
+ *
+ * A "discontinuity" is meant to cover the case of a switch from one source
+ * of clock to another. A single free-running crystal oscillator (XO)
+ * will generally not have any discontinuities, and this can be set and
+ * left at 0.
+ *
+ * If, however, the timeNs value (HW clock) is derived from a composite of
+ * sources, that is not as smooth as a typical XO, or is otherwise stopped &
+ * restarted, then this value shall be incremented each time a discontinuity
+ * occurs. (E.g. this value can start at zero at device boot-up and
+ * increment each time there is a change in clock continuity. In the
+ * unlikely event that this value reaches full scale, rollover (not
+ * clamping) is required, such that this value continues to change, during
+ * subsequent discontinuity events.)
+ *
+ * While this number stays the same, between GnssClock reports, it can be
+ * safely assumed that the timeNs value has been running continuously, e.g.
+ * derived from a single, high quality clock (XO like, or better, that is
+ * typically used during continuous GNSS signal sampling.)
+ *
+ * It is expected, esp. during periods where there are few GNSS signals
+ * available, that the HW clock be discontinuity-free as long as possible,
+ * as this avoids the need to use (waste) a GNSS measurement to fully
+ * re-solve for the GNSS clock bias and drift, when using the accompanying
+ * measurements, from consecutive GnssData reports.
+ */
+ uint32_t hwClockDiscontinuityCount;
+
+ };
+
+ /*
+ * Represents a GNSS Measurement, it contains raw and computed information.
+ *
+ * All signal measurement information (e.g. svTime,
+ * pseudorangeRate, multipathIndicator) reported in this struct must be
+ * based on GNSS signal measurements only. You must not synthesize measurements
+ * by calculating or reporting expected measurements based on known or estimated
+ * position, velocity, or time.
+ */
+ struct GnssMeasurement{
+ /*
+ * A set of flags indicating the validity of the fields in this data
+ * structure.
+ */
+ GnssMeasurementFlags flags;
+
+ /*
+ * Satellite vehicle ID number, as defined in GnssSvInfo::svid
+ * This is a mandatory value.
+ */
+ int16_t svid;
+
+ /*
+ * Defines the constellation of the given SV.
+ */
+ GnssConstellationType constellation;
+
+ /*
+ * Time offset at which the measurement was taken in nanoseconds.
+ * The reference receiver's time is specified by GnssData::clock::timeNs.
+ *
+ * The sign of timeOffsetNs is given by the following equation:
+ * measurement time = GnssClock::timeNs + timeOffsetNs
+ *
+ * It provides an individual time-stamp for the measurement, and allows
+ * sub-nanosecond accuracy.
+ * This is a mandatory value.
+ */
+ double timeOffsetNs;
+
+ /*
+ * Per satellite sync state. It represents the current sync state for the
+ * associated satellite.
+ * Based on the sync state, the 'received GNSS tow' field must be interpreted
+ * accordingly.
+ *
+ * This is a mandatory value.
+ */
+ GnssMeasurementState state;
+
+ /*
+ * The received GNSS Time-of-Week at the measurement time, in nanoseconds.
+ * For GNSS & QZSS, this is the received GNSS Time-of-Week at the
+ * measurement time, in nanoseconds. The value is relative to the
+ * beginning of the current GNSS week.
+ *
+ * Given the highest sync state that can be achieved, per each satellite,
+ * valid range for this field can be:
+ * Searching : [ 0 ] : STATE_UNKNOWN
+ * C/A code lock : [ 0 1ms ] : STATE_CODE_LOCK set
+ * Bit sync : [ 0 20ms ] : STATE_BIT_SYNC set
+ * Subframe sync : [ 0 6s ] : STATE_SUBFRAME_SYNC set
+ * TOW decoded : [ 0 1week ] : STATE_TOW_DECODED set
+ *
+ * Note: If there is any ambiguity in integer millisecond,
+ * GNSS_MEASUREMENT_STATE_MSEC_AMBIGUOUS must be set accordingly, in the
+ * 'state' field.
+ *
+ * This value must be populated if 'state' != STATE_UNKNOWN.
+ *
+ * For Glonass, this is the received Glonass time of day, at the
+ * measurement time in nanoseconds.
+ *
+ * Given the highest sync state that can be achieved, per each satellite,
+ * valid range for this field can be:
+ * Searching : [ 0 ] : STATE_UNKNOWN set
+ * C/A code lock : [ 0 1ms ] : STATE_CODE_LOCK set
+ * Symbol sync : [ 0 10ms ] : STATE_SYMBOL_SYNC set
+ * Bit sync : [ 0 20ms ] : STATE_BIT_SYNC set
+ * String sync : [ 0 2s ] : STATE_GLO_STRING_SYNC set
+ * Time of day : [ 0 1day ] : STATE_GLO_TOW_DECODED set
+ *
+ * For Beidou, this is the received Beidou time of week,
+ * at the measurement time in nanoseconds.
+ *
+ * Given the highest sync state that can be achieved, per each satellite,
+ * valid range for this field can be:
+ * Searching : [ 0 ] : STATE_UNKNOWN set.
+ * C/A code lock: [ 0 1ms ] : STATE_CODE_LOCK set.
+ * Bit sync (D2): [ 0 2ms ] : STATE_BDS_D2_BIT_SYNC set.
+ * Bit sync (D1): [ 0 20ms ] : STATE_BIT_SYNC set.
+ * Subframe (D2): [ 0 0.6s ] : STATE_BDS_D2_SUBFRAME_SYNC set.
+ * Subframe (D1): [ 0 6s ] : STATE_SUBFRAME_SYNC set.
+ * Time of week : [ 0 1week ] : STATE_TOW_DECODED set.
+ *
+ * For Galileo, this is the received Galileo time of week,
+ * at the measurement time in nanoseconds.
+ *
+ * E1BC code lock : [ 0 4ms ] : STATE_GAL_E1BC_CODE_LOCK set.
+ * E1C 2nd code lock: [ 0 100ms] : STATE_GAL_E1C_2ND_CODE_LOCK set.
+ * E1B page : [ 0 2s ] : STATE_GAL_E1B_PAGE_SYNC set.
+ * Time of week : [ 0 1week] : STATE_TOW_DECODED is set.
+ *
+ * For SBAS, this is received SBAS time, at the measurement time in
+ * nanoseconds.
+ *
+ * Given the highest sync state that can be achieved, per each satellite,
+ * valid range for this field can be:
+ * Searching : [ 0 ] : STATE_UNKNOWN
+ * C/A code lock: [ 0 1ms ] : STATE_CODE_LOCK is set
+ * Symbol sync : [ 0 2ms ] : STATE_SYMBOL_SYNC is set
+ * Message : [ 0 1s ] : STATE_SBAS_SYNC is set
+ */
+ int64_t receivedSvTimeInNs;
+
+ /*
+ * 1-Sigma uncertainty of the Received GNSS Time-of-Week in nanoseconds.
+ *
+ * This value must be populated if 'state' != STATE_UNKNOWN.
+ */
+ int64_t receivedSvTimeUncertaintyInNs;
+
+ /*
+ * Carrier-to-noise density in dB-Hz, typically in the range [0, 63].
+ * It contains the measured C/N0 value for the signal at the antenna port.
+ *
+ * This is a mandatory value.
+ */
+ double cN0DbHz;
+
+ /*
+ * Pseudorange rate at the timestamp in m/s. The correction of a given
+ * Pseudorange Rate value includes corrections for receiver and satellite
+ * clock frequency errors. Ensure that this field is independent (see
+ * comment at top of GnssMeasurement struct.)
+ *
+ * It is mandatory to provide the 'uncorrected' 'pseudorange rate', and
+ * provide GnssClock's 'drift' field as well. When providing the
+ * uncorrected pseudorange rate, do not apply the corrections described above.)
+ *
+ * The value includes the 'pseudorange rate uncertainty' in it.
+ * A positive 'uncorrected' value indicates that the SV is moving away from
+ * the receiver.
+ *
+ * The sign of the 'uncorrected' 'pseudorange rate' and its relation to the
+ * sign of 'doppler shift' is given by the equation:
+ * pseudorange rate = -k * doppler shift (where k is a constant)
+ *
+ * This must be the most accurate pseudorange rate available, based on
+ * fresh signal measurements from this channel.
+ *
+ * It is mandatory that this value be provided at typical carrier phase PRR
+ * quality (few cm/sec per second of uncertainty, or better) - when signals
+ * are sufficiently strong & stable, e.g. signals from a GNSS simulator at >=
+ * 35 dB-Hz.
+ */
+ double pseudorangeRateMps;
+
+ /*
+ * 1-Sigma uncertainty of the pseudorangeRateMps.
+ * The uncertainty is represented as an absolute (single sided) value.
+ *
+ * This is a mandatory value.
+ */
+ double pseudorangeRateUncertaintyMps;
+
+ /*
+ * Accumulated delta range's state. It indicates whether ADR is reset or
+ * there is a cycle slip(indicating loss of lock).
+ *
+ * This is a mandatory value.
+ */
+ GnssAccumulatedDeltaRangeState accumulatedDeltaRangeState;
+
+ /*
+ * Accumulated delta range since the last channel reset in meters.
+ * A positive value indicates that the SV is moving away from the receiver.
+ *
+ * The sign of the 'accumulated delta range' and its relation to the sign of
+ * 'carrier phase' is given by the equation:
+ * accumulated delta range = -k * carrier phase (where k is a constant)
+ *
+ * This value must be populated if 'accumulated delta range state' !=
+ * ADR_STATE_UNKNOWN.
+ * However, it is expected that the data is only accurate when:
+ * 'accumulated delta range state' == ADR_STATE_VALID.
+ */
+ double accumulatedDeltaRangeM;
+
+ /*
+ * 1-Sigma uncertainty of the accumulated delta range in meters.
+ * This value must be populated if 'accumulated delta range state' !=
+ * ADR_STATE_UNKNOWN.
+ */
+ double accumulatedDeltaRangeUncertaintyM;
+
+ /*
+ * Carrier frequency at which codes and messages are modulated, it can
+ * be L1 or L2. If the field is not set, the carrier frequency is
+ * assumed to be L1.
+ *
+ * If the data is available, gnssClockFlags must contain
+ * HAS_CARRIER_FREQUENCY.
+ */
+ float carrierFrequencyHz;
+
+ /*
+ * The number of full carrier cycles between the satellite and the
+ * receiver. The reference frequency is given by the field
+ * 'carrierFrequencyHz'. Indications of possible cycle slips and
+ * resets in the accumulation of this value can be inferred from the
+ * accumulatedDeltaRangeState flags.
+ *
+ * If the data is available, gnssClockFlags must contain
+ * HAS_CARRIER_CYCLES.
+ */
+ int64_t carrierCycles;
+
+ /*
+ * The RF phase detected by the receiver, in the range [0.0, 1.0].
+ * This is usually the fractional part of the complete carrier phase
+ * measurement.
+ *
+ * The reference frequency is given by the field 'carrierFrequencyHz'.
+ * The value contains the 'carrier-phase uncertainty' in it.
+ *
+ * If the data is available, gnssClockFlags must contain
+ * HAS_CARRIER_PHASE.
+ */
+ double carrierPhase;
+
+ /*
+ * 1-Sigma uncertainty of the carrier-phase.
+ * If the data is available, gnssClockFlags must contain
+ * HAS_CARRIER_PHASE_UNCERTAINTY.
+ */
+ double carrierPhaseUncertainty;
+
+ /*
+ * An enumeration that indicates the 'multipath' state of the event.
+ *
+ * The multipath Indicator is intended to report the presence of overlapping
+ * signals that manifest as distorted correlation peaks.
+ *
+ * - if there is a distorted correlation peak shape, report that multipath
+ * is MULTIPATH_INDICATOR_PRESENT.
+ * - if there is no distorted correlation peak shape, report
+ * MULTIPATH_INDICATOR_NOT_PRESENT
+ * - if signals are too weak to discern this information, report
+ * MULTIPATH_INDICATOR_UNKNOWN
+ *
+ * Example: when doing the standardized overlapping Multipath Performance
+ * test (3GPP TS 34.171) the Multipath indicator must report
+ * MULTIPATH_INDICATOR_PRESENT for those signals that are tracked, and
+ * contain multipath, and MULTIPATH_INDICATOR_NOT_PRESENT for those
+ * signals that are tracked and do not contain multipath.
+ */
+ GnssMultipathIndicator multipathIndicator;
+
+ /*
+ * Signal-to-noise ratio at correlator output in dB.
+ * If the data is available, gnssClockFlags must contain MEASUREMENT_HAS_SNR.
+ * This is the power ratio of the "correlation peak height above the
+ * observed noise floor" to "the noise RMS".
+ */
+ double snrDb;
+ };
+
+ /*
+ * Represents a reading of GNSS measurements. For devices where GnssSystemInfo's
+ * yearOfHw is set to 2016+, it is mandatory that these be provided, on
+ * request, when the GNSS receiver is searching/tracking signals.
+ *
+ * - Reporting of GNSS constellation measurements is mandatory.
+ * - Reporting of all tracked constellations are encouraged.
+ */
+ struct GnssData {
+ /* Number of GnssMeasurement elements. */
+ uint32_t measurementCount;
+
+ /* The array of measurements. */
+ GnssMeasurement[ConstS32:GNSS_MAX_MEASUREMENT] measurements;
+
+ /** The GNSS clock time reading. */
+ GnssClock clock;
+ };
+
+ /*
+ * Callback for the hal to pass a GnssData structure back to the client.
+ *
+ * @param data Contains a reading of GNSS measurements.
+ */
+ GnssMeasurementCb(GnssData data);
+};
diff --git a/gnss/1.0/IGnssNavigationMessage.hal b/gnss/1.0/IGnssNavigationMessage.hal
new file mode 100644
index 0000000..d59b538
--- /dev/null
+++ b/gnss/1.0/IGnssNavigationMessage.hal
@@ -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.
+ */
+
+package android.hardware.gnss@1.0;
+
+import IGnssNavigationMessageCallback;
+
+/*
+ * Extended interface for GNSS navigation message reporting support.
+ */
+interface IGnssNavigationMessage {
+ enum GnssNavigationMessageStatus : int32_t {
+ SUCCESS = 0,
+ ERROR_ALREADY_INIT = -100,
+ ERROR_GENERIC = -101
+ };
+
+ /*
+ * Initializes the interface and registers the callback routines with the HAL.
+ * After a successful call to 'setCallback' the HAL must begin to provide updates as
+ * they become available.
+ * @param callback handle to IGnssNavigationMessageCallack interface.
+ *
+ * @return initRet Returns SUCCESS if the operation
+ * is successful.
+ * Returns ERROR_ALREADY_INIT if a callback has
+ * already been registered without a corresponding call to close().
+ * Returns ERROR_GENERIC if any other error occurred. It is
+ * expected that the HAL will not generate any updates upon returning
+ * this error code.
+ */
+ setCallback(IGnssNavigationMessageCallback callback) generates (int32_t initRet);
+
+ /*
+ * Stops updates from the HAL, and unregisters the callback routines.
+ * After a call to close(), the previously registered callbacks must be
+ * considered invalid by the HAL.
+ * If close() is invoked without a previous setCallback, this function must perform
+ * no work.
+ */
+ close();
+};
diff --git a/gnss/1.0/IGnssNavigationMessageCallback.hal b/gnss/1.0/IGnssNavigationMessageCallback.hal
new file mode 100644
index 0000000..a714fd7
--- /dev/null
+++ b/gnss/1.0/IGnssNavigationMessageCallback.hal
@@ -0,0 +1,166 @@
+/*
+ * 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.
+ */
+
+package android.hardware.gnss@1.0;
+
+/** Represents a GNSS navigation message (or a fragment of it). */
+interface IGnssNavigationMessageCallback {
+ /*
+ * Enumeration of available values to indicate the GNSS Navigation message
+ * types.
+ *
+ * For convenience, first byte is the GnssConstellationType on which that signal
+ * is typically transmitted.
+ */
+ enum GnssNavigationMessageType : int16_t {
+ TYPE_UNKNOWN = 0,
+ /** GNSS L1 C/A message contained in the structure. */
+ GNSS_L1CA = 0x0101,
+ /** GNSS L2-CNAV message contained in the structure. */
+ GNSS_L2CNAV = 0x0102,
+ /** GNSS L5-CNAV message contained in the structure. */
+ GNSS_L5CNAV = 0x0103,
+ /** GNSS CNAV-2 message contained in the structure. */
+ GNSS_CNAV2 = 0x0104,
+ /** Glonass L1 CA message contained in the structure. */
+ GLO_L1CA = 0x0301,
+ /** Beidou D1 message contained in the structure. */
+ BDS_D1 = 0x0501,
+ /** Beidou D2 message contained in the structure. */
+ BDS_D2 = 0x0502,
+ /** Galileo I/NAV message contained in the structure. */
+ GAL_I = 0x0601,
+ /** Galileo F/NAV message contained in the structure. */
+ GAL_F = 0x0602
+ };
+
+ /*
+ * Status of Navigation Message
+ * When a message is received properly without any parity error in its
+ * navigation words, the status must be set to PARITY_PASSED. But if a message is
+ * received with words that failed parity check, but GNSS is able to correct
+ * those words, the status must be set to PARITY_REBUILT.
+ * No need to send any navigation message that contains words with parity error
+ * and cannot be corrected.
+ */
+ enum NavigationMessageStatus : uint16_t {
+ PARITY_PASSED = (1 << 0),
+ PARITY_REBUILT = (1 << 1),
+ STATUS_UNKOWN = 0
+ };
+
+ struct GnssNavigationMessage {
+ /*
+ * Satellite vehicle ID number, as defined in GnssSvInfo::svid
+ * This is a mandatory value.
+ */
+ int16_t svid;
+
+ /*
+ * The type of message contained in the structure.
+ * This is a mandatory value.
+ */
+ GnssNavigationMessageType type;
+
+ /*
+ * The status of the received navigation message.
+ * No need to send any navigation message that contains words with parity
+ * error and cannot be corrected.
+ */
+ NavigationMessageStatus status;
+
+ /*
+ * Message identifier. It provides an index so the complete Navigation
+ * Message can be assembled.
+ *
+ * - For GNSS L1 C/A subframe 4 and 5, this value corresponds to the 'frame
+ * id' of the navigation message, in the range of 1-25 (Subframe 1, 2, 3
+ * does not contain a 'frame id' and this value can be set to -1.)
+ *
+ * - For Glonass L1 C/A, this refers to the frame ID, in the range of 1-5.
+ *
+ * - For BeiDou D1, this refers to the frame number in the range of 1-24
+ *
+ * - For Beidou D2, this refers to the frame number, in the range of 1-120
+ *
+ * - For Galileo F/NAV nominal frame structure, this refers to the subframe
+ * number, in the range of 1-12
+ *
+ * - For Galileo I/NAV nominal frame structure, this refers to the subframe
+ * number in the range of 1-24
+ */
+ int16_t messageId;
+
+ /*
+ * Sub-message identifier. If required by the message 'type', this value
+ * contains a sub-index within the current message (or frame) that is being
+ * transmitted.
+ *
+ * - For GNSS L1 C/A, BeiDou D1 & BeiDou D2, the submessage id corresponds to
+ * the subframe number of the navigation message, in the range of 1-5.
+ *
+ * - For Glonass L1 C/A, this refers to the String number, in the range from
+ * 1-15
+ *
+ * - For Galileo F/NAV, this refers to the page type in the range 1-6
+ *
+ * - For Galileo I/NAV, this refers to the word type in the range 1-10+
+ */
+ int16_t submessageId;
+
+ /*
+ * The data of the reported GNSS message. The bytes (or words) are specified
+ * using big endian format (MSB first). The data is stored and decoded
+ * in a server for research purposes.
+ *
+ * - For GNSS L1 C/A, Beidou D1 & Beidou D2, each subframe contains 10 30-bit
+ * words. Each word (30 bits) must fit into the last 30 bits in a
+ * 4-byte word (skip B31 and B32), with MSB first, for a total of 40
+ * bytes, covering a time period of 6, 6, and 0.6 seconds, respectively.
+ * The standard followed is 1995 SPS Signal specification.
+ *
+ * - For Glonass L1 C/A, each string contains 85 data bits, including the
+ * checksum. These bits must fit into 11 bytes, with MSB first (skip
+ * B86-B88), covering a time period of 2 seconds.
+ * The standard followed is Glonass Interface Control Document Edition 5.1.
+ *
+ * - For Galileo F/NAV, each word consists of 238-bit (sync & tail symbols
+ * excluded). Each word must fit into 30-bytes, with MSB first (skip
+ * B239, B240), covering a time period of 10 seconds. The standard
+ * followed is European GNSS(Galileo) Signal in Space Interface
+ * Control Document Issue 1.2.
+ *
+ * - For Galileo I/NAV, each page contains 2 page parts, even and odd, with
+ * a total of 2x114 = 228 bits, (sync & tail excluded) that must fit
+ * into 29 bytes, with MSB first (skip B229-B232). The standard followed
+ * is same as above.
+ *
+ * TODO(b/32022567): Describe this relationship with data to the VTS
+ * via custom annotations and plug in a VTS test to verify that the data
+ * correctly follows the standard.
+ *
+ */
+ vec<uint8_t> data;
+ };
+
+ /*
+ * The callback to report an available fragment of a GNSS navigation messages
+ * from the HAL.
+ *
+ * @param message - The GNSS navigation submessage/subframe representation.
+ */
+ gnssNavigationMessageCb(GnssNavigationMessage message);
+};
diff --git a/gnss/1.0/IGnssNi.hal b/gnss/1.0/IGnssNi.hal
new file mode 100644
index 0000000..c823bf0
--- /dev/null
+++ b/gnss/1.0/IGnssNi.hal
@@ -0,0 +1,41 @@
+/*
+ * 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.
+ */
+
+package android.hardware.gnss@1.0;
+import IGnssNiCallback;
+
+/*
+ * Extended interface for Network-initiated (NI) support. This interface is used
+ * to respond to NI notifications originating from the HAL.
+ */
+interface IGnssNi {
+ /*
+ * Registers the callbacks for HAL to use.
+ *
+ * @param callback handle to IGnssNiCallback interface.
+ */
+ setCallback(IGnssNiCallback callback);
+
+ /*
+ * Sends a response to HAL.
+ *
+ * @param notifId An ID generated by HAL to associate NI notifications and
+ * framework responses.
+ * @param userResponse A GNSS Ni response indicating if the notification was
+ * accepted, denied or not responded to.
+ */
+ respond(int32_t notifId, GnssUserResponseType userResponse);
+};
diff --git a/gnss/1.0/IGnssNiCallback.hal b/gnss/1.0/IGnssNiCallback.hal
new file mode 100644
index 0000000..c696a92
--- /dev/null
+++ b/gnss/1.0/IGnssNiCallback.hal
@@ -0,0 +1,123 @@
+/*
+ * 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.
+ */
+
+package android.hardware.gnss@1.0;
+
+/* GNSS Network Initiated callback interface. */
+interface IGnssNiCallback {
+ /*
+ * GnssNiType constants
+ */
+ enum GnssNiType : uint32_t {
+ VOICE = 1,
+ UMTS_SUPL = 2,
+ UMTS_CTRL_PLANE = 3
+ };
+
+ /*
+ * GnssNiNotifyFlags constants
+ */
+ enum GnssNiNotifyFlags : uint32_t {
+ /** NI requires notification */
+ NEED_NOTIFY = 0x0001,
+ /** NI requires verification */
+ NEED_VERIFY = 0x0002,
+ /** NI requires privacy override, no notification/minimal trace */
+ PRIVACY_OVERRIDE = 0x0004,
+ };
+
+ /*
+ * GNSS NI responses, used to define the response in
+ * NI structures
+ */
+ enum GnssUserResponseType : int32_t {
+ RESPONSE_ACCEPT = 1,
+ RESPONSE_DENY = 2,
+ RESPONSE_NORESP = 3,
+ };
+
+ /*
+ * NI data encoding scheme
+ */
+ enum GnssNiEncodingType : int32_t {
+ ENC_NONE = 0,
+ ENC_SUPL_GSM_DEFAULT = 1,
+ ENC_SUPL_UTF8 = 2,
+ ENC_SUPL_UCS2 = 3,
+ ENC_UNKNOWN = -1,
+ };
+
+ /** Represents an NI request */
+ struct GnssNiNotification{
+ /*
+ * An ID generated by HAL to associate NI notifications and UI
+ * responses.
+ */
+ int32_t notificationId;
+
+ /*
+ * A type used to distinguish different categories of NI
+ * events, such as VOICE, UMTS_SUPL etc.
+ */
+ GnssNiType niType;
+
+ /*
+ * Notification/verification options, combinations of GnssNiNotifyFlags
+ * constants.
+ */
+ GnssNiNotifyFlags notifyFlags;
+
+ /*
+ * Timeout period to wait for user response.
+ * Set to 0 for no timeout limit. Specified in seconds.
+ */
+ uint32_t timeoutSec;
+
+ /*
+ * Default response when timeout.
+ */
+ GnssUserResponseType defaultResponse;
+
+ /*
+ * String representing the requester of the network inititated location
+ * request.
+ */
+ string requestorId;
+
+ /*
+ * Notification message. String representing the service(for eg. SUPL-service)
+ * who sent the network initiated location request.
+ */
+ string notificationMessage;
+
+ /*
+ * requestorId decoding scheme.
+ */
+ GnssNiEncodingType requestorIdEncoding;
+
+ /*
+ * notificationId decoding scheme
+ */
+ GnssNiEncodingType notificationIdEncoding;
+ };
+
+ /*
+ * Callback with a network initiated request.
+ *
+ * @param notification network initiated request.
+ */
+ niNotifyCb(GnssNiNotification notification);
+};
diff --git a/gnss/1.0/IGnssXtra.hal b/gnss/1.0/IGnssXtra.hal
new file mode 100644
index 0000000..5222fde
--- /dev/null
+++ b/gnss/1.0/IGnssXtra.hal
@@ -0,0 +1,27 @@
+package android.hardware.gnss@1.0;
+import IGnssXtraCallback;
+
+/*
+ * This interface is used by the GNSS HAL to request the framework
+ * to download XTRA data.
+ */
+interface IGnssXtra {
+ /*
+ * Opens the XTRA interface and provides the callback routines
+ * to the implementation of this interface.
+ *
+ * @param callback Handle to the IGnssXtraCallback interface.
+ *
+ * @return success True if the operation is successful.
+ */
+ setCallback(IGnssXtraCallback callback) generates (bool success);
+
+ /*
+ * Inject the downloaded XTRA data into the GNSS receiver.
+ *
+ * @param xtraData GNSS XTRA data.
+ *
+ * @return success True if the operation is successful.
+ */
+ injectXtraData(string xtraData) generates (bool success);
+};
diff --git a/gnss/1.0/IGnssXtraCallback.hal b/gnss/1.0/IGnssXtraCallback.hal
new file mode 100644
index 0000000..42df082
--- /dev/null
+++ b/gnss/1.0/IGnssXtraCallback.hal
@@ -0,0 +1,12 @@
+package android.hardware.gnss@1.0;
+
+/*
+ * This interface is used by the GNSS HAL to request download of XTRA data.
+ */
+interface IGnssXtraCallback {
+ /*
+ * Callback to request the client to download XTRA data. The client should
+ * download XTRA data and inject it by calling injectXtraData().
+ */
+ downloadRequestCb();
+};
diff --git a/gnss/1.0/types.hal b/gnss/1.0/types.hal
new file mode 100644
index 0000000..3120648
--- /dev/null
+++ b/gnss/1.0/types.hal
@@ -0,0 +1,71 @@
+/*
+ * 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.
+ */
+
+package android.hardware.gnss@1.0;
+
+enum ConstS32 : int32_t {
+/** Maximum number of SVs for gnssSvStatusCb(). */
+ GNSS_MAX_SVS = 64,
+
+/* Maximum number of Measurements in gnssMeasurementCb(). */
+ GNSS_MAX_MEASUREMENT = 64,
+};
+
+/* Milliseconds since January 1, 1970 */
+typedef int64_t GnssUtcTime;
+
+/*
+ * Constellation type of GnssSvInfo
+ */
+enum GnssConstellationType : uint8_t {
+ UNKNOWN = 0,
+ GNSS = 1,
+ SBAS = 2,
+ GLONASS = 3,
+ QZSS = 4,
+ BEIDOU = 5,
+ GALILEO = 6,
+};
+
+/* Represents a location. */
+struct GnssLocation {
+ /* Contains GnssLocationFlags bits. */
+ uint16_t gnssLocationFlags;
+
+ /* Represents latitude in degrees. */
+ double latitude;
+
+ /* Represents longitude in degrees. */
+ double longitude;
+
+ /*
+ * Represents altitude in meters above the WGS 84 reference ellipsoid.
+ */
+ double altitude;
+
+ /* Represents speed in meters per second. */
+ float speedMetersperSec;
+
+ /* Represents heading in degrees. */
+ float bearingDegrees;
+
+ /* Represents expected accuracy in meters. */
+ float accuracyMeters;
+
+ /* Timestamp for the location fix. */
+ GnssUtcTime timestamp;
+
+};
diff --git a/graphics/composer/2.1/Android.bp b/graphics/composer/2.1/Android.bp
new file mode 100644
index 0000000..3c63a68
--- /dev/null
+++ b/graphics/composer/2.1/Android.bp
@@ -0,0 +1,55 @@
+// This file is autogenerated by hidl-gen. Do not edit manually.
+
+genrule {
+ name: "android.hardware.graphics.composer@2.1_genc++",
+ tool: "hidl-gen",
+ cmd: "$tool -o $genDir -Lc++ -randroid.hardware:hardware/interfaces android.hardware.graphics.composer@2.1",
+ srcs: [
+ "types.hal",
+ "IComposer.hal",
+ "IComposerCallback.hal",
+ ],
+ out: [
+ "android/hardware/graphics/composer/2.1/types.cpp",
+ "android/hardware/graphics/composer/2.1/ComposerAll.cpp",
+ "android/hardware/graphics/composer/2.1/ComposerCallbackAll.cpp",
+ ],
+}
+
+genrule {
+ name: "android.hardware.graphics.composer@2.1_genc++_headers",
+ tool: "hidl-gen",
+ cmd: "$tool -o $genDir -Lc++ -randroid.hardware:hardware/interfaces android.hardware.graphics.composer@2.1",
+ srcs: [
+ "types.hal",
+ "IComposer.hal",
+ "IComposerCallback.hal",
+ ],
+ out: [
+ "android/hardware/graphics/composer/2.1/types.h",
+ "android/hardware/graphics/composer/2.1/IComposer.h",
+ "android/hardware/graphics/composer/2.1/IHwComposer.h",
+ "android/hardware/graphics/composer/2.1/BnComposer.h",
+ "android/hardware/graphics/composer/2.1/BpComposer.h",
+ "android/hardware/graphics/composer/2.1/BsComposer.h",
+ "android/hardware/graphics/composer/2.1/IComposerCallback.h",
+ "android/hardware/graphics/composer/2.1/IHwComposerCallback.h",
+ "android/hardware/graphics/composer/2.1/BnComposerCallback.h",
+ "android/hardware/graphics/composer/2.1/BpComposerCallback.h",
+ "android/hardware/graphics/composer/2.1/BsComposerCallback.h",
+ ],
+}
+
+cc_library_shared {
+ name: "android.hardware.graphics.composer@2.1",
+ generated_sources: ["android.hardware.graphics.composer@2.1_genc++"],
+ generated_headers: ["android.hardware.graphics.composer@2.1_genc++_headers"],
+ export_generated_headers: ["android.hardware.graphics.composer@2.1_genc++_headers"],
+ shared_libs: [
+ "libhidl",
+ "libhwbinder",
+ "libutils",
+ "libcutils",
+ "android.hardware.graphics.allocator@2.0",
+ ],
+}
diff --git a/graphics/composer/2.1/IComposer.hal b/graphics/composer/2.1/IComposer.hal
new file mode 100644
index 0000000..7bfa22b
--- /dev/null
+++ b/graphics/composer/2.1/IComposer.hal
@@ -0,0 +1,1166 @@
+/*
+ * 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.
+ */
+
+package android.hardware.graphics.composer@2.1;
+
+import android.hardware.graphics.allocator@2.0::PixelFormat;
+import IComposerCallback;
+
+interface IComposer {
+ /*
+ * Optional capabilities which may be supported by some devices. The
+ * particular set of supported capabilities for a given device may be
+ * retrieved using getCapabilities.
+ */
+ enum Capability : int32_t {
+ INVALID = 0,
+
+ /*
+ * Specifies that the device supports sideband stream layers, for
+ * which buffer content updates and other synchronization will not be
+ * provided through the usual validate/present cycle and must be
+ * handled by an external implementation-defined mechanism. Only
+ * changes to layer state (such as position, size, etc.) need to be
+ * performed through the validate/present cycle.
+ */
+ SIDEBAND_STREAM = 1,
+
+ /*
+ * Specifies that the device will apply a color transform even when
+ * either the client or the device has chosen that all layers should
+ * be composed by the client. This will prevent the client from
+ * applying the color transform during its composition step.
+ */
+ SKIP_CLIENT_COLOR_TRANSFORM = 2,
+ };
+
+ /* Display attributes queryable through getDisplayAttribute. */
+ enum Attribute : int32_t {
+ INVALID = 0,
+
+ /* Dimensions in pixels */
+ WIDTH = 1,
+ HEIGHT = 2,
+
+ /* Vsync period in nanoseconds */
+ VSYNC_PERIOD = 3,
+
+ /*
+ * Dots per thousand inches (DPI * 1000). Scaling by 1000 allows these
+ * numbers to be stored in an int32_t without losing too much
+ * precision. If the DPI for a configuration is unavailable or is
+ * considered unreliable, the device may return UNSUPPORTED instead.
+ */
+ DPI_X = 4,
+ DPI_Y = 5,
+ };
+
+ /* Display requests returned by getDisplayRequests. */
+ enum DisplayRequest : uint32_t {
+ /*
+ * Instructs the client to provide a new client target buffer, even if
+ * no layers are marked for client composition.
+ */
+ FLIP_CLIENT_TARGET = 1 << 0,
+
+ /*
+ * Instructs the client to write the result of client composition
+ * directly into the virtual display output buffer. If any of the
+ * layers are not marked as Composition::CLIENT or the given display
+ * is not a virtual display, this request has no effect.
+ */
+ WRITE_CLIENT_TARGET_TO_OUTPUT = 1 << 1,
+ };
+
+ /* Layer requests returned from getDisplayRequests. */
+ enum LayerRequest : uint32_t {
+ /*
+ * The client should clear its target with transparent pixels where
+ * this layer would be. The client may ignore this request if the
+ * layer must be blended.
+ */
+ CLEAR_CLIENT_TARGET = 1 << 0,
+ };
+
+ /* Power modes for use with setPowerMode. */
+ enum PowerMode : int32_t {
+ /* The display is fully off (blanked). */
+ OFF = 0,
+
+ /*
+ * These are optional low power modes. getDozeSupport may be called to
+ * determine whether a given display supports these modes.
+ */
+
+ /*
+ * The display is turned on and configured in a low power state that
+ * is suitable for presenting ambient information to the user,
+ * possibly with lower fidelity than ON, but with greater efficiency.
+ */
+ DOZE = 1,
+
+ /*
+ * The display is configured as in DOZE but may stop applying display
+ * updates from the client. This is effectively a hint to the device
+ * that drawing to the display has been suspended and that the the
+ * device should remain on in a low power state and continue
+ * displaying its current contents indefinitely until the power mode
+ * changes.
+ *
+ * This mode may also be used as a signal to enable hardware-based
+ * doze functionality. In this case, the device is free to take over
+ * the display and manage it autonomously to implement a low power
+ * always-on display.
+ */
+ DOZE_SUSPEND = 3,
+
+ /* The display is fully on. */
+ ON = 2,
+ };
+
+ /* Vsync values passed to setVsyncEnabled. */
+ enum Vsync : int32_t {
+ INVALID = 0,
+
+ /* Enable vsync. */
+ ENABLE = 1,
+
+ /* Disable vsync. */
+ DISABLE = 2,
+ };
+
+ /* Blend modes, settable per layer. */
+ enum BlendMode : int32_t {
+ INVALID = 0,
+
+ /* colorOut = colorSrc */
+ NONE = 1,
+
+ /* colorOut = colorSrc + colorDst * (1 - alphaSrc) */
+ PREMULTIPLIED = 2,
+
+ /* colorOut = colorSrc * alphaSrc + colorDst * (1 - alphaSrc) */
+ COVERAGE = 3,
+ };
+
+ /* Possible composition types for a given layer. */
+ enum Composition : int32_t {
+ INVALID = 0,
+
+ /*
+ * The client will composite this layer into the client target buffer
+ * (provided to the device through setClientTarget).
+ *
+ * The device must not request any composition type changes for layers
+ * of this type.
+ */
+ CLIENT = 1,
+
+ /*
+ * The device will handle the composition of this layer through a
+ * hardware overlay or other similar means.
+ *
+ * Upon validateDisplay, the device may request a change from this
+ * type to CLIENT.
+ */
+ DEVICE = 2,
+
+ /*
+ * The device will render this layer using the color set through
+ * setLayerColor. If this functionality is not supported on a layer
+ * that the client sets to SOLID_COLOR, the device must request that
+ * the composition type of that layer is changed to CLIENT upon the
+ * next call to validateDisplay.
+ *
+ * Upon validateDisplay, the device may request a change from this
+ * type to CLIENT.
+ */
+ SOLID_COLOR = 3,
+
+ /*
+ * Similar to DEVICE, but the position of this layer may also be set
+ * asynchronously through setCursorPosition. If this functionality is
+ * not supported on a layer that the client sets to CURSOR, the device
+ * must request that the composition type of that layer is changed to
+ * CLIENT upon the next call to validateDisplay.
+ *
+ * Upon validateDisplay, the device may request a change from this
+ * type to either DEVICE or CLIENT. Changing to DEVICE will prevent
+ * the use of setCursorPosition but still permit the device to
+ * composite the layer.
+ */
+ CURSOR = 4,
+
+ /*
+ * The device will handle the composition of this layer, as well as
+ * its buffer updates and content synchronization. Only supported on
+ * devices which provide Capability::SIDEBAND_STREAM.
+ *
+ * Upon validateDisplay, the device may request a change from this
+ * type to either DEVICE or CLIENT, but it is unlikely that content
+ * will display correctly in these cases.
+ */
+ SIDEBAND = 5,
+ };
+
+ /* Display types returned by getDisplayType. */
+ enum DisplayType : int32_t {
+ INVALID = 0,
+
+ /*
+ * All physical displays, including both internal displays and
+ * hotpluggable external displays.
+ */
+ PHYSICAL = 1,
+
+ /* Virtual displays created by createVirtualDisplay. */
+ VIRTUAL = 2,
+ };
+
+ struct Rect {
+ int32_t left;
+ int32_t top;
+ int32_t right;
+ int32_t bottom;
+ };
+
+ struct FRect {
+ float left;
+ float top;
+ float right;
+ float bottom;
+ };
+
+ struct Color {
+ uint8_t r;
+ uint8_t g;
+ uint8_t b;
+ uint8_t a;
+ };
+
+ /*
+ * Provides a list of supported capabilities (as described in the
+ * definition of Capability above). This list must not change after
+ * initialization.
+ *
+ * @return capabilities is a list of supported capabilities.
+ */
+ getCapabilities() generates (vec<Capability> capabilities);
+
+ /*
+ * Retrieves implementation-defined debug information, which will be
+ * displayed during, for example, `dumpsys SurfaceFlinger`.
+ *
+ * @return debugInfo is a string of debug information.
+ */
+ dumpDebugInfo() generates (string debugInfo);
+
+ /*
+ * Provides a IComposerCallback object for the device to call.
+ *
+ * @param callback is the IComposerCallback object.
+ */
+ registerCallback(IComposerCallback callback);
+
+ /*
+ * Returns the maximum number of virtual displays supported by this device
+ * (which may be 0). The client will not attempt to create more than this
+ * many virtual displays on this device. This number must not change for
+ * the lifetime of the device.
+ */
+ getMaxVirtualDisplayCount() generates (uint32_t count);
+
+ /*
+ * Creates a new virtual display with the given width and height. The
+ * format passed into this function is the default format requested by the
+ * consumer of the virtual display output buffers.
+ *
+ * The display will be assumed to be on from the time the first frame is
+ * presented until the display is destroyed.
+ *
+ * @param width is the width in pixels.
+ * @param height is the height in pixels.
+ * @param formatHint is the default output buffer format selected by
+ * the consumer.
+ * @return error is NONE upon success. Otherwise,
+ * UNSUPPORTED when the width or height is too large for the
+ * device to be able to create a virtual display.
+ * NO_RESOURCES when the device is unable to create a new virtual
+ * display at this time.
+ * @return display is the newly-created virtual display.
+ * @return format is the format of the buffer the device will produce.
+ */
+ createVirtualDisplay(uint32_t width,
+ uint32_t height,
+ PixelFormat formatHint)
+ generates (Error error,
+ Display display,
+ PixelFormat format);
+
+ /*
+ * Destroys a virtual display. After this call all resources consumed by
+ * this display may be freed by the device and any operations performed on
+ * this display should fail.
+ *
+ * @param display is the virtual display to destroy.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_PARAMETER when the display handle which was passed in does
+ * not refer to a virtual display.
+ */
+ destroyVirtualDisplay(Display display) generates (Error error);
+
+ /*
+ * Accepts the changes required by the device from the previous
+ * validateDisplay call (which may be queried using
+ * getChangedCompositionTypes) and revalidates the display. This function
+ * is equivalent to requesting the changed types from
+ * getChangedCompositionTypes, setting those types on the corresponding
+ * layers, and then calling validateDisplay again.
+ *
+ * After this call it must be valid to present this display. Calling this
+ * after validateDisplay returns 0 changes must succeed with NONE, but
+ * should have no other effect.
+ *
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * NOT_VALIDATED when validateDisplay has not been called.
+ */
+ acceptDisplayChanges(Display display) generates (Error error);
+
+ /*
+ * Creates a new layer on the given display.
+ *
+ * @param display is the display on which to create the layer.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * NO_RESOURCES when the device was unable to create a layer this
+ * time.
+ * @return layer is the handle of the new layer.
+ */
+ createLayer(Display display) generates (Error error, Layer layer);
+
+ /*
+ * Destroys the given layer.
+ *
+ * @param display is the display on which the layer was created.
+ * @param layer is the layer to destroy.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_LAYER when an invalid layer handle was passed in.
+ */
+ destroyLayer(Display display, Layer layer) generates (Error error);
+
+ /*
+ * Retrieves which display configuration is currently active.
+ *
+ * If no display configuration is currently active, this function must
+ * return BAD_CONFIG. It is the responsibility of the client to call
+ * setActiveConfig with a valid configuration before attempting to present
+ * anything on the display.
+ *
+ * @param display is the display to which the active config is queried.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_CONFIG when no configuration is currently active.
+ * @return config is the currently active display configuration.
+ */
+ getActiveConfig(Display display) generates (Error error, Config config);
+
+ /*
+ * Retrieves the layers for which the device requires a different
+ * composition type than had been set prior to the last call to
+ * validateDisplay. The client will either update its state with these
+ * types and call acceptDisplayChanges, or will set new types and attempt
+ * to validate the display again.
+ *
+ * The number of changed layers must be the same as the value returned in
+ * numTypes from the last call to validateDisplay.
+ *
+ * @param display is the display to query.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * NOT_VALIDATED when validateDisplay has not been called.
+ * @return layers is an array of layer handles.
+ * @return types is an array of composition types, each corresponding to
+ * an element of layers.
+ */
+ getChangedCompositionTypes(Display display)
+ generates (Error error,
+ vec<Layer> layers,
+ vec<Composition> types);
+
+ /*
+ * Returns whether a client target with the given properties can be
+ * handled by the device.
+ *
+ * This function must return true for a client target with width and
+ * height equal to the active display configuration dimensions,
+ * PixelFormat::RGBA_8888, and Dataspace::UNKNOWN. It is not required to
+ * return true for any other configuration.
+ *
+ * @param display is the display to query.
+ * @param width is the client target width in pixels.
+ * @param height is the client target height in pixels.
+ * @param format is the client target format.
+ * @param dataspace is the client target dataspace, as described in
+ * setLayerDataspace.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * UNSUPPORTED when the given configuration is not supported.
+ */
+ getClientTargetSupport(Display display,
+ uint32_t width,
+ uint32_t height,
+ PixelFormat format,
+ Dataspace dataspace)
+ generates (Error error);
+
+ /*
+ * Returns the color modes supported on this display.
+ *
+ * All devices must support at least ColorMode::NATIVE.
+ *
+ * @param display is the display to query.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * @return modes is an array of color modes.
+ */
+ getColorModes(Display display)
+ generates (Error error,
+ vec<ColorMode> modes);
+
+ /*
+ * Returns a display attribute value for a particular display
+ * configuration.
+ *
+ * @param display is the display to query.
+ * @param config is the display configuration for which to return
+ * attribute values.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_CONFIG when config does not name a valid configuration for
+ * this display.
+ * BAD_PARAMETER when attribute is unrecognized.
+ * UNSUPPORTED when attribute cannot be queried for the config.
+ * @return value is the value of the attribute.
+ */
+ getDisplayAttribute(Display display,
+ Config config,
+ Attribute attribute)
+ generates (Error error,
+ int32_t value);
+
+ /*
+ * Returns handles for all of the valid display configurations on this
+ * display.
+ *
+ * @param display is the display to query.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * @return configs is an array of configuration handles.
+ */
+ getDisplayConfigs(Display display)
+ generates (Error error,
+ vec<Config> configs);
+
+ /*
+ * Returns a human-readable version of the display's name.
+ *
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * @return name is the name of the display.
+ */
+ getDisplayName(Display display) generates (Error error, string name);
+
+ /*
+ * Returns the display requests and the layer requests required for the
+ * last validated configuration.
+ *
+ * Display requests provide information about how the client should handle
+ * the client target. Layer requests provide information about how the
+ * client should handle an individual layer.
+ *
+ * The number of layer requests must be equal to the value returned in
+ * numRequests from the last call to validateDisplay.
+ *
+ * @param display is the display to query.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * NOT_VALIDATED when validateDisplay has not been called.
+ * @return displayRequestMask is the display requests for the current
+ * validated state.
+ * @return layers is an array of layers which all have at least one
+ * request.
+ * @return layerRequestMasks is the requests corresponding to each element
+ * of layers.
+ */
+ getDisplayRequests(Display display)
+ generates (Error error,
+ uint32_t displayRequestMask,
+ vec<Layer> layers,
+ vec<uint32_t> layerRequestMasks);
+
+ /*
+ * Returns whether the given display is a physical or virtual display.
+ *
+ * @param display is the display to query.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * @return type is the type of the display.
+ */
+ getDisplayType(Display display) generates (Error error, DisplayType type);
+
+ /*
+ * Returns whether the given display supports PowerMode::DOZE and
+ * PowerMode::DOZE_SUSPEND. DOZE_SUSPEND may not provide any benefit over
+ * DOZE (see the definition of PowerMode for more information), but if
+ * both DOZE and DOZE_SUSPEND are no different from PowerMode::ON, the
+ * device should not claim support.
+ *
+ * @param display is the display to query.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * @return support is true only when the display supports doze modes.
+ */
+ getDozeSupport(Display display) generates (Error error, bool support);
+
+ /*
+ * Returns the high dynamic range (HDR) capabilities of the given display,
+ * which are invariant with regard to the active configuration.
+ *
+ * Displays which are not HDR-capable must return no types.
+ *
+ * @param display is the display to query.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * @return types is an array of HDR types, may have 0 elements if the
+ * display is not HDR-capable.
+ * @return maxLuminance is the desired content maximum luminance for this
+ * display in cd/m^2.
+ * @return maxAverageLuminance - the desired content maximum frame-average
+ * luminance for this display in cd/m^2.
+ * @return minLuminance is the desired content minimum luminance for this
+ * display in cd/m^2.
+ */
+ getHdrCapabilities(Display display)
+ generates (Error error,
+ vec<Hdr> types,
+ float maxLuminance,
+ float maxAverageLuminance,
+ float minLuminance);
+
+ /*
+ * Retrieves the release fences for device layers on this display which
+ * will receive new buffer contents this frame.
+ *
+ * A release fence is a file descriptor referring to a sync fence object
+ * which will be signaled after the device has finished reading from the
+ * buffer presented in the prior frame. This indicates that it is safe to
+ * start writing to the buffer again. If a given layer's fence is not
+ * returned from this function, it will be assumed that the buffer
+ * presented on the previous frame is ready to be written.
+ *
+ * The fences returned by this function should be unique for each layer
+ * (even if they point to the same underlying sync object).
+ *
+ * @param display is the display to query.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * @return layers is an array of layer handles.
+ * @return fences is handle that contains an array of sync fence file
+ * descriptors as described above, each corresponding to an
+ * element of layers.
+ */
+ getReleaseFences(Display display)
+ generates (Error error,
+ vec<Layer> layers,
+ handle releaseFences);
+
+ /*
+ * Presents the current display contents on the screen (or in the case of
+ * virtual displays, into the output buffer).
+ *
+ * Prior to calling this function, the display must be successfully
+ * validated with validateDisplay. Note that setLayerBuffer and
+ * setLayerSurfaceDamage specifically do not count as layer state, so if
+ * there are no other changes to the layer state (or to the buffer's
+ * properties as described in setLayerBuffer), then it is safe to call
+ * this function without first validating the display.
+ *
+ * If this call succeeds, presentFence will be populated with a file
+ * descriptor referring to a present sync fence object. For physical
+ * displays, this fence will be signaled at the vsync when the result of
+ * composition of this frame starts to appear (for video-mode panels) or
+ * starts to transfer to panel memory (for command-mode panels). For
+ * virtual displays, this fence will be signaled when writes to the output
+ * buffer have completed and it is safe to read from it.
+ *
+ * @param display is the display to present.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * NO_RESOURCES when no valid output buffer has been set for a
+ * virtual display.
+ * NOT_VALIDATED when validateDisplay has not successfully been
+ * called for this display.
+ * @return presentFence is a sync fence file descriptor as described
+ * above.
+ */
+ presentDisplay(Display display)
+ generates (Error error,
+ handle presentFence);
+
+ /*
+ * Sets the active configuration for this display. Upon returning, the
+ * given display configuration should be active and remain so until either
+ * this function is called again or the display is disconnected.
+ *
+ * @param display is the display to which the active config is set.
+ * @param config is the new display configuration.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_CONFIG when the configuration handle passed in is not valid
+ * for this display.
+ */
+ setActiveConfig(Display display, Config config) generates (Error error);
+
+ /*
+ * Sets the buffer handle which will receive the output of client
+ * composition. Layers marked as Composition::CLIENT will be composited
+ * into this buffer prior to the call to presentDisplay, and layers not
+ * marked as Composition::CLIENT should be composited with this buffer by
+ * the device.
+ *
+ * The buffer handle provided may be empty if no layers are being
+ * composited by the client. This must not result in an error (unless an
+ * invalid display handle is also provided).
+ *
+ * Also provides a file descriptor referring to an acquire sync fence
+ * object, which will be signaled when it is safe to read from the client
+ * target buffer. If it is already safe to read from this buffer, an
+ * empty handle may be passed instead.
+ *
+ * For more about dataspaces, see setLayerDataspace.
+ *
+ * The damage parameter describes a surface damage region as defined in
+ * the description of setLayerSurfaceDamage.
+ *
+ * Will be called before presentDisplay if any of the layers are marked as
+ * Composition::CLIENT. If no layers are so marked, then it is not
+ * necessary to call this function. It is not necessary to call
+ * validateDisplay after changing the target through this function.
+ *
+ * @param display is the display to which the client target is set.
+ * @param target is the new target buffer.
+ * @param acquireFence is a sync fence file descriptor as described above.
+ * @param dataspace is the dataspace of the buffer, as described in
+ * setLayerDataspace.
+ * @param damage is the surface damage region.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_PARAMETER when the new target handle was invalid.
+ */
+ setClientTarget(Display display,
+ handle target,
+ handle acquireFence,
+ Dataspace dataspace,
+ vec<Rect> damage)
+ generates (Error error);
+
+ /*
+ * Sets the color mode of the given display.
+ *
+ * Upon returning from this function, the color mode change must have
+ * fully taken effect.
+ *
+ * All devices must support at least ColorMode::NATIVE, and displays are
+ * assumed to be in this mode upon hotplug.
+ *
+ * @param display is the display to which the color mode is set.
+ * @param mode is the mode to set to.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_PARAMETER when mode is not a valid color mode.
+ * UNSUPPORTED when mode is not supported on this display.
+ */
+ setColorMode(Display display, ColorMode mode) generates (Error error);
+
+ /*
+ * Sets a color transform which will be applied after composition.
+ *
+ * If hint is not ColorTransform::ARBITRARY, then the device may use the
+ * hint to apply the desired color transform instead of using the color
+ * matrix directly.
+ *
+ * If the device is not capable of either using the hint or the matrix to
+ * apply the desired color transform, it should force all layers to client
+ * composition during validateDisplay.
+ *
+ * If Capability::SKIP_CLIENT_COLOR_TRANSFORM is present, then the client
+ * will never apply the color transform during client composition, even if
+ * all layers are being composed by the client.
+ *
+ * The matrix provided is an affine color transformation of the following
+ * form:
+ *
+ * |r.r r.g r.b 0|
+ * |g.r g.g g.b 0|
+ * |b.r b.g b.b 0|
+ * |Tr Tg Tb 1|
+ *
+ * This matrix will be provided in row-major form:
+ *
+ * {r.r, r.g, r.b, 0, g.r, ...}.
+ *
+ * Given a matrix of this form and an input color [R_in, G_in, B_in], the
+ * output color [R_out, G_out, B_out] will be:
+ *
+ * R_out = R_in * r.r + G_in * g.r + B_in * b.r + Tr
+ * G_out = R_in * r.g + G_in * g.g + B_in * b.g + Tg
+ * B_out = R_in * r.b + G_in * g.b + B_in * b.b + Tb
+ *
+ * @param display is the display to which the color transform is set.
+ * @param matrix is a 4x4 transform matrix (16 floats) as described above.
+ * @param hint is a hint value which may be used instead of the given
+ * matrix unless it is ColorTransform::ARBITRARY.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_PARAMETER when hint is not a valid color transform hint.
+ */
+ setColorTransform(Display display,
+ vec<float> matrix,
+ ColorTransform hint)
+ generates (Error error);
+
+ /*
+ * Sets the output buffer for a virtual display. That is, the buffer to
+ * which the composition result will be written.
+ *
+ * Also provides a file descriptor referring to a release sync fence
+ * object, which will be signaled when it is safe to write to the output
+ * buffer. If it is already safe to write to the output buffer, an empty
+ * handle may be passed instead.
+ *
+ * Must be called at least once before presentDisplay, but does not have
+ * any interaction with layer state or display validation.
+ *
+ * @param display is the virtual display to which the output buffer is
+ * set.
+ * @param buffer is the new output buffer.
+ * @param releaseFence is a sync fence file descriptor as described above.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_PARAMETER when the new output buffer handle was invalid.
+ * UNSUPPORTED when display does not refer to a virtual display.
+ */
+ setOutputBuffer(Display display,
+ handle buffer,
+ handle releaseFence)
+ generates (Error error);
+
+ /*
+ * Sets the power mode of the given display. The transition must be
+ * complete when this function returns. It is valid to call this function
+ * multiple times with the same power mode.
+ *
+ * All displays must support PowerMode::ON and PowerMode::OFF. Whether a
+ * display supports PowerMode::DOZE or PowerMode::DOZE_SUSPEND may be
+ * queried using getDozeSupport.
+ *
+ * @param display is the display to which the power mode is set.
+ * @param mode is the new power mode.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_PARAMETER when mode was not a valid power mode.
+ * UNSUPPORTED when mode is not supported on this display.
+ */
+ setPowerMode(Display display, PowerMode mode) generates (Error error);
+
+ /*
+ * Enables or disables the vsync signal for the given display. Virtual
+ * displays never generate vsync callbacks, and any attempt to enable
+ * vsync for a virtual display though this function must succeed and have
+ * no other effect.
+ *
+ * @param display is the display to which the vsync mode is set.
+ * @param enabled indicates whether to enable or disable vsync
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_PARAMETER when enabled was an invalid value.
+ */
+ setVsyncEnabled(Display display, Vsync enabled) generates (Error error);
+
+ /*
+ * Instructs the device to inspect all of the layer state and determine if
+ * there are any composition type changes necessary before presenting the
+ * display. Permitted changes are described in the definition of
+ * Composition above.
+ *
+ * Also returns the number of layer requests required by the given layer
+ * configuration.
+ *
+ * @param display is the display to validate.
+ * @return error is NONE or HAS_CHANGES upon success.
+ * NONE when no changes are necessary and it is safe to present
+ * the display using the current layer state.
+ * HAS_CHANGES when composition type changes are needed.
+ * Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * @return numTypes is the number of composition type changes required by
+ * the device; if greater than 0, the client must either set and
+ * validate new types, or call acceptDisplayChanges to accept the
+ * changes returned by getChangedCompositionTypes. It must be the
+ * same as the number of changes returned by
+ * getChangedCompositionTypes (see the declaration of that
+ * function for more information).
+ * @return numRequests is the number of layer requests required by this
+ * layer configuration. It must be equal to the number of layer
+ * requests returned by getDisplayRequests (see the declaration of
+ * that function for more information).
+ */
+ validateDisplay(Display display)
+ generates (Error error,
+ uint32_t numTypes,
+ uint32_t numRequests);
+
+ /*
+ * Layer Functions
+ *
+ * These are functions which operate on layers, but which do not modify
+ * state that must be validated before use. See also 'Layer State
+ * Functions' below.
+ */
+
+ /*
+ * Asynchonously sets the position of a cursor layer.
+ *
+ * Prior to validateDisplay, a layer may be marked as Composition::CURSOR.
+ * If validation succeeds (i.e., the device does not request a composition
+ * change for that layer), then once a buffer has been set for the layer
+ * and it has been presented, its position may be set by this function at
+ * any time between presentDisplay and any subsequent validateDisplay
+ * calls for this display.
+ *
+ * Once validateDisplay is called, this function will not be called again
+ * until the validate/present sequence is completed.
+ *
+ * May be called from any thread so long as it is not interleaved with the
+ * validate/present sequence as described above.
+ *
+ * @param display is the display on which the layer was created.
+ * @param layer is the layer to which the position is set.
+ * @param x is the new x coordinate (in pixels from the left of the
+ * screen).
+ * @param y is the new y coordinate (in pixels from the top of the
+ * screen).
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_LAYER when the layer is invalid or is not currently marked
+ * as Composition::CURSOR.
+ * NOT_VALIDATED when the device is currently in the middle of the
+ * validate/present sequence.
+ */
+ setCursorPosition(Display display,
+ Layer layer,
+ int32_t x,
+ int32_t y)
+ generates (Error error);
+
+ /*
+ * Sets the buffer handle to be displayed for this layer. If the buffer
+ * properties set at allocation time (width, height, format, and usage)
+ * have not changed since the previous frame, it is not necessary to call
+ * validateDisplay before calling presentDisplay unless new state needs to
+ * be validated in the interim.
+ *
+ * Also provides a file descriptor referring to an acquire sync fence
+ * object, which will be signaled when it is safe to read from the given
+ * buffer. If it is already safe to read from the buffer, an empty handle
+ * may be passed instead.
+ *
+ * This function must return NONE and have no other effect if called for a
+ * layer with a composition type of Composition::SOLID_COLOR (because it
+ * has no buffer) or Composition::SIDEBAND or Composition::CLIENT (because
+ * synchronization and buffer updates for these layers are handled
+ * elsewhere).
+ *
+ * @param display is the display on which the layer was created.
+ * @param layer is the layer to which the buffer is set.
+ * @param buffer is the buffer handle to set.
+ * @param acquireFence is a sync fence file descriptor as described above.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_LAYER when an invalid layer handle was passed in.
+ * BAD_PARAMETER when the buffer handle passed in was invalid.
+ */
+ setLayerBuffer(Display display,
+ Layer layer,
+ handle buffer,
+ handle acquireFence)
+ generates (Error error);
+
+ /*
+ * Provides the region of the source buffer which has been modified since
+ * the last frame. This region does not need to be validated before
+ * calling presentDisplay.
+ *
+ * Once set through this function, the damage region remains the same
+ * until a subsequent call to this function.
+ *
+ * If damage is non-empty, then it may be assumed that any portion of the
+ * source buffer not covered by one of the rects has not been modified
+ * this frame. If damage is empty, then the whole source buffer must be
+ * treated as if it has been modified.
+ *
+ * If the layer's contents are not modified relative to the prior frame,
+ * damage will contain exactly one empty rect([0, 0, 0, 0]).
+ *
+ * The damage rects are relative to the pre-transformed buffer, and their
+ * origin is the top-left corner. They will not exceed the dimensions of
+ * the latched buffer.
+ *
+ * @param display is the display on which the layer was created.
+ * @param layer is the layer to which the damage region is set.
+ * @param damage is the new surface damage region.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_LAYER when an invalid layer handle was passed in.
+ */
+ setLayerSurfaceDamage(Display display,
+ Layer layer,
+ vec<Rect> damage)
+ generates (Error error);
+
+ /*
+ * Layer State Functions
+ *
+ * These functions modify the state of a given layer. They do not take
+ * effect until the display configuration is successfully validated with
+ * validateDisplay and the display contents are presented with
+ * presentDisplay.
+ */
+
+ /*
+ * Sets the blend mode of the given layer.
+ *
+ * @param display is the display on which the layer was created.
+ * @param layer is the layer to which the blend mode is set.
+ * @param mode is the new blend mode.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_LAYER when an invalid layer handle was passed in.
+ * BAD_PARAMETER when an invalid blend mode was passed in.
+ */
+ setLayerBlendMode(Display display,
+ Layer layer,
+ BlendMode mode)
+ generates (Error error);
+
+ /*
+ * Sets the color of the given layer. If the composition type of the layer
+ * is not Composition::SOLID_COLOR, this call must succeed and have no
+ * other effect.
+ *
+ * @param display is the display on which the layer was created.
+ * @param layer is the layer to which the blend mode is set.
+ * @param color is the new color.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_LAYER when an invalid layer handle was passed in.
+ */
+ setLayerColor(Display display,
+ Layer layer,
+ Color color)
+ generates (Error error);
+
+ /*
+ * Sets the desired composition type of the given layer. During
+ * validateDisplay, the device may request changes to the composition
+ * types of any of the layers as described in the definition of
+ * Composition above.
+ *
+ * @param display is the display on which the layer was created.
+ * @param layer is the layer to which the blend mode is set.
+ * @param type is the new composition type.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_LAYER when an invalid layer handle was passed in.
+ * BAD_PARAMETER when an invalid composition type was passed in.
+ * UNSUPPORTED when a valid composition type was passed in, but it
+ * is not supported by this device.
+ */
+ setLayerCompositionType(Display display,
+ Layer layer,
+ Composition type)
+ generates (Error error);
+
+ /*
+ * Sets the dataspace that the current buffer on this layer is in.
+ *
+ * The dataspace provides more information about how to interpret the
+ * buffer contents, such as the encoding standard and color transform.
+ *
+ * See the values of Dataspace for more information.
+ *
+ * @param display is the display on which the layer was created.
+ * @param layer is the layer to which the dataspace is set.
+ * @param dataspace is the new dataspace.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_LAYER when an invalid layer handle was passed in.
+ */
+ setLayerDataspace(Display display,
+ Layer layer,
+ Dataspace dataspace)
+ generates (Error error);
+
+ /*
+ * Sets the display frame (the portion of the display covered by a layer)
+ * of the given layer. This frame will not exceed the display dimensions.
+ *
+ * @param display is the display on which the layer was created.
+ * @param layer is the layer to which the frame is set.
+ * @param frame is the new display frame.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_LAYER when an invalid layer handle was passed in.
+ */
+ setLayerDisplayFrame(Display display,
+ Layer layer,
+ Rect frame)
+ generates (Error error);
+
+ /*
+ * Sets an alpha value (a floating point value in the range [0.0, 1.0])
+ * which will be applied to the whole layer. It can be conceptualized as a
+ * preprocessing step which applies the following function:
+ * if (blendMode == BlendMode::PREMULTIPLIED)
+ * out.rgb = in.rgb * planeAlpha
+ * out.a = in.a * planeAlpha
+ *
+ * If the device does not support this operation on a layer which is
+ * marked Composition::DEVICE, it must request a composition type change
+ * to Composition::CLIENT upon the next validateDisplay call.
+ *
+ * @param display is the display on which the layer was created.
+ * @param layer is the layer to which the plane alpha is set.
+ * @param alpha is the plane alpha value to apply.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_LAYER when an invalid layer handle was passed in.
+ */
+ setLayerPlaneAlpha(Display display,
+ Layer layer,
+ float alpha)
+ generates (Error error);
+
+ /*
+ * Sets the sideband stream for this layer. If the composition type of the
+ * given layer is not Composition::SIDEBAND, this call must succeed and
+ * have no other effect.
+ *
+ * @param display is the display on which the layer was created.
+ * @param layer is the layer to which the sideband stream is set.
+ * @param stream is the new sideband stream.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_LAYER when an invalid layer handle was passed in.
+ * BAD_PARAMETER when an invalid sideband stream was passed in.
+ */
+ setLayerSidebandStream(Display display,
+ Layer layer,
+ handle stream)
+ generates (Error error);
+
+ /*
+ * Sets the source crop (the portion of the source buffer which will fill
+ * the display frame) of the given layer. This crop rectangle will not
+ * exceed the dimensions of the latched buffer.
+ *
+ * If the device is not capable of supporting a true float source crop
+ * (i.e., it will truncate or round the floats to integers), it should set
+ * this layer to Composition::CLIENT when crop is non-integral for the
+ * most accurate rendering.
+ *
+ * If the device cannot support float source crops, but still wants to
+ * handle the layer, it should use the following code (or similar) to
+ * convert to an integer crop:
+ * intCrop.left = (int) ceilf(crop.left);
+ * intCrop.top = (int) ceilf(crop.top);
+ * intCrop.right = (int) floorf(crop.right);
+ * intCrop.bottom = (int) floorf(crop.bottom);
+ *
+ * @param display is the display on which the layer was created.
+ * @param layer is the layer to which the source crop is set.
+ * @param crop is the new source crop.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_LAYER when an invalid layer handle was passed in.
+ */
+ setLayerSourceCrop(Display display,
+ Layer layer,
+ FRect crop)
+ generates (Error error);
+
+ /*
+ * Sets the transform (rotation/flip) of the given layer.
+ *
+ * @param display is the display on which the layer was created.
+ * @param layer is the layer to which the transform is set.
+ * @param transform is the new transform.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_LAYER when an invalid layer handle was passed in.
+ * BAD_PARAMETER when an invalid transform was passed in.
+ */
+ setLayerTransform(Display display,
+ Layer layer,
+ Transform transform)
+ generates (Error error);
+
+ /*
+ * Specifies the portion of the layer that is visible, including portions
+ * under translucent areas of other layers. The region is in screen space,
+ * and will not exceed the dimensions of the screen.
+ *
+ * @param display is the display on which the layer was created.
+ * @param layer is the layer to which the visible region is set.
+ * @param visible is the new visible region, in screen space.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_LAYER when an invalid layer handle was passed in.
+ */
+ setLayerVisibleRegion(Display display,
+ Layer layer,
+ vec<Rect> visible)
+ generates (Error error);
+
+ /*
+ * Sets the desired Z order (height) of the given layer. A layer with a
+ * greater Z value occludes a layer with a lesser Z value.
+ *
+ * @param display is the display on which the layer was created.
+ * @param layer is the layer to which the Z order is set.
+ * @param z is the new Z order.
+ * @return error is NONE upon success. Otherwise,
+ * BAD_DISPLAY when an invalid display handle was passed in.
+ * BAD_LAYER when an invalid layer handle was passed in.
+ */
+ setLayerZOrder(Display display,
+ Layer layer,
+ uint32_t z)
+ generates (Error error);
+};
diff --git a/graphics/composer/2.1/IComposerCallback.hal b/graphics/composer/2.1/IComposerCallback.hal
new file mode 100644
index 0000000..a8ca168
--- /dev/null
+++ b/graphics/composer/2.1/IComposerCallback.hal
@@ -0,0 +1,72 @@
+/*
+ * 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.
+ */
+
+package android.hardware.graphics.composer@2.1;
+
+interface IComposerCallback {
+ enum Connection : int32_t {
+ INVALID = 0,
+
+ /* The display has been connected */
+ CONNECTED = 1,
+ /* The display has been disconnected */
+ DISCONNECTED = 2,
+ };
+
+ /*
+ * Notifies the client that the given display has either been connected or
+ * disconnected. Every active display (even a built-in physical display)
+ * must trigger at least one hotplug notification, even if it only occurs
+ * immediately after callback registration.
+ *
+ * Displays which have been connected are assumed to be in PowerMode::OFF,
+ * and the onVsync callback should not be called for a display until vsync
+ * has been enabled with setVsyncEnabled.
+ *
+ * The client may call back into the device while the callback is in
+ * progress. The device must serialize calls to this callback such that
+ * only one thread is calling it at a time.
+ *
+ * @param display is the display that triggers the hotplug event.
+ * @param connected indicates whether the display is connected or
+ * disconnected.
+ */
+ onHotplug(Display display, Connection connected);
+
+ /*
+ * Notifies the client to trigger a screen refresh. This forces all layer
+ * state for this display to be resent, and the display to be validated
+ * and presented, even if there have been no changes.
+
+ * This refresh will occur some time after the callback is initiated, but
+ * not necessarily before it returns. It is safe to trigger this callback
+ * from other functions which call into the device.
+ *
+ * @param display is the display to refresh.
+ */
+ oneway onRefresh(Display display);
+
+ /*
+ * Notifies the client that a vsync event has occurred. This callback must
+ * only be triggered when vsync is enabled for this display (through
+ * setVsyncEnabled).
+ *
+ * @param display is the display which has received a vsync event
+ * @param timestamp is the CLOCK_MONOTONIC time at which the vsync event
+ * occurred, in nanoseconds.
+ */
+ oneway onVsync(Display display, int64_t timestamp);
+};
diff --git a/graphics/composer/2.1/default/Android.bp b/graphics/composer/2.1/default/Android.bp
new file mode 100644
index 0000000..f91c9a2
--- /dev/null
+++ b/graphics/composer/2.1/default/Android.bp
@@ -0,0 +1,16 @@
+cc_library_shared {
+ name: "android.hardware.graphics.composer@2.1-impl",
+ relative_install_path: "hw",
+ srcs: ["Hwc.cpp"],
+ shared_libs: [
+ "android.hardware.graphics.allocator@2.0",
+ "android.hardware.graphics.composer@2.1",
+ "libbase",
+ "libcutils",
+ "libhardware",
+ "libhidl",
+ "libhwbinder",
+ "liblog",
+ "libutils",
+ ],
+}
diff --git a/graphics/composer/2.1/default/Hwc.cpp b/graphics/composer/2.1/default/Hwc.cpp
new file mode 100644
index 0000000..09c62f0
--- /dev/null
+++ b/graphics/composer/2.1/default/Hwc.cpp
@@ -0,0 +1,1292 @@
+/*
+ * Copyright 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 "HwcPassthrough"
+
+#include <mutex>
+#include <type_traits>
+#include <unordered_map>
+#include <unordered_set>
+#include <utility>
+#include <vector>
+
+#include <hardware/gralloc.h>
+#include <hardware/gralloc1.h>
+#include <hardware/hwcomposer2.h>
+#include <log/log.h>
+
+#include "Hwc.h"
+
+namespace android {
+namespace hardware {
+namespace graphics {
+namespace composer {
+namespace V2_1 {
+namespace implementation {
+
+using android::hardware::graphics::allocator::V2_0::PixelFormat;
+
+namespace {
+
+class HandleImporter {
+public:
+ HandleImporter() : mInitialized(false) {}
+
+ bool initialize()
+ {
+ // allow only one client
+ if (mInitialized) {
+ return false;
+ }
+
+ if (!openGralloc()) {
+ return false;
+ }
+
+ mInitialized = true;
+ return true;
+ }
+
+ void cleanup()
+ {
+ if (!mInitialized) {
+ return;
+ }
+
+ closeGralloc();
+ mInitialized = false;
+ }
+
+ // In IComposer, any buffer_handle_t is owned by the caller and we need to
+ // make a clone for hwcomposer2. We also need to translate empty handle
+ // to nullptr. This function does that, in-place.
+ bool importBuffer(buffer_handle_t& handle)
+ {
+ if (!handle->numFds && !handle->numInts) {
+ handle = nullptr;
+ return true;
+ }
+
+ buffer_handle_t clone = cloneBuffer(handle);
+ if (!clone) {
+ return false;
+ }
+
+ handle = clone;
+ return true;
+ }
+
+ void freeBuffer(buffer_handle_t handle)
+ {
+ if (!handle) {
+ return;
+ }
+
+ releaseBuffer(handle);
+ }
+
+ bool importFence(const native_handle_t* handle, int& fd)
+ {
+ if (handle->numFds == 0) {
+ fd = -1;
+ } else if (handle->numFds == 1) {
+ fd = dup(handle->data[0]);
+ if (fd < 0) {
+ ALOGE("failed to dup fence fd %d", handle->data[0]);
+ return false;
+ }
+ } else {
+ ALOGE("invalid fence handle with %d file descriptors",
+ handle->numFds);
+ return false;
+ }
+
+ return true;
+ }
+
+ void closeFence(int fd)
+ {
+ if (fd >= 0) {
+ close(fd);
+ }
+ }
+
+private:
+ bool mInitialized;
+
+ // Some existing gralloc drivers do not support retaining more than once,
+ // when we are in passthrough mode.
+#ifdef BINDERIZED
+ bool openGralloc()
+ {
+ const hw_module_t* module;
+ int err = hw_get_module(GRALLOC_HARDWARE_MODULE_ID, &module);
+ if (err) {
+ ALOGE("failed to get gralloc module");
+ return false;
+ }
+
+ uint8_t major = (module->module_api_version >> 8) & 0xff;
+ if (major > 1) {
+ ALOGE("unknown gralloc module major version %d", major);
+ return false;
+ }
+
+ if (major == 1) {
+ err = gralloc1_open(module, &mDevice);
+ if (err) {
+ ALOGE("failed to open gralloc1 device");
+ return false;
+ }
+
+ mRetain = reinterpret_cast<GRALLOC1_PFN_RETAIN>(
+ mDevice->getFunction(mDevice, GRALLOC1_FUNCTION_RETAIN));
+ mRelease = reinterpret_cast<GRALLOC1_PFN_RELEASE>(
+ mDevice->getFunction(mDevice, GRALLOC1_FUNCTION_RELEASE));
+ if (!mRetain || !mRelease) {
+ ALOGE("invalid gralloc1 device");
+ gralloc1_close(mDevice);
+ return false;
+ }
+ } else {
+ mModule = reinterpret_cast<const gralloc_module_t*>(module);
+ }
+
+ return true;
+ }
+
+ void closeGralloc()
+ {
+ if (mDevice) {
+ gralloc1_close(mDevice);
+ }
+ }
+
+ buffer_handle_t cloneBuffer(buffer_handle_t handle)
+ {
+ native_handle_t* clone = native_handle_clone(handle);
+ if (!clone) {
+ ALOGE("failed to clone buffer %p", handle);
+ return nullptr;
+ }
+
+ bool err;
+ if (mDevice) {
+ err = (mRetain(mDevice, clone) != GRALLOC1_ERROR_NONE);
+ } else {
+ err = (mModule->registerBuffer(mModule, clone) != 0);
+ }
+
+ if (err) {
+ ALOGE("failed to retain/register buffer %p", clone);
+ native_handle_close(clone);
+ native_handle_delete(clone);
+ return nullptr;
+ }
+
+ return clone;
+ }
+
+ void releaseBuffer(buffer_handle_t handle)
+ {
+ if (mDevice) {
+ mRelease(mDevice, handle);
+ } else {
+ mModule->unregisterBuffer(mModule, handle);
+ native_handle_close(handle);
+ native_handle_delete(const_cast<native_handle_t*>(handle));
+ }
+ }
+
+ // gralloc1
+ gralloc1_device_t* mDevice;
+ GRALLOC1_PFN_RETAIN mRetain;
+ GRALLOC1_PFN_RELEASE mRelease;
+
+ // gralloc0
+ const gralloc_module_t* mModule;
+#else
+ bool openGralloc() { return true; }
+ void closeGralloc() {}
+ buffer_handle_t cloneBuffer(buffer_handle_t handle) { return handle; }
+ void releaseBuffer(buffer_handle_t) {}
+#endif
+};
+
+HandleImporter sHandleImporter;
+
+class BufferClone {
+public:
+ BufferClone() : mHandle(nullptr) {}
+
+ BufferClone(BufferClone&& other)
+ {
+ mHandle = other.mHandle;
+ other.mHandle = nullptr;
+ }
+
+ BufferClone(const BufferClone& other) = delete;
+ BufferClone& operator=(const BufferClone& other) = delete;
+
+ BufferClone& operator=(buffer_handle_t handle)
+ {
+ clear();
+ mHandle = handle;
+ return *this;
+ }
+
+ ~BufferClone()
+ {
+ clear();
+ }
+
+private:
+ void clear()
+ {
+ if (mHandle) {
+ sHandleImporter.freeBuffer(mHandle);
+ }
+ }
+
+ buffer_handle_t mHandle;
+};
+
+} // anonymous namespace
+
+class HwcHal : public IComposer {
+public:
+ HwcHal(const hw_module_t* module);
+ virtual ~HwcHal();
+
+ // IComposer interface
+ Return<void> getCapabilities(getCapabilities_cb hidl_cb) override;
+ Return<void> dumpDebugInfo(dumpDebugInfo_cb hidl_cb) override;
+ Return<void> registerCallback(const sp<IComposerCallback>& callback) override;
+ Return<uint32_t> getMaxVirtualDisplayCount() override;
+ Return<void> createVirtualDisplay(uint32_t width, uint32_t height,
+ PixelFormat formatHint, createVirtualDisplay_cb hidl_cb) override;
+ Return<Error> destroyVirtualDisplay(Display display) override;
+ Return<Error> acceptDisplayChanges(Display display) override;
+ Return<void> createLayer(Display display,
+ createLayer_cb hidl_cb) override;
+ Return<Error> destroyLayer(Display display, Layer layer) override;
+ Return<void> getActiveConfig(Display display,
+ getActiveConfig_cb hidl_cb) override;
+ Return<void> getChangedCompositionTypes(Display display,
+ getChangedCompositionTypes_cb hidl_cb) override;
+ Return<Error> getClientTargetSupport(Display display,
+ uint32_t width, uint32_t height,
+ PixelFormat format, Dataspace dataspace) override;
+ Return<void> getColorModes(Display display,
+ getColorModes_cb hidl_cb) override;
+ Return<void> getDisplayAttribute(Display display,
+ Config config, Attribute attribute,
+ getDisplayAttribute_cb hidl_cb) override;
+ Return<void> getDisplayConfigs(Display display,
+ getDisplayConfigs_cb hidl_cb) override;
+ Return<void> getDisplayName(Display display,
+ getDisplayName_cb hidl_cb) override;
+ Return<void> getDisplayRequests(Display display,
+ getDisplayRequests_cb hidl_cb) override;
+ Return<void> getDisplayType(Display display,
+ getDisplayType_cb hidl_cb) override;
+ Return<void> getDozeSupport(Display display,
+ getDozeSupport_cb hidl_cb) override;
+ Return<void> getHdrCapabilities(Display display,
+ getHdrCapabilities_cb hidl_cb) override;
+ Return<void> getReleaseFences(Display display,
+ getReleaseFences_cb hidl_cb) override;
+ Return<void> presentDisplay(Display display,
+ presentDisplay_cb hidl_cb) override;
+ Return<Error> setActiveConfig(Display display, Config config) override;
+ Return<Error> setClientTarget(Display display,
+ const native_handle_t* target,
+ const native_handle_t* acquireFence,
+ Dataspace dataspace, const hidl_vec<Rect>& damage) override;
+ Return<Error> setColorMode(Display display, ColorMode mode) override;
+ Return<Error> setColorTransform(Display display,
+ const hidl_vec<float>& matrix, ColorTransform hint) override;
+ Return<Error> setOutputBuffer(Display display,
+ const native_handle_t* buffer,
+ const native_handle_t* releaseFence) override;
+ Return<Error> setPowerMode(Display display, PowerMode mode) override;
+ Return<Error> setVsyncEnabled(Display display, Vsync enabled) override;
+ Return<void> validateDisplay(Display display,
+ validateDisplay_cb hidl_cb) override;
+ Return<Error> setCursorPosition(Display display,
+ Layer layer, int32_t x, int32_t y) override;
+ Return<Error> setLayerBuffer(Display display,
+ Layer layer, const native_handle_t* buffer,
+ const native_handle_t* acquireFence) override;
+ Return<Error> setLayerSurfaceDamage(Display display,
+ Layer layer, const hidl_vec<Rect>& damage) override;
+ Return<Error> setLayerBlendMode(Display display,
+ Layer layer, BlendMode mode) override;
+ Return<Error> setLayerColor(Display display,
+ Layer layer, const Color& color) override;
+ Return<Error> setLayerCompositionType(Display display,
+ Layer layer, Composition type) override;
+ Return<Error> setLayerDataspace(Display display,
+ Layer layer, Dataspace dataspace) override;
+ Return<Error> setLayerDisplayFrame(Display display,
+ Layer layer, const Rect& frame) override;
+ Return<Error> setLayerPlaneAlpha(Display display,
+ Layer layer, float alpha) override;
+ Return<Error> setLayerSidebandStream(Display display,
+ Layer layer, const native_handle_t* stream) override;
+ Return<Error> setLayerSourceCrop(Display display,
+ Layer layer, const FRect& crop) override;
+ Return<Error> setLayerTransform(Display display,
+ Layer layer, Transform transform) override;
+ Return<Error> setLayerVisibleRegion(Display display,
+ Layer layer, const hidl_vec<Rect>& visible) override;
+ Return<Error> setLayerZOrder(Display display,
+ Layer layer, uint32_t z) override;
+
+private:
+ void initCapabilities();
+
+ template<typename T>
+ void initDispatch(T& func, hwc2_function_descriptor_t desc);
+ void initDispatch();
+
+ bool hasCapability(Capability capability) const;
+
+ static void hotplugHook(hwc2_callback_data_t callbackData,
+ hwc2_display_t display, int32_t connected);
+ static void refreshHook(hwc2_callback_data_t callbackData,
+ hwc2_display_t display);
+ static void vsyncHook(hwc2_callback_data_t callbackData,
+ hwc2_display_t display, int64_t timestamp);
+
+ hwc2_device_t* mDevice;
+
+ std::unordered_set<Capability> mCapabilities;
+
+ struct {
+ HWC2_PFN_ACCEPT_DISPLAY_CHANGES acceptDisplayChanges;
+ HWC2_PFN_CREATE_LAYER createLayer;
+ HWC2_PFN_CREATE_VIRTUAL_DISPLAY createVirtualDisplay;
+ HWC2_PFN_DESTROY_LAYER destroyLayer;
+ HWC2_PFN_DESTROY_VIRTUAL_DISPLAY destroyVirtualDisplay;
+ HWC2_PFN_DUMP dump;
+ HWC2_PFN_GET_ACTIVE_CONFIG getActiveConfig;
+ HWC2_PFN_GET_CHANGED_COMPOSITION_TYPES getChangedCompositionTypes;
+ HWC2_PFN_GET_CLIENT_TARGET_SUPPORT getClientTargetSupport;
+ HWC2_PFN_GET_COLOR_MODES getColorModes;
+ HWC2_PFN_GET_DISPLAY_ATTRIBUTE getDisplayAttribute;
+ HWC2_PFN_GET_DISPLAY_CONFIGS getDisplayConfigs;
+ HWC2_PFN_GET_DISPLAY_NAME getDisplayName;
+ HWC2_PFN_GET_DISPLAY_REQUESTS getDisplayRequests;
+ HWC2_PFN_GET_DISPLAY_TYPE getDisplayType;
+ HWC2_PFN_GET_DOZE_SUPPORT getDozeSupport;
+ HWC2_PFN_GET_HDR_CAPABILITIES getHdrCapabilities;
+ HWC2_PFN_GET_MAX_VIRTUAL_DISPLAY_COUNT getMaxVirtualDisplayCount;
+ HWC2_PFN_GET_RELEASE_FENCES getReleaseFences;
+ HWC2_PFN_PRESENT_DISPLAY presentDisplay;
+ HWC2_PFN_REGISTER_CALLBACK registerCallback;
+ HWC2_PFN_SET_ACTIVE_CONFIG setActiveConfig;
+ HWC2_PFN_SET_CLIENT_TARGET setClientTarget;
+ HWC2_PFN_SET_COLOR_MODE setColorMode;
+ HWC2_PFN_SET_COLOR_TRANSFORM setColorTransform;
+ HWC2_PFN_SET_CURSOR_POSITION setCursorPosition;
+ HWC2_PFN_SET_LAYER_BLEND_MODE setLayerBlendMode;
+ HWC2_PFN_SET_LAYER_BUFFER setLayerBuffer;
+ HWC2_PFN_SET_LAYER_COLOR setLayerColor;
+ HWC2_PFN_SET_LAYER_COMPOSITION_TYPE setLayerCompositionType;
+ HWC2_PFN_SET_LAYER_DATASPACE setLayerDataspace;
+ HWC2_PFN_SET_LAYER_DISPLAY_FRAME setLayerDisplayFrame;
+ HWC2_PFN_SET_LAYER_PLANE_ALPHA setLayerPlaneAlpha;
+ HWC2_PFN_SET_LAYER_SIDEBAND_STREAM setLayerSidebandStream;
+ HWC2_PFN_SET_LAYER_SOURCE_CROP setLayerSourceCrop;
+ HWC2_PFN_SET_LAYER_SURFACE_DAMAGE setLayerSurfaceDamage;
+ HWC2_PFN_SET_LAYER_TRANSFORM setLayerTransform;
+ HWC2_PFN_SET_LAYER_VISIBLE_REGION setLayerVisibleRegion;
+ HWC2_PFN_SET_LAYER_Z_ORDER setLayerZOrder;
+ HWC2_PFN_SET_OUTPUT_BUFFER setOutputBuffer;
+ HWC2_PFN_SET_POWER_MODE setPowerMode;
+ HWC2_PFN_SET_VSYNC_ENABLED setVsyncEnabled;
+ HWC2_PFN_VALIDATE_DISPLAY validateDisplay;
+ } mDispatch;
+
+ // cloned buffers for a display
+ struct DisplayBuffers {
+ BufferClone ClientTarget;
+ BufferClone OutputBuffer;
+
+ std::unordered_map<Layer, BufferClone> LayerBuffers;
+ std::unordered_map<Layer, BufferClone> LayerSidebandStreams;
+ };
+
+ std::mutex mCallbackMutex;
+ sp<IComposerCallback> mCallback;
+
+ std::mutex mDisplayMutex;
+ std::unordered_map<Display, DisplayBuffers> mDisplays;
+};
+
+HwcHal::HwcHal(const hw_module_t* module)
+ : mDevice(nullptr), mDispatch()
+{
+ if (!sHandleImporter.initialize()) {
+ LOG_ALWAYS_FATAL("failed to initialize handle importer");
+ }
+
+ int status = hwc2_open(module, &mDevice);
+ if (status) {
+ LOG_ALWAYS_FATAL("failed to open hwcomposer2 device: %s",
+ strerror(-status));
+ }
+
+ initCapabilities();
+ initDispatch();
+}
+
+HwcHal::~HwcHal()
+{
+ hwc2_close(mDevice);
+ mDisplays.clear();
+ sHandleImporter.cleanup();
+}
+
+void HwcHal::initCapabilities()
+{
+ uint32_t count = 0;
+ mDevice->getCapabilities(mDevice, &count, nullptr);
+
+ std::vector<Capability> caps(count);
+ mDevice->getCapabilities(mDevice, &count, reinterpret_cast<
+ std::underlying_type<Capability>::type*>(caps.data()));
+ caps.resize(count);
+
+ mCapabilities.insert(caps.cbegin(), caps.cend());
+}
+
+template<typename T>
+void HwcHal::initDispatch(T& func, hwc2_function_descriptor_t desc)
+{
+ auto pfn = mDevice->getFunction(mDevice, desc);
+ if (!pfn) {
+ LOG_ALWAYS_FATAL("failed to get hwcomposer2 function %d", desc);
+ }
+
+ func = reinterpret_cast<T>(pfn);
+}
+
+void HwcHal::initDispatch()
+{
+ initDispatch(mDispatch.acceptDisplayChanges,
+ HWC2_FUNCTION_ACCEPT_DISPLAY_CHANGES);
+ initDispatch(mDispatch.createLayer, HWC2_FUNCTION_CREATE_LAYER);
+ initDispatch(mDispatch.createVirtualDisplay,
+ HWC2_FUNCTION_CREATE_VIRTUAL_DISPLAY);
+ initDispatch(mDispatch.destroyLayer, HWC2_FUNCTION_DESTROY_LAYER);
+ initDispatch(mDispatch.destroyVirtualDisplay,
+ HWC2_FUNCTION_DESTROY_VIRTUAL_DISPLAY);
+ initDispatch(mDispatch.dump, HWC2_FUNCTION_DUMP);
+ initDispatch(mDispatch.getActiveConfig, HWC2_FUNCTION_GET_ACTIVE_CONFIG);
+ initDispatch(mDispatch.getChangedCompositionTypes,
+ HWC2_FUNCTION_GET_CHANGED_COMPOSITION_TYPES);
+ initDispatch(mDispatch.getClientTargetSupport,
+ HWC2_FUNCTION_GET_CLIENT_TARGET_SUPPORT);
+ initDispatch(mDispatch.getColorModes, HWC2_FUNCTION_GET_COLOR_MODES);
+ initDispatch(mDispatch.getDisplayAttribute,
+ HWC2_FUNCTION_GET_DISPLAY_ATTRIBUTE);
+ initDispatch(mDispatch.getDisplayConfigs,
+ HWC2_FUNCTION_GET_DISPLAY_CONFIGS);
+ initDispatch(mDispatch.getDisplayName, HWC2_FUNCTION_GET_DISPLAY_NAME);
+ initDispatch(mDispatch.getDisplayRequests,
+ HWC2_FUNCTION_GET_DISPLAY_REQUESTS);
+ initDispatch(mDispatch.getDisplayType, HWC2_FUNCTION_GET_DISPLAY_TYPE);
+ initDispatch(mDispatch.getDozeSupport, HWC2_FUNCTION_GET_DOZE_SUPPORT);
+ initDispatch(mDispatch.getHdrCapabilities,
+ HWC2_FUNCTION_GET_HDR_CAPABILITIES);
+ initDispatch(mDispatch.getMaxVirtualDisplayCount,
+ HWC2_FUNCTION_GET_MAX_VIRTUAL_DISPLAY_COUNT);
+ initDispatch(mDispatch.getReleaseFences,
+ HWC2_FUNCTION_GET_RELEASE_FENCES);
+ initDispatch(mDispatch.presentDisplay, HWC2_FUNCTION_PRESENT_DISPLAY);
+ initDispatch(mDispatch.registerCallback, HWC2_FUNCTION_REGISTER_CALLBACK);
+ initDispatch(mDispatch.setActiveConfig, HWC2_FUNCTION_SET_ACTIVE_CONFIG);
+ initDispatch(mDispatch.setClientTarget, HWC2_FUNCTION_SET_CLIENT_TARGET);
+ initDispatch(mDispatch.setColorMode, HWC2_FUNCTION_SET_COLOR_MODE);
+ initDispatch(mDispatch.setColorTransform,
+ HWC2_FUNCTION_SET_COLOR_TRANSFORM);
+ initDispatch(mDispatch.setCursorPosition,
+ HWC2_FUNCTION_SET_CURSOR_POSITION);
+ initDispatch(mDispatch.setLayerBlendMode,
+ HWC2_FUNCTION_SET_LAYER_BLEND_MODE);
+ initDispatch(mDispatch.setLayerBuffer, HWC2_FUNCTION_SET_LAYER_BUFFER);
+ initDispatch(mDispatch.setLayerColor, HWC2_FUNCTION_SET_LAYER_COLOR);
+ initDispatch(mDispatch.setLayerCompositionType,
+ HWC2_FUNCTION_SET_LAYER_COMPOSITION_TYPE);
+ initDispatch(mDispatch.setLayerDataspace,
+ HWC2_FUNCTION_SET_LAYER_DATASPACE);
+ initDispatch(mDispatch.setLayerDisplayFrame,
+ HWC2_FUNCTION_SET_LAYER_DISPLAY_FRAME);
+ initDispatch(mDispatch.setLayerPlaneAlpha,
+ HWC2_FUNCTION_SET_LAYER_PLANE_ALPHA);
+
+ if (hasCapability(Capability::SIDEBAND_STREAM)) {
+ initDispatch(mDispatch.setLayerSidebandStream,
+ HWC2_FUNCTION_SET_LAYER_SIDEBAND_STREAM);
+ }
+
+ initDispatch(mDispatch.setLayerSourceCrop,
+ HWC2_FUNCTION_SET_LAYER_SOURCE_CROP);
+ initDispatch(mDispatch.setLayerSurfaceDamage,
+ HWC2_FUNCTION_SET_LAYER_SURFACE_DAMAGE);
+ initDispatch(mDispatch.setLayerTransform,
+ HWC2_FUNCTION_SET_LAYER_TRANSFORM);
+ initDispatch(mDispatch.setLayerVisibleRegion,
+ HWC2_FUNCTION_SET_LAYER_VISIBLE_REGION);
+ initDispatch(mDispatch.setLayerZOrder, HWC2_FUNCTION_SET_LAYER_Z_ORDER);
+ initDispatch(mDispatch.setOutputBuffer, HWC2_FUNCTION_SET_OUTPUT_BUFFER);
+ initDispatch(mDispatch.setPowerMode, HWC2_FUNCTION_SET_POWER_MODE);
+ initDispatch(mDispatch.setVsyncEnabled, HWC2_FUNCTION_SET_VSYNC_ENABLED);
+ initDispatch(mDispatch.validateDisplay, HWC2_FUNCTION_VALIDATE_DISPLAY);
+}
+
+bool HwcHal::hasCapability(Capability capability) const
+{
+ return (mCapabilities.count(capability) > 0);
+}
+
+Return<void> HwcHal::getCapabilities(getCapabilities_cb hidl_cb)
+{
+ std::vector<Capability> caps(
+ mCapabilities.cbegin(), mCapabilities.cend());
+
+ hidl_vec<Capability> caps_reply;
+ caps_reply.setToExternal(caps.data(), caps.size());
+ hidl_cb(caps_reply);
+
+ return Void();
+}
+
+Return<void> HwcHal::dumpDebugInfo(dumpDebugInfo_cb hidl_cb)
+{
+ uint32_t len;
+ mDispatch.dump(mDevice, &len, nullptr);
+
+ std::vector<char> buf(len + 1);
+ mDispatch.dump(mDevice, &len, buf.data());
+ buf.resize(len + 1);
+ buf[len] = '\0';
+
+ hidl_string buf_reply;
+ buf_reply.setToExternal(buf.data(), len);
+ hidl_cb(buf_reply);
+
+ return Void();
+}
+
+void HwcHal::hotplugHook(hwc2_callback_data_t callbackData,
+ hwc2_display_t display, int32_t connected)
+{
+ auto hal = reinterpret_cast<HwcHal*>(callbackData);
+
+ {
+ std::lock_guard<std::mutex> lock(hal->mDisplayMutex);
+
+ if (connected == HWC2_CONNECTION_CONNECTED) {
+ hal->mDisplays.emplace(display, DisplayBuffers());
+ } else if (connected == HWC2_CONNECTION_DISCONNECTED) {
+ hal->mDisplays.erase(display);
+ }
+ }
+
+ hal->mCallback->onHotplug(display,
+ static_cast<IComposerCallback::Connection>(connected));
+}
+
+void HwcHal::refreshHook(hwc2_callback_data_t callbackData,
+ hwc2_display_t display)
+{
+ auto hal = reinterpret_cast<HwcHal*>(callbackData);
+ hal->mCallback->onRefresh(display);
+}
+
+void HwcHal::vsyncHook(hwc2_callback_data_t callbackData,
+ hwc2_display_t display, int64_t timestamp)
+{
+ auto hal = reinterpret_cast<HwcHal*>(callbackData);
+ hal->mCallback->onVsync(display, timestamp);
+}
+
+Return<void> HwcHal::registerCallback(const sp<IComposerCallback>& callback)
+{
+ std::lock_guard<std::mutex> lock(mCallbackMutex);
+
+ mCallback = callback;
+
+ mDispatch.registerCallback(mDevice, HWC2_CALLBACK_HOTPLUG, this,
+ reinterpret_cast<hwc2_function_pointer_t>(hotplugHook));
+ mDispatch.registerCallback(mDevice, HWC2_CALLBACK_REFRESH, this,
+ reinterpret_cast<hwc2_function_pointer_t>(refreshHook));
+ mDispatch.registerCallback(mDevice, HWC2_CALLBACK_VSYNC, this,
+ reinterpret_cast<hwc2_function_pointer_t>(vsyncHook));
+
+ return Void();
+}
+
+Return<uint32_t> HwcHal::getMaxVirtualDisplayCount()
+{
+ return mDispatch.getMaxVirtualDisplayCount(mDevice);
+}
+
+Return<void> HwcHal::createVirtualDisplay(uint32_t width, uint32_t height,
+ PixelFormat formatHint, createVirtualDisplay_cb hidl_cb)
+{
+ int32_t format = static_cast<int32_t>(formatHint);
+ hwc2_display_t display;
+ auto error = mDispatch.createVirtualDisplay(mDevice, width, height,
+ &format, &display);
+ if (error == HWC2_ERROR_NONE) {
+ std::lock_guard<std::mutex> lock(mDisplayMutex);
+
+ mDisplays.emplace(display, DisplayBuffers());
+ }
+
+ hidl_cb(static_cast<Error>(error), display,
+ static_cast<PixelFormat>(format));
+
+ return Void();
+}
+
+Return<Error> HwcHal::destroyVirtualDisplay(Display display)
+{
+ auto error = mDispatch.destroyVirtualDisplay(mDevice, display);
+ if (error == HWC2_ERROR_NONE) {
+ std::lock_guard<std::mutex> lock(mDisplayMutex);
+
+ mDisplays.erase(display);
+ }
+
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::acceptDisplayChanges(Display display)
+{
+ auto error = mDispatch.acceptDisplayChanges(mDevice, display);
+ return static_cast<Error>(error);
+}
+
+Return<void> HwcHal::createLayer(Display display, createLayer_cb hidl_cb)
+{
+ hwc2_layer_t layer;
+ auto error = mDispatch.createLayer(mDevice, display, &layer);
+
+ hidl_cb(static_cast<Error>(error), layer);
+
+ return Void();
+}
+
+Return<Error> HwcHal::destroyLayer(Display display, Layer layer)
+{
+ auto error = mDispatch.destroyLayer(mDevice, display, layer);
+ return static_cast<Error>(error);
+}
+
+Return<void> HwcHal::getActiveConfig(Display display,
+ getActiveConfig_cb hidl_cb)
+{
+ hwc2_config_t config;
+ auto error = mDispatch.getActiveConfig(mDevice, display, &config);
+
+ hidl_cb(static_cast<Error>(error), config);
+
+ return Void();
+}
+
+Return<void> HwcHal::getChangedCompositionTypes(Display display,
+ getChangedCompositionTypes_cb hidl_cb)
+{
+ uint32_t count = 0;
+ auto error = mDispatch.getChangedCompositionTypes(mDevice, display,
+ &count, nullptr, nullptr);
+ if (error != HWC2_ERROR_NONE) {
+ count = 0;
+ }
+
+ std::vector<hwc2_layer_t> layers(count);
+ std::vector<Composition> types(count);
+ error = mDispatch.getChangedCompositionTypes(mDevice, display,
+ &count, layers.data(),
+ reinterpret_cast<std::underlying_type<Composition>::type*>(
+ types.data()));
+ if (error != HWC2_ERROR_NONE) {
+ count = 0;
+ }
+ layers.resize(count);
+ types.resize(count);
+
+ hidl_vec<Layer> layers_reply;
+ layers_reply.setToExternal(layers.data(), layers.size());
+
+ hidl_vec<Composition> types_reply;
+ types_reply.setToExternal(types.data(), types.size());
+
+ hidl_cb(static_cast<Error>(error), layers_reply, types_reply);
+
+ return Void();
+}
+
+Return<Error> HwcHal::getClientTargetSupport(Display display,
+ uint32_t width, uint32_t height,
+ PixelFormat format, Dataspace dataspace)
+{
+ auto error = mDispatch.getClientTargetSupport(mDevice, display,
+ width, height, static_cast<int32_t>(format),
+ static_cast<int32_t>(dataspace));
+ return static_cast<Error>(error);
+}
+
+Return<void> HwcHal::getColorModes(Display display, getColorModes_cb hidl_cb)
+{
+ uint32_t count = 0;
+ auto error = mDispatch.getColorModes(mDevice, display, &count, nullptr);
+ if (error != HWC2_ERROR_NONE) {
+ count = 0;
+ }
+
+ std::vector<ColorMode> modes(count);
+ error = mDispatch.getColorModes(mDevice, display, &count,
+ reinterpret_cast<std::underlying_type<ColorMode>::type*>(
+ modes.data()));
+ if (error != HWC2_ERROR_NONE) {
+ count = 0;
+ }
+ modes.resize(count);
+
+ hidl_vec<ColorMode> modes_reply;
+ modes_reply.setToExternal(modes.data(), modes.size());
+ hidl_cb(static_cast<Error>(error), modes_reply);
+
+ return Void();
+}
+
+Return<void> HwcHal::getDisplayAttribute(Display display,
+ Config config, Attribute attribute,
+ getDisplayAttribute_cb hidl_cb)
+{
+ int32_t value;
+ auto error = mDispatch.getDisplayAttribute(mDevice, display, config,
+ static_cast<int32_t>(attribute), &value);
+
+ hidl_cb(static_cast<Error>(error), value);
+
+ return Void();
+}
+
+Return<void> HwcHal::getDisplayConfigs(Display display,
+ getDisplayConfigs_cb hidl_cb)
+{
+ uint32_t count = 0;
+ auto error = mDispatch.getDisplayConfigs(mDevice, display,
+ &count, nullptr);
+ if (error != HWC2_ERROR_NONE) {
+ count = 0;
+ }
+
+ std::vector<hwc2_config_t> configs(count);
+ error = mDispatch.getDisplayConfigs(mDevice, display,
+ &count, configs.data());
+ if (error != HWC2_ERROR_NONE) {
+ count = 0;
+ }
+ configs.resize(count);
+
+ hidl_vec<Config> configs_reply;
+ configs_reply.setToExternal(configs.data(), configs.size());
+ hidl_cb(static_cast<Error>(error), configs_reply);
+
+ return Void();
+}
+
+Return<void> HwcHal::getDisplayName(Display display,
+ getDisplayName_cb hidl_cb)
+{
+ uint32_t count = 0;
+ auto error = mDispatch.getDisplayName(mDevice, display, &count, nullptr);
+ if (error != HWC2_ERROR_NONE) {
+ count = 0;
+ }
+
+ std::vector<char> name(count + 1);
+ error = mDispatch.getDisplayName(mDevice, display, &count, name.data());
+ if (error != HWC2_ERROR_NONE) {
+ count = 0;
+ }
+ name.resize(count + 1);
+ name[count] = '\0';
+
+ hidl_string name_reply;
+ name_reply.setToExternal(name.data(), count);
+ hidl_cb(static_cast<Error>(error), name_reply);
+
+ return Void();
+}
+
+Return<void> HwcHal::getDisplayRequests(Display display,
+ getDisplayRequests_cb hidl_cb)
+{
+ int32_t display_reqs;
+ uint32_t count = 0;
+ auto error = mDispatch.getDisplayRequests(mDevice, display,
+ &display_reqs, &count, nullptr, nullptr);
+ if (error != HWC2_ERROR_NONE) {
+ count = 0;
+ }
+
+ std::vector<hwc2_layer_t> layers(count);
+ std::vector<int32_t> layer_reqs(count);
+ error = mDispatch.getDisplayRequests(mDevice, display,
+ &display_reqs, &count, layers.data(), layer_reqs.data());
+ if (error != HWC2_ERROR_NONE) {
+ count = 0;
+ }
+ layers.resize(count);
+ layer_reqs.resize(count);
+
+ hidl_vec<Layer> layers_reply;
+ layers_reply.setToExternal(layers.data(), layers.size());
+
+ hidl_vec<uint32_t> layer_reqs_reply;
+ layer_reqs_reply.setToExternal(
+ reinterpret_cast<uint32_t*>(layer_reqs.data()),
+ layer_reqs.size());
+
+ hidl_cb(static_cast<Error>(error), display_reqs,
+ layers_reply, layer_reqs_reply);
+
+ return Void();
+}
+
+Return<void> HwcHal::getDisplayType(Display display,
+ getDisplayType_cb hidl_cb)
+{
+ int32_t type;
+ auto error = mDispatch.getDisplayType(mDevice, display, &type);
+
+ hidl_cb(static_cast<Error>(error), static_cast<DisplayType>(type));
+
+ return Void();
+}
+
+Return<void> HwcHal::getDozeSupport(Display display,
+ getDozeSupport_cb hidl_cb)
+{
+ int32_t support;
+ auto error = mDispatch.getDozeSupport(mDevice, display, &support);
+
+ hidl_cb(static_cast<Error>(error), support);
+
+ return Void();
+}
+
+Return<void> HwcHal::getHdrCapabilities(Display display,
+ getHdrCapabilities_cb hidl_cb)
+{
+ float max_lumi, max_avg_lumi, min_lumi;
+ uint32_t count = 0;
+ auto error = mDispatch.getHdrCapabilities(mDevice, display,
+ &count, nullptr, &max_lumi, &max_avg_lumi, &min_lumi);
+ if (error != HWC2_ERROR_NONE) {
+ count = 0;
+ }
+
+ std::vector<Hdr> types(count);
+ error = mDispatch.getHdrCapabilities(mDevice, display, &count,
+ reinterpret_cast<std::underlying_type<Hdr>::type*>(types.data()),
+ &max_lumi, &max_avg_lumi, &min_lumi);
+ if (error != HWC2_ERROR_NONE) {
+ count = 0;
+ }
+ types.resize(count);
+
+ hidl_vec<Hdr> types_reply;
+ types_reply.setToExternal(types.data(), types.size());
+ hidl_cb(static_cast<Error>(error), types_reply,
+ max_lumi, max_avg_lumi, min_lumi);
+
+ return Void();
+}
+
+Return<void> HwcHal::getReleaseFences(Display display,
+ getReleaseFences_cb hidl_cb)
+{
+ uint32_t count = 0;
+ auto error = mDispatch.getReleaseFences(mDevice, display,
+ &count, nullptr, nullptr);
+ if (error != HWC2_ERROR_NONE) {
+ count = 0;
+ }
+
+ std::vector<hwc2_layer_t> layers(count);
+ std::vector<int32_t> fences(count);
+ error = mDispatch.getReleaseFences(mDevice, display,
+ &count, layers.data(), fences.data());
+ if (error != HWC2_ERROR_NONE) {
+ count = 0;
+ }
+ layers.resize(count);
+ fences.resize(count);
+
+ // filter out layers with release fence -1
+ std::vector<hwc2_layer_t> filtered_layers;
+ std::vector<int> filtered_fences;
+ for (size_t i = 0; i < layers.size(); i++) {
+ if (fences[i] >= 0) {
+ filtered_layers.push_back(layers[i]);
+ filtered_fences.push_back(fences[i]);
+ }
+ }
+
+ hidl_vec<Layer> layers_reply;
+ native_handle_t* fences_reply =
+ native_handle_create(filtered_fences.size(), 0);
+ if (fences_reply) {
+ layers_reply.setToExternal(filtered_layers.data(),
+ filtered_layers.size());
+ memcpy(fences_reply->data, filtered_fences.data(),
+ sizeof(int) * filtered_fences.size());
+
+ hidl_cb(static_cast<Error>(error), layers_reply, fences_reply);
+
+ native_handle_close(fences_reply);
+ native_handle_delete(fences_reply);
+ } else {
+ NATIVE_HANDLE_DECLARE_STORAGE(fences_storage, 0, 0);
+ fences_reply = native_handle_init(fences_storage, 0, 0);
+
+ hidl_cb(Error::NO_RESOURCES, layers_reply, fences_reply);
+
+ for (auto fence : filtered_fences) {
+ close(fence);
+ }
+ }
+
+ return Void();
+}
+
+Return<void> HwcHal::presentDisplay(Display display,
+ presentDisplay_cb hidl_cb)
+{
+ int32_t fence = -1;
+ auto error = mDispatch.presentDisplay(mDevice, display, &fence);
+
+ NATIVE_HANDLE_DECLARE_STORAGE(fence_storage, 1, 0);
+ native_handle_t* fence_reply;
+ if (fence >= 0) {
+ fence_reply = native_handle_init(fence_storage, 1, 0);
+ fence_reply->data[0] = fence;
+ } else {
+ fence_reply = native_handle_init(fence_storage, 0, 0);
+ }
+
+ hidl_cb(static_cast<Error>(error), fence_reply);
+
+ if (fence >= 0) {
+ close(fence);
+ }
+
+ return Void();
+}
+
+Return<Error> HwcHal::setActiveConfig(Display display, Config config)
+{
+ auto error = mDispatch.setActiveConfig(mDevice, display, config);
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setClientTarget(Display display,
+ const native_handle_t* target,
+ const native_handle_t* acquireFence,
+ Dataspace dataspace, const hidl_vec<Rect>& damage)
+{
+ if (!sHandleImporter.importBuffer(target)) {
+ return Error::NO_RESOURCES;
+ }
+
+ int32_t fence;
+ if (!sHandleImporter.importFence(acquireFence, fence)) {
+ sHandleImporter.freeBuffer(target);
+ return Error::NO_RESOURCES;
+ }
+
+ hwc_region_t damage_region = { damage.size(),
+ reinterpret_cast<const hwc_rect_t*>(&damage[0]) };
+
+ int32_t error = mDispatch.setClientTarget(mDevice, display,
+ target, fence, static_cast<int32_t>(dataspace),
+ damage_region);
+ if (error == HWC2_ERROR_NONE) {
+ std::lock_guard<std::mutex> lock(mDisplayMutex);
+
+ auto dpy = mDisplays.find(display);
+ dpy->second.ClientTarget = target;
+ } else {
+ sHandleImporter.freeBuffer(target);
+ sHandleImporter.closeFence(fence);
+ }
+
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setColorMode(Display display, ColorMode mode)
+{
+ auto error = mDispatch.setColorMode(mDevice, display,
+ static_cast<int32_t>(mode));
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setColorTransform(Display display,
+ const hidl_vec<float>& matrix, ColorTransform hint)
+{
+ auto error = mDispatch.setColorTransform(mDevice, display,
+ &matrix[0], static_cast<int32_t>(hint));
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setOutputBuffer(Display display,
+ const native_handle_t* buffer,
+ const native_handle_t* releaseFence)
+{
+ if (!sHandleImporter.importBuffer(buffer)) {
+ return Error::NO_RESOURCES;
+ }
+
+ int32_t fence;
+ if (!sHandleImporter.importFence(releaseFence, fence)) {
+ sHandleImporter.freeBuffer(buffer);
+ return Error::NO_RESOURCES;
+ }
+
+ int32_t error = mDispatch.setOutputBuffer(mDevice,
+ display, buffer, fence);
+ if (error == HWC2_ERROR_NONE) {
+ std::lock_guard<std::mutex> lock(mDisplayMutex);
+
+ auto dpy = mDisplays.find(display);
+ dpy->second.OutputBuffer = buffer;
+ } else {
+ sHandleImporter.freeBuffer(buffer);
+ }
+
+ // unlike in setClientTarget, fence is owned by us and is always closed
+ sHandleImporter.closeFence(fence);
+
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setPowerMode(Display display, PowerMode mode)
+{
+ auto error = mDispatch.setPowerMode(mDevice, display,
+ static_cast<int32_t>(mode));
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setVsyncEnabled(Display display,
+ Vsync enabled)
+{
+ auto error = mDispatch.setVsyncEnabled(mDevice, display,
+ static_cast<int32_t>(enabled));
+ return static_cast<Error>(error);
+}
+
+Return<void> HwcHal::validateDisplay(Display display,
+ validateDisplay_cb hidl_cb)
+{
+ uint32_t types_count = 0;
+ uint32_t reqs_count = 0;
+ auto error = mDispatch.validateDisplay(mDevice, display,
+ &types_count, &reqs_count);
+
+ hidl_cb(static_cast<Error>(error), types_count, reqs_count);
+
+ return Void();
+}
+
+Return<Error> HwcHal::setCursorPosition(Display display,
+ Layer layer, int32_t x, int32_t y)
+{
+ auto error = mDispatch.setCursorPosition(mDevice, display, layer, x, y);
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setLayerBuffer(Display display,
+ Layer layer, const native_handle_t* buffer,
+ const native_handle_t* acquireFence)
+{
+ if (!sHandleImporter.importBuffer(buffer)) {
+ return Error::NO_RESOURCES;
+ }
+
+ int32_t fence;
+ if (!sHandleImporter.importFence(acquireFence, fence)) {
+ sHandleImporter.freeBuffer(buffer);
+ return Error::NO_RESOURCES;
+ }
+
+ int32_t error = mDispatch.setLayerBuffer(mDevice,
+ display, layer, buffer, fence);
+ if (error == HWC2_ERROR_NONE) {
+ std::lock_guard<std::mutex> lock(mDisplayMutex);
+
+ auto dpy = mDisplays.find(display);
+ dpy->second.LayerBuffers[layer] = buffer;
+ } else {
+ sHandleImporter.freeBuffer(buffer);
+ sHandleImporter.closeFence(fence);
+ }
+
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setLayerSurfaceDamage(Display display,
+ Layer layer, const hidl_vec<Rect>& damage)
+{
+ hwc_region_t damage_region = { damage.size(),
+ reinterpret_cast<const hwc_rect_t*>(&damage[0]) };
+
+ auto error = mDispatch.setLayerSurfaceDamage(mDevice, display, layer,
+ damage_region);
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setLayerBlendMode(Display display,
+ Layer layer, BlendMode mode)
+{
+ auto error = mDispatch.setLayerBlendMode(mDevice, display, layer,
+ static_cast<int32_t>(mode));
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setLayerColor(Display display,
+ Layer layer, const Color& color)
+{
+ hwc_color_t hwc_color{color.r, color.g, color.b, color.a};
+ auto error = mDispatch.setLayerColor(mDevice, display, layer, hwc_color);
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setLayerCompositionType(Display display,
+ Layer layer, Composition type)
+{
+ auto error = mDispatch.setLayerCompositionType(mDevice, display, layer,
+ static_cast<int32_t>(type));
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setLayerDataspace(Display display,
+ Layer layer, Dataspace dataspace)
+{
+ auto error = mDispatch.setLayerDataspace(mDevice, display, layer,
+ static_cast<int32_t>(dataspace));
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setLayerDisplayFrame(Display display,
+ Layer layer, const Rect& frame)
+{
+ hwc_rect_t hwc_frame{frame.left, frame.top, frame.right, frame.bottom};
+ auto error = mDispatch.setLayerDisplayFrame(mDevice, display, layer,
+ hwc_frame);
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setLayerPlaneAlpha(Display display,
+ Layer layer, float alpha)
+{
+ auto error = mDispatch.setLayerPlaneAlpha(mDevice, display, layer, alpha);
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setLayerSidebandStream(Display display,
+ Layer layer, const native_handle_t* stream)
+{
+ if (!sHandleImporter.importBuffer(stream)) {
+ return Error::NO_RESOURCES;
+ }
+
+ int32_t error = mDispatch.setLayerSidebandStream(mDevice,
+ display, layer, stream);
+ if (error == HWC2_ERROR_NONE) {
+ std::lock_guard<std::mutex> lock(mDisplayMutex);
+
+ auto dpy = mDisplays.find(display);
+ dpy->second.LayerSidebandStreams[layer] = stream;
+ } else {
+ sHandleImporter.freeBuffer(stream);
+ }
+
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setLayerSourceCrop(Display display,
+ Layer layer, const FRect& crop)
+{
+ hwc_frect_t hwc_crop{crop.left, crop.top, crop.right, crop.bottom};
+ auto error = mDispatch.setLayerSourceCrop(mDevice, display, layer,
+ hwc_crop);
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setLayerTransform(Display display,
+ Layer layer, Transform transform)
+{
+ auto error = mDispatch.setLayerTransform(mDevice, display, layer,
+ static_cast<int32_t>(transform));
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setLayerVisibleRegion(Display display,
+ Layer layer, const hidl_vec<Rect>& visible)
+{
+ hwc_region_t visible_region = { visible.size(),
+ reinterpret_cast<const hwc_rect_t*>(&visible[0]) };
+
+ auto error = mDispatch.setLayerVisibleRegion(mDevice, display, layer,
+ visible_region);
+ return static_cast<Error>(error);
+}
+
+Return<Error> HwcHal::setLayerZOrder(Display display,
+ Layer layer, uint32_t z)
+{
+ auto error = mDispatch.setLayerZOrder(mDevice, display, layer, z);
+ return static_cast<Error>(error);
+}
+
+IComposer* HIDL_FETCH_IComposer(const char*)
+{
+ const hw_module_t* module;
+ int err = hw_get_module(HWC_HARDWARE_MODULE_ID, &module);
+ if (err) {
+ ALOGE("failed to get hwcomposer module");
+ return nullptr;
+ }
+
+ return new HwcHal(module);
+}
+
+} // namespace implementation
+} // namespace V2_1
+} // namespace composer
+} // namespace graphics
+} // namespace hardware
+} // namespace android
diff --git a/graphics/composer/2.1/default/Hwc.h b/graphics/composer/2.1/default/Hwc.h
new file mode 100644
index 0000000..de69417
--- /dev/null
+++ b/graphics/composer/2.1/default/Hwc.h
@@ -0,0 +1,38 @@
+/*
+ * Copyright 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.
+ */
+
+#ifndef ANDROID_HARDWARE_GRAPHICS_COMPOSER_V2_1_HWC_H
+#define ANDROID_HARDWARE_GRAPHICS_COMPOSER_V2_1_HWC_H
+
+#include <android/hardware/graphics/composer/2.1/IComposer.h>
+
+namespace android {
+namespace hardware {
+namespace graphics {
+namespace composer {
+namespace V2_1 {
+namespace implementation {
+
+extern "C" IComposer* HIDL_FETCH_IComposer(const char* name);
+
+} // namespace implementation
+} // namespace V2_1
+} // namespace composer
+} // namespace graphics
+} // namespace hardware
+} // namespace android
+
+#endif // ANDROID_HARDWARE_GRAPHICS_COMPOSER_V2_1_HWC_H
diff --git a/graphics/composer/2.1/types.hal b/graphics/composer/2.1/types.hal
new file mode 100644
index 0000000..3c591b3
--- /dev/null
+++ b/graphics/composer/2.1/types.hal
@@ -0,0 +1,163 @@
+/*
+ * 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.
+ */
+
+package android.hardware.graphics.composer@2.1;
+
+/* Return codes from all functions. */
+enum Error : int32_t {
+ NONE = 0, /* no error */
+ BAD_CONFIG = 1, /* invalid Config */
+ BAD_DISPLAY = 2, /* invalid Display */
+ BAD_LAYER = 3, /* invalid Layer */
+ BAD_PARAMETER = 4, /* invalid width, height, etc. */
+ HAS_CHANGES = 5,
+ NO_RESOURCES = 6, /* temporary failure due to resource contention */
+ NOT_VALIDATED = 7, /* validateDisplay has not been called */
+ UNSUPPORTED = 8, /* permanent failure */
+};
+
+typedef uint32_t Config;
+typedef uint64_t Display;
+typedef uint64_t Layer;
+
+/*
+ * Copied from android_transform_t
+ *
+ * TODO(olv) copy comments over and generate android_transform_t
+ */
+enum Transform : int32_t {
+ FLIP_H = 0x1,
+ FLIP_V = 0x2,
+ ROT_90 = 0x4,
+ ROT_180 = 0x3,
+ ROT_270 = 0x7,
+ RESERVED = 0x8,
+};
+
+/*
+ * Copied from android_color_mode_t
+ *
+ * TODO(olv) copy comments over and generate android_color_mode_t
+ */
+enum ColorMode : int32_t {
+ NATIVE = 0,
+ STANDARD_BT601_625 = 1,
+ STANDARD_BT601_625_UNADJUSTED = 2,
+ STANDARD_BT601_525 = 3,
+ STANDARD_BT601_525_UNADJUSTED = 4,
+ STANDARD_BT709 = 5,
+ DCI_P3 = 6,
+ SRGB = 7,
+ ADOBE_RGB = 8,
+};
+
+/*
+ * Copied from android_color_transform_t
+ *
+ * TODO(olv) copy comments over and generate android_color_transform_t
+ */
+enum ColorTransform : int32_t {
+ IDENTITY = 0,
+ ARBITRARY_MATRIX = 1,
+ VALUE_INVERSE = 2,
+ GRAYSCALE = 3,
+ CORRECT_PROTANOPIA = 4,
+ CORRECT_DEUTERANOPIA = 5,
+ CORRECT_TRITANOPIA = 6
+};
+
+/*
+ * Copied from android_dataspace_t
+ *
+ * TODO(olv) copy comments over and generate android_dataspace_t
+ */
+enum Dataspace : int32_t {
+ UNKNOWN = 0x0,
+ ARBITRARY = 0x1,
+
+ STANDARD_SHIFT = 16,
+ STANDARD_MASK = 63 << STANDARD_SHIFT,
+ STANDARD_UNSPECIFIED = 0 << STANDARD_SHIFT,
+ STANDARD_BT709 = 1 << STANDARD_SHIFT,
+ STANDARD_BT601_625 = 2 << STANDARD_SHIFT,
+ STANDARD_BT601_625_UNADJUSTED = 3 << STANDARD_SHIFT,
+ STANDARD_BT601_525 = 4 << STANDARD_SHIFT,
+ STANDARD_BT601_525_UNADJUSTED = 5 << STANDARD_SHIFT,
+ STANDARD_BT2020 = 6 << STANDARD_SHIFT,
+ STANDARD_BT2020_CONSTANT_LUMINANCE = 7 << STANDARD_SHIFT,
+ STANDARD_BT470M = 8 << STANDARD_SHIFT,
+ STANDARD_FILM = 9 << STANDARD_SHIFT,
+
+ TRANSFER_SHIFT = 22,
+ TRANSFER_MASK = 31 << TRANSFER_SHIFT,
+ TRANSFER_UNSPECIFIED = 0 << TRANSFER_SHIFT,
+ TRANSFER_LINEAR = 1 << TRANSFER_SHIFT,
+ TRANSFER_SRGB = 2 << TRANSFER_SHIFT,
+ TRANSFER_SMPTE_170M = 3 << TRANSFER_SHIFT,
+ TRANSFER_GAMMA2_2 = 4 << TRANSFER_SHIFT,
+ TRANSFER_GAMMA2_8 = 5 << TRANSFER_SHIFT,
+ TRANSFER_ST2084 = 6 << TRANSFER_SHIFT,
+ TRANSFER_HLG = 7 << TRANSFER_SHIFT,
+
+ RANGE_SHIFT = 27,
+ RANGE_MASK = 7 << RANGE_SHIFT,
+ RANGE_UNSPECIFIED = 0 << RANGE_SHIFT,
+ RANGE_FULL = 1 << RANGE_SHIFT,
+ RANGE_LIMITED = 2 << RANGE_SHIFT,
+
+ SRGB_LINEAR = 0x200,
+ V0_SRGB_LINEAR = STANDARD_BT709 |
+ TRANSFER_LINEAR |
+ RANGE_FULL,
+
+ SRGB = 0x201,
+ V0_SRGB = STANDARD_BT709 |
+ TRANSFER_SRGB |
+ RANGE_FULL,
+
+ JFIF = 0x101,
+ V0_JFIF = STANDARD_BT601_625 |
+ TRANSFER_SMPTE_170M |
+ RANGE_FULL,
+
+ BT601_625 = 0x102,
+ V0_BT601_625 = STANDARD_BT601_625 |
+ TRANSFER_SMPTE_170M |
+ RANGE_LIMITED,
+
+ BT601_525 = 0x103,
+ V0_BT601_525 = STANDARD_BT601_525 |
+ TRANSFER_SMPTE_170M |
+ RANGE_LIMITED,
+
+ BT709 = 0x104,
+ V0_BT709 = STANDARD_BT709 |
+ TRANSFER_SMPTE_170M |
+ RANGE_LIMITED,
+
+ DEPTH = 0x1000,
+};
+
+/*
+ * Copied from android_hdr_t
+ *
+ * TODO(olv) copy comments over and generate android_hdr_t
+ */
+enum Hdr : int32_t {
+ DOLBY_VISION = 1,
+ HDR10 = 2,
+ HLG = 3,
+};
diff --git a/light/2.0/default/service.cpp b/light/2.0/default/service.cpp
index 582d224..e446878 100644
--- a/light/2.0/default/service.cpp
+++ b/light/2.0/default/service.cpp
@@ -27,11 +27,11 @@
ALOGI("Retrieving default implementation of instance %s.",
instance);
- android::sp<ILight> service = ILight::getService(instance, true);
+ android::sp<ILight> service = ILight::getService(instance, true /* getStub */);
if (service.get() == nullptr) {
ALOGE("ILight::getService returned NULL, exiting");
- return -1;
+ return EXIT_FAILURE;
}
LOG_FATAL_IF(service->isRemote(), "Implementation is REMOTE!");
diff --git a/memtrack/1.0/default/Android.bp b/memtrack/1.0/default/Android.bp
index 50d2318..c6ab6b9 100644
--- a/memtrack/1.0/default/Android.bp
+++ b/memtrack/1.0/default/Android.bp
@@ -32,7 +32,6 @@
cc_binary {
relative_install_path: "hw",
name: "android.hardware.memtrack@1.0-service",
- init_rc: ["android.hardware.memtrack@1.0-service.rc"],
srcs: ["service.cpp"],
shared_libs: [
diff --git a/memtrack/1.0/default/android.hardware.memtrack@1.0-service.rc b/memtrack/1.0/default/android.hardware.memtrack@1.0-service.rc
deleted file mode 100644
index 14e7d00..0000000
--- a/memtrack/1.0/default/android.hardware.memtrack@1.0-service.rc
+++ /dev/null
@@ -1,4 +0,0 @@
-service memtrack-hal-1-0 /system/bin/hw/android.hardware.memtrack@1.0-service
- class hal
- user system
- group system
diff --git a/nfc/1.0/default/service.cpp b/nfc/1.0/default/service.cpp
index 8952052..e70388d 100644
--- a/nfc/1.0/default/service.cpp
+++ b/nfc/1.0/default/service.cpp
@@ -26,7 +26,7 @@
const char instance[] = "nfc_nci";
ALOGI("Retrieving default implementation of instance %s.",
instance);
- android::sp<INfc> service = INfc::getService(instance, true);
+ android::sp<INfc> service = INfc::getService(instance, true /* getStub */);
if (service.get() == nullptr) {
ALOGE("INfc::getService returned NULL, exiting");
return -1;
@@ -35,7 +35,7 @@
instance, (service->isRemote() ? "REMOTE" : "LOCAL"));
LOG_FATAL_IF(service->isRemote(), "Implementation is REMOTE!");
ALOGI("Registering instance %s.", instance);
- service->registerAsService("nfc_nci");
+ service->registerAsService(instance);
ALOGI("Ready.");
ProcessState::self()->setThreadPoolMaxThreadCount(0);
diff --git a/sensors/1.0/Android.bp b/sensors/1.0/Android.bp
new file mode 100644
index 0000000..32ee049
--- /dev/null
+++ b/sensors/1.0/Android.bp
@@ -0,0 +1,46 @@
+// This file is autogenerated by hidl-gen. Do not edit manually.
+
+genrule {
+ name: "android.hardware.sensors@1.0_genc++",
+ tool: "hidl-gen",
+ cmd: "$tool -o $genDir -Lc++ -randroid.hardware:hardware/interfaces android.hardware.sensors@1.0",
+ srcs: [
+ "types.hal",
+ "ISensors.hal",
+ ],
+ out: [
+ "android/hardware/sensors/1.0/types.cpp",
+ "android/hardware/sensors/1.0/SensorsAll.cpp",
+ ],
+}
+
+genrule {
+ name: "android.hardware.sensors@1.0_genc++_headers",
+ tool: "hidl-gen",
+ cmd: "$tool -o $genDir -Lc++ -randroid.hardware:hardware/interfaces android.hardware.sensors@1.0",
+ srcs: [
+ "types.hal",
+ "ISensors.hal",
+ ],
+ out: [
+ "android/hardware/sensors/1.0/types.h",
+ "android/hardware/sensors/1.0/ISensors.h",
+ "android/hardware/sensors/1.0/IHwSensors.h",
+ "android/hardware/sensors/1.0/BnSensors.h",
+ "android/hardware/sensors/1.0/BpSensors.h",
+ "android/hardware/sensors/1.0/BsSensors.h",
+ ],
+}
+
+cc_library_shared {
+ name: "android.hardware.sensors@1.0",
+ generated_sources: ["android.hardware.sensors@1.0_genc++"],
+ generated_headers: ["android.hardware.sensors@1.0_genc++_headers"],
+ export_generated_headers: ["android.hardware.sensors@1.0_genc++_headers"],
+ shared_libs: [
+ "libhidl",
+ "libhwbinder",
+ "libutils",
+ "libcutils",
+ ],
+}
diff --git a/sensors/1.0/ISensors.hal b/sensors/1.0/ISensors.hal
new file mode 100644
index 0000000..adacfe0
--- /dev/null
+++ b/sensors/1.0/ISensors.hal
@@ -0,0 +1,124 @@
+/*
+ * 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.
+ */
+
+package android.hardware.sensors@1.0;
+
+interface ISensors {
+ /**
+ * Enumerate all available (static) sensors.
+ */
+ getSensorsList() generates (vec<SensorInfo> list);
+
+ /**
+ * Place the module in a specific mode. The following modes are defined
+ *
+ * SENSOR_HAL_NORMAL_MODE - Normal operation. Default state of the module.
+ *
+ * SENSOR_HAL_DATA_INJECTION_MODE - Loopback mode.
+ * Data is injected for the supported sensors by the sensor service in
+ * this mode.
+ *
+ * @return OK on success
+ * BAD_VALUE if requested mode is not supported
+ * PERMISSION_DENIED if operation is not allowed
+ */
+ setOperationMode(OperationMode mode) generates (Result result);
+
+ /* Activate/de-activate one sensor.
+ *
+ * sensorHandle is the handle of the sensor to change.
+ * enabled set to true to enable, or false to disable the sensor.
+ *
+ * After sensor de-activation, existing sensor events that have not
+ * been picked up by poll() should be abandoned immediately so that
+ * subsequent activation will not get stale sensor events (events
+ * that are generated prior to the latter activation).
+ *
+ * Returns OK on success, BAD_VALUE if sensorHandle is invalid.
+ */
+ activate(int32_t sensorHandle, bool enabled) generates (Result result);
+
+ /**
+ * Set the sampling period in nanoseconds for a given sensor.
+ * If samplingPeriodNs > maxDelay it will be truncated to
+ * maxDelay and if samplingPeriodNs < minDelay it will be
+ * replaced by minDelay.
+ *
+ * Returns OK on success, BAD_VALUE if sensorHandle is invalid.
+ */
+ setDelay(int32_t sensorHandle, int64_t samplingPeriodNs)
+ generates (Result result);
+
+ /**
+ * Generate a vector of sensor events containing at most "maxCount"
+ * entries.
+ *
+ * Additionally a vector of SensorInfos is returned for any dynamic sensors
+ * connected as notified by returned events of type DYNAMIC_SENSOR_META.
+ *
+ * This function should block if there is no sensor event
+ * available when being called.
+ *
+ * Returns OK on success or BAD_VALUE if maxCount <= 0.
+ */
+ poll(int32_t maxCount)
+ generates (
+ Result result,
+ vec<Event> data,
+ vec<SensorInfo> dynamicSensorsAdded);
+
+ /*
+ * Sets a sensor’s parameters, including sampling frequency and maximum
+ * report latency. This function can be called while the sensor is
+ * activated, in which case it must not cause any sensor measurements to
+ * be lost: transitioning from one sampling rate to the other cannot cause
+ * lost events, nor can transitioning from a high maximum report latency to
+ * a low maximum report latency.
+ * See the Batching sensor results page for details:
+ * http://source.android.com/devices/sensors/batching.html
+ *
+ * Returns OK on success, BAD_VALUE if any parameters are invalid.
+ */
+ batch(int32_t sensorHandle,
+ int32_t flags,
+ int64_t samplingPeriodNs,
+ int64_t maxReportLatencyNs) generates (Result result);
+
+ /*
+ * Flush adds a FLUSH_COMPLETE metadata event to the end of the "batch mode"
+ * FIFO for the specified sensor and flushes the FIFO.
+ * If the FIFO is empty or if the sensor doesn't support batching
+ * (FIFO size zero), it should return SUCCESS along with a trivial
+ * FLUSH_COMPLETE event added to the event stream.
+ * This applies to all sensors other than one-shot sensors.
+ * If the sensor is a one-shot sensor, flush must return BAD_VALUE and not
+ * generate any flush complete metadata.
+ * If the sensor is not active at the time flush() is called, flush() should
+ * return BAD_VALUE.
+ * Returns OK on success and BAD_VALUE if sensorHandle is invalid.
+ */
+ flush(int32_t sensorHandle) generates (Result result);
+
+ /*
+ * Inject a single sensor sample to this device.
+ * data points to the sensor event to be injected
+ * Returns OK on success
+ * PERMISSION_DENIED if operation is not allowed
+ * INVALID_OPERATION, if this functionality is unsupported
+ * BAD_VALUE if sensor event cannot be injected
+ */
+ injectSensorData(Event event) generates (Result result);
+};
diff --git a/sensors/1.0/default/Android.bp b/sensors/1.0/default/Android.bp
new file mode 100644
index 0000000..d454cdb
--- /dev/null
+++ b/sensors/1.0/default/Android.bp
@@ -0,0 +1,38 @@
+cc_library_shared {
+ name: "android.hardware.sensors@1.0-impl",
+ relative_install_path: "hw",
+ srcs: ["Sensors.cpp"],
+ shared_libs: [
+ "liblog",
+ "libcutils",
+ "libhardware",
+ "libhwbinder",
+ "libbase",
+ "libcutils",
+ "libutils",
+ "libhidl",
+ "android.hardware.sensors@1.0",
+ ],
+ static_libs: [
+ "android.hardware.sensors@1.0-convert",
+ ],
+}
+
+cc_library_static {
+ name: "android.hardware.sensors@1.0-convert",
+ srcs: ["convert.cpp"],
+ export_include_dirs: ["include"],
+ shared_libs: [
+ "liblog",
+ "libcutils",
+ "libhardware",
+ "libhwbinder",
+ "libbase",
+ "libcutils",
+ "libutils",
+ "libhidl",
+ "android.hardware.sensors@1.0",
+ ],
+}
+
+
diff --git a/sensors/1.0/default/Android.mk b/sensors/1.0/default/Android.mk
new file mode 100644
index 0000000..4f418cb
--- /dev/null
+++ b/sensors/1.0/default/Android.mk
@@ -0,0 +1,24 @@
+LOCAL_PATH:= $(call my-dir)
+
+include $(CLEAR_VARS)
+LOCAL_MODULE_RELATIVE_PATH := hw
+LOCAL_MODULE := android.hardware.sensors@1.0-service
+LOCAL_INIT_RC := android.hardware.sensors@1.0-service.rc
+LOCAL_SRC_FILES := \
+ service.cpp \
+
+LOCAL_SHARED_LIBRARIES := \
+ liblog \
+ libcutils \
+ libdl \
+ libbase \
+ libutils \
+ libhardware_legacy \
+ libhardware \
+
+LOCAL_SHARED_LIBRARIES += \
+ libhwbinder \
+ libhidl \
+ android.hardware.sensors@1.0 \
+
+include $(BUILD_EXECUTABLE)
diff --git a/sensors/1.0/default/Sensors.cpp b/sensors/1.0/default/Sensors.cpp
new file mode 100644
index 0000000..ef052c3
--- /dev/null
+++ b/sensors/1.0/default/Sensors.cpp
@@ -0,0 +1,250 @@
+/*
+ * 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.
+ */
+
+#include "Sensors.h"
+
+#include "convert.h"
+
+#include <android-base/logging.h>
+
+namespace android {
+namespace hardware {
+namespace sensors {
+namespace V1_0 {
+namespace implementation {
+
+static Result ResultFromStatus(status_t err) {
+ switch (err) {
+ case OK:
+ return Result::OK;
+ case BAD_VALUE:
+ return Result::BAD_VALUE;
+ case PERMISSION_DENIED:
+ return Result::PERMISSION_DENIED;
+ default:
+ return Result::INVALID_OPERATION;
+ }
+}
+
+Sensors::Sensors()
+ : mInitCheck(NO_INIT),
+ mSensorModule(nullptr),
+ mSensorDevice(nullptr) {
+ status_t err = hw_get_module(
+ SENSORS_HARDWARE_MODULE_ID,
+ (hw_module_t const **)&mSensorModule);
+
+ if (mSensorModule == NULL) {
+ err = UNKNOWN_ERROR;
+ }
+
+ if (err != OK) {
+ LOG(ERROR) << "Couldn't load "
+ << SENSORS_HARDWARE_MODULE_ID
+ << " module ("
+ << strerror(-err)
+ << ")";
+
+ mInitCheck = err;
+ return;
+ }
+
+ err = sensors_open_1(&mSensorModule->common, &mSensorDevice);
+
+ if (err != OK) {
+ LOG(ERROR) << "Couldn't open device for module "
+ << SENSORS_HARDWARE_MODULE_ID
+ << " ("
+ << strerror(-err)
+ << ")";
+
+ mInitCheck = err;
+ return;
+ }
+
+ // Require all the old HAL APIs to be present except for injection, which
+ // is considered optional.
+ CHECK_GE(getHalDeviceVersion(), SENSORS_DEVICE_API_VERSION_1_3);
+
+ mInitCheck = OK;
+}
+
+status_t Sensors::initCheck() const {
+ return mInitCheck;
+}
+
+Return<void> Sensors::getSensorsList(getSensorsList_cb _aidl_cb) {
+ sensor_t const *list;
+ size_t count = mSensorModule->get_sensors_list(mSensorModule, &list);
+
+ hidl_vec<SensorInfo> out;
+ out.resize(count);
+
+ for (size_t i = 0; i < count; ++i) {
+ const sensor_t *src = &list[i];
+ SensorInfo *dst = &out[i];
+
+ convertFromSensor(*src, dst);
+ }
+
+ _aidl_cb(out);
+
+ return Void();
+}
+
+int Sensors::getHalDeviceVersion() const {
+ if (!mSensorDevice) {
+ return -1;
+ }
+
+ return mSensorDevice->common.version;
+}
+
+Return<Result> Sensors::setOperationMode(OperationMode mode) {
+ return ResultFromStatus(mSensorModule->set_operation_mode((uint32_t)mode));
+}
+
+Return<Result> Sensors::activate(
+ int32_t sensor_handle, bool enabled) {
+ return ResultFromStatus(
+ mSensorDevice->activate(
+ reinterpret_cast<sensors_poll_device_t *>(mSensorDevice),
+ sensor_handle,
+ enabled));
+}
+
+Return<Result> Sensors::setDelay(
+ int32_t sensor_handle, int64_t sampling_period_ns) {
+ return ResultFromStatus(
+ mSensorDevice->setDelay(
+ reinterpret_cast<sensors_poll_device_t *>(mSensorDevice),
+ sensor_handle,
+ sampling_period_ns));
+}
+
+Return<void> Sensors::poll(int32_t maxCount, poll_cb _aidl_cb) {
+ hidl_vec<Event> out;
+ hidl_vec<SensorInfo> dynamicSensorsAdded;
+
+ if (maxCount <= 0) {
+ _aidl_cb(Result::BAD_VALUE, out, dynamicSensorsAdded);
+ return Void();
+ }
+
+ std::unique_ptr<sensors_event_t[]> data(new sensors_event_t[maxCount]);
+
+ int err = mSensorDevice->poll(
+ reinterpret_cast<sensors_poll_device_t *>(mSensorDevice),
+ data.get(),
+ maxCount);
+
+ if (err < 0) {
+ _aidl_cb(ResultFromStatus(err), out, dynamicSensorsAdded);
+ return Void();
+ }
+
+ const size_t count = (size_t)err;
+
+ for (size_t i = 0; i < count; ++i) {
+ if (data[i].type != SENSOR_TYPE_DYNAMIC_SENSOR_META) {
+ continue;
+ }
+
+ const dynamic_sensor_meta_event_t *dyn = &data[i].dynamic_sensor_meta;
+
+ if (!dyn->connected) {
+ continue;
+ }
+
+ CHECK(dyn->sensor != nullptr);
+ CHECK_EQ(dyn->sensor->handle, dyn->handle);
+
+ SensorInfo info;
+ convertFromSensor(*dyn->sensor, &info);
+
+ size_t numDynamicSensors = dynamicSensorsAdded.size();
+ dynamicSensorsAdded.resize(numDynamicSensors + 1);
+ dynamicSensorsAdded[numDynamicSensors] = info;
+ }
+
+ out.resize(count);
+ convertFromSensorEvents(err, data.get(), &out);
+
+ _aidl_cb(Result::OK, out, dynamicSensorsAdded);
+
+ return Void();
+}
+
+Return<Result> Sensors::batch(
+ int32_t sensor_handle,
+ int32_t flags,
+ int64_t sampling_period_ns,
+ int64_t max_report_latency_ns) {
+ return ResultFromStatus(
+ mSensorDevice->batch(
+ mSensorDevice,
+ sensor_handle,
+ flags,
+ sampling_period_ns,
+ max_report_latency_ns));
+}
+
+Return<Result> Sensors::flush(int32_t sensor_handle) {
+ return ResultFromStatus(mSensorDevice->flush(mSensorDevice, sensor_handle));
+}
+
+Return<Result> Sensors::injectSensorData(const Event& event) {
+ if (getHalDeviceVersion() < SENSORS_DEVICE_API_VERSION_1_4) {
+ return Result::INVALID_OPERATION;
+ }
+
+ sensors_event_t out;
+ convertToSensorEvent(event, &out);
+
+ return ResultFromStatus(
+ mSensorDevice->inject_sensor_data(mSensorDevice, &out));
+}
+
+// static
+void Sensors::convertFromSensorEvents(
+ size_t count,
+ const sensors_event_t *srcArray,
+ hidl_vec<Event> *dstVec) {
+ for (size_t i = 0; i < count; ++i) {
+ const sensors_event_t &src = srcArray[i];
+ Event *dst = &(*dstVec)[i];
+
+ convertFromSensorEvent(src, dst);
+ }
+}
+
+ISensors *HIDL_FETCH_ISensors(const char * /* hal */) {
+ Sensors *sensors = new Sensors;
+ if (sensors->initCheck() != OK) {
+ delete sensors;
+ sensors = nullptr;
+
+ return nullptr;
+ }
+
+ return sensors;
+}
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace sensors
+} // namespace hardware
+} // namespace android
diff --git a/sensors/1.0/default/Sensors.h b/sensors/1.0/default/Sensors.h
new file mode 100644
index 0000000..f9b837d
--- /dev/null
+++ b/sensors/1.0/default/Sensors.h
@@ -0,0 +1,78 @@
+/*
+ * 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.
+ */
+
+#ifndef HARDWARE_INTERFACES_SENSORS_V1_0_DEFAULT_SENSORS_H_
+
+#define HARDWARE_INTERFACES_SENSORS_V1_0_DEFAULT_SENSORS_H_
+
+#include <android/hardware/sensors/1.0/ISensors.h>
+#include <hardware/sensors.h>
+
+namespace android {
+namespace hardware {
+namespace sensors {
+namespace V1_0 {
+namespace implementation {
+
+struct Sensors : public ::android::hardware::sensors::V1_0::ISensors {
+ Sensors();
+
+ status_t initCheck() const;
+
+ Return<void> getSensorsList(getSensorsList_cb _aidl_cb) override;
+
+ Return<Result> setOperationMode(OperationMode mode) override;
+
+ Return<Result> activate(
+ int32_t sensor_handle, bool enabled) override;
+
+ Return<Result> setDelay(
+ int32_t sensor_handle, int64_t sampling_period_ns) override;
+
+ Return<void> poll(int32_t maxCount, poll_cb _hidl_cb) override;
+
+ Return<Result> batch(
+ int32_t sensor_handle,
+ int32_t flags,
+ int64_t sampling_period_ns,
+ int64_t max_report_latency_ns) override;
+
+ Return<Result> flush(int32_t sensor_handle) override;
+
+ Return<Result> injectSensorData(const Event& event) override;
+
+private:
+ status_t mInitCheck;
+ sensors_module_t *mSensorModule;
+ sensors_poll_device_1_t *mSensorDevice;
+
+ int getHalDeviceVersion() const;
+
+ static void convertFromSensorEvents(
+ size_t count, const sensors_event_t *src, hidl_vec<Event> *dst);
+
+ DISALLOW_COPY_AND_ASSIGN(Sensors);
+};
+
+extern "C" ISensors *HIDL_FETCH_ISensors(const char *name);
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace sensors
+} // namespace hardware
+} // namespace android
+
+#endif // HARDWARE_INTERFACES_SENSORS_V1_0_DEFAULT_SENSORS_H_
diff --git a/sensors/1.0/default/android.hardware.sensors@1.0-service.rc b/sensors/1.0/default/android.hardware.sensors@1.0-service.rc
new file mode 100644
index 0000000..2cba0fc
--- /dev/null
+++ b/sensors/1.0/default/android.hardware.sensors@1.0-service.rc
@@ -0,0 +1,4 @@
+service sensors-hal-1-0 /system/bin/hw/android.hardware.sensors@1.0-service
+ class main
+ user system
+ group system readproc
diff --git a/sensors/1.0/default/convert.cpp b/sensors/1.0/default/convert.cpp
new file mode 100644
index 0000000..f4e1841
--- /dev/null
+++ b/sensors/1.0/default/convert.cpp
@@ -0,0 +1,346 @@
+/*
+ * 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.
+ */
+
+#include "include/convert.h"
+
+#include <android-base/logging.h>
+
+namespace android {
+namespace hardware {
+namespace sensors {
+namespace V1_0 {
+namespace implementation {
+
+void convertFromSensor(const sensor_t &src, SensorInfo *dst) {
+ dst->name = src.name;
+ dst->vendor = src.vendor;
+ dst->version = src.version;
+ dst->sensorHandle = src.handle;
+ dst->type = (SensorType)src.type;
+ dst->maxRange = src.maxRange;
+ dst->resolution = src.resolution;
+ dst->power = src.power;
+ dst->minDelay = src.minDelay;
+ dst->fifoReservedEventCount = src.fifoReservedEventCount;
+ dst->fifoMaxEventCount = src.fifoMaxEventCount;
+ dst->typeAsString = src.stringType;
+ dst->requiredPermission = src.requiredPermission;
+ dst->maxDelay = src.maxDelay;
+ dst->flags = src.flags;
+}
+
+void convertToSensor(
+ const ::android::hardware::sensors::V1_0::SensorInfo &src,
+ sensor_t *dst) {
+ dst->name = strdup(src.name.c_str());
+ dst->vendor = strdup(src.vendor.c_str());
+ dst->version = src.version;
+ dst->handle = src.sensorHandle;
+ dst->type = (int)src.type;
+ dst->maxRange = src.maxRange;
+ dst->resolution = src.resolution;
+ dst->power = src.power;
+ dst->minDelay = src.minDelay;
+ dst->fifoReservedEventCount = src.fifoReservedEventCount;
+ dst->fifoMaxEventCount = src.fifoMaxEventCount;
+ dst->stringType = strdup(src.typeAsString.c_str());
+ dst->requiredPermission = strdup(src.requiredPermission.c_str());
+ dst->maxDelay = src.maxDelay;
+ dst->flags = src.flags;
+ dst->reserved[0] = dst->reserved[1] = 0;
+}
+
+void convertFromSensorEvent(const sensors_event_t &src, Event *dst) {
+ typedef ::android::hardware::sensors::V1_0::SensorType SensorType;
+ typedef ::android::hardware::sensors::V1_0::MetaDataEventType MetaDataEventType;
+
+ dst->sensorHandle = src.sensor;
+ dst->sensorType = (SensorType)src.type;
+ dst->timestamp = src.timestamp;
+
+ switch (dst->sensorType) {
+ case SensorType::SENSOR_TYPE_META_DATA:
+ {
+ dst->u.meta.what = (MetaDataEventType)src.meta_data.what;
+ break;
+ }
+
+ case SensorType::SENSOR_TYPE_ACCELEROMETER:
+ case SensorType::SENSOR_TYPE_GEOMAGNETIC_FIELD:
+ case SensorType::SENSOR_TYPE_ORIENTATION:
+ case SensorType::SENSOR_TYPE_GYROSCOPE:
+ case SensorType::SENSOR_TYPE_GRAVITY:
+ case SensorType::SENSOR_TYPE_LINEAR_ACCELERATION:
+ {
+ dst->u.vec3.x = src.acceleration.x;
+ dst->u.vec3.y = src.acceleration.y;
+ dst->u.vec3.z = src.acceleration.z;
+ dst->u.vec3.status = (SensorStatus)src.acceleration.status;
+ break;
+ }
+
+ case SensorType::SENSOR_TYPE_ROTATION_VECTOR:
+ case SensorType::SENSOR_TYPE_GAME_ROTATION_VECTOR:
+ case SensorType::SENSOR_TYPE_GEOMAGNETIC_ROTATION_VECTOR:
+ {
+ dst->u.vec4.x = src.data[0];
+ dst->u.vec4.y = src.data[1];
+ dst->u.vec4.z = src.data[2];
+ dst->u.vec4.w = src.data[3];
+ break;
+ }
+
+ case SensorType::SENSOR_TYPE_MAGNETIC_FIELD_UNCALIBRATED:
+ case SensorType::SENSOR_TYPE_GYROSCOPE_UNCALIBRATED:
+ {
+ dst->u.uncal.x = src.uncalibrated_gyro.x_uncalib;
+ dst->u.uncal.y = src.uncalibrated_gyro.y_uncalib;
+ dst->u.uncal.z = src.uncalibrated_gyro.z_uncalib;
+ dst->u.uncal.x_bias = src.uncalibrated_gyro.x_bias;
+ dst->u.uncal.y_bias = src.uncalibrated_gyro.y_bias;
+ dst->u.uncal.z_bias = src.uncalibrated_gyro.z_bias;
+ break;
+ }
+
+ case SensorType::SENSOR_TYPE_DEVICE_ORIENTATION:
+ case SensorType::SENSOR_TYPE_LIGHT:
+ case SensorType::SENSOR_TYPE_PRESSURE:
+ case SensorType::SENSOR_TYPE_TEMPERATURE:
+ case SensorType::SENSOR_TYPE_PROXIMITY:
+ case SensorType::SENSOR_TYPE_RELATIVE_HUMIDITY:
+ case SensorType::SENSOR_TYPE_AMBIENT_TEMPERATURE:
+ case SensorType::SENSOR_TYPE_SIGNIFICANT_MOTION:
+ case SensorType::SENSOR_TYPE_STEP_DETECTOR:
+ case SensorType::SENSOR_TYPE_TILT_DETECTOR:
+ case SensorType::SENSOR_TYPE_WAKE_GESTURE:
+ case SensorType::SENSOR_TYPE_GLANCE_GESTURE:
+ case SensorType::SENSOR_TYPE_PICK_UP_GESTURE:
+ case SensorType::SENSOR_TYPE_WRIST_TILT_GESTURE:
+ case SensorType::SENSOR_TYPE_STATIONARY_DETECT:
+ case SensorType::SENSOR_TYPE_MOTION_DETECT:
+ case SensorType::SENSOR_TYPE_HEART_BEAT:
+ {
+ dst->u.scalar = src.data[0];
+ break;
+ }
+
+ case SensorType::SENSOR_TYPE_STEP_COUNTER:
+ {
+ dst->u.stepCount = src.u64.step_counter;
+ break;
+ }
+
+ case SensorType::SENSOR_TYPE_HEART_RATE:
+ {
+ dst->u.heartRate.bpm = src.heart_rate.bpm;
+ dst->u.heartRate.status = (SensorStatus)src.heart_rate.status;
+ break;
+ }
+
+ case SensorType::SENSOR_TYPE_POSE_6DOF: // 15 floats
+ {
+ for (size_t i = 0; i < 15; ++i) {
+ dst->u.pose6DOF[i] = src.data[i];
+ }
+ break;
+ }
+
+ case SensorType::SENSOR_TYPE_DYNAMIC_SENSOR_META:
+ {
+ dst->u.dynamic.connected = src.dynamic_sensor_meta.connected;
+ dst->u.dynamic.sensorHandle = src.dynamic_sensor_meta.handle;
+
+ memcpy(dst->u.dynamic.uuid.data(),
+ src.dynamic_sensor_meta.uuid,
+ 16);
+
+ break;
+ }
+
+ case SensorType::SENSOR_TYPE_ADDITIONAL_INFO:
+ {
+ ::android::hardware::sensors::V1_0::AdditionalInfo *dstInfo =
+ &dst->u.additional;
+
+ const additional_info_event_t &srcInfo = src.additional_info;
+
+ dstInfo->type =
+ (::android::hardware::sensors::V1_0::AdditionalInfoType)
+ srcInfo.type;
+
+ dstInfo->serial = srcInfo.serial;
+
+ CHECK_EQ(sizeof(dstInfo->u), sizeof(srcInfo.data_int32));
+ memcpy(&dstInfo->u, srcInfo.data_int32, sizeof(srcInfo.data_int32));
+ break;
+ }
+
+ default:
+ {
+ CHECK_GE((int32_t)dst->sensorType,
+ (int32_t)SensorType::SENSOR_TYPE_DEVICE_PRIVATE_BASE);
+
+ memcpy(dst->u.data.data(), src.data, 16 * sizeof(float));
+ break;
+ }
+ }
+}
+
+void convertToSensorEvent(const Event &src, sensors_event_t *dst) {
+ dst->version = sizeof(sensors_event_t);
+ dst->sensor = src.sensorHandle;
+ dst->type = (int32_t)src.sensorType;
+ dst->reserved0 = 0;
+ dst->timestamp = src.timestamp;
+ dst->flags = 0;
+ dst->reserved1[0] = dst->reserved1[1] = dst->reserved1[2] = 0;
+
+ switch (src.sensorType) {
+ case SensorType::SENSOR_TYPE_META_DATA:
+ {
+ dst->meta_data.what = (int32_t)src.u.meta.what;
+ dst->meta_data.sensor = dst->sensor;
+ break;
+ }
+
+ case SensorType::SENSOR_TYPE_ACCELEROMETER:
+ case SensorType::SENSOR_TYPE_GEOMAGNETIC_FIELD:
+ case SensorType::SENSOR_TYPE_ORIENTATION:
+ case SensorType::SENSOR_TYPE_GYROSCOPE:
+ case SensorType::SENSOR_TYPE_GRAVITY:
+ case SensorType::SENSOR_TYPE_LINEAR_ACCELERATION:
+ {
+ dst->acceleration.x = src.u.vec3.x;
+ dst->acceleration.y = src.u.vec3.y;
+ dst->acceleration.z = src.u.vec3.z;
+ dst->acceleration.status = (int8_t)src.u.vec3.status;
+ break;
+ }
+
+ case SensorType::SENSOR_TYPE_ROTATION_VECTOR:
+ case SensorType::SENSOR_TYPE_GAME_ROTATION_VECTOR:
+ case SensorType::SENSOR_TYPE_GEOMAGNETIC_ROTATION_VECTOR:
+ {
+ dst->data[0] = src.u.vec4.x;
+ dst->data[1] = src.u.vec4.y;
+ dst->data[2] = src.u.vec4.z;
+ dst->data[3] = src.u.vec4.w;
+ break;
+ }
+
+ case SensorType::SENSOR_TYPE_MAGNETIC_FIELD_UNCALIBRATED:
+ case SensorType::SENSOR_TYPE_GYROSCOPE_UNCALIBRATED:
+ {
+ dst->uncalibrated_gyro.x_uncalib = src.u.uncal.x;
+ dst->uncalibrated_gyro.y_uncalib = src.u.uncal.y;
+ dst->uncalibrated_gyro.z_uncalib = src.u.uncal.z;
+ dst->uncalibrated_gyro.x_bias = src.u.uncal.x_bias;
+ dst->uncalibrated_gyro.y_bias = src.u.uncal.y_bias;
+ dst->uncalibrated_gyro.z_bias = src.u.uncal.z_bias;
+ break;
+ }
+
+ case SensorType::SENSOR_TYPE_DEVICE_ORIENTATION:
+ case SensorType::SENSOR_TYPE_LIGHT:
+ case SensorType::SENSOR_TYPE_PRESSURE:
+ case SensorType::SENSOR_TYPE_TEMPERATURE:
+ case SensorType::SENSOR_TYPE_PROXIMITY:
+ case SensorType::SENSOR_TYPE_RELATIVE_HUMIDITY:
+ case SensorType::SENSOR_TYPE_AMBIENT_TEMPERATURE:
+ case SensorType::SENSOR_TYPE_SIGNIFICANT_MOTION:
+ case SensorType::SENSOR_TYPE_STEP_DETECTOR:
+ case SensorType::SENSOR_TYPE_TILT_DETECTOR:
+ case SensorType::SENSOR_TYPE_WAKE_GESTURE:
+ case SensorType::SENSOR_TYPE_GLANCE_GESTURE:
+ case SensorType::SENSOR_TYPE_PICK_UP_GESTURE:
+ case SensorType::SENSOR_TYPE_WRIST_TILT_GESTURE:
+ case SensorType::SENSOR_TYPE_STATIONARY_DETECT:
+ case SensorType::SENSOR_TYPE_MOTION_DETECT:
+ case SensorType::SENSOR_TYPE_HEART_BEAT:
+ {
+ dst->data[0] = src.u.scalar;
+ break;
+ }
+
+ case SensorType::SENSOR_TYPE_STEP_COUNTER:
+ {
+ dst->u64.step_counter = src.u.stepCount;
+ break;
+ }
+
+ case SensorType::SENSOR_TYPE_HEART_RATE:
+ {
+ dst->heart_rate.bpm = src.u.heartRate.bpm;
+ dst->heart_rate.status = (int8_t)src.u.heartRate.status;
+ break;
+ }
+
+ case SensorType::SENSOR_TYPE_POSE_6DOF: // 15 floats
+ {
+ for (size_t i = 0; i < 15; ++i) {
+ dst->data[i] = src.u.pose6DOF[i];
+ }
+ break;
+ }
+
+ case SensorType::SENSOR_TYPE_DYNAMIC_SENSOR_META:
+ {
+ dst->dynamic_sensor_meta.connected = src.u.dynamic.connected;
+ dst->dynamic_sensor_meta.handle = src.u.dynamic.sensorHandle;
+ dst->dynamic_sensor_meta.sensor = NULL; // to be filled in later
+
+ memcpy(dst->dynamic_sensor_meta.uuid,
+ src.u.dynamic.uuid.data(),
+ 16);
+
+ break;
+ }
+
+ case SensorType::SENSOR_TYPE_ADDITIONAL_INFO:
+ {
+ const ::android::hardware::sensors::V1_0::AdditionalInfo &srcInfo =
+ src.u.additional;
+
+ additional_info_event_t *dstInfo = &dst->additional_info;
+ dstInfo->type = (int32_t)srcInfo.type;
+ dstInfo->serial = srcInfo.serial;
+
+ CHECK_EQ(sizeof(srcInfo.u), sizeof(dstInfo->data_int32));
+
+ memcpy(dstInfo->data_int32,
+ &srcInfo.u,
+ sizeof(dstInfo->data_int32));
+
+ break;
+ }
+
+ default:
+ {
+ CHECK_GE((int32_t)src.sensorType,
+ (int32_t)SensorType::SENSOR_TYPE_DEVICE_PRIVATE_BASE);
+
+ memcpy(dst->data, src.u.data.data(), 16 * sizeof(float));
+ break;
+ }
+ }
+}
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace sensors
+} // namespace hardware
+} // namespace android
+
diff --git a/sensors/1.0/default/include/convert.h b/sensors/1.0/default/include/convert.h
new file mode 100644
index 0000000..d289a81
--- /dev/null
+++ b/sensors/1.0/default/include/convert.h
@@ -0,0 +1,42 @@
+/*
+ * 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.
+ */
+
+#ifndef HARDWARE_INTERFACES_SENSORS_V1_0_DEFAULT_INCLUDE_CONVERT_H_
+
+#define HARDWARE_INTERFACES_SENSORS_V1_0_DEFAULT_INCLUDE_CONVERT_H_
+
+#include <android/hardware/sensors/1.0/ISensors.h>
+#include <hardware/sensors.h>
+
+namespace android {
+namespace hardware {
+namespace sensors {
+namespace V1_0 {
+namespace implementation {
+
+void convertFromSensor(const sensor_t &src, SensorInfo *dst);
+void convertToSensor(const SensorInfo &src, sensor_t *dst);
+
+void convertFromSensorEvent(const sensors_event_t &src, Event *dst);
+void convertToSensorEvent(const Event &src, sensors_event_t *dst);
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace sensors
+} // namespace hardware
+} // namespace android
+
+#endif // HARDWARE_INTERFACES_SENSORS_V1_0_DEFAULT_INCLUDE_CONVERT_H_
diff --git a/sensors/1.0/default/service.cpp b/sensors/1.0/default/service.cpp
new file mode 100644
index 0000000..da543ef
--- /dev/null
+++ b/sensors/1.0/default/service.cpp
@@ -0,0 +1,51 @@
+/*
+ * 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.
+ */
+
+#include <android-base/logging.h>
+#include <android/hardware/sensors/1.0/ISensors.h>
+#include <hwbinder/IPCThreadState.h>
+#include <hwbinder/ProcessState.h>
+
+int main() {
+ using android::hardware::sensors::V1_0::ISensors;
+ using android::sp;
+ using android::OK;
+ using namespace android::hardware;
+
+ LOG(INFO) << "Service is starting.";
+ sp<ISensors> sensors = ISensors::getService("sensors", true /* getStub */);
+
+ if (sensors.get() == nullptr) {
+ LOG(ERROR) << "ISensors::getService returned nullptr, exiting.";
+ return 1;
+ }
+
+ LOG(INFO) << "Default implementation using sensors is "
+ << (sensors->isRemote() ? "REMOTE" : "LOCAL");
+
+ CHECK(!sensors->isRemote());
+
+ LOG(INFO) << "Registering instance sensors.";
+ sensors->registerAsService("sensors");
+ LOG(INFO) << "Ready.";
+
+ ProcessState::self()->setThreadPoolMaxThreadCount(0);
+ ProcessState::self()->startThreadPool();
+ IPCThreadState::self()->joinThreadPool();
+
+ return 0;
+}
+
diff --git a/sensors/1.0/types.hal b/sensors/1.0/types.hal
new file mode 100644
index 0000000..ba4921c
--- /dev/null
+++ b/sensors/1.0/types.hal
@@ -0,0 +1,1064 @@
+/*
+ * 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.
+ */
+
+package android.hardware.sensors@1.0;
+
+/**
+ * Please see the Sensors section of source.android.com for an
+ * introduction to and detailed descriptions of Android sensor types:
+ * http://source.android.com/devices/sensors/index.html
+ */
+
+/* Type enumerating various result codes returned from ISensors methods */
+enum Result : int32_t {
+ OK,
+ BAD_VALUE,
+ PERMISSION_DENIED,
+ INVALID_OPERATION,
+};
+
+/*
+ * Sensor HAL modes used in setOperationMode method
+ */
+@export(name="")
+enum OperationMode : int32_t {
+ SENSOR_HAL_NORMAL_MODE = 0,
+ SENSOR_HAL_DATA_INJECTION_MODE = 1,
+};
+
+/*
+ * Sensor type
+ *
+ * Each sensor has a type which defines what this sensor measures and how
+ * measures are reported. See the Base sensors and Composite sensors lists
+ * for complete descriptions:
+ * http://source.android.com/devices/sensors/base_triggers.html
+ * http://source.android.com/devices/sensors/composite_sensors.html
+ *
+ * Device manufacturers (OEMs) can define their own sensor types, for
+ * their private use by applications or services provided by them. Such
+ * sensor types are specific to an OEM and can't be exposed in the SDK.
+ * These types must start at SENSOR_TYPE_DEVICE_PRIVATE_BASE.
+ *
+ * All sensors defined outside of the device private range must correspond to
+ * a type defined in this file, and must satisfy the characteristics listed in
+ * the description of the sensor type.
+ *
+ * Each sensor also has a "typeAsString".
+ * - StringType of sensors inside of the device private range MUST be prefixed
+ * by the sensor provider's or OEM reverse domain name. In particular, they
+ * cannot use the "android.sensor" prefix.
+ * - StringType of sensors outside of the device private range MUST correspond
+ * to the one defined in this file (starting with "android.sensor").
+ * For example, accelerometers must have
+ * type=SENSOR_TYPE_ACCELEROMETER and
+ * stringType=SENSOR_STRING_TYPE_ACCELEROMETER
+ *
+ * When android introduces a new sensor type that can replace an OEM-defined
+ * sensor type, the OEM must use the official sensor type and stringType on
+ * versions of the HAL that support this new official sensor type.
+ *
+ * Example (made up): Suppose Google's Glass team wants to surface a sensor
+ * detecting that Glass is on a head.
+ * - Such a sensor is not officially supported in android KitKat
+ * - Glass devices launching on KitKat can implement a sensor with
+ * type = 0x10001 and stringType = "com.google.glass.onheaddetector"
+ * - In L android release, if android decides to define
+ * SENSOR_TYPE_ON_HEAD_DETECTOR and STRING_SENSOR_TYPE_ON_HEAD_DETECTOR,
+ * those types should replace the Glass-team-specific types in all future
+ * launches.
+ * - When launching Glass on the L release, Google should now use the official
+ * type (SENSOR_TYPE_ON_HEAD_DETECTOR) and stringType.
+ * - This way, all applications can now use this sensor.
+ */
+
+/*
+ * Wake up sensors.
+ * Each sensor may have either or both a wake-up and a non-wake variant.
+ * When registered in batch mode, wake-up sensors will wake up the AP when
+ * their FIFOs are full or when the batch timeout expires. A separate FIFO has
+ * to be maintained for wake up sensors and non wake up sensors. The non
+ * wake-up sensors need to overwrite their FIFOs when they are full till the AP
+ * wakes up and the wake-up sensors will wake-up the AP when their FIFOs are
+ * full or when the batch timeout expires without losing events.
+ * Wake-up and non wake-up variants of each sensor can be activated at
+ * different rates independently of each other.
+ *
+ * Note: Proximity sensor and significant motion sensor which were defined in
+ * previous releases are also wake-up sensors and should be treated as such.
+ * Wake-up one-shot sensors like SIGNIFICANT_MOTION cannot be batched, hence
+ * the text about batch above doesn't apply to them. See the definitions of
+ * SENSOR_TYPE_PROXIMITY and SENSOR_TYPE_SIGNIFICANT_MOTION for more info.
+ *
+ * Set SENSOR_FLAG_WAKE_UP flag for all wake-up sensors.
+ *
+ * For example, A device can have two sensors both of SENSOR_TYPE_ACCELEROMETER
+ * and one of them can be a wake_up sensor (with SENSOR_FLAG_WAKE_UP flag set)
+ * and the other can be a regular non wake_up sensor. Both of these sensors
+ * must be activated/deactivated independently of the other.
+ */
+
+@export(name="")
+enum SensorType : int32_t {
+ /* META_DATA is a special event type used to populate the MetaData
+ * structure. It doesn't correspond to a physical sensor. Events of this
+ * type exist only inside the HAL, their primary purpose is to signal the
+ * completion of a flush request.
+ */
+ SENSOR_TYPE_META_DATA = 0,
+
+ /*
+ * SENSOR_TYPE_ACCELEROMETER
+ * reporting-mode: continuous
+ *
+ * All values are in SI units (m/s^2) and measure the acceleration of the
+ * device minus the force of gravity.
+ *
+ * Implement the non-wake-up version of this sensor and implement the
+ * wake-up version if the system possesses a wake up fifo.
+ */
+ SENSOR_TYPE_ACCELEROMETER = 1,
+
+ /*
+ * SENSOR_TYPE_GEOMAGNETIC_FIELD
+ * reporting-mode: continuous
+ *
+ * All values are in micro-Tesla (uT) and measure the geomagnetic
+ * field in the X, Y and Z axis.
+ *
+ * Implement the non-wake-up version of this sensor and implement the
+ * wake-up version if the system possesses a wake up fifo.
+ */
+ SENSOR_TYPE_GEOMAGNETIC_FIELD = 2,
+
+ /*
+ * SENSOR_TYPE_ORIENTATION
+ * reporting-mode: continuous
+ *
+ * All values are angles in degrees.
+ *
+ * Orientation sensors return sensor events for all 3 axes at a constant
+ * rate defined by setDelay().
+ *
+ * Implement the non-wake-up version of this sensor and implement the
+ * wake-up version if the system possesses a wake up fifo.
+ */
+ SENSOR_TYPE_ORIENTATION = 3,
+
+ /*
+ * SENSOR_TYPE_GYROSCOPE
+ * reporting-mode: continuous
+ *
+ * All values are in radians/second and measure the rate of rotation
+ * around the X, Y and Z axis.
+ *
+ * Implement the non-wake-up version of this sensor and implement the
+ * wake-up version if the system possesses a wake up fifo.
+ */
+ SENSOR_TYPE_GYROSCOPE = 4,
+
+ /*
+ * SENSOR_TYPE_LIGHT
+ * reporting-mode: on-change
+ *
+ * The light sensor value is returned in SI lux units.
+ *
+ * Both wake-up and non wake-up versions are useful.
+ */
+ SENSOR_TYPE_LIGHT = 5,
+
+ /*
+ * SENSOR_TYPE_PRESSURE
+ * reporting-mode: continuous
+ *
+ * The pressure sensor return the athmospheric pressure in hectopascal (hPa)
+ *
+ * Implement the non-wake-up version of this sensor and implement the
+ * wake-up version if the system possesses a wake up fifo.
+ */
+ SENSOR_TYPE_PRESSURE = 6,
+
+ /* SENSOR_TYPE_TEMPERATURE is deprecated in the HAL */
+ SENSOR_TYPE_TEMPERATURE = 7,
+
+ /*
+ * SENSOR_TYPE_PROXIMITY
+ * reporting-mode: on-change
+ *
+ * The proximity sensor which turns the screen off and back on during calls
+ * is the wake-up proximity sensor. Implement wake-up proximity sensor
+ * before implementing a non wake-up proximity sensor. For the wake-up
+ * proximity sensor set the flag SENSOR_FLAG_WAKE_UP.
+ * The value corresponds to the distance to the nearest object in
+ * centimeters.
+ */
+ SENSOR_TYPE_PROXIMITY = 8,
+
+ /*
+ * SENSOR_TYPE_GRAVITY
+ * reporting-mode: continuous
+ *
+ * A gravity output indicates the direction of and magnitude of gravity in
+ * the devices's coordinates.
+ *
+ * Implement the non-wake-up version of this sensor and implement the
+ * wake-up version if the system possesses a wake up fifo.
+ */
+ SENSOR_TYPE_GRAVITY = 9,
+
+ /*
+ * SENSOR_TYPE_LINEAR_ACCELERATION
+ * reporting-mode: continuous
+ *
+ * Indicates the linear acceleration of the device in device coordinates,
+ * not including gravity.
+ *
+ * Implement the non-wake-up version of this sensor and implement the
+ * wake-up version if the system possesses a wake up fifo.
+ */
+ SENSOR_TYPE_LINEAR_ACCELERATION = 10,
+
+ /*
+ * SENSOR_TYPE_ROTATION_VECTOR
+ * reporting-mode: continuous
+ *
+ * The rotation vector symbolizes the orientation of the device relative to
+ * the East-North-Up coordinates frame.
+ *
+ * Implement the non-wake-up version of this sensor and implement the
+ * wake-up version if the system possesses a wake up fifo.
+ */
+ SENSOR_TYPE_ROTATION_VECTOR = 11,
+
+ /*
+ * SENSOR_TYPE_RELATIVE_HUMIDITY
+ * reporting-mode: on-change
+ *
+ * A relative humidity sensor measures relative ambient air humidity and
+ * returns a value in percent.
+ *
+ * Both wake-up and non wake-up versions are useful.
+ */
+ SENSOR_TYPE_RELATIVE_HUMIDITY = 12,
+
+ /*
+ * SENSOR_TYPE_AMBIENT_TEMPERATURE
+ * reporting-mode: on-change
+ *
+ * The ambient (room) temperature in degree Celsius.
+ *
+ * Both wake-up and non wake-up versions are useful.
+ */
+ SENSOR_TYPE_AMBIENT_TEMPERATURE = 13,
+
+ /*
+ * SENSOR_TYPE_MAGNETIC_FIELD_UNCALIBRATED
+ * reporting-mode: continuous
+ *
+ * Similar to SENSOR_TYPE_MAGNETIC_FIELD, but the hard iron calibration is
+ * reported separately instead of being included in the measurement.
+ *
+ * Implement the non-wake-up version of this sensor and implement the
+ * wake-up version if the system possesses a wake up fifo.
+ */
+ SENSOR_TYPE_MAGNETIC_FIELD_UNCALIBRATED = 14,
+
+ /*
+ * SENSOR_TYPE_GAME_ROTATION_VECTOR
+ * reporting-mode: continuous
+ *
+ * Similar to SENSOR_TYPE_ROTATION_VECTOR, but not using the geomagnetic
+ * field.
+ *
+ * Implement the non-wake-up version of this sensor and implement the
+ * wake-up version if the system possesses a wake up fifo.
+ */
+ SENSOR_TYPE_GAME_ROTATION_VECTOR = 15,
+
+ /*
+ * SENSOR_TYPE_GYROSCOPE_UNCALIBRATED
+ * reporting-mode: continuous
+ *
+ * All values are in radians/second and measure the rate of rotation
+ * around the X, Y and Z axis.
+ *
+ * Implement the non-wake-up version of this sensor and implement the
+ * wake-up version if the system possesses a wake up fifo.
+ */
+ SENSOR_TYPE_GYROSCOPE_UNCALIBRATED = 16,
+
+ /*
+ * SENSOR_TYPE_SIGNIFICANT_MOTION
+ * reporting-mode: one-shot
+ *
+ * A sensor of this type triggers an event each time significant motion
+ * is detected and automatically disables itself.
+ * For Significant Motion sensor to be useful, it must be defined as a
+ * wake-up sensor. (set SENSOR_FLAG_WAKE_UP). Implement the wake-up
+ * significant motion sensor. A non wake-up version is not useful.
+ * The only allowed value to return is 1.0.
+ */
+ SENSOR_TYPE_SIGNIFICANT_MOTION = 17,
+
+ /*
+ * SENSOR_TYPE_STEP_DETECTOR
+ * reporting-mode: special
+ *
+ * A sensor of this type triggers an event each time a step is taken
+ * by the user. The only allowed value to return is 1.0 and an event
+ * is generated for each step.
+ *
+ * Both wake-up and non wake-up versions are useful.
+ */
+ SENSOR_TYPE_STEP_DETECTOR = 18,
+
+ /*
+ * SENSOR_TYPE_STEP_COUNTER
+ * reporting-mode: on-change
+ *
+ * A sensor of this type returns the number of steps taken by the user since
+ * the last reboot while activated. The value is returned as a uint64_t and
+ * is reset to zero only on a system / android reboot.
+ *
+ * Implement the non-wake-up version of this sensor and implement the
+ * wake-up version if the system possesses a wake up fifo.
+ */
+ SENSOR_TYPE_STEP_COUNTER = 19,
+
+ /*
+ * SENSOR_TYPE_GEOMAGNETIC_ROTATION_VECTOR
+ * reporting-mode: continuous
+ *
+ * Similar to SENSOR_TYPE_ROTATION_VECTOR, but using a magnetometer instead
+ * of using a gyroscope.
+ *
+ * Implement the non-wake-up version of this sensor and implement the
+ * wake-up version if the system possesses a wake up fifo.
+ */
+ SENSOR_TYPE_GEOMAGNETIC_ROTATION_VECTOR = 20,
+
+ /*
+ * SENSOR_TYPE_HEART_RATE
+ * reporting-mode: on-change
+ *
+ * A sensor of this type returns the current heart rate.
+ * The events contain the current heart rate in beats per minute (BPM) and
+ * the status of the sensor during the measurement. See "HeartRate" below
+ * for more details.
+ *
+ * Because this sensor is on-change, events must be generated when and only
+ * when heart_rate.bpm or heart_rate.status have changed since the last
+ * event. In particular, upon the first activation, unless the device is
+ * known to not be on the body, the status field of the first event must be
+ * set to SENSOR_STATUS_UNRELIABLE. The event should be generated no faster
+ * than every period_ns passed to setDelay() or to batch().
+ * See the definition of the on-change reporting mode for more information.
+ *
+ * SensorInfo.requiredPermission must be set to
+ * SENSOR_PERMISSION_BODY_SENSORS.
+ *
+ * Both wake-up and non wake-up versions are useful.
+ */
+ SENSOR_TYPE_HEART_RATE = 21,
+
+ /*
+ * SENSOR_TYPE_WAKE_UP_TILT_DETECTOR
+ * reporting-mode: special (setDelay has no impact)
+ *
+ * A sensor of this type generates an event each time a tilt event is
+ * detected. A tilt event should be generated if the direction of the
+ * 2-seconds window average gravity changed by at least 35 degrees since the
+ * activation or the last trigger of the sensor.
+ *
+ * reference_estimated_gravity = average of accelerometer measurements over
+ * the first 1 second after activation or the estimated gravity at the last
+ * trigger.
+ *
+ * current_estimated_gravity = average of accelerometer measurements over
+ * the last 2 seconds.
+ *
+ * trigger when
+ * angle(reference_estimated_gravity, current_estimated_gravity)
+ * > 35 degrees
+ *
+ * Large accelerations without a change in phone orientation should not
+ * trigger a tilt event.
+ * For example, a sharp turn or strong acceleration while driving a car
+ * should not trigger a tilt event, even though the angle of the average
+ * acceleration might vary by more than 35 degrees.
+ *
+ * Typically, this sensor is implemented with the help of only an
+ * accelerometer. Other sensors can be used as well if they do not increase
+ * the power consumption significantly. This is a low power sensor that
+ * should allow the AP to go into suspend mode. Do not emulate this sensor
+ * in the HAL.
+ * Like other wake up sensors, the driver is expected to a hold a wake_lock
+ * with a timeout of 200 ms while reporting this event. The only allowed
+ * return value is 1.0.
+ *
+ * Implement only the wake-up version of this sensor.
+ */
+ SENSOR_TYPE_TILT_DETECTOR = 22,
+
+ /*
+ * SENSOR_TYPE_WAKE_GESTURE
+ * reporting-mode: one-shot
+ *
+ * A sensor enabling waking up the device based on a device specific motion.
+ *
+ * When this sensor triggers, the device behaves as if the power button was
+ * pressed, turning the screen on. This behavior (turning on the screen when
+ * this sensor triggers) might be deactivated by the user in the device
+ * settings. Changes in settings do not impact the behavior of the sensor:
+ * only whether the framework turns the screen on when it triggers.
+ *
+ * The actual gesture to be detected is not specified, and can be chosen by
+ * the manufacturer of the device.
+ * This sensor must be low power, as it is likely to be activated 24/7.
+ * The only allowed value to return is 1.0.
+ *
+ * Implement only the wake-up version of this sensor.
+ */
+ SENSOR_TYPE_WAKE_GESTURE = 23,
+
+ /*
+ * SENSOR_TYPE_GLANCE_GESTURE
+ * reporting-mode: one-shot
+ *
+ * A sensor enabling briefly turning the screen on to enable the user to
+ * glance content on screen based on a specific motion. The device should
+ * turn the screen off after a few moments.
+ *
+ * When this sensor triggers, the device turns the screen on momentarily
+ * to allow the user to glance notifications or other content while the
+ * device remains locked in a non-interactive state (dozing). This behavior
+ * (briefly turning on the screen when this sensor triggers) might be
+ * deactivated by the user in the device settings.
+ * Changes in settings do not impact the behavior of the sensor: only
+ * whether the framework briefly turns the screen on when it triggers.
+ *
+ * The actual gesture to be detected is not specified, and can be chosen by
+ * the manufacturer of the device.
+ * This sensor must be low power, as it is likely to be activated 24/7.
+ * The only allowed value to return is 1.0.
+ *
+ * Implement only the wake-up version of this sensor.
+ */
+ SENSOR_TYPE_GLANCE_GESTURE = 24,
+
+ /**
+ * SENSOR_TYPE_PICK_UP_GESTURE
+ * reporting-mode: one-shot
+ *
+ * A sensor of this type triggers when the device is picked up regardless of
+ * wherever is was before (desk, pocket, bag). The only allowed return value
+ * is 1.0. This sensor de-activates itself immediately after it triggers.
+ *
+ * Implement only the wake-up version of this sensor.
+ */
+ SENSOR_TYPE_PICK_UP_GESTURE = 25,
+
+ /*
+ * SENSOR_TYPE_WRIST_TILT_GESTURE
+ * trigger-mode: special
+ * wake-up sensor: yes
+ *
+ * A sensor of this type triggers an event each time a tilt of the
+ * wrist-worn device is detected.
+ *
+ * This sensor must be low power, as it is likely to be activated 24/7.
+ * The only allowed value to return is 1.0.
+ *
+ * Implement only the wake-up version of this sensor.
+ */
+ SENSOR_TYPE_WRIST_TILT_GESTURE = 26,
+
+ /*
+ * SENSOR_TYPE_DEVICE_ORIENTATION
+ * reporting-mode: on-change
+ *
+ * The current orientation of the device. The value should be reported in
+ * the "scalar" element of the EventPayload in Event. The
+ * only values that can be reported are (please refer to Android Sensor
+ * Coordinate System to understand the X and Y axis direction with respect
+ * to default orientation):
+ * - 0: device is in default orientation (Y axis is vertical and points up)
+ * - 1: device is rotated 90 degrees counter-clockwise from default
+ * orientation (X axis is vertical and points up)
+ * - 2: device is rotated 180 degrees from default orientation (Y axis is
+ * vertical and points down)
+ * - 3: device is rotated 90 degrees clockwise from default orientation
+ * (X axis is vertical and points down)
+ *
+ * Moving the device to an orientation where the Z axis is vertical (either
+ * up or down) should not cause a new event to be reported.
+ *
+ * To improve the user experience of this sensor, it is recommended to
+ * implement some physical (i.e., rotation angle) and temporal (i.e., delay)
+ * hysteresis.
+ * In other words, minor or transient rotations should not cause a new event
+ * to be reported.
+ *
+ * This sensor should only be implemented with the help of an accelerometer.
+ * This is a low power sensor that should reduce the number of interrupts of
+ * the AP. Do not emulate this sensor in the HAL.
+ *
+ * Both wake-up and non wake-up versions are useful.
+ */
+ SENSOR_TYPE_DEVICE_ORIENTATION = 27,
+
+ /*
+ * SENSOR_TYPE_POSE_6DOF
+ * trigger-mode: continuous
+ *
+ * A sensor of this type returns the pose of the device.
+ * Pose of the device is defined as the orientation of the device from a
+ * Earth Centered Earth Fixed frame and the translation from an arbitrary
+ * point at subscription.
+ *
+ * This sensor can be high power. It can use any and all of the following
+ * . Accelerometer
+ * . Gyroscope
+ * . Camera
+ * . Depth Camera
+ *
+ */
+ SENSOR_TYPE_POSE_6DOF = 28,
+
+ /*
+ * SENSOR_TYPE_STATIONARY_DETECT
+ * trigger mode: one shot
+ *
+ * A sensor of this type returns an event if the device is still/stationary
+ * for a while. The period of time to monitor for statinarity should be
+ * greater than 5 seconds, and less than 10 seconds.
+ *
+ * Stationarity here refers to absolute stationarity. eg: device on desk.
+ *
+ * The only allowed value to return is 1.0.
+ */
+ SENSOR_TYPE_STATIONARY_DETECT = 29,
+
+ /*
+ * SENSOR_TYPE_MOTION_DETECT
+ * trigger mode: one shot
+ *
+ * A sensor of this type returns an event if the device is not still for
+ * a while. The period of time to monitor for statinarity should be greater
+ * than 5 seconds, and less than 10 seconds.
+ *
+ * Motion here refers to any mechanism in which the device is causes to be
+ * moved in its inertial frame. eg: Pickin up the device and walking with it
+ * to a nearby room may trigger motion wherewas keeping the device on a
+ * table on a smooth train moving at constant velocity may not trigger
+ * motion.
+ *
+ * The only allowed value to return is 1.0.
+ */
+ SENSOR_TYPE_MOTION_DETECT = 30,
+
+ /*
+ * SENSOR_TYPE_HEART_BEAT
+ * trigger mode: continuous
+ *
+ * A sensor of this type returns an event everytime a hear beat peak is
+ * detected.
+ *
+ * Peak here ideally corresponds to the positive peak in the QRS complex of
+ * and ECG signal.
+ *
+ * The sensor is not expected to be optimized for latency. As a guide, a
+ * latency of up to 10 seconds is acceptable. However the timestamp attached
+ * to the event should be accurate and should correspond to the time the
+ * peak occured.
+ *
+ * The sensor event contains a parameter for the confidence in the detection
+ * of the peak where 0.0 represent no information at all, and 1.0 represents
+ * certainty.
+ */
+ SENSOR_TYPE_HEART_BEAT = 31,
+
+ /**
+ * SENSOR_TYPE_DYNAMIC_SENSOR_META
+ * trigger-mode: special
+ *
+ * A sensor event of this type is received when a dynamic sensor is added to
+ * or removed from the system. At most one sensor of this type can be
+ * present in one sensor HAL implementation and presence of a sensor of this
+ * type in sensor HAL implementation indicates that this sensor HAL supports
+ * dynamic sensor feature. Operations, such as batch, activate and setDelay,
+ * to this special purpose sensor should be treated as no-op and return
+ * successful; flush() also has to generate flush complete event as if this
+ * is a sensor that does not support batching.
+ *
+ * A dynamic sensor connection indicates connection of a physical device or
+ * instantiation of a virtual sensor backed by algorithm; and a dynamic
+ * sensor disconnection indicates the the opposite. A sensor event of
+ * SENSOR_TYPE_DYNAMIC_SENSOR_META type should be delivered regardless of
+ * the activation status of the sensor in the event of dynamic sensor
+ * connection and disconnection. In the sensor event, besides the common
+ * data entries, "dynamic_sensor_meta", which includes fields for connection
+ * status, handle of the sensor involved, pointer to sensor_t structure and
+ * a uuid field, should be populated.
+ *
+ * At a dynamic sensor connection event, fields of sensor_t structure
+ * referenced by a pointer in dynamic_sensor_meta should be filled as if it
+ * was regular sensors. Sensor HAL is responsible for recovery of memory if
+ * the corresponding data is dynamicially allocated. However, the the
+ * pointer must be valid until the first activate call to the sensor
+ * reported in this connection event. At a dynamic sensor disconnection,
+ * the sensor_t pointer should be NULL.
+ *
+ * The sensor handle assigned to dynamic sensors should never be the same as
+ * that of any regular static sensors, and should be unique until next boot.
+ * In another word, if a handle h is used for a dynamic sensor A, that same
+ * number cannot be used for the same dynamic sensor A or another dynamic
+ * sensor B even after disconnection of A until reboot.
+ *
+ * The UUID field will be used for identifying the sensor in addition to
+ * name, vendor and version and type. For physical sensors of the same
+ * model, all sensors will have the same values in sensor_t, but the UUID
+ * should be unique and persistent for each individual unit. An all zero
+ * UUID indicates it is not possible to differentiate individual sensor
+ * unit.
+ *
+ */
+ SENSOR_TYPE_DYNAMIC_SENSOR_META = 32,
+
+ /**
+ * SENSOR_TYPE_ADDITIONAL_INFO
+ * reporting-mode: N/A
+ *
+ * This sensor type is for delivering additional sensor information aside
+ * from sensor event data.
+ * Additional information may include sensor front-end group delay, internal
+ * calibration parameters, noise level metrics, device internal temperature,
+ * etc.
+ *
+ * This type will never bind to a sensor. In other words, no sensor in the
+ * sensor list should be of the type SENSOR_TYPE_ADDITIONAL_INFO. If a
+ * sensor HAL supports sensor additional information feature, it reports
+ * sensor_event_t with "sensor" field set to handle of the reporting sensor
+ * and "type" field set to SENSOR_TYPE_ADDITIONAL_INFO. Delivery of
+ * additional information events is triggered under two conditions: an
+ * enable activate() call or a flush() call to the corresponding sensor.
+ *
+ * A single additional information report consists of multiple frames.
+ * Sequences of these frames are ordered using timestamps, which means the
+ * timestamps of sequential frames have to be at least 1 nanosecond apart
+ * from each other. Each frame is a sensor_event_t delivered through the HAL
+ * interface, with related data stored in the "additional_info" field, which
+ * is of type additional_info_event_t.
+ * The "type" field of additional_info_event_t denotes the nature of the
+ * payload data (see additional_info_type_t).
+ * The "serial" field is used to keep the sequence of payload data that
+ * spans multiple frames. The first frame of the entire report is always of
+ * type AINFO_BEGIN, and the last frame is always AINFO_END.
+ *
+ * All additional information frames have to be delivered after flush
+ * complete event if flush() was triggering the report.
+ */
+ SENSOR_TYPE_ADDITIONAL_INFO = 33,
+
+ /*
+ * Base for device manufacturers private sensor types.
+ * These sensor types can't be exposed in the SDK.
+ */
+ SENSOR_TYPE_DEVICE_PRIVATE_BASE = 0x10000
+};
+
+@export(name="")
+enum SensorFlagBits : uint64_t {
+ /*
+ * Whether this sensor wakes up the AP from suspend mode when data is
+ * available. Whenever sensor events are delivered from a wake_up sensor,
+ * the driver needs to hold a wake_lock till the events are read by the
+ * SensorService i.e till ISensors::poll() is called the next time.
+ * Once poll is called again it means events have been read by the
+ * SensorService, the driver can safely release the wake_lock. SensorService
+ * will continue to hold a wake_lock till the app actually reads the events.
+ */
+ SENSOR_FLAG_WAKE_UP = 1,
+
+ /*
+ * Reporting modes for various sensors. Each sensor will have exactly one of
+ * these modes set.
+ * The least significant 2nd, 3rd and 4th bits are used to represent four
+ * possible reporting modes.
+ */
+ SENSOR_FLAG_CONTINUOUS_MODE = 0,
+ SENSOR_FLAG_ON_CHANGE_MODE = 2,
+ SENSOR_FLAG_ONE_SHOT_MODE = 4,
+ SENSOR_FLAG_SPECIAL_REPORTING_MODE = 6,
+
+ /*
+ * Set this flag if the sensor supports data_injection mode and allows data
+ * to be injected from the SensorService. When in data_injection ONLY
+ * sensors with this flag set are injected sensor data and only sensors with
+ * this flag set are activated. Eg: Accelerometer and Step Counter sensors
+ * can be set with this flag and SensorService will inject accelerometer
+ * data and read the corresponding step counts.
+ */
+ SENSOR_FLAG_SUPPORTS_DATA_INJECTION = 0x10,
+
+ /*
+ * Set this flag if the sensor is a dynamically connected sensor. See
+ * DynamicSensorInfo and DYNAMIC_SENSOR_META for details.
+ */
+ SENSOR_FLAG_DYNAMIC_SENSOR = 0x20,
+
+ /*
+ * Set this flag if sensor additional information is supported.
+ * See ADDITIONAL_INFO and AdditionalInfo for details.
+ */
+ SENSOR_FLAG_ADDITIONAL_INFO = 0x40,
+};
+
+struct SensorInfo {
+ /* handle that identifies this sensors. This handle is used to reference
+ * this sensor throughout the HAL API.
+ */
+ int32_t sensorHandle;
+
+ /* Name of this sensor.
+ * All sensors of the same "type" must have a different "name".
+ */
+ string name;
+
+ /* vendor of the hardware part */
+ string vendor;
+
+ /* version of the hardware part + driver. The value of this field
+ * must increase when the driver is updated in a way that changes the
+ * output of this sensor. This is important for fused sensors when the
+ * fusion algorithm is updated.
+ */
+ int32_t version;
+
+ /* this sensor's type. */
+ SensorType type;
+
+ /* type of this sensor as a string. Set to corresponding
+ * SENSOR_STRING_TYPE_*.
+ * When defining an OEM specific sensor or sensor manufacturer specific
+ * sensor, use your reserve domain name as a prefix.
+ * ex: com.google.glass.onheaddetector
+ * For sensors of known type, the android framework might overwrite this
+ * string automatically.
+ */
+ string typeAsString;
+
+ /* maximum range of this sensor's value in SI units */
+ float maxRange;
+
+ /* smallest difference between two values reported by this sensor */
+ float resolution;
+
+ /* rough estimate of this sensor's power consumption in mA */
+ float power;
+
+ /* this value depends on the reporting mode:
+ *
+ * continuous: minimum sample period allowed in microseconds
+ * on-change : 0
+ * one-shot :-1
+ * special : 0, unless otherwise noted
+ */
+ int32_t minDelay;
+
+ /* number of events reserved for this sensor in the batch mode FIFO.
+ * If there is a dedicated FIFO for this sensor, then this is the
+ * size of this FIFO. If the FIFO is shared with other sensors,
+ * this is the size reserved for that sensor and it can be zero.
+ */
+ uint32_t fifoReservedEventCount;
+
+ /* maximum number of events of this sensor that could be batched.
+ * This is especially relevant when the FIFO is shared between
+ * several sensors; this value is then set to the size of that FIFO.
+ */
+ uint32_t fifoMaxEventCount;
+
+ /* permission required to see this sensor, register to it and receive data.
+ * Set to "" if no permission is required. Some sensor types like the
+ * heart rate monitor have a mandatory require_permission.
+ * For sensors that always require a specific permission, like the heart
+ * rate monitor, the android framework might overwrite this string
+ * automatically.
+ */
+ string requiredPermission;
+
+ /* This value is defined only for continuous mode and on-change sensors.
+ * It is the delay between two sensor events corresponding to the lowest
+ * frequency that this sensor supports. When lower frequencies are requested
+ * through batch()/setDelay() the events will be generated at this frequency
+ * instead.
+ * It can be used by the framework or applications to estimate when the
+ * batch FIFO may be full.
+ *
+ * NOTE: periodNs is in nanoseconds where as maxDelay/minDelay are in
+ * microseconds.
+ *
+ * continuous, on-change: maximum sampling period allowed in
+ * microseconds.
+ *
+ * one-shot, special : 0
+ */
+ int32_t maxDelay;
+
+ /* Bitmask of SensorFlagBits */
+ uint64_t flags;
+};
+
+@export(name="")
+enum SensorStatus : int8_t {
+ SENSOR_STATUS_NO_CONTACT = -1,
+ SENSOR_STATUS_UNRELIABLE = 0,
+ SENSOR_STATUS_ACCURACY_LOW = 1,
+ SENSOR_STATUS_ACCURACY_MEDIUM = 2,
+ SENSOR_STATUS_ACCURACY_HIGH = 3,
+};
+
+struct Vec3 {
+ float x;
+ float y;
+ float z;
+ SensorStatus status;
+};
+
+struct Vec4 {
+ float x;
+ float y;
+ float z;
+ float w;
+};
+
+struct Uncal {
+ float x;
+ float y;
+ float z;
+ float x_bias;
+ float y_bias;
+ float z_bias;
+};
+
+struct HeartRate {
+ /* Heart rate in beats per minute.
+ * Set to 0 when status is SENSOR_STATUS_UNRELIABLE or ..._NO_CONTACT
+ */
+ float bpm;
+
+ /* Status of the sensor for this reading. Set to one SENSOR_STATUS_...
+ * Note that this value should only be set for sensors that explicitly
+ * define the meaning of this field. This field is not piped through the
+ * framework for other sensors.
+ */
+ SensorStatus status;
+};
+
+@export(name="")
+enum MetaDataEventType : uint32_t {
+ META_DATA_FLUSH_COMPLETE = 1,
+};
+
+struct MetaData {
+ MetaDataEventType what;
+};
+
+struct DynamicSensorInfo {
+ bool connected;
+ int32_t sensorHandle;
+
+ /* UUID of a dynamic sensor (using RFC 4122 byte order)
+ * For UUID 12345678-90AB-CDEF-1122-334455667788 the uuid field should be
+ * initialized as:
+ * {0x12, 0x34, 0x56, 0x78, 0x90, 0xAB, 0xCD, 0xEF, 0x11, ...}
+ */
+ uint8_t[16] uuid;
+};
+
+@export(name="additional_info_type_t")
+enum AdditionalInfoType : uint32_t {
+ /* Marks the beginning of additional information frames */
+ AINFO_BEGIN = 0,
+
+ /* Marks the end of additional information frames */
+ AINFO_END = 1,
+
+ /* Estimation of the delay that is not tracked by sensor timestamps. This
+ * includes delay introduced by sensor front-end filtering, data transport,
+ * etc.
+ * float[2]: delay in seconds, standard deviation of estimated value
+ */
+ AINFO_UNTRACKED_DELAY = 0x10000,
+
+ /* float: Celsius temperature */
+ AINFO_INTERNAL_TEMPERATURE,
+
+ /* First three rows of a homogeneous matrix, which represents calibration to
+ * a three-element vector raw sensor reading.
+ * float[12]: 3x4 matrix in row major order
+ */
+ AINFO_VEC3_CALIBRATION,
+
+ /* Location and orientation of sensor element in the device frame: origin is
+ * the geometric center of the mobile device screen surface; the axis
+ * definition corresponds to Android sensor definitions.
+ * float[12]: 3x4 matrix in row major order
+ */
+ AINFO_SENSOR_PLACEMENT,
+
+ /* float[2]: raw sample period in seconds,
+ * standard deviation of sampling period
+ */
+ AINFO_SAMPLING,
+
+ /* Sampling channel modeling information
+ * int32_t: noise type
+ * float[n]: parameters
+ */
+ AINFO_CHANNEL_NOISE = 0x20000,
+
+ /* float[3]: sample period, standard deviation of sample period,
+ * quantization unit
+ */
+ AINFO_CHANNEL_SAMPLER,
+
+ /* Represents a filter:
+ * \sum_j a_j y[n-j] == \sum_i b_i x[n-i]
+ *
+ * int32_t[3]: number of feedforward coeffients M,
+ * number of feedback coefficients N (for FIR filter, N = 1).
+ * bit mask that represents which element the filter is applied
+ * to. (bit 0==1 means this filter applies to vector element 0).
+ * float[M+N]: filter coefficients (b0, b1, ..., b_{M-1}), then
+ * (a0, a1, ..., a_{N-1}), a0 is always 1.
+ *
+ * Multiple frames may be needed for higher number of taps.
+ */
+ AINFO_CHANNEL_FILTER,
+
+ /* int32_t[2]: size in (row, column) ... 1st frame
+ * float[n]: matrix element values in row major order.
+ */
+ AINFO_CHANNEL_LINEAR_TRANSFORM,
+
+ /* int32_t[2]: extrapolate method, interpolate method
+ * float[n]: mapping key points in paris, (in, out)...
+ * (may be used to model saturation).
+ */
+ AINFO_CHANNEL_NONLINEAR_MAP,
+
+ /* int32_t: resample method (0-th order, 1st order...)
+ * float[1]: resample ratio (upsampling if < 1.0, downsampling if > 1.0).
+ */
+ AINFO_CHANNEL_RESAMPLER,
+
+ /* Custom information */
+ AINFO_CUSTOM_START = 0x10000000,
+
+ /* Debugging */
+ AINFO_DEBUGGING_START = 0x40000000,
+};
+
+struct AdditionalInfo {
+ /* type of payload data, see AdditionalInfoType */
+ AdditionalInfoType type;
+
+ /* sequence number of this frame for this type */
+ int32_t serial;
+
+ union Payload {
+ /* for each frame, a single data type, either int32_t or float,
+ * should be used.
+ */
+ int32_t[14] data_int32;
+ float[14] data_float;
+ } u;
+};
+
+/* acceleration values are in meter per second per second (m/s^2)
+ * magnetic vector values are in micro-Tesla (uT)
+ * orientation values are in degrees
+ * gyroscope values are in rad/s
+ * temperature is in degrees centigrade (Celsius)
+ * distance in centimeters
+ * light in SI lux units
+ * pressure in hectopascal (hPa)
+ * relative humidity in percent
+ */
+union EventPayload {
+ /* SENSOR_TYPE_ACCELEROMETER, SENSOR_TYPE_GEOMAGNETIC_FIELD,
+ * SENSOR_TYPE_ORIENTATION, SENSOR_TYPE_GYROSCOPE, SENSOR_TYPE_GRAVITY,
+ * SENSOR_TYPE_LINEAR_ACCELERATION
+ */
+ Vec3 vec3;
+
+ /* SENSOR_TYPE_ROTATION_VECTOR, SENSOR_TYPE_GAME_ROTATION_VECTOR,
+ * SENSOR_TYPE_GEOMAGNETIC_ROTATION_VECTOR
+ */
+ Vec4 vec4;
+
+ /* SENSOR_TYPE_MAGNETIC_FIELD_UNCALIBRATED,
+ * SENSOR_TYPE_GYROSCOPE_UNCALIBRATED
+ */
+ Uncal uncal;
+
+ /* SENSOR_TYPE_META_DATA */
+ MetaData meta;
+
+ /* SENSOR_TYPE_DEVICE_ORIENTATION, SENSOR_TYPE_LIGHT, SENSOR_TYPE_PRESSURE,
+ * SENSOR_TYPE_TEMPERATURE, SENSOR_TYPE_PROXIMITY,
+ * SENSOR_TYPE_RELATIVE_HUMIDITY, SENSOR_TYPE_AMBIENT_TEMPERATURE,
+ * SENSOR_TYPE_SIGNIFICANT_MOTION, SENSOR_TYPE_STEP_DETECTOR,
+ * SENSOR_TYPE_TILT_DETECTOR, SENSOR_TYPE_WAKE_GESTURE,
+ * SENSOR_TYPE_GLANCE_GESTURE, SENSOR_TYPE_PICK_UP_GESTURE,
+ * SENSOR_TYPE_WRIST_TILT_GESTURE, SENSOR_TYPE_STATIONARY_DETECT,
+ * SENSOR_TYPE_MOTION_DETECT, SENSOR_TYPE_HEART_BEAT
+ */
+ float scalar;
+
+ /* SENSOR_TYPE_STEP_COUNTER */
+ uint64_t stepCount;
+
+ /* SENSOR_TYPE_HEART_RATE */
+ HeartRate heartRate;
+
+ /* SENSOR_TYPE_POSE_6DOF */
+ float[15] pose6DOF;
+
+ /* SENSOR_TYPE_DYNAMIC_SENSOR_META */
+ DynamicSensorInfo dynamic;
+
+ /* SENSOR_TYPE_ADDITIONAL_INFO */
+ AdditionalInfo additional;
+
+ /* undefined/custom sensor type, >= SENSOR_TYPE_DEVICE_PRIVATE_BASE */
+ float[16] data;
+};
+
+struct Event {
+ /* Time measured in nanoseconds, in "elapsedRealtimeNano()'s" timebase. */
+ int64_t timestamp;
+
+ /* sensor identifier */
+ int32_t sensorHandle;
+
+ SensorType sensorType;
+
+ /* Union discriminated on sensorType */
+ EventPayload u;
+};
diff --git a/soundtrigger/2.0/ISoundTriggerHw.hal b/soundtrigger/2.0/ISoundTriggerHw.hal
index a1be85d..cf35ef1 100644
--- a/soundtrigger/2.0/ISoundTriggerHw.hal
+++ b/soundtrigger/2.0/ISoundTriggerHw.hal
@@ -159,6 +159,34 @@
generates (int32_t retval, SoundModelHandle modelHandle);
/*
+ * Load a key phrase sound model. Once loaded, recognition of this model can
+ * be started and stopped. Only one active recognition per model at a time.
+ * The SoundTrigger service must handle concurrent recognition requests by
+ * different users/applications on the same model.
+ * The implementation returns a unique handle used by other functions
+ * (unloadSoundModel(), startRecognition(), etc...
+ * @param soundModel A PhraseSoundModel structure describing the sound model
+ * to load.
+ * @param callback The callback interface on which the soundmodelCallback()
+ * method will be called upon completion.
+ * @param cookie The value of the cookie argument passed to the completion
+ * callback. This unique context information is assigned and
+ * used only by the framework.
+ * @return retval Operation completion status: 0 in case of success,
+ * -EINVAL in case of invalid sound model (e.g 0 data size),
+ * -ENOSYS in case of invalid operation (e.g max number of
+ * models exceeded),
+ * -ENOMEM in case of memory allocation failure,
+ * -ENODEV in case of initialization error.
+ * @return modelHandle A unique handle assigned by the HAL for use by the
+ * framework when controlling activity for this sound model.
+ */
+ loadPhraseSoundModel(PhraseSoundModel soundModel,
+ ISoundTriggerHwCallback callback,
+ CallbackCookie cookie)
+ generates (int32_t retval, SoundModelHandle modelHandle);
+
+ /*
* Unload a sound model. A sound model may be unloaded to make room for a
* new one to overcome implementation limitations.
* @param modelHandle the handle of the sound model to unload
diff --git a/soundtrigger/2.0/ISoundTriggerHwCallback.hal b/soundtrigger/2.0/ISoundTriggerHwCallback.hal
index 294d451..c6555f6 100644
--- a/soundtrigger/2.0/ISoundTriggerHwCallback.hal
+++ b/soundtrigger/2.0/ISoundTriggerHwCallback.hal
@@ -92,6 +92,17 @@
* started (see ISoundtriggerHw.startRecognition()
*/
recognitionCallback(RecognitionEvent event, CallbackCookie cookie);
+
+ /*
+ * Callback method called by the HAL when the sound recognition triggers
+ * for a key phrase sound model.
+ * @param event A RecognitionEvent structure containing detailed results
+ * of the recognition triggered
+ * @param cookie The cookie passed by the framework when recognition was
+ * started (see ISoundtriggerHw.startRecognition()
+ */
+ phraseRecognitionCallback(PhraseRecognitionEvent event,
+ CallbackCookie cookie);
/*
* Callback method called by the HAL when the sound model loading completes
* @param event A ModelEvent structure containing detailed results of the
diff --git a/tests/bar/1.0/default/Android.bp b/tests/bar/1.0/default/Android.bp
new file mode 100644
index 0000000..0d47001
--- /dev/null
+++ b/tests/bar/1.0/default/Android.bp
@@ -0,0 +1,21 @@
+
+
+cc_library_shared {
+ name: "android.hardware.tests.bar@1.0-impl",
+ relative_install_path: "hw",
+ srcs: [
+ "Bar.cpp",
+ "ImportTypes.cpp",
+ ],
+
+ shared_libs: [
+ "libbase",
+ "libhidl",
+ "libhwbinder",
+ "liblog",
+ "libutils",
+ "android.hardware.tests.foo@1.0",
+ "android.hardware.tests.bar@1.0",
+ ],
+
+}
diff --git a/tests/bar/1.0/default/Bar.cpp b/tests/bar/1.0/default/Bar.cpp
new file mode 100644
index 0000000..4433802
--- /dev/null
+++ b/tests/bar/1.0/default/Bar.cpp
@@ -0,0 +1,137 @@
+
+#define LOG_TAG "hidl_test"
+
+#include "Bar.h"
+#include <android-base/logging.h>
+#include <inttypes.h>
+
+namespace android {
+namespace hardware {
+namespace tests {
+namespace bar {
+namespace V1_0 {
+namespace implementation {
+
+Bar::Bar() {
+ mFoo = IFoo::getService("", true);
+}
+
+// Methods from ::android::hardware::tests::foo::V1_0::IFoo follow.
+Return<void> Bar::doThis(float param) {
+ return mFoo->doThis(param);
+}
+
+Return<void> Bar::doThis(uint32_t param) {
+ return mFoo->doThis(param);
+}
+
+Return<int32_t> Bar::doThatAndReturnSomething(
+ int64_t param) {
+ return mFoo->doThatAndReturnSomething(param);
+}
+
+Return<double> Bar::doQuiteABit(
+ int32_t a,
+ int64_t b,
+ float c,
+ double d) {
+ return mFoo->doQuiteABit(a, b, c, d);
+}
+
+Return<void> Bar::doSomethingElse(
+ const hidl_array<int32_t, 15> ¶m, doSomethingElse_cb _cb) {
+ return mFoo->doSomethingElse(param, _cb);
+}
+
+Return<void> Bar::doStuffAndReturnAString(
+ doStuffAndReturnAString_cb _cb) {
+ return mFoo->doStuffAndReturnAString(_cb);
+}
+
+Return<void> Bar::mapThisVector(
+ const hidl_vec<int32_t> ¶m, mapThisVector_cb _cb) {
+ return mFoo->mapThisVector(param, _cb);
+}
+
+Return<void> Bar::callMe(
+ const sp<IFooCallback> &cb) {
+ return mFoo->callMe(cb);
+}
+
+Return<Bar::SomeEnum> Bar::useAnEnum(SomeEnum param) {
+ return mFoo->useAnEnum(param);
+}
+
+Return<void> Bar::haveAGooberVec(const hidl_vec<Goober>& param) {
+ return mFoo->haveAGooberVec(param);
+}
+
+Return<void> Bar::haveAGoober(const Goober &g) {
+ return mFoo->haveAGoober(g);
+}
+
+Return<void> Bar::haveAGooberArray(const hidl_array<Goober, 20> &lots) {
+ return mFoo->haveAGooberArray(lots);
+}
+
+Return<void> Bar::haveATypeFromAnotherFile(const Abc &def) {
+ return mFoo->haveATypeFromAnotherFile(def);
+}
+
+Return<void> Bar::haveSomeStrings(
+ const hidl_array<hidl_string, 3> &array,
+ haveSomeStrings_cb _cb) {
+ return mFoo->haveSomeStrings(array, _cb);
+}
+
+Return<void> Bar::haveAStringVec(
+ const hidl_vec<hidl_string> &vector,
+ haveAStringVec_cb _cb) {
+ return mFoo->haveAStringVec(vector, _cb);
+}
+
+Return<void> Bar::transposeMe(
+ const hidl_array<float, 3, 5> &in, transposeMe_cb _cb) {
+ return mFoo->transposeMe(in, _cb);
+}
+
+Return<void> Bar::callingDrWho(
+ const MultiDimensional &in, callingDrWho_cb _hidl_cb) {
+ return mFoo->callingDrWho(in, _hidl_cb);
+}
+
+Return<void> Bar::transpose(const StringMatrix5x3 &in, transpose_cb _hidl_cb) {
+ return mFoo->transpose(in, _hidl_cb);
+}
+
+Return<void> Bar::transpose2(
+ const hidl_array<hidl_string, 5, 3> &in, transpose2_cb _hidl_cb) {
+ return mFoo->transpose2(in, _hidl_cb);
+}
+
+Return<void> Bar::sendVec(
+ const hidl_vec<uint8_t> &data, sendVec_cb _hidl_cb) {
+ return mFoo->sendVec(data, _hidl_cb);
+}
+
+Return<void> Bar::sendVecVec(sendVecVec_cb _hidl_cb) {
+ return mFoo->sendVecVec(_hidl_cb);
+}
+
+// Methods from ::android::hardware::tests::bar::V1_0::IBar follow.
+Return<void> Bar::thisIsNew() {
+ ALOGI("SERVER(Bar) thisIsNew");
+
+ return Void();
+}
+
+IBar* HIDL_FETCH_IBar(const char* /* name */) {
+ return new Bar();
+}
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace bar
+} // namespace tests
+} // namespace hardware
+} // namespace android
diff --git a/tests/bar/1.0/default/Bar.h b/tests/bar/1.0/default/Bar.h
new file mode 100644
index 0000000..58d9f9a
--- /dev/null
+++ b/tests/bar/1.0/default/Bar.h
@@ -0,0 +1,68 @@
+#ifndef HIDL_GENERATED_android_hardware_tests_bar_V1_0_Bar_H_
+#define HIDL_GENERATED_android_hardware_tests_bar_V1_0_Bar_H_
+
+#include <android/hardware/tests/bar/1.0/IBar.h>
+#include <hidl/Status.h>
+
+#include <hidl/MQDescriptor.h>
+namespace android {
+namespace hardware {
+namespace tests {
+namespace bar {
+namespace V1_0 {
+namespace implementation {
+
+using ::android::hardware::tests::bar::V1_0::IBar;
+using ::android::hardware::tests::foo::V1_0::Abc;
+using ::android::hardware::tests::foo::V1_0::IFoo;
+using ::android::hardware::tests::foo::V1_0::IFooCallback;
+using ::android::hardware::Return;
+using ::android::hardware::Void;
+using ::android::hardware::hidl_vec;
+using ::android::hardware::hidl_string;
+using ::android::sp;
+
+struct Bar : public IBar {
+
+ Bar();
+
+ // Methods from ::android::hardware::tests::foo::V1_0::IFoo follow.
+ virtual Return<void> doThis(float param) override;
+ virtual Return<void> doThis(uint32_t param) override;
+ virtual Return<int32_t> doThatAndReturnSomething(int64_t param) override;
+ virtual Return<double> doQuiteABit(int32_t a, int64_t b, float c, double d) override;
+ virtual Return<void> doSomethingElse(const hidl_array<int32_t, 15 /* 15 */>& param, doSomethingElse_cb _hidl_cb) override;
+ virtual Return<void> doStuffAndReturnAString(doStuffAndReturnAString_cb _hidl_cb) override;
+ virtual Return<void> mapThisVector(const hidl_vec<int32_t>& param, mapThisVector_cb _hidl_cb) override;
+ virtual Return<void> callMe(const sp<IFooCallback>& cb) override;
+ virtual Return<IFoo::SomeEnum> useAnEnum(IFoo::SomeEnum zzz) override;
+ virtual Return<void> haveAGooberVec(const hidl_vec<IFoo::Goober>& param) override;
+ virtual Return<void> haveAGoober(const IFoo::Goober& g) override;
+ virtual Return<void> haveAGooberArray(const hidl_array<IFoo::Goober, 20 /* 20 */>& lots) override;
+ virtual Return<void> haveATypeFromAnotherFile(const Abc& def) override;
+ virtual Return<void> haveSomeStrings(const hidl_array<hidl_string, 3 /* 3 */>& array, haveSomeStrings_cb _hidl_cb) override;
+ virtual Return<void> haveAStringVec(const hidl_vec<hidl_string>& vector, haveAStringVec_cb _hidl_cb) override;
+ virtual Return<void> transposeMe(const hidl_array<float, 3 /* 3 */, 5 /* 5 */>& in, transposeMe_cb _hidl_cb) override;
+ virtual Return<void> callingDrWho(const IFoo::MultiDimensional& in, callingDrWho_cb _hidl_cb) override;
+ virtual Return<void> transpose(const IFoo::StringMatrix5x3& in, transpose_cb _hidl_cb) override;
+ virtual Return<void> transpose2(const hidl_array<hidl_string, 5 /* 5 */, 3 /* 3 */>& in, transpose2_cb _hidl_cb) override;
+ virtual Return<void> sendVec(const hidl_vec<uint8_t>& data, sendVec_cb _hidl_cb) override;
+ virtual Return<void> sendVecVec(sendVecVec_cb _hidl_cb) override;
+
+ // Methods from ::android::hardware::tests::bar::V1_0::IBar follow.
+ Return<void> thisIsNew() override;
+
+private:
+ sp<IFoo> mFoo;
+};
+
+extern "C" IBar* HIDL_FETCH_IBar(const char* name);
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace bar
+} // namespace tests
+} // namespace hardware
+} // namespace android
+
+#endif // HIDL_GENERATED_android_hardware_tests_bar_V1_0_Bar_H_
diff --git a/tests/bar/1.0/default/ImportTypes.cpp b/tests/bar/1.0/default/ImportTypes.cpp
new file mode 100644
index 0000000..06ce4e5
--- /dev/null
+++ b/tests/bar/1.0/default/ImportTypes.cpp
@@ -0,0 +1,21 @@
+#include "ImportTypes.h"
+
+namespace android {
+namespace hardware {
+namespace tests {
+namespace bar {
+namespace V1_0 {
+namespace implementation {
+
+// Methods from ::android::hardware::tests::bar::V1_0::IImportTypes follow.
+
+IImportTypes* HIDL_FETCH_IImportTypes(const char* /* name */) {
+ return new ImportTypes();
+}
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace bar
+} // namespace tests
+} // namespace hardware
+} // namespace android
diff --git a/tests/bar/1.0/default/ImportTypes.h b/tests/bar/1.0/default/ImportTypes.h
new file mode 100644
index 0000000..b43be70
--- /dev/null
+++ b/tests/bar/1.0/default/ImportTypes.h
@@ -0,0 +1,36 @@
+#ifndef HIDL_GENERATED_android_hardware_tests_bar_V1_0_ImportTypes_H_
+#define HIDL_GENERATED_android_hardware_tests_bar_V1_0_ImportTypes_H_
+
+#include <android/hardware/tests/bar/1.0/IImportTypes.h>
+#include <hidl/Status.h>
+
+#include <hidl/MQDescriptor.h>
+namespace android {
+namespace hardware {
+namespace tests {
+namespace bar {
+namespace V1_0 {
+namespace implementation {
+
+using ::android::hardware::tests::bar::V1_0::IImportTypes;
+using ::android::hardware::Return;
+using ::android::hardware::Void;
+using ::android::hardware::hidl_vec;
+using ::android::hardware::hidl_string;
+using ::android::sp;
+
+struct ImportTypes : public IImportTypes {
+ // Methods from ::android::hardware::tests::bar::V1_0::IImportTypes follow.
+
+};
+
+extern "C" IImportTypes* HIDL_FETCH_IImportTypes(const char* name);
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace bar
+} // namespace tests
+} // namespace hardware
+} // namespace android
+
+#endif // HIDL_GENERATED_android_hardware_tests_bar_V1_0_ImportTypes_H_
diff --git a/tests/foo/1.0/default/Android.bp b/tests/foo/1.0/default/Android.bp
new file mode 100644
index 0000000..a2acd14
--- /dev/null
+++ b/tests/foo/1.0/default/Android.bp
@@ -0,0 +1,22 @@
+
+
+cc_library_shared {
+ name: "android.hardware.tests.foo@1.0-impl",
+ relative_install_path: "hw",
+ srcs: [
+ "Foo.cpp",
+ "FooCallback.cpp",
+ "MyTypes.cpp",
+ "TheirTypes.cpp",
+ ],
+
+ shared_libs: [
+ "libbase",
+ "libhidl",
+ "libhwbinder",
+ "liblog",
+ "libutils",
+ "android.hardware.tests.foo@1.0",
+ ],
+
+}
diff --git a/tests/foo/1.0/default/Foo.cpp b/tests/foo/1.0/default/Foo.cpp
new file mode 100644
index 0000000..81aa78b
--- /dev/null
+++ b/tests/foo/1.0/default/Foo.cpp
@@ -0,0 +1,409 @@
+
+#define LOG_TAG "hidl_test"
+
+#include "Foo.h"
+#include "FooCallback.h"
+#include <android-base/logging.h>
+#include <inttypes.h>
+#include <utils/Timers.h>
+
+namespace android {
+namespace hardware {
+namespace tests {
+namespace foo {
+namespace V1_0 {
+namespace implementation {
+
+// Methods from ::android::hardware::tests::foo::V1_0::IFoo follow.
+Return<void> Foo::doThis(float param) {
+ ALOGI("SERVER(Foo) doThis(%.2f)", param);
+
+ return Void();
+}
+
+Return<void> Foo::doThis(uint32_t param) {
+ ALOGI("SERVER(Foo) doThis (int) (%d)", param);
+ return Void();
+}
+
+Return<int32_t> Foo::doThatAndReturnSomething(
+ int64_t param) {
+ LOG(INFO) << "SERVER(Foo) doThatAndReturnSomething(" << param << ")";
+
+ return 666;
+}
+
+Return<double> Foo::doQuiteABit(
+ int32_t a,
+ int64_t b,
+ float c,
+ double d) {
+ LOG(INFO) << "SERVER(Foo) doQuiteABit("
+ << a
+ << ", "
+ << b
+ << ", "
+ << c
+ << ", "
+ << d
+ << ")";
+
+ return 666.5;
+}
+
+Return<void> Foo::doSomethingElse(
+ const hidl_array<int32_t, 15> ¶m, doSomethingElse_cb _cb) {
+ ALOGI("SERVER(Foo) doSomethingElse(...)");
+
+ hidl_array<int32_t, 32> result;
+ for (size_t i = 0; i < 15; ++i) {
+ result[i] = 2 * param[i];
+ result[15 + i] = param[i];
+ }
+ result[30] = 1;
+ result[31] = 2;
+
+ _cb(result);
+
+ return Void();
+}
+
+Return<void> Foo::doStuffAndReturnAString(
+ doStuffAndReturnAString_cb _cb) {
+ ALOGI("SERVER(Foo) doStuffAndReturnAString");
+
+ hidl_string s;
+ s = "Hello, world";
+
+ _cb(s);
+
+ return Void();
+}
+
+Return<void> Foo::mapThisVector(
+ const hidl_vec<int32_t> ¶m, mapThisVector_cb _cb) {
+ ALOGI("SERVER(Foo) mapThisVector");
+
+ hidl_vec<int32_t> out;
+ out.resize(param.size());
+
+ for (size_t i = 0; i < out.size(); ++i) {
+ out[i] = param[i] * 2;
+ }
+
+ _cb(out);
+
+ return Void();
+}
+
+Return<void> Foo::callMe(
+ const sp<IFooCallback> &cb) {
+ ALOGI("SERVER(Foo) callMe %p", cb.get());
+
+ if (cb != NULL) {
+
+ hidl_array<nsecs_t, 3> c;
+ ALOGI("SERVER(Foo) callMe %p calling IFooCallback::heyItsYou, " \
+ "should return immediately", cb.get());
+ c[0] = systemTime();
+ cb->heyItsYou(cb);
+ c[0] = systemTime() - c[0];
+ ALOGI("SERVER(Foo) callMe %p calling IFooCallback::heyItsYou " \
+ "returned after %" PRId64 "ns", cb.get(), c[0]);
+
+ ALOGI("SERVER(Foo) callMe %p calling IFooCallback::heyItsYouIsntIt, " \
+ "should block for %" PRId64 " seconds", cb.get(),
+ FooCallback::DELAY_S);
+ c[1] = systemTime();
+ bool answer = cb->heyItsYouIsntIt(cb);
+ c[1] = systemTime() - c[1];
+ ALOGI("SERVER(Foo) callMe %p IFooCallback::heyItsYouIsntIt " \
+ "responded with %d after %" PRId64 "ns", cb.get(), answer, c[1]);
+
+ ALOGI("SERVER(Foo) callMe %p calling " \
+ "IFooCallback::heyItsTheMeaningOfLife, " \
+ "should return immediately ", cb.get());
+ c[2] = systemTime();
+ cb->heyItsTheMeaningOfLife(42);
+ c[2] = systemTime() - c[2];
+ ALOGI("SERVER(Foo) callMe %p After call to " \
+ "IFooCallback::heyItsTheMeaningOfLife " \
+ "responded after %" PRId64 "ns", cb.get(), c[2]);
+
+ ALOGI("SERVER(Foo) callMe %p calling IFooCallback::youBlockedMeFor " \
+ "to report times", cb.get());
+ cb->youBlockedMeFor(c);
+ ALOGI("SERVER(Foo) callMe %p After call to " \
+ "IFooCallback::heyYouBlockedMeFor", cb.get());
+ }
+
+ return Void();
+}
+
+Return<Foo::SomeEnum> Foo::useAnEnum(SomeEnum param) {
+ ALOGI("SERVER(Foo) useAnEnum %d", (int)param);
+
+ return SomeEnum::goober;
+}
+
+Return<void> Foo::haveAGooberVec(const hidl_vec<Goober>& param) {
+ ALOGI("SERVER(Foo) haveAGooberVec ¶m = %p", ¶m);
+
+ return Void();
+}
+
+Return<void> Foo::haveAGoober(const Goober &g) {
+ ALOGI("SERVER(Foo) haveaGoober g=%p", &g);
+
+ return Void();
+}
+
+Return<void> Foo::haveAGooberArray(const hidl_array<Goober, 20> & /* lots */) {
+ ALOGI("SERVER(Foo) haveAGooberArray");
+
+ return Void();
+}
+
+Return<void> Foo::haveATypeFromAnotherFile(const Abc &def) {
+ ALOGI("SERVER(Foo) haveATypeFromAnotherFile def=%p", &def);
+
+ return Void();
+}
+
+Return<void> Foo::haveSomeStrings(
+ const hidl_array<hidl_string, 3> &array,
+ haveSomeStrings_cb _cb) {
+ ALOGI("SERVER(Foo) haveSomeStrings([\"%s\", \"%s\", \"%s\"])",
+ array[0].c_str(),
+ array[1].c_str(),
+ array[2].c_str());
+
+ hidl_array<hidl_string, 2> result;
+ result[0] = "Hello";
+ result[1] = "World";
+
+ _cb(result);
+
+ return Void();
+}
+
+Return<void> Foo::haveAStringVec(
+ const hidl_vec<hidl_string> &vector,
+ haveAStringVec_cb _cb) {
+ ALOGI("SERVER(Foo) haveAStringVec([\"%s\", \"%s\", \"%s\"])",
+ vector[0].c_str(),
+ vector[1].c_str(),
+ vector[2].c_str());
+
+ hidl_vec<hidl_string> result;
+ result.resize(2);
+
+ result[0] = "Hello";
+ result[1] = "World";
+
+ _cb(result);
+
+ return Void();
+}
+
+// NOTE: duplicated code in hidl_test
+using std::to_string;
+
+static std::string to_string(const IFoo::StringMatrix5x3 &M);
+static std::string to_string(const IFoo::StringMatrix3x5 &M);
+static std::string to_string(const hidl_string &s);
+
+template<typename T>
+static std::string to_string(const T *elems, size_t n) {
+ std::string out;
+ out = "[";
+ for (size_t i = 0; i < n; ++i) {
+ if (i > 0) {
+ out += ", ";
+ }
+ out += to_string(elems[i]);
+ }
+ out += "]";
+
+ return out;
+}
+
+template<typename T, size_t SIZE>
+static std::string to_string(const hidl_array<T, SIZE> &array) {
+ return to_string(&array[0], SIZE);
+}
+
+template<typename T, size_t SIZE1, size_t SIZE2>
+static std::string to_string(const hidl_array<T, SIZE1, SIZE2> &array) {
+ std::string out;
+ out = "[";
+ for (size_t i = 0; i < SIZE1; ++i) {
+ if (i > 0) {
+ out += ", ";
+ }
+
+ out += "[";
+ for (size_t j = 0; j < SIZE2; ++j) {
+ if (j > 0) {
+ out += ", ";
+ }
+
+ out += to_string(array[i][j]);
+ }
+ out += "]";
+ }
+ out += "]";
+
+ return out;
+}
+
+template<typename T>
+static std::string to_string(const hidl_vec<T> &vec) {
+ return to_string(&vec[0], vec.size());
+}
+
+static std::string to_string(const IFoo::StringMatrix5x3 &M) {
+ return to_string(M.s);
+}
+
+static std::string to_string(const IFoo::StringMatrix3x5 &M) {
+ return to_string(M.s);
+}
+
+static std::string to_string(const hidl_string &s) {
+ return std::string("'") + s.c_str() + "'";
+}
+
+Return<void> Foo::transposeMe(
+ const hidl_array<float, 3, 5> &in, transposeMe_cb _cb) {
+ ALOGI("SERVER(Foo) transposeMe(%s)", to_string(in).c_str());
+
+ hidl_array<float, 5, 3> out;
+ for (size_t i = 0; i < 5; ++i) {
+ for (size_t j = 0; j < 3; ++j) {
+ out[i][j] = in[j][i];
+ }
+ }
+
+ ALOGI("SERVER(Foo) transposeMe returning %s", to_string(out).c_str());
+
+ _cb(out);
+
+ return Void();
+}
+// end duplicated code
+
+static std::string QuuxToString(const IFoo::Quux &val) {
+ std::string s;
+
+ s = "Quux(first='";
+ s += val.first.c_str();
+ s += "', last='";
+ s += val.last.c_str();
+ s += "')";
+
+ return s;
+}
+
+static std::string MultiDimensionalToString(const IFoo::MultiDimensional &val) {
+ std::string s;
+
+ s += "MultiDimensional(";
+
+ s += "quuxMatrix=[";
+
+ size_t k = 0;
+ for (size_t i = 0; i < 5; ++i) {
+ if (i > 0) {
+ s += ", ";
+ }
+
+ s += "[";
+ for (size_t j = 0; j < 3; ++j, ++k) {
+ if (j > 0) {
+ s += ", ";
+ }
+
+ s += QuuxToString(val.quuxMatrix[i][j]);
+ }
+ }
+ s += "]";
+
+ s += ")";
+
+ return s;
+}
+
+Return<void> Foo::callingDrWho(
+ const MultiDimensional &in, callingDrWho_cb _hidl_cb) {
+ ALOGI("SERVER(Foo) callingDrWho(%s)", MultiDimensionalToString(in).c_str());
+
+ MultiDimensional out;
+ for (size_t i = 0; i < 5; ++i) {
+ for (size_t j = 0; j < 3; ++j) {
+ out.quuxMatrix[i][j].first = in.quuxMatrix[4 - i][2 - j].last;
+ out.quuxMatrix[i][j].last = in.quuxMatrix[4 - i][2 - j].first;
+ }
+ }
+
+ _hidl_cb(out);
+
+ return Void();
+}
+
+Return<void> Foo::transpose(const StringMatrix5x3 &in, transpose_cb _hidl_cb) {
+ LOG(INFO) << "SERVER(Foo) transpose " << to_string(in);
+
+ StringMatrix3x5 out;
+ for (size_t i = 0; i < 3; ++i) {
+ for (size_t j = 0; j < 5; ++j) {
+ out.s[i][j] = in.s[j][i];
+ }
+ }
+
+ _hidl_cb(out);
+
+ return Void();
+}
+
+Return<void> Foo::transpose2(
+ const hidl_array<hidl_string, 5, 3> &in, transpose2_cb _hidl_cb) {
+ LOG(INFO) << "SERVER(Foo) transpose2 " << to_string(in);
+
+ hidl_array<hidl_string, 3, 5> out;
+ for (size_t i = 0; i < 3; ++i) {
+ for (size_t j = 0; j < 5; ++j) {
+ out[i][j] = in[j][i];
+ }
+ }
+
+ _hidl_cb(out);
+
+ return Void();
+}
+
+Return<void> Foo::sendVec(
+ const hidl_vec<uint8_t> &data, sendVec_cb _hidl_cb) {
+ _hidl_cb(data);
+
+ return Void();
+}
+
+Return<void> Foo::sendVecVec(sendVecVec_cb _hidl_cb) {
+ hidl_vec<hidl_vec<uint8_t>> data;
+ _hidl_cb(data);
+
+ return Void();
+}
+
+
+IFoo* HIDL_FETCH_IFoo(const char* /* name */) {
+ return new Foo();
+}
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace foo
+} // namespace tests
+} // namespace hardware
+} // namespace android
diff --git a/tests/foo/1.0/default/Foo.h b/tests/foo/1.0/default/Foo.h
new file mode 100644
index 0000000..00a29f5
--- /dev/null
+++ b/tests/foo/1.0/default/Foo.h
@@ -0,0 +1,59 @@
+#ifndef HIDL_GENERATED_android_hardware_tests_foo_V1_0_Foo_H_
+#define HIDL_GENERATED_android_hardware_tests_foo_V1_0_Foo_H_
+
+#include <android/hardware/tests/foo/1.0/IFoo.h>
+#include <hidl/Status.h>
+
+#include <hidl/MQDescriptor.h>
+namespace android {
+namespace hardware {
+namespace tests {
+namespace foo {
+namespace V1_0 {
+namespace implementation {
+
+using ::android::hardware::tests::foo::V1_0::Abc;
+using ::android::hardware::tests::foo::V1_0::IFoo;
+using ::android::hardware::tests::foo::V1_0::IFooCallback;
+using ::android::hardware::Return;
+using ::android::hardware::Void;
+using ::android::hardware::hidl_vec;
+using ::android::hardware::hidl_string;
+using ::android::sp;
+
+struct Foo : public IFoo {
+ // Methods from ::android::hardware::tests::foo::V1_0::IFoo follow.
+ virtual Return<void> doThis(float param) override;
+ virtual Return<void> doThis(uint32_t param) override;
+ virtual Return<int32_t> doThatAndReturnSomething(int64_t param) override;
+ virtual Return<double> doQuiteABit(int32_t a, int64_t b, float c, double d) override;
+ virtual Return<void> doSomethingElse(const hidl_array<int32_t, 15 /* 15 */>& param, doSomethingElse_cb _hidl_cb) override;
+ virtual Return<void> doStuffAndReturnAString(doStuffAndReturnAString_cb _hidl_cb) override;
+ virtual Return<void> mapThisVector(const hidl_vec<int32_t>& param, mapThisVector_cb _hidl_cb) override;
+ virtual Return<void> callMe(const sp<IFooCallback>& cb) override;
+ virtual Return<IFoo::SomeEnum> useAnEnum(IFoo::SomeEnum zzz) override;
+ virtual Return<void> haveAGooberVec(const hidl_vec<IFoo::Goober>& param) override;
+ virtual Return<void> haveAGoober(const IFoo::Goober& g) override;
+ virtual Return<void> haveAGooberArray(const hidl_array<IFoo::Goober, 20 /* 20 */>& lots) override;
+ virtual Return<void> haveATypeFromAnotherFile(const Abc& def) override;
+ virtual Return<void> haveSomeStrings(const hidl_array<hidl_string, 3 /* 3 */>& array, haveSomeStrings_cb _hidl_cb) override;
+ virtual Return<void> haveAStringVec(const hidl_vec<hidl_string>& vector, haveAStringVec_cb _hidl_cb) override;
+ virtual Return<void> transposeMe(const hidl_array<float, 3 /* 3 */, 5 /* 5 */>& in, transposeMe_cb _hidl_cb) override;
+ virtual Return<void> callingDrWho(const IFoo::MultiDimensional& in, callingDrWho_cb _hidl_cb) override;
+ virtual Return<void> transpose(const IFoo::StringMatrix5x3& in, transpose_cb _hidl_cb) override;
+ virtual Return<void> transpose2(const hidl_array<hidl_string, 5 /* 5 */, 3 /* 3 */>& in, transpose2_cb _hidl_cb) override;
+ virtual Return<void> sendVec(const hidl_vec<uint8_t>& data, sendVec_cb _hidl_cb) override;
+ virtual Return<void> sendVecVec(sendVecVec_cb _hidl_cb) override;
+
+};
+
+extern "C" IFoo* HIDL_FETCH_IFoo(const char* name);
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace foo
+} // namespace tests
+} // namespace hardware
+} // namespace android
+
+#endif // HIDL_GENERATED_android_hardware_tests_foo_V1_0_Foo_H_
diff --git a/tests/foo/1.0/default/FooCallback.cpp b/tests/foo/1.0/default/FooCallback.cpp
new file mode 100644
index 0000000..d3eef77
--- /dev/null
+++ b/tests/foo/1.0/default/FooCallback.cpp
@@ -0,0 +1,132 @@
+
+#define LOG_TAG "hidl_test"
+
+#include "FooCallback.h"
+#include <android-base/logging.h>
+#include <inttypes.h>
+
+namespace android {
+namespace hardware {
+namespace tests {
+namespace foo {
+namespace V1_0 {
+namespace implementation {
+
+enum {
+ NOT_REPORTED = -1LL
+};
+
+FooCallback::FooCallback()
+ : mLock{}, mCond{} {
+ for (size_t i = 0; i < invokeInfo.size(); i++) {
+ invokeInfo[i].invoked = false;
+ invokeInfo[i].timeNs = NOT_REPORTED;
+ invokeInfo[i].callerBlockedNs = NOT_REPORTED;
+ }
+}
+
+Return<void> FooCallback::heyItsYou(
+ const sp<IFooCallback> &_cb) {
+ nsecs_t start = systemTime();
+ ALOGI("SERVER(FooCallback) 1: heyItsYou cb = %p", _cb.get());
+ nsecs_t end = systemTime();
+ {
+ Mutex::Autolock lock(mLock);
+ invokeInfo[0].invoked = true;
+ invokeInfo[0].timeNs = end - start;
+ mCond.signal();
+ }
+ ALOGI("SERVER(FooCallback) 2: heyItsYou returned");
+ return Void();
+}
+
+Return<bool> FooCallback::heyItsYouIsntIt(const sp<IFooCallback> &_cb) {
+ nsecs_t start = systemTime();
+ ALOGI("SERVER(FooCallback) 3: heyItsYouIsntIt cb = %p sleeping for %" PRId64 " seconds", _cb.get(), DELAY_S);
+ sleep(DELAY_S);
+ ALOGI("SERVER(FooCallback) 4: heyItsYouIsntIt cb = %p responding", _cb.get());
+ nsecs_t end = systemTime();
+ {
+ Mutex::Autolock lock(mLock);
+ invokeInfo[1].invoked = true;
+ invokeInfo[1].timeNs = end - start;
+ mCond.signal();
+ }
+ ALOGI("SERVER(FooCallback) 5: heyItsYouIsntIt cb = %p responding", _cb.get());
+ return true;
+}
+
+Return<void> FooCallback::heyItsTheMeaningOfLife(uint8_t tmol) {
+ nsecs_t start = systemTime();
+ ALOGI("SERVER(FooCallback) 6.1: heyItsTheMeaningOfLife = %d sleeping for %" PRId64 " seconds", tmol, DELAY_S);
+ sleep(DELAY_S);
+ ALOGI("SERVER(FooCallback) 6.2: heyItsTheMeaningOfLife = %d done sleeping", tmol);
+ nsecs_t end = systemTime();
+ {
+ Mutex::Autolock lock(mLock);
+ invokeInfo[2].invoked = true;
+ invokeInfo[2].timeNs = end - start;
+ mCond.signal();
+ }
+ ALOGI("SERVER(FooCallback) 6.3: heyItsTheMeaningOfLife returned");
+ return Void();
+}
+
+Return<void> FooCallback::reportResults(int64_t ns, reportResults_cb cb) {
+ ALOGI("SERVER(FooCallback) 8.1: reportResults(%" PRId64 " seconds)", nanoseconds_to_seconds(ns));
+ nsecs_t leftToWaitNs = ns;
+ bool cond;
+ {
+ Mutex::Autolock lock(mLock);
+ while ((cond = ((!invokeInfo[0].invoked ||
+ !invokeInfo[1].invoked ||
+ !invokeInfo[2].invoked ||
+ invokeInfo[0].callerBlockedNs == NOT_REPORTED ||
+ invokeInfo[1].callerBlockedNs == NOT_REPORTED ||
+ invokeInfo[2].callerBlockedNs == NOT_REPORTED) &&
+ leftToWaitNs > 0))) {
+ nsecs_t start = systemTime();
+ ::android::status_t rc = mCond.waitRelative(mLock, leftToWaitNs);
+ if (rc != ::android::OK) {
+ ALOGW("SERVER(FooCallback)::reportResults(%" PRId64 " ns) Condition::waitRelative(%" PRId64 ") returned error (%d)", ns, leftToWaitNs, rc);
+ if (rc == -ETIMEDOUT) {
+ // time's up
+ leftToWaitNs = -1;
+ }
+ break;
+ }
+ ALOGI("SERVER(FooCallback)::reportResults(%" PRId64 " ns) Condition::waitRelative was signalled", ns);
+ leftToWaitNs -= systemTime() - start;
+ }
+ }
+ ALOGI("SERVER(FooCallback) 8.2: reportResults returned;"
+ "invoked? %d, %d, %d; leftToWaitNs = %" PRId64 "; cond = %d",
+ invokeInfo[0].invoked, invokeInfo[1].invoked, invokeInfo[2].invoked,
+ leftToWaitNs, cond);
+ cb(leftToWaitNs, invokeInfo);
+ return Void();
+}
+
+Return<void> FooCallback::youBlockedMeFor(const hidl_array<int64_t, 3> &ns) {
+ ALOGI("SERVER(FooCallback) 7.1: youBlockedMeFor");
+ {
+ Mutex::Autolock lock(mLock);
+ for (size_t i = 0; i < 3; i++) {
+ invokeInfo[i].callerBlockedNs = ns[i];
+ }
+ mCond.signal();
+ }
+ ALOGI("SERVER(FooCallback) 7.2: returned");
+ return Void();
+}
+
+IFooCallback* HIDL_FETCH_IFooCallback(const char* /* name */) {
+ return new FooCallback();
+}
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace foo
+} // namespace tests
+} // namespace hardware
+} // namespace android
diff --git a/tests/foo/1.0/default/FooCallback.h b/tests/foo/1.0/default/FooCallback.h
new file mode 100644
index 0000000..5921972
--- /dev/null
+++ b/tests/foo/1.0/default/FooCallback.h
@@ -0,0 +1,52 @@
+#ifndef HIDL_GENERATED_android_hardware_tests_foo_V1_0_FooCallback_H_
+#define HIDL_GENERATED_android_hardware_tests_foo_V1_0_FooCallback_H_
+
+#include <android/hardware/tests/foo/1.0/IFooCallback.h>
+#include <hidl/Status.h>
+#include <hidl/MQDescriptor.h>
+
+#include <utils/Condition.h>
+#include <utils/Timers.h>
+namespace android {
+namespace hardware {
+namespace tests {
+namespace foo {
+namespace V1_0 {
+namespace implementation {
+
+using ::android::hardware::tests::foo::V1_0::IFooCallback;
+using ::android::hardware::Return;
+using ::android::hardware::Void;
+using ::android::hardware::hidl_vec;
+using ::android::hardware::hidl_string;
+using ::android::sp;
+
+struct FooCallback : public IFooCallback {
+ FooCallback();
+ // Methods from ::android::hardware::tests::foo::V1_0::IFooCallback follow.
+ Return<void> heyItsYou(const sp<IFooCallback>& cb) override;
+ Return<bool> heyItsYouIsntIt(const sp<IFooCallback>& cb) override;
+ Return<void> heyItsTheMeaningOfLife(uint8_t tmol) override;
+ Return<void> reportResults(int64_t ns, reportResults_cb _hidl_cb) override;
+ Return<void> youBlockedMeFor(const hidl_array<int64_t, 3 /* 3 */>& callerBlockedInfo) override;
+
+ static constexpr nsecs_t DELAY_S = 1;
+ static constexpr nsecs_t DELAY_NS = seconds_to_nanoseconds(DELAY_S);
+ static constexpr nsecs_t TOLERANCE_NS = milliseconds_to_nanoseconds(10);
+ static constexpr nsecs_t ONEWAY_TOLERANCE_NS = milliseconds_to_nanoseconds(1);
+
+ hidl_array<InvokeInfo, 3> invokeInfo;
+ Mutex mLock;
+ Condition mCond;
+};
+
+extern "C" IFooCallback* HIDL_FETCH_IFooCallback(const char* name);
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace foo
+} // namespace tests
+} // namespace hardware
+} // namespace android
+
+#endif // HIDL_GENERATED_android_hardware_tests_foo_V1_0_FooCallback_H_
diff --git a/tests/foo/1.0/default/MyTypes.cpp b/tests/foo/1.0/default/MyTypes.cpp
new file mode 100644
index 0000000..0d1a458
--- /dev/null
+++ b/tests/foo/1.0/default/MyTypes.cpp
@@ -0,0 +1,21 @@
+#include "MyTypes.h"
+
+namespace android {
+namespace hardware {
+namespace tests {
+namespace foo {
+namespace V1_0 {
+namespace implementation {
+
+// Methods from ::android::hardware::tests::foo::V1_0::IMyTypes follow.
+
+IMyTypes* HIDL_FETCH_IMyTypes(const char* /* name */) {
+ return new MyTypes();
+}
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace foo
+} // namespace tests
+} // namespace hardware
+} // namespace android
diff --git a/tests/foo/1.0/default/MyTypes.h b/tests/foo/1.0/default/MyTypes.h
new file mode 100644
index 0000000..6e9a3e1
--- /dev/null
+++ b/tests/foo/1.0/default/MyTypes.h
@@ -0,0 +1,36 @@
+#ifndef HIDL_GENERATED_android_hardware_tests_foo_V1_0_MyTypes_H_
+#define HIDL_GENERATED_android_hardware_tests_foo_V1_0_MyTypes_H_
+
+#include <android/hardware/tests/foo/1.0/IMyTypes.h>
+#include <hidl/Status.h>
+
+#include <hidl/MQDescriptor.h>
+namespace android {
+namespace hardware {
+namespace tests {
+namespace foo {
+namespace V1_0 {
+namespace implementation {
+
+using ::android::hardware::tests::foo::V1_0::IMyTypes;
+using ::android::hardware::Return;
+using ::android::hardware::Void;
+using ::android::hardware::hidl_vec;
+using ::android::hardware::hidl_string;
+using ::android::sp;
+
+struct MyTypes : public IMyTypes {
+ // Methods from ::android::hardware::tests::foo::V1_0::IMyTypes follow.
+
+};
+
+extern "C" IMyTypes* HIDL_FETCH_IMyTypes(const char* name);
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace foo
+} // namespace tests
+} // namespace hardware
+} // namespace android
+
+#endif // HIDL_GENERATED_android_hardware_tests_foo_V1_0_MyTypes_H_
diff --git a/tests/foo/1.0/default/TheirTypes.cpp b/tests/foo/1.0/default/TheirTypes.cpp
new file mode 100644
index 0000000..0f678f0
--- /dev/null
+++ b/tests/foo/1.0/default/TheirTypes.cpp
@@ -0,0 +1,21 @@
+#include "TheirTypes.h"
+
+namespace android {
+namespace hardware {
+namespace tests {
+namespace foo {
+namespace V1_0 {
+namespace implementation {
+
+// Methods from ::android::hardware::tests::foo::V1_0::ITheirTypes follow.
+
+ITheirTypes* HIDL_FETCH_ITheirTypes(const char* /* name */) {
+ return new TheirTypes();
+}
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace foo
+} // namespace tests
+} // namespace hardware
+} // namespace android
diff --git a/tests/foo/1.0/default/TheirTypes.h b/tests/foo/1.0/default/TheirTypes.h
new file mode 100644
index 0000000..24ade70
--- /dev/null
+++ b/tests/foo/1.0/default/TheirTypes.h
@@ -0,0 +1,36 @@
+#ifndef HIDL_GENERATED_android_hardware_tests_foo_V1_0_TheirTypes_H_
+#define HIDL_GENERATED_android_hardware_tests_foo_V1_0_TheirTypes_H_
+
+#include <android/hardware/tests/foo/1.0/ITheirTypes.h>
+#include <hidl/Status.h>
+
+#include <hidl/MQDescriptor.h>
+namespace android {
+namespace hardware {
+namespace tests {
+namespace foo {
+namespace V1_0 {
+namespace implementation {
+
+using ::android::hardware::tests::foo::V1_0::ITheirTypes;
+using ::android::hardware::Return;
+using ::android::hardware::Void;
+using ::android::hardware::hidl_vec;
+using ::android::hardware::hidl_string;
+using ::android::sp;
+
+struct TheirTypes : public ITheirTypes {
+ // Methods from ::android::hardware::tests::foo::V1_0::ITheirTypes follow.
+
+};
+
+extern "C" ITheirTypes* HIDL_FETCH_ITheirTypes(const char* name);
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace foo
+} // namespace tests
+} // namespace hardware
+} // namespace android
+
+#endif // HIDL_GENERATED_android_hardware_tests_foo_V1_0_TheirTypes_H_
diff --git a/tests/msgq/1.0/ITestMsgQ.hal b/tests/msgq/1.0/ITestMsgQ.hal
index 93a6e8a..fc96181 100644
--- a/tests/msgq/1.0/ITestMsgQ.hal
+++ b/tests/msgq/1.0/ITestMsgQ.hal
@@ -20,24 +20,26 @@
/*
* This method requests the service to set up Synchronous read/write
* wait-free FMQ with the client as reader.
- * @return ret Will be 0 if the setup is successful.
+ * @return ret Will be true if the setup is successful, false otherwise.
* @return mqDesc This structure describes the FMQ that was
* set up by the service. Client can use it to set up the FMQ at its end.
*/
configureFmqSyncReadWrite()
- generates(int32_t ret, MQDescriptorSync mqDesc);
+ generates(bool ret, MQDescriptorSync mqDesc);
/*
* This method request the service to write into the FMQ.
* @param count Number to messages to write.
- * @ret Number of messages succesfully written.
+ * @return ret Will be true if the write operation was successful,
+ * false otherwise.
*/
- requestWrite(int32_t count) generates(int32_t ret);
+ requestWrite(int32_t count) generates(bool ret);
/*
* This method request the service to read from the FMQ.
* @param count Number to messages to read.
- * @ret Number of messages succesfully read.
+ * @return ret Will be true if the read operation was successful, false
+ * otherwise.
*/
- requestRead(int32_t count) generates(int32_t ret);
+ requestRead(int32_t count) generates(bool ret);
};
diff --git a/tests/pointer/1.0/IPointer.hal b/tests/pointer/1.0/IPointer.hal
index e68fb31..4560a4a 100644
--- a/tests/pointer/1.0/IPointer.hal
+++ b/tests/pointer/1.0/IPointer.hal
@@ -17,6 +17,8 @@
package android.hardware.tests.pointer@1.0;
interface IPointer {
+ struct S { int32_t data; };
+ struct A { S s; };
// type declarations
struct Sam { int32_t data; };
struct Ada { ref<Sam> s_ptr; };
diff --git a/tests/pointer/1.0/default/Android.bp b/tests/pointer/1.0/default/Android.bp
new file mode 100644
index 0000000..cee6c91
--- /dev/null
+++ b/tests/pointer/1.0/default/Android.bp
@@ -0,0 +1,20 @@
+
+
+cc_library_shared {
+ name: "android.hardware.tests.pointer@1.0-impl",
+ relative_install_path: "hw",
+ srcs: [
+ "Graph.cpp",
+ "Pointer.cpp",
+ ],
+
+ shared_libs: [
+ "libbase",
+ "libhidl",
+ "libhwbinder",
+ "liblog",
+ "libutils",
+ "android.hardware.tests.pointer@1.0",
+ ],
+
+}
diff --git a/tests/pointer/1.0/default/Graph.cpp b/tests/pointer/1.0/default/Graph.cpp
new file mode 100644
index 0000000..a43df81
--- /dev/null
+++ b/tests/pointer/1.0/default/Graph.cpp
@@ -0,0 +1,116 @@
+#include "Graph.h"
+#include <android-base/logging.h>
+
+#define PUSH_ERROR_IF(__cond__) if(__cond__) { errors.push_back(std::to_string(__LINE__) + ": " + #__cond__); }
+
+namespace android {
+namespace hardware {
+namespace tests {
+namespace pointer {
+namespace V1_0 {
+namespace implementation {
+
+static void simpleGraph(IGraph::Graph& g) {
+ g.nodes.resize(2);
+ g.edges.resize(1);
+ g.nodes[0].data = 10;
+ g.nodes[1].data = 20;
+ g.edges[0].left = &g.nodes[0];
+ g.edges[0].right = &g.nodes[1];
+}
+
+static bool isSimpleGraph(const IGraph::Graph &g) {
+ if(g.nodes.size() != 2) return false;
+ if(g.edges.size() != 1) return false;
+ if(g.nodes[0].data != 10) return false;
+ if(g.nodes[1].data != 20) return false;
+ if(g.edges[0].left != &g.nodes[0]) return false;
+ if(g.edges[0].right != &g.nodes[1]) return false;
+ return true;
+}
+
+static void logSimpleGraph(const char *prefix, const IGraph::Graph& g) {
+ ALOGI("%s Graph %p, %d nodes, %d edges", prefix, &g, (int)g.nodes.size(), (int)g.edges.size());
+ std::ostringstream os;
+ for(size_t i = 0; i < g.nodes.size(); i++)
+ os << &g.nodes[i] << " = " << g.nodes[i].data << ", ";
+ ALOGI("%s Nodes: [%s]", prefix, os.str().c_str());
+ os.str("");
+ os.clear();
+ for(size_t i = 0; i < g.edges.size(); i++)
+ os << g.edges[i].left << " -> " << g.edges[i].right << ", ";
+ ALOGI("%s Edges: [%s]", prefix, os.str().c_str());
+}
+
+// Methods from ::android::hardware::tests::pointer::V1_0::IGraph follow.
+Return<void> Graph::passAGraph(const IGraph::Graph& g) {
+ ALOGI("SERVER(Graph) passAGraph start.");
+ PUSH_ERROR_IF(!isSimpleGraph(g));
+ // logSimpleGraph("SERVER(Graph) passAGraph:", g);
+ return Void();
+}
+
+Return<void> Graph::giveAGraph(giveAGraph_cb _cb) {
+ IGraph::Graph g;
+ simpleGraph(g);
+ _cb(g);
+ return Void();
+}
+
+Return<void> Graph::passANode(const IGraph::Node& n) {
+ PUSH_ERROR_IF(n.data != 10);
+ return Void();
+}
+
+Return<void> Graph::passTwoGraphs(IGraph::Graph const* g1, IGraph::Graph const* g2) {
+ PUSH_ERROR_IF(g1 != g2);
+ PUSH_ERROR_IF(!isSimpleGraph(*g1));
+ logSimpleGraph("SERVER(Graph): passTwoGraphs", *g2);
+ return Void();
+}
+
+Return<void> Graph::passAGamma(const IGraph::Gamma& c) {
+ if(c.a_ptr == nullptr && c.b_ptr == nullptr)
+ return Void();
+ ALOGI("SERVER(Graph) passAGamma received c.a = %p, c.b = %p, c.a->s = %p, c.b->s = %p",
+ c.a_ptr, c.b_ptr, c.a_ptr->s_ptr, c.b_ptr->s_ptr);
+ ALOGI("SERVER(Graph) passAGamma received data %d, %d",
+ (int)c.a_ptr->s_ptr->data, (int)c.b_ptr->s_ptr->data);
+ PUSH_ERROR_IF(c.a_ptr->s_ptr != c.b_ptr->s_ptr);
+ return Void();
+}
+Return<void> Graph::passASimpleRef(const IGraph::Alpha * a_ptr) {
+ ALOGI("SERVER(Graph) passASimpleRef received %d", a_ptr->s_ptr->data);
+ PUSH_ERROR_IF(a_ptr->s_ptr->data != 500);
+ return Void();
+}
+Return<void> Graph::passASimpleRefS(const IGraph::Theta * s_ptr) {
+ ALOGI("SERVER(Graph) passASimpleRefS received %d @ %p", s_ptr->data, s_ptr);
+ PUSH_ERROR_IF(s_ptr->data == 10);
+ return Void();
+}
+Return<void> Graph::giveASimpleRef(giveASimpleRef_cb _cb) {
+ IGraph::Theta s; s.data = 500;
+ IGraph::Alpha a; a.s_ptr = &s;
+ _cb(&a);
+ return Void();
+}
+
+Return<int32_t> Graph::getErrors() {
+ if(!errors.empty()) {
+ for(const auto& e : errors)
+ ALOGW("SERVER(Graph) error: %s", e.c_str());
+ }
+ return errors.size();
+}
+
+IGraph* HIDL_FETCH_IGraph(const char* /* name */) {
+ return new Graph();
+}
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace pointer
+} // namespace tests
+} // namespace hardware
+} // namespace android
diff --git a/tests/pointer/1.0/default/Graph.h b/tests/pointer/1.0/default/Graph.h
new file mode 100644
index 0000000..cbd5a8a
--- /dev/null
+++ b/tests/pointer/1.0/default/Graph.h
@@ -0,0 +1,47 @@
+#ifndef HIDL_GENERATED_android_hardware_tests_pointer_V1_0_Graph_H_
+#define HIDL_GENERATED_android_hardware_tests_pointer_V1_0_Graph_H_
+
+#include <android/hardware/tests/pointer/1.0/IGraph.h>
+#include <hidl/Status.h>
+
+#include <hidl/MQDescriptor.h>
+namespace android {
+namespace hardware {
+namespace tests {
+namespace pointer {
+namespace V1_0 {
+namespace implementation {
+
+using ::android::hardware::tests::pointer::V1_0::IGraph;
+using ::android::hardware::Return;
+using ::android::hardware::Void;
+using ::android::hardware::hidl_vec;
+using ::android::hardware::hidl_string;
+using ::android::sp;
+
+struct Graph : public IGraph {
+ // Methods from ::android::hardware::tests::pointer::V1_0::IGraph follow.
+ Return<void> passANode(const IGraph::Node& n) override;
+ Return<void> passAGraph(const IGraph::Graph& g) override;
+ Return<void> passTwoGraphs(::android::hardware::tests::pointer::V1_0::IGraph::Graph const* g1, ::android::hardware::tests::pointer::V1_0::IGraph::Graph const* g2) override;
+ Return<void> giveAGraph(giveAGraph_cb _hidl_cb) override;
+ Return<void> passAGamma(const IGraph::Gamma& c) override;
+ Return<void> passASimpleRef(::android::hardware::tests::pointer::V1_0::IGraph::Alpha const* a) override;
+ Return<void> passASimpleRefS(::android::hardware::tests::pointer::V1_0::IGraph::Theta const* s) override;
+ Return<void> giveASimpleRef(giveASimpleRef_cb _hidl_cb) override;
+ Return<int32_t> getErrors() override;
+private:
+ std::vector<std::string> errors;
+
+};
+
+extern "C" IGraph* HIDL_FETCH_IGraph(const char* name);
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace pointer
+} // namespace tests
+} // namespace hardware
+} // namespace android
+
+#endif // HIDL_GENERATED_android_hardware_tests_pointer_V1_0_Graph_H_
diff --git a/tests/pointer/1.0/default/Pointer.cpp b/tests/pointer/1.0/default/Pointer.cpp
new file mode 100644
index 0000000..d7cd772
--- /dev/null
+++ b/tests/pointer/1.0/default/Pointer.cpp
@@ -0,0 +1,19 @@
+#include "Pointer.h"
+
+namespace android {
+namespace hardware {
+namespace tests {
+namespace pointer {
+namespace V1_0 {
+namespace implementation {
+
+IPointer* HIDL_FETCH_IPointer(const char* /* name */) {
+ return new Pointer();
+}
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace pointer
+} // namespace tests
+} // namespace hardware
+} // namespace android
diff --git a/tests/pointer/1.0/default/Pointer.h b/tests/pointer/1.0/default/Pointer.h
new file mode 100644
index 0000000..1579aea
--- /dev/null
+++ b/tests/pointer/1.0/default/Pointer.h
@@ -0,0 +1,348 @@
+#ifndef HIDL_GENERATED_android_hardware_tests_pointer_V1_0_Pointer_H_
+#define HIDL_GENERATED_android_hardware_tests_pointer_V1_0_Pointer_H_
+
+#include <android/hardware/tests/pointer/1.0/IPointer.h>
+#include <android-base/logging.h>
+#include <hidl/Status.h>
+
+#include <hidl/MQDescriptor.h>
+
+// TODO move to Pointer.cpp so that I won't have weird macros in headers
+#define PUSH_ERROR_IF(__cond__) if(__cond__) { errors.push_back(std::to_string(__LINE__) + ": " + #__cond__); }
+
+namespace android {
+namespace hardware {
+namespace tests {
+namespace pointer {
+namespace V1_0 {
+namespace implementation {
+
+using ::android::hardware::tests::pointer::V1_0::IPointer;
+using ::android::hardware::Return;
+using ::android::hardware::Void;
+using ::android::hardware::hidl_vec;
+using ::android::hardware::hidl_string;
+using ::android::sp;
+
+struct Pointer : public IPointer {
+private:
+ std::vector<std::string> errors;
+public:
+ Return<int32_t> getErrors() {
+ if(!errors.empty()) {
+ for(const auto& e : errors)
+ ALOGW("SERVER(Pointer) error: %s", e.c_str());
+ }
+ return errors.size();
+ }
+ Return<void> foo1(const IPointer::Sam& s, IPointer::Sam const* s_ptr) override {
+ PUSH_ERROR_IF(!(&s == s_ptr));
+ return Void();
+ }
+ Return<void> foo2(const IPointer::Sam& s, const IPointer::Ada& a) override {
+ PUSH_ERROR_IF(!(&s == a.s_ptr));
+ return Void();
+ }
+ Return<void> foo3(const IPointer::Sam& s, const IPointer::Ada& a, const IPointer::Bob& b) override {
+ PUSH_ERROR_IF(!(&a == b.a_ptr && a.s_ptr == b.s_ptr && a.s_ptr == &s));
+ return Void();
+ }
+ Return<void> foo4(IPointer::Sam const* s_ptr) override {
+ PUSH_ERROR_IF(!(s_ptr->data == 500));
+ return Void();
+ }
+ Return<void> foo5(const IPointer::Ada& a, const IPointer::Bob& b) override {
+ PUSH_ERROR_IF(!(a.s_ptr == b.s_ptr && b.a_ptr == &a));
+ return Void();
+ }
+ Return<void> foo6(IPointer::Ada const* a_ptr) override {
+ PUSH_ERROR_IF(!(a_ptr->s_ptr->data == 500));
+ return Void();
+ }
+ Return<void> foo7(IPointer::Ada const* a_ptr, IPointer::Bob const* b_ptr) override {
+ PUSH_ERROR_IF(!(a_ptr->s_ptr == b_ptr->s_ptr && a_ptr == b_ptr->a_ptr && a_ptr->s_ptr->data == 500));
+ return Void();
+ }
+ Return<void> foo8(const IPointer::Dom& d) override {
+ const IPointer::Cin& c = d.c;
+ PUSH_ERROR_IF(&c.a != c.b_ptr->a_ptr);
+ PUSH_ERROR_IF(c.a.s_ptr != c.b_ptr->s_ptr);
+ PUSH_ERROR_IF(c.a.s_ptr->data != 500);
+ return Void();
+ }
+ Return<void> foo9(::android::hardware::hidl_string const* str_ref) override {
+ ALOGI("SERVER(Pointer) foo9 got string @ %p (size = %ld) \"%s\"",
+ str_ref->c_str(),
+ (unsigned long) str_ref->size(), str_ref->c_str());
+ PUSH_ERROR_IF(!(strcmp(str_ref->c_str(), "meowmeowmeow") == 0));
+ return Void();
+ }
+ Return<void> foo10(const ::android::hardware::hidl_vec<IPointer::Sam const*>& s_ptr_vec) override {
+ PUSH_ERROR_IF(s_ptr_vec[0]->data != 500);
+ if(s_ptr_vec.size() != 5) {
+ errors.push_back("foo10: s_ptr_vec.size() != 5");
+ return Void();
+ }
+ for(size_t i = 0; i < s_ptr_vec.size(); i++)
+ PUSH_ERROR_IF(s_ptr_vec[0] != s_ptr_vec[i]);
+ return Void();
+ }
+ Return<void> foo11(::android::hardware::hidl_vec<IPointer::Sam> const* s_vec_ptr) override {
+ if(s_vec_ptr->size() != 5) {
+ errors.push_back("foo11: s_vec_ptr->size() != 5");
+ return Void();
+ }
+ for(size_t i = 0; i < 5; i++)
+ PUSH_ERROR_IF((*s_vec_ptr)[i].data != 500);
+ return Void();
+ }
+ Return<void> foo12(hidl_array<IPointer::Sam, 5> const* s_array_ref) override {
+ for(size_t i = 0; i < 5; ++i)
+ PUSH_ERROR_IF((*s_array_ref)[i].data != 500);
+ return Void();
+ }
+ Return<void> foo13(const hidl_array<IPointer::Sam const*, 5>& s_ref_array) override {
+ PUSH_ERROR_IF(s_ref_array[0]->data != 500)
+ for(size_t i = 0; i < 5; i++)
+ PUSH_ERROR_IF(s_ref_array[i] != s_ref_array[0])
+ return Void();
+ }
+ Return<void> foo14(IPointer::Sam const* const* const* s_3ptr) override {
+ PUSH_ERROR_IF(!((***s_3ptr).data == 500))
+ return Void();
+ }
+ Return<void> foo15(int32_t const* const* const* i_3ptr) override {
+ PUSH_ERROR_IF(!((***i_3ptr) == 500))
+ return Void();
+ }
+
+ Return<void> foo16(const IPointer::Ptr& p) override {
+ PUSH_ERROR_IF((*p.array_ptr)[0].s_ptr->data != 500);
+ for(size_t i = 0; i < 5; i++) PUSH_ERROR_IF((*p.array_ptr)[i].s_ptr != (*p.array_ptr)[0].s_ptr);
+ PUSH_ERROR_IF(*(p.int_ptr) != 500);
+ for(size_t i = 0; i < 5; i++) PUSH_ERROR_IF((*p.int_array_ptr)[i] != 500);
+ for(size_t i = 0; i < 5; i++) PUSH_ERROR_IF(p.int_ptr_array[i] != p.int_ptr);
+ PUSH_ERROR_IF(p.a_ptr_vec.size() != 5);
+ PUSH_ERROR_IF(p.a_ptr_vec[0]->s_ptr->data != 500);
+ for(size_t i = 0; i < 5; i++) PUSH_ERROR_IF(p.a_ptr_vec[i]->s_ptr != p.a_ptr_vec[0]->s_ptr);
+ PUSH_ERROR_IF(strcmp(p.str_ref->c_str(), "meowmeowmeow") != 0);
+ PUSH_ERROR_IF(p.a_vec_ptr->size() != 5);
+ PUSH_ERROR_IF((*p.a_vec_ptr)[0].s_ptr->data != 500);
+ for(size_t i = 0; i < 5; i++) PUSH_ERROR_IF((*p.a_vec_ptr)[i].s_ptr != (*p.a_vec_ptr)[0].s_ptr);
+ return Void();
+ };
+ Return<void> foo17(IPointer::Ptr const* p) override {
+ return foo16(*p);
+ };
+ Return<void> foo18(hidl_string const* str_ref, hidl_string const* str_ref2, const hidl_string& str) override {
+ PUSH_ERROR_IF(&str != str_ref);
+ PUSH_ERROR_IF(str_ref != str_ref2);
+ PUSH_ERROR_IF(strcmp(str.c_str(), "meowmeowmeow") != 0)
+ return Void();
+ };
+ Return<void> foo19(
+ hidl_vec<IPointer::Ada> const* a_vec_ref,
+ const hidl_vec<IPointer::Ada>& a_vec,
+ hidl_vec<IPointer::Ada> const* a_vec_ref2) {
+ PUSH_ERROR_IF(&a_vec != a_vec_ref);
+ PUSH_ERROR_IF(a_vec_ref2 != a_vec_ref);
+ PUSH_ERROR_IF(a_vec.size() != 5);
+ PUSH_ERROR_IF(a_vec[0].s_ptr->data != 500);
+ for(size_t i = 0; i < 5; i++)
+ PUSH_ERROR_IF(a_vec[i].s_ptr != a_vec[0].s_ptr);
+ return Void();
+ };
+
+ Return<void> foo20(const hidl_vec<IPointer::Sam const*>&) override {
+ return Void();
+ }
+ Return<void> foo21(hidl_array<IPointer::Ada, 3, 2, 1> const* a_array_ptr) override {
+ const hidl_array<IPointer::Ada, 3, 2, 1>& a_array = *a_array_ptr;
+ PUSH_ERROR_IF(a_array[0][0][0].s_ptr->data != 500);
+ for(size_t i = 0; i < 3; i++)
+ for(size_t j = 0; j < 2; j++)
+ for(size_t k = 0; k < 1; k++)
+ PUSH_ERROR_IF(a_array[i][j][k].s_ptr != a_array[0][0][0].s_ptr);
+ return Void();
+ }
+ Return<void> foo22(const hidl_array<IPointer::Ada const*, 3, 2, 1>& a_ptr_array) override {
+ PUSH_ERROR_IF(a_ptr_array[0][0][0]->s_ptr->data != 500);
+ for(size_t i = 0; i < 3; i++)
+ for(size_t j = 0; j < 2; j++)
+ for(size_t k = 0; k < 1; k++)
+ PUSH_ERROR_IF(a_ptr_array[i][j][k] != a_ptr_array[0][0][0]);
+ return Void();
+ }
+
+ IPointer::Sam *s;
+ IPointer::Ada *a;
+ IPointer::Bob *b;
+ IPointer::Cin *c;
+ IPointer::Dom *d;
+
+ IPointer::Ptr p;
+ hidl_array<IPointer::Ada, 5> a_array;
+ int32_t someInt;
+ hidl_array<int32_t, 5> someIntArray;
+ hidl_string str;
+ hidl_vec<IPointer::Ada> a_vec;
+ Pointer() {
+ d = new IPointer::Dom();
+ s = new IPointer::Sam();
+ b = new IPointer::Bob();
+ c = &d->c;
+ a = &c->a;
+ b->s_ptr = a->s_ptr = s;
+ b->a_ptr = a;
+ c->b_ptr = b;
+ s->data = 500;
+
+ someInt = 500;
+ for(size_t i = 0; i < 5; i++) someIntArray[i] = 500;
+
+ for(size_t i = 0; i < 5; i++) a_array[i] = *a;
+
+ for(size_t i = 0; i < 5; i++) p.ptr_array[i] = a;
+ p.array_ptr = &a_array;
+ p.int_ptr = &someInt;
+ p.int_array_ptr = &someIntArray;
+ for(size_t i = 0; i < 5; i++) p.int_ptr_array[i] = &someInt;
+ p.a_ptr_vec.resize(5);
+ for(size_t i = 0; i < 5; i++) p.a_ptr_vec[i] = a;
+ str = "meowmeowmeow";
+ p.str_ref = &str;
+ a_vec.resize(5);
+ for(size_t i = 0; i < 5; i++) a_vec[i].s_ptr = s;
+ p.a_vec_ptr = &a_vec;
+ }
+ ~Pointer() {
+ delete d; delete s; delete b;
+ }
+ Return<void> bar1(bar1_cb _cb) override {
+ _cb(*s, s);
+ return Void();
+ }
+ Return<void> bar2(bar2_cb _cb) override {
+ _cb(*s, *a);
+ return Void();
+ }
+ Return<void> bar3(bar3_cb _cb) override {
+ _cb(*s, *a, *b);
+ return Void();
+ }
+ Return<void> bar4(bar4_cb _cb) override {
+ _cb(s);
+ return Void();
+ }
+ Return<void> bar5(bar5_cb _cb) override {
+ _cb(*a, *b);
+ return Void();
+ }
+ Return<void> bar6(bar6_cb _cb) override {
+ _cb(a);
+ return Void();
+ }
+ Return<void> bar7(bar7_cb _cb) override {
+ _cb(a, b);
+ return Void();
+ }
+ Return<void> bar8(bar8_cb _cb) override {
+ _cb(*d);
+ return Void();
+ }
+ Return<void> bar9(bar9_cb _cb) override {
+ _cb(&str);
+ return Void();
+ }
+ Return<void> bar10(bar10_cb _cb) override {
+ hidl_vec<const IPointer::Sam *> v; v.resize(5);
+ for(size_t i = 0; i < 5; i++) v[i] = s;
+ _cb(v);
+ return Void();
+ }
+ Return<void> bar11(bar11_cb _cb) override {
+ hidl_vec<IPointer::Sam> v; v.resize(5);
+ for(size_t i = 0; i < 5; i++) v[i].data = 500;
+ _cb(&v);
+ return Void();
+ }
+ Return<void> bar12(bar12_cb _cb) override {
+ hidl_array<IPointer::Sam, 5> array;
+ for(size_t i = 0; i < 5; i++) array[i] = *s;
+ _cb(&array);
+ return Void();
+ }
+ Return<void> bar13(bar13_cb _cb) override {
+ hidl_array<const IPointer::Sam *, 5> array;
+ for(size_t i = 0; i < 5; i++) array[i] = s;
+ _cb(array);
+ return Void();
+ }
+ Return<void> bar14(bar14_cb _cb) override {
+ IPointer::Sam const* p1 = s;
+ IPointer::Sam const* const* p2 = &p1;
+ _cb(&p2);
+ return Void();
+ }
+ Return<void> bar15(bar15_cb _cb) override {
+ int32_t const* p1 = &someInt;
+ int32_t const* const* p2 = &p1;
+ _cb(&p2);
+ return Void();
+ }
+ Return<void> bar16(bar16_cb _cb) override {
+ _cb(p);
+ return Void();
+ }
+ Return<void> bar17(bar17_cb _cb) override {
+ _cb(&p);
+ return Void();
+ }
+ Return<void> bar18(bar18_cb _cb) override {
+ _cb(&str, &str, str);
+ return Void();
+ }
+ Return<void> bar19(bar19_cb _cb) override {
+ _cb(&a_vec, a_vec, &a_vec);
+ return Void();
+ }
+ Return<void> bar20(bar20_cb _cb) override {
+ // 1026 == PARCEL_REF_CAP + 2.
+ // 1026 means 1 writeBuffer and 1025 writeReferences. 1025 > PARCEL_REF_CAP.
+ hidl_vec<const IPointer::Sam *> v; v.resize(1026);
+ for(size_t i = 0; i < 1026; i++) v[i] = s;
+ _cb(v);
+ return Void();
+ }
+ Return<void> bar21(bar21_cb _cb) override {
+ hidl_array<IPointer::Ada, 3, 2, 1> a_array;
+ for(size_t i = 0; i < 3; i++)
+ for(size_t j = 0; j < 2; j++)
+ for(size_t k = 0; k < 1; k++)
+ a_array[i][j][k] = *a;
+ _cb(&a_array);
+ return Void();
+ }
+ Return<void> bar22(bar22_cb _cb) override {
+ hidl_array<const IPointer::Ada *, 3, 2, 1> a_ptr_array;
+ for(size_t i = 0; i < 3; i++)
+ for(size_t j = 0; j < 2; j++)
+ for(size_t k = 0; k < 1; k++)
+ a_ptr_array[i][j][k] = a;
+ _cb(a_ptr_array);
+ return Void();
+ }
+};
+
+extern "C" IPointer* HIDL_FETCH_IPointer(const char* name);
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace pointer
+} // namespace tests
+} // namespace hardware
+} // namespace android
+
+#undef PUSH_ERROR_IF
+
+#endif // HIDL_GENERATED_android_hardware_tests_pointer_V1_0_Pointer_H_
diff --git a/thermal/1.0/Android.bp b/thermal/1.0/Android.bp
new file mode 100644
index 0000000..0c5dd19
--- /dev/null
+++ b/thermal/1.0/Android.bp
@@ -0,0 +1,46 @@
+// This file is autogenerated by hidl-gen. Do not edit manually.
+
+genrule {
+ name: "android.hardware.thermal@1.0_genc++",
+ tool: "hidl-gen",
+ cmd: "$tool -o $genDir -Lc++ -randroid.hardware:hardware/interfaces android.hardware.thermal@1.0",
+ srcs: [
+ "types.hal",
+ "IThermal.hal",
+ ],
+ out: [
+ "android/hardware/thermal/1.0/types.cpp",
+ "android/hardware/thermal/1.0/ThermalAll.cpp",
+ ],
+}
+
+genrule {
+ name: "android.hardware.thermal@1.0_genc++_headers",
+ tool: "hidl-gen",
+ cmd: "$tool -o $genDir -Lc++ -randroid.hardware:hardware/interfaces android.hardware.thermal@1.0",
+ srcs: [
+ "types.hal",
+ "IThermal.hal",
+ ],
+ out: [
+ "android/hardware/thermal/1.0/types.h",
+ "android/hardware/thermal/1.0/IThermal.h",
+ "android/hardware/thermal/1.0/IHwThermal.h",
+ "android/hardware/thermal/1.0/BnThermal.h",
+ "android/hardware/thermal/1.0/BpThermal.h",
+ "android/hardware/thermal/1.0/BsThermal.h",
+ ],
+}
+
+cc_library_shared {
+ name: "android.hardware.thermal@1.0",
+ generated_sources: ["android.hardware.thermal@1.0_genc++"],
+ generated_headers: ["android.hardware.thermal@1.0_genc++_headers"],
+ export_generated_headers: ["android.hardware.thermal@1.0_genc++_headers"],
+ shared_libs: [
+ "libhidl",
+ "libhwbinder",
+ "libutils",
+ "libcutils",
+ ],
+}
diff --git a/thermal/1.0/Android.mk b/thermal/1.0/Android.mk
new file mode 100644
index 0000000..47a4d61
--- /dev/null
+++ b/thermal/1.0/Android.mk
@@ -0,0 +1,306 @@
+# This file is autogenerated by hidl-gen. Do not edit manually.
+
+LOCAL_PATH := $(call my-dir)
+
+################################################################################
+
+include $(CLEAR_VARS)
+LOCAL_MODULE := android.hardware.thermal@1.0-java
+LOCAL_MODULE_CLASS := JAVA_LIBRARIES
+
+intermediates := $(local-generated-sources-dir)
+
+HIDL := $(HOST_OUT_EXECUTABLES)/hidl-gen$(HOST_EXECUTABLE_SUFFIX)
+
+#
+# Build types.hal (CoolingDevice)
+#
+GEN := $(intermediates)/android/hardware/thermal/1.0/CoolingDevice.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.thermal@1.0::types.CoolingDevice
+
+$(GEN): $(LOCAL_PATH)/types.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+
+#
+# Build types.hal (CoolingType)
+#
+GEN := $(intermediates)/android/hardware/thermal/1.0/CoolingType.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.thermal@1.0::types.CoolingType
+
+$(GEN): $(LOCAL_PATH)/types.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+
+#
+# Build types.hal (CpuUsage)
+#
+GEN := $(intermediates)/android/hardware/thermal/1.0/CpuUsage.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.thermal@1.0::types.CpuUsage
+
+$(GEN): $(LOCAL_PATH)/types.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+
+#
+# Build types.hal (Temperature)
+#
+GEN := $(intermediates)/android/hardware/thermal/1.0/Temperature.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.thermal@1.0::types.Temperature
+
+$(GEN): $(LOCAL_PATH)/types.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+
+#
+# Build types.hal (TemperatureType)
+#
+GEN := $(intermediates)/android/hardware/thermal/1.0/TemperatureType.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.thermal@1.0::types.TemperatureType
+
+$(GEN): $(LOCAL_PATH)/types.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+
+#
+# Build types.hal (ThermalStatus)
+#
+GEN := $(intermediates)/android/hardware/thermal/1.0/ThermalStatus.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.thermal@1.0::types.ThermalStatus
+
+$(GEN): $(LOCAL_PATH)/types.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+
+#
+# Build types.hal (ThermalStatusCode)
+#
+GEN := $(intermediates)/android/hardware/thermal/1.0/ThermalStatusCode.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.thermal@1.0::types.ThermalStatusCode
+
+$(GEN): $(LOCAL_PATH)/types.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+
+#
+# Build IThermal.hal
+#
+GEN := $(intermediates)/android/hardware/thermal/1.0/IThermal.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/IThermal.hal
+$(GEN): PRIVATE_DEPS += $(LOCAL_PATH)/types.hal
+$(GEN): $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.thermal@1.0::IThermal
+
+$(GEN): $(LOCAL_PATH)/IThermal.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+include $(BUILD_JAVA_LIBRARY)
+
+
+################################################################################
+
+include $(CLEAR_VARS)
+LOCAL_MODULE := android.hardware.thermal@1.0-java-static
+LOCAL_MODULE_CLASS := JAVA_LIBRARIES
+
+intermediates := $(local-generated-sources-dir)
+
+HIDL := $(HOST_OUT_EXECUTABLES)/hidl-gen$(HOST_EXECUTABLE_SUFFIX)
+
+#
+# Build types.hal (CoolingDevice)
+#
+GEN := $(intermediates)/android/hardware/thermal/1.0/CoolingDevice.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.thermal@1.0::types.CoolingDevice
+
+$(GEN): $(LOCAL_PATH)/types.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+
+#
+# Build types.hal (CoolingType)
+#
+GEN := $(intermediates)/android/hardware/thermal/1.0/CoolingType.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.thermal@1.0::types.CoolingType
+
+$(GEN): $(LOCAL_PATH)/types.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+
+#
+# Build types.hal (CpuUsage)
+#
+GEN := $(intermediates)/android/hardware/thermal/1.0/CpuUsage.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.thermal@1.0::types.CpuUsage
+
+$(GEN): $(LOCAL_PATH)/types.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+
+#
+# Build types.hal (Temperature)
+#
+GEN := $(intermediates)/android/hardware/thermal/1.0/Temperature.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.thermal@1.0::types.Temperature
+
+$(GEN): $(LOCAL_PATH)/types.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+
+#
+# Build types.hal (TemperatureType)
+#
+GEN := $(intermediates)/android/hardware/thermal/1.0/TemperatureType.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.thermal@1.0::types.TemperatureType
+
+$(GEN): $(LOCAL_PATH)/types.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+
+#
+# Build types.hal (ThermalStatus)
+#
+GEN := $(intermediates)/android/hardware/thermal/1.0/ThermalStatus.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.thermal@1.0::types.ThermalStatus
+
+$(GEN): $(LOCAL_PATH)/types.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+
+#
+# Build types.hal (ThermalStatusCode)
+#
+GEN := $(intermediates)/android/hardware/thermal/1.0/ThermalStatusCode.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.thermal@1.0::types.ThermalStatusCode
+
+$(GEN): $(LOCAL_PATH)/types.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+
+#
+# Build IThermal.hal
+#
+GEN := $(intermediates)/android/hardware/thermal/1.0/IThermal.java
+$(GEN): $(HIDL)
+$(GEN): PRIVATE_HIDL := $(HIDL)
+$(GEN): PRIVATE_DEPS := $(LOCAL_PATH)/IThermal.hal
+$(GEN): PRIVATE_DEPS += $(LOCAL_PATH)/types.hal
+$(GEN): $(LOCAL_PATH)/types.hal
+$(GEN): PRIVATE_OUTPUT_DIR := $(intermediates)
+$(GEN): PRIVATE_CUSTOM_TOOL = \
+ $(PRIVATE_HIDL) -o $(PRIVATE_OUTPUT_DIR) \
+ -Ljava -randroid.hardware:hardware/interfaces \
+ android.hardware.thermal@1.0::IThermal
+
+$(GEN): $(LOCAL_PATH)/IThermal.hal
+ $(transform-generated-source)
+LOCAL_GENERATED_SOURCES += $(GEN)
+include $(BUILD_STATIC_JAVA_LIBRARY)
+
+
+
+include $(call all-makefiles-under,$(LOCAL_PATH))
diff --git a/thermal/1.0/IThermal.hal b/thermal/1.0/IThermal.hal
new file mode 100644
index 0000000..4697f32
--- /dev/null
+++ b/thermal/1.0/IThermal.hal
@@ -0,0 +1,69 @@
+/*
+ * 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.
+ */
+
+package android.hardware.thermal@1.0;
+
+interface IThermal {
+
+ /*
+ * Retrieves temperatures in Celsius.
+ *
+ * @return status Status of the operation. If status code is FAILURE,
+ * the status.debugMessage must be populated with the human-readable
+ * error message.
+ * @return temperatures If status code is SUCCESS, it's filled with the
+ * current temperatures. The order of temperatures of built-in
+ * devices (such as CPUs, GPUs and etc.) in the list must be kept
+ * the same regardless the number of calls to this method even if
+ * they go offline, if these devices exist on boot. The method
+ * always returns and never removes such temperatures.
+ *
+ */
+ getTemperatures()
+ generates (ThermalStatus status, vec<Temperature> temperatures);
+
+ /*
+ * Retrieves CPU usage information of each core: active and total times
+ * in ms since first boot.
+ *
+ * @return status Status of the operation. If status code is FAILURE,
+ * the status.debugMessage must be populated with the human-readable
+ * error message.
+ * @return cpuUsages If status code is SUCCESS, it's filled with the current
+ * CPU usages. The order and number of CPUs in the list must be kept
+ * the same regardless the number of calls to this method.
+ *
+ */
+ getCpuUsages() generates (ThermalStatus status, vec<CpuUsage> cpuUsages);
+
+ /*
+ * Retrieves the cooling devices information.
+ *
+ * @return status Status of the operation. If status code is FAILURE,
+ * the status.debugMessage must be populated with the human-readable
+ * error message.
+ * @return devices If status code is SUCCESS, it's filled with the current
+ * cooling device information. The order of built-in coolling
+ * devices in the list must be kept the same regardless the number
+ * of calls to this method even if they go offline, if these devices
+ * exist on boot. The method always returns and never removes from
+ * the list such coolling devices.
+ *
+ */
+ getCoolingDevices()
+ generates (ThermalStatus status, vec<CoolingDevice> devices);
+
+};
diff --git a/thermal/1.0/default/Android.bp b/thermal/1.0/default/Android.bp
new file mode 100644
index 0000000..626dcaf
--- /dev/null
+++ b/thermal/1.0/default/Android.bp
@@ -0,0 +1,16 @@
+cc_library_shared {
+ name: "android.hardware.thermal@1.0-impl",
+ relative_install_path: "hw",
+ srcs: ["Thermal.cpp"],
+ shared_libs: [
+ "liblog",
+ "libcutils",
+ "libhardware",
+ "libhwbinder",
+ "libbase",
+ "libcutils",
+ "libutils",
+ "libhidl",
+ "android.hardware.thermal@1.0",
+ ],
+}
diff --git a/thermal/1.0/default/Android.mk b/thermal/1.0/default/Android.mk
new file mode 100644
index 0000000..fa7414e
--- /dev/null
+++ b/thermal/1.0/default/Android.mk
@@ -0,0 +1,39 @@
+#
+# 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.
+
+LOCAL_PATH:= $(call my-dir)
+
+include $(CLEAR_VARS)
+LOCAL_MODULE_RELATIVE_PATH := hw
+LOCAL_MODULE := android.hardware.thermal@1.0-service
+LOCAL_INIT_RC := android.hardware.thermal@1.0-service.rc
+LOCAL_SRC_FILES := \
+ service.cpp \
+
+LOCAL_SHARED_LIBRARIES := \
+ liblog \
+ libcutils \
+ libdl \
+ libbase \
+ libutils \
+ libhardware_legacy \
+ libhardware \
+
+LOCAL_SHARED_LIBRARIES += \
+ libhwbinder \
+ libhidl \
+ android.hardware.thermal@1.0 \
+
+include $(BUILD_EXECUTABLE)
diff --git a/thermal/1.0/default/Thermal.cpp b/thermal/1.0/default/Thermal.cpp
new file mode 100644
index 0000000..1b91687
--- /dev/null
+++ b/thermal/1.0/default/Thermal.cpp
@@ -0,0 +1,202 @@
+/*
+ * 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.thermal@1.0-impl"
+#include <utils/Log.h>
+
+#include <errno.h>
+#include <hardware/hardware.h>
+#include <hardware/thermal.h>
+
+#include "Thermal.h"
+
+namespace android {
+namespace hardware {
+namespace thermal {
+namespace V1_0 {
+namespace implementation {
+
+Thermal::Thermal(thermal_module_t* module) : mModule(module) {
+}
+
+// Methods from ::android::hardware::thermal::V1_0::IThermal follow.
+Return<void> Thermal::getTemperatures(getTemperatures_cb _hidl_cb) {
+ ThermalStatus status;
+ status.code = ThermalStatusCode::SUCCESS;
+ hidl_vec<Temperature> temperatures;
+
+ if (!mModule || !mModule->getTemperatures) {
+ ALOGI("getTemperatures is not implemented in Thermal HAL.");
+ _hidl_cb(status, temperatures);
+ return Void();
+ }
+
+ ssize_t list_size = mModule->getTemperatures(mModule, nullptr, 0);
+ if (list_size >= 0) {
+ temperature_t *list = new temperature_t[list_size];
+ ssize_t size = mModule->getTemperatures(mModule, list, list_size);
+ if (size >= 0) {
+ if (list_size > size) {
+ list_size = size;
+ }
+
+ temperatures.resize(list_size);
+ for (ssize_t i = 0; i < list_size; ++i) {
+ switch (list[i].type) {
+ case DEVICE_TEMPERATURE_UNKNOWN:
+ temperatures[i].type = TemperatureType::UNKNOWN;
+ break;
+ case DEVICE_TEMPERATURE_CPU:
+ temperatures[i].type = TemperatureType::CPU;
+ break;
+ case DEVICE_TEMPERATURE_GPU:
+ temperatures[i].type = TemperatureType::GPU;
+ break;
+ case DEVICE_TEMPERATURE_BATTERY:
+ temperatures[i].type = TemperatureType::BATTERY;
+ break;
+ case DEVICE_TEMPERATURE_SKIN:
+ temperatures[i].type = TemperatureType::SKIN;
+ break;
+ default:
+ ALOGE("Unknown temperature %s type", list[i].name);;
+ }
+ temperatures[i].name = list[i].name;
+ temperatures[i].currentValue = list[i].current_value;
+ temperatures[i].throttlingThreshold = list[i].throttling_threshold;
+ temperatures[i].shutdownThreshold = list[i].shutdown_threshold;
+ temperatures[i].vrThrottlingThreshold = list[i].vr_throttling_threshold;
+ }
+ } else {
+ status.code = ThermalStatusCode::FAILURE;
+ status.debugMessage = strerror(-size);
+ }
+ delete[] list;
+ } else {
+ status.code = ThermalStatusCode::FAILURE;
+ status.debugMessage = strerror(-list_size);
+ }
+ _hidl_cb(status, temperatures);
+ return Void();
+}
+
+Return<void> Thermal::getCpuUsages(getCpuUsages_cb _hidl_cb) {
+ ThermalStatus status;
+ hidl_vec<CpuUsage> cpuUsages;
+ status.code = ThermalStatusCode::SUCCESS;
+
+ if (!mModule || !mModule->getCpuUsages) {
+ ALOGI("getCpuUsages is not implemented in Thermal HAL");
+ _hidl_cb(status, cpuUsages);
+ return Void();
+ }
+
+ ssize_t size = mModule->getCpuUsages(mModule, nullptr);
+ if (size >= 0) {
+ cpu_usage_t *list = new cpu_usage_t[size];
+ size = mModule->getCpuUsages(mModule, list);
+ if (size >= 0) {
+ cpuUsages.resize(size);
+ for (ssize_t i = 0; i < size; ++i) {
+ cpuUsages[i].name = list[i].name;
+ cpuUsages[i].active = list[i].active;
+ cpuUsages[i].total = list[i].total;
+ cpuUsages[i].isOnline = list[i].is_online;
+ }
+ } else {
+ status.code = ThermalStatusCode::FAILURE;
+ status.debugMessage = strerror(-size);
+ }
+ delete[] list;
+ } else {
+ status.code = ThermalStatusCode::FAILURE;
+ status.debugMessage = strerror(-size);
+ }
+ _hidl_cb(status, cpuUsages);
+ return Void();
+}
+
+Return<void> Thermal::getCoolingDevices(getCoolingDevices_cb _hidl_cb) {
+ ThermalStatus status;
+ status.code = ThermalStatusCode::SUCCESS;
+ hidl_vec<CoolingDevice> coolingDevices;
+
+ if (!mModule || !mModule->getCoolingDevices) {
+ ALOGI("getCoolingDevices is not implemented in Thermal HAL.");
+ _hidl_cb(status, coolingDevices);
+ return Void();
+ }
+
+ ssize_t list_size = mModule->getCoolingDevices(mModule, nullptr, 0);
+ if (list_size >= 0) {
+ cooling_device_t *list = new cooling_device_t[list_size];
+ ssize_t size = mModule->getCoolingDevices(mModule, list, list_size);
+ if (size >= 0) {
+ if (list_size > size) {
+ list_size = size;
+ }
+ coolingDevices.resize(list_size);
+ for (ssize_t i = 0; i < list_size; ++i) {
+ switch (list[i].type) {
+ case FAN_RPM:
+ coolingDevices[i].type = CoolingType::FAN_RPM;
+ break;
+ default:
+ ALOGE("Unknown cooling device %s type", list[i].name);
+ }
+ coolingDevices[i].name = list[i].name;
+ coolingDevices[i].currentValue = list[i].current_value;
+ }
+
+ } else {
+ status.code = ThermalStatusCode::FAILURE;
+ status.debugMessage = strerror(-size);
+ }
+ delete[] list;
+ } else {
+ status.code = ThermalStatusCode::FAILURE;
+ status.debugMessage = strerror(-list_size);
+ }
+ _hidl_cb(status, coolingDevices);
+ return Void();
+}
+
+IThermal* HIDL_FETCH_IThermal(const char* /* name */) {
+ thermal_module_t* module;
+ status_t err = hw_get_module(THERMAL_HARDWARE_MODULE_ID,
+ const_cast<hw_module_t const**>(reinterpret_cast<hw_module_t**>(&module)));
+ if (err || !module) {
+ ALOGE("Couldn't load %s module (%s)", THERMAL_HARDWARE_MODULE_ID,
+ strerror(-err));
+ }
+
+ if (err == 0 && module->common.methods->open) {
+ struct hw_device_t* device;
+ err = module->common.methods->open(&module->common, THERMAL_HARDWARE_MODULE_ID, &device);
+ if (err) {
+ ALOGE("Couldn't open %s module (%s)", THERMAL_HARDWARE_MODULE_ID, strerror(-err));
+ } else {
+ return new Thermal(reinterpret_cast<thermal_module_t*>(device));
+ }
+ }
+ return new Thermal(module);
+}
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace thermal
+} // namespace hardware
+} // namespace android
diff --git a/thermal/1.0/default/Thermal.h b/thermal/1.0/default/Thermal.h
new file mode 100644
index 0000000..8212ab9
--- /dev/null
+++ b/thermal/1.0/default/Thermal.h
@@ -0,0 +1,45 @@
+#ifndef HIDL_GENERATED_android_hardware_thermal_V1_0_Thermal_H_
+#define HIDL_GENERATED_android_hardware_thermal_V1_0_Thermal_H_
+
+#include <android/hardware/thermal/1.0/IThermal.h>
+#include <hidl/Status.h>
+#include <hardware/thermal.h>
+
+#include <hidl/MQDescriptor.h>
+
+namespace android {
+namespace hardware {
+namespace thermal {
+namespace V1_0 {
+namespace implementation {
+
+using ::android::hardware::thermal::V1_0::CoolingDevice;
+using ::android::hardware::thermal::V1_0::CpuUsage;
+using ::android::hardware::thermal::V1_0::IThermal;
+using ::android::hardware::thermal::V1_0::Temperature;
+using ::android::hardware::thermal::V1_0::ThermalStatus;
+using ::android::hardware::Return;
+using ::android::hardware::Void;
+using ::android::hardware::hidl_vec;
+using ::android::hardware::hidl_string;
+using ::android::sp;
+
+struct Thermal : public IThermal {
+ Thermal(thermal_module_t* module);
+ // Methods from ::android::hardware::thermal::V1_0::IThermal follow.
+ Return<void> getTemperatures(getTemperatures_cb _hidl_cb) override;
+ Return<void> getCpuUsages(getCpuUsages_cb _hidl_cb) override;
+ Return<void> getCoolingDevices(getCoolingDevices_cb _hidl_cb) override;
+ private:
+ thermal_module_t* mModule;
+};
+
+extern "C" IThermal* HIDL_FETCH_IThermal(const char* name);
+
+} // namespace implementation
+} // namespace V1_0
+} // namespace thermal
+} // namespace hardware
+} // namespace android
+
+#endif // HIDL_GENERATED_android_hardware_thermal_V1_0_Thermal_H_
diff --git a/thermal/1.0/default/android.hardware.thermal@1.0-service.rc b/thermal/1.0/default/android.hardware.thermal@1.0-service.rc
new file mode 100644
index 0000000..cc7ba6a
--- /dev/null
+++ b/thermal/1.0/default/android.hardware.thermal@1.0-service.rc
@@ -0,0 +1,4 @@
+service thermal-hal-1-0 /system/bin/hw/android.hardware.thermal@1.0-service
+ class hal
+ user system
+ group system readproc
diff --git a/thermal/1.0/default/service.cpp b/thermal/1.0/default/service.cpp
new file mode 100644
index 0000000..b09b5ec
--- /dev/null
+++ b/thermal/1.0/default/service.cpp
@@ -0,0 +1,53 @@
+/*
+ * 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.
+ */
+
+#include <iostream>
+#include <unistd.h>
+
+#include <android/hardware/thermal/1.0/IThermal.h>
+
+#include <hidl/IServiceManager.h>
+#include <hwbinder/IPCThreadState.h>
+#include <hwbinder/ProcessState.h>
+#include <utils/Errors.h>
+
+#define LOG_TAG "android.hardware.thermal@1.0-service"
+#include <utils/Log.h>
+#include <utils/StrongPointer.h>
+
+using android::sp;
+
+// libhwbinder:
+using android::hardware::IPCThreadState;
+using android::hardware::ProcessState;
+
+// Generated HIDL files
+using android::hardware::thermal::V1_0::IThermal;
+
+int main() {
+ const char instance[] = "thermal";
+ sp<IThermal> service = IThermal::getService(instance, true /* getStub */);
+ if (service.get() == nullptr) {
+ ALOGE("IThermal::getService returned NULL, exiting");
+ return EXIT_FAILURE;
+ }
+ LOG_FATAL_IF(service->isRemote(), "Implementation is REMOTE!");
+ service->registerAsService(instance);
+
+ ProcessState::self()->setThreadPoolMaxThreadCount(0);
+ ProcessState::self()->startThreadPool();
+ IPCThreadState::self()->joinThreadPool();
+}
diff --git a/thermal/1.0/types.hal b/thermal/1.0/types.hal
new file mode 100644
index 0000000..b3dcc7d
--- /dev/null
+++ b/thermal/1.0/types.hal
@@ -0,0 +1,140 @@
+/*
+ * 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.
+ */
+
+package android.hardware.thermal@1.0;
+
+/** Device temperature types */
+enum TemperatureType : int32_t {
+ UNKNOWN = -1,
+ CPU = 0,
+ GPU = 1,
+ BATTERY = 2,
+ SKIN = 3,
+};
+
+enum CoolingType : int32_t {
+ /** Fan cooling device speed in RPM. */
+ FAN_RPM = 0,
+};
+
+struct Temperature {
+ /**
+ * This temperature's type.
+ */
+ TemperatureType type;
+
+ /**
+ * Name of this temperature.
+ * All temperatures of the same "type" must have a different "name",
+ * e.g., cpu0, battery.
+ */
+ string name;
+
+ /**
+ * Current temperature in Celsius. If not available set by HAL to
+ * UNKNOWN_TEMPERATURE.
+ * Current temperature can be in any units if type=UNKNOWN.
+ */
+ float currentValue;
+
+ /**
+ * Throttling temperature constant for this temperature.
+ * If not available, set by HAL to UNKNOWN_TEMPERATURE.
+ */
+ float throttlingThreshold;
+
+ /**
+ * Shutdown temperature constant for this temperature.
+ * If not available, set by HAL to UNKNOWN_TEMPERATURE.
+ */
+ float shutdownThreshold;
+
+ /**
+ * Threshold temperature above which the VR mode clockrate minimums cannot
+ * be maintained for this device.
+ * If not available, set by HAL to UNKNOWN_TEMPERATURE.
+ */
+ float vrThrottlingThreshold;
+
+};
+
+struct CoolingDevice {
+ /**
+ * This cooling device type.
+ */
+ CoolingType type;
+
+ /**
+ * Name of this cooling device.
+ * All cooling devices of the same "type" must have a different "name".
+ */
+ string name;
+
+ /**
+ * Current cooling device value. Units depend on cooling device "type".
+ */
+ float currentValue;
+
+};
+
+struct CpuUsage {
+ /**
+ * Name of this CPU.
+ * All CPUs must have a different "name".
+ */
+ string name;
+
+ /**
+ * Active time since the last boot in ms.
+ */
+ uint64_t active;
+
+ /**
+ * Total time since the last boot in ms.
+ */
+ uint64_t total;
+
+ /**
+ * Is set to true when a core is online.
+ * If the core is offline, all other members except |name| should be ignored.
+ */
+ bool isOnline;
+
+};
+
+enum ThermalStatusCode : uint32_t {
+ /** No errors. */
+ SUCCESS,
+ /** Unknown failure occured. */
+ FAILURE
+};
+
+/**
+ * Generic structure to return the status of any thermal operation.
+ */
+struct ThermalStatus {
+ ThermalStatusCode code;
+
+ /**
+ * A specific error message to provide more information.
+ * This can be used for debugging purposes only.
+ */
+ string debugMessage;
+};
+
+/**
+ * TODO(pbond): add float constant UNDEFINED_TEMPERATURE.
+ */