From ce27e8ffaca5cb7ffda94797116a895172a94ca5 Mon Sep 17 00:00:00 2001 From: kuailexs <952415538@qq.com> Date: Thu, 11 Apr 2024 00:49:37 +0800 Subject: [PATCH] Arian los21 patches --- ...date-sepolicy-for-health-HAL-service.patch | 43 ++ ...ra-Wideband-icon-carrier-config-keys.patch | 116 ++++ ...es-for-5G-Ultra-Wideband-icon-carrie.patch | 39 ++ .../0001-Add-dummy-sensors-sub-HAL.patch | 620 ++++++++++++++++++ ...s-Make-sensor-batch-function-virtual.patch | 26 + ...ors-Make-sensor-run-function-virtual.patch | 26 + ...s-Make-sensor-flush-function-virtual.patch | 26 + ...sor-set-mode-operation-function-virt.patch | 27 + ...ve-one-shot-sensor-out-of-main-class.patch | 61 ++ ...ing-around-setOperationMode-and-acti.patch | 38 ++ ...-sensors-Add-udfps-long-press-sensor.patch | 239 +++++++ ...fod-press-status-without-coordinates.patch | 35 + ...fingerprint-Add-enroll-methods-to-ud.patch | 61 ++ patch.sh | 27 + repopicks.sh | 46 ++ ...tbs-Respect-miboard-id-while-merging.patch | 204 ++++++ 16 files changed, 1634 insertions(+) create mode 100644 device/qcom/sepolicy_vndr/sm8450/0001-sepolicy_vndr-update-sepolicy-for-health-HAL-service.patch create mode 100644 frameworks/base/0001-Add-5G-Ultra-Wideband-icon-carrier-config-keys.patch create mode 100644 frameworks/base/0002-Fix-default-values-for-5G-Ultra-Wideband-icon-carrie.patch create mode 100644 hardware/xiaomi/0001-Add-dummy-sensors-sub-HAL.patch create mode 100644 hardware/xiaomi/0002-sensors-Make-sensor-batch-function-virtual.patch create mode 100644 hardware/xiaomi/0003-sensors-Make-sensor-run-function-virtual.patch create mode 100644 hardware/xiaomi/0004-sensors-Make-sensor-flush-function-virtual.patch create mode 100644 hardware/xiaomi/0005-sensors-Make-sensor-set-mode-operation-function-virt.patch create mode 100644 hardware/xiaomi/0006-sensors-Move-one-shot-sensor-out-of-main-class.patch create mode 100644 hardware/xiaomi/0007-sensors-Fix-locking-around-setOperationMode-and-acti.patch create mode 100644 hardware/xiaomi/0008-sensors-Add-udfps-long-press-sensor.patch create mode 100644 hardware/xiaomi/0009-sensors-Handle-fod-press-status-without-coordinates.patch create mode 100644 hardware/xiaomi/0010-hidl-biometrics-fingerprint-Add-enroll-methods-to-ud.patch create mode 100644 patch.sh create mode 100644 repopicks.sh create mode 100644 vendor/lineage/0001-android-merge_dtbs-Respect-miboard-id-while-merging.patch diff --git a/device/qcom/sepolicy_vndr/sm8450/0001-sepolicy_vndr-update-sepolicy-for-health-HAL-service.patch b/device/qcom/sepolicy_vndr/sm8450/0001-sepolicy_vndr-update-sepolicy-for-health-HAL-service.patch new file mode 100644 index 0000000..d834eb4 --- /dev/null +++ b/device/qcom/sepolicy_vndr/sm8450/0001-sepolicy_vndr-update-sepolicy-for-health-HAL-service.patch @@ -0,0 +1,43 @@ +From 7381bc84b63f27e923a4478707f738d20e628645 Mon Sep 17 00:00:00 2001 +From: Fenglin Wu +Date: Thu, 23 Jun 2022 16:40:50 +0800 +Subject: [PATCH] sepolicy_vndr: update sepolicy for health HAL service + +Add label for QTI health AIDL HAL service and add policy for it to +access power supply devices. + +Change-Id: I17d6c274e3e5fc76ca07019fe2e404c7c5171e57 +--- + qva/vendor/common/file_contexts | 1 + + qva/vendor/common/hal_health.te | 7 +++++++ + 2 files changed, 8 insertions(+) + create mode 100644 qva/vendor/common/hal_health.te + +diff --git a/qva/vendor/common/file_contexts b/qva/vendor/common/file_contexts +index b076001cb..d0088e5a4 100644 +--- a/qva/vendor/common/file_contexts ++++ b/qva/vendor/common/file_contexts +@@ -105,6 +105,7 @@ + /(vendor|system/vendor)/bin/hw/vendor\.qti\.hardware\.soter@1\.0-service u:object_r:vendor_hal_soter_qti_exec:s0 + /vendor/bin/hw/vendor\.qti\.hardware\.vibrator@1\.[0-3]-service u:object_r:hal_vibrator_default_exec:s0 + /vendor/bin/hw/vendor\.qti\.hardware\.vibrator\.service u:object_r:hal_vibrator_default_exec:s0 ++/vendor/bin/hw/android\.hardware\.health-service\.qti u:object_r:hal_health_default_exec:s0 + /(vendor|system/vendor)/bin/hw/vendor\.qti\.power\.pasrmanager\@1\.0-service u:object_r:vendor_hal_pasrmanager_qti_exec:s0 + /(vendor|system/vendor)/bin/hw/vendor\.qti\.memory\.pasrmanager\@1\.0-service u:object_r:vendor_pasrmanager_memory_qti_exec:s0 + /(vendor|system/vendor)/bin/hw/vendor\.qti\.psiclient\@1\.0-service u:object_r:vendor_psiservice_exec:s0 +diff --git a/qva/vendor/common/hal_health.te b/qva/vendor/common/hal_health.te +new file mode 100644 +index 000000000..13e48238a +--- /dev/null ++++ b/qva/vendor/common/hal_health.te +@@ -0,0 +1,7 @@ ++# Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved. ++# SPDX-License-Identifier: BSD-3-Clause-Clear ++ ++allow hal_health vendor_sysfs_battery_supply:{file lnk_file} r_file_perms; ++allow hal_health vendor_sysfs_battery_supply:dir r_dir_perms; ++allow hal_health vendor_sysfs_usb_supply:{file lnk_file} r_file_perms; ++allow hal_health vendor_sysfs_usb_supply:dir r_dir_perms; +-- +2.25.1 + diff --git a/frameworks/base/0001-Add-5G-Ultra-Wideband-icon-carrier-config-keys.patch b/frameworks/base/0001-Add-5G-Ultra-Wideband-icon-carrier-config-keys.patch new file mode 100644 index 0000000..adca4be --- /dev/null +++ b/frameworks/base/0001-Add-5G-Ultra-Wideband-icon-carrier-config-keys.patch @@ -0,0 +1,116 @@ +From d019a2cf56c0c25c2e99caa79c42e18c4e18ae00 Mon Sep 17 00:00:00 2001 +From: Vala Zadeh +Date: Wed, 18 May 2022 16:57:43 -0700 +Subject: [PATCH 1/2] Add 5G Ultra Wideband icon carrier config keys + +Change-Id: Idc6da92fb41a780d01c961d676f61ae4b91d2a7b +CRs-Fixed: 3218447 +--- + .../telephony/CarrierConfigManager.java | 84 +++++++++++++++++++ + 1 file changed, 84 insertions(+) + +diff --git a/telephony/java/android/telephony/CarrierConfigManager.java b/telephony/java/android/telephony/CarrierConfigManager.java +index 7cb2cc398c46..570ee2aa8628 100644 +--- a/telephony/java/android/telephony/CarrierConfigManager.java ++++ b/telephony/java/android/telephony/CarrierConfigManager.java +@@ -10038,6 +10038,81 @@ public class CarrierConfigManager { + public static final String KEY_AUTO_DATA_SWITCH_RAT_SIGNAL_SCORE_BUNDLE = + "auto_data_switch_rat_signal_score_string_bundle"; + ++ /** ++ * Determines the SIB2 value for showing the 5G Ultra Wideband icon. ++ * The rest of the NR Ultra Wideband configs will be considere only if this value is 1. A value ++ * of 0 means the other NR Ultra Wideband configs will not be considered. ++ * ++ * @hide ++ */ ++ public static final String KEY_NR_ULTRA_WIDEBAND_ICON_SIB2_VALUE = ++ "5g_ultra_wideband_icon_sib2_value"; ++ ++ /** ++ * Determines the minimum aggregate bandwidth for showing the 5G Ultra Wideband icon. ++ * ++ * @hide ++ */ ++ public static final String KEY_NR_ULTRA_WIDEBAND_ICON_MIN_BANDWIDTH_VALUE = ++ "5g_ultra_wideband_icon_min_bandwidth_value"; ++ ++ /** ++ * Determines the minimum aggregate bandwidth mode for which the 5G Ultra Wideband icon will be ++ * shown. The following modes are allowed: NONE, CONNECTED, IDLE, CONNECTED_AND_IDLE ++ * ++ * @hide ++ */ ++ public static final String KEY_NR_ULTRA_WIDEBAND_ICON_MIN_BANDWIDTH_MODE = ++ "5g_ultra_wideband_icon_min_bandwidth_mode"; ++ ++ /** ++ * Determines the 5G Ultra Wideband icon refresh timer type (key) and the refresh timer value ++ * (value) in seconds. ++ * The following types are allowed for the type: SCG_TO_MCG, IDLE_TO_CONNECT, IDLE ++ * ++ * @hide ++ */ ++ public static final String KEY_NR_ULTRA_WIDEBAND_ICON_REFRESH_TIMER_MAP = ++ "5g_ultra_wideband_icon_refresh_timer_map"; ++ ++ /** ++ * Determines the mode in which the 5G Ultra Wideband icon will be shown for 5G NSA bands. ++ * The following modes are allowed: NONE, CONNECTED, IDLE, CONNECTED_AND_IDLE ++ * ++ * @hide ++ */ ++ public static final String KEY_NR_ULTRA_WIDEBAND_ICON_NSA_BAND_MODE = ++ "5g_ultra_wideband_icon_nsa_band_mode"; ++ ++ /** ++ * Determines the list of 5G NSA bands for which 5G Ultra Wideband icons must be shown. ++ * For each list entry, the allowed values are either enabled (show the 5G Ultra Wideband icon) ++ * or disabled (do not show the 5G Ultra Wideband icon). ++ * ++ * @hide ++ */ ++ public static final String KEY_NR_ULTRA_WIDEBAND_ICON_NSA_BAND_ARRAY = ++ "5g_ultra_wideband_icon_nsa_band_array"; ++ ++ /** ++ * Determines the mode in which the 5G Ultra Wideband icon will be shown for 5G SA bands. ++ * The following modes are allowed: NONE, CONNECTED, IDLE, CONNECTED_AND_IDLE ++ * ++ * @hide ++ */ ++ public static final String KEY_NR_ULTRA_WIDEBAND_ICON_SA_BAND_MODE = ++ "5g_ultra_wideband_icon_sa_band_mode"; ++ ++ /** ++ * Determines the list of 5G SA bands for which 5G Ultra Wideband icons must be shown. ++ * For each list entry, the allowed values are either enabled (show the 5G Ultra Wideband icon) ++ * or disabled (do not show the 5G Ultra Wideband icon). ++ * ++ * @hide ++ */ ++ public static final String KEY_NR_ULTRA_WIDEBAND_ICON_SA_BAND_ARRAY = ++ "5g_ultra_wideband_icon_sa_band_array"; ++ + /** The default value for every variable. */ + private static final PersistableBundle sDefaults; + +@@ -10671,6 +10746,15 @@ public class CarrierConfigManager { + "enterprise:0", "default:1", "mms:2", "supl:2", "dun:2", "hipri:3", "fota:2", + "ims:2", "cbs:2", "ia:2", "emergency:2", "mcx:3", "xcap:3" + }); ++ sDefaults.putInt(KEY_NR_ULTRA_WIDEBAND_ICON_SIB2_VALUE, -1); ++ sDefaults.putInt(KEY_NR_ULTRA_WIDEBAND_ICON_MIN_BANDWIDTH_VALUE, 0); ++ sDefaults.putInt(KEY_NR_ULTRA_WIDEBAND_ICON_MIN_BANDWIDTH_MODE, 0); ++ sDefaults.putPersistableBundle(KEY_NR_ULTRA_WIDEBAND_ICON_REFRESH_TIMER_MAP, ++ PersistableBundle.EMPTY); ++ sDefaults.putInt(KEY_NR_ULTRA_WIDEBAND_ICON_NSA_BAND_MODE, 0); ++ sDefaults.putIntArray(KEY_NR_ULTRA_WIDEBAND_ICON_SA_BAND_ARRAY, new int[]{}); ++ sDefaults.putInt(KEY_NR_ULTRA_WIDEBAND_ICON_SA_BAND_MODE, 0); ++ sDefaults.putIntArray(KEY_NR_ULTRA_WIDEBAND_ICON_NSA_BAND_ARRAY, new int[]{}); + + // Do not modify the priority unless you know what you are doing. This will have significant + // impacts on the order of data network setup. +-- +2.25.1 + diff --git a/frameworks/base/0002-Fix-default-values-for-5G-Ultra-Wideband-icon-carrie.patch b/frameworks/base/0002-Fix-default-values-for-5G-Ultra-Wideband-icon-carrie.patch new file mode 100644 index 0000000..b9f741a --- /dev/null +++ b/frameworks/base/0002-Fix-default-values-for-5G-Ultra-Wideband-icon-carrie.patch @@ -0,0 +1,39 @@ +From 3d887846df2b6ff5c4330118a81d99708607032c Mon Sep 17 00:00:00 2001 +From: Vala Zadeh +Date: Wed, 22 Jun 2022 16:39:27 -0700 +Subject: [PATCH 2/2] Fix default values for 5G Ultra Wideband icon carrier + config keys + +Change-Id: Ie143a0489163177d3be3e0de280bc3ed0d017437 +CRs-Fixed: 3218447 +--- + .../java/android/telephony/CarrierConfigManager.java | 10 +++++----- + 1 file changed, 5 insertions(+), 5 deletions(-) + +diff --git a/telephony/java/android/telephony/CarrierConfigManager.java b/telephony/java/android/telephony/CarrierConfigManager.java +index 570ee2aa8628..c09eaab59da5 100644 +--- a/telephony/java/android/telephony/CarrierConfigManager.java ++++ b/telephony/java/android/telephony/CarrierConfigManager.java +@@ -10746,14 +10746,14 @@ public class CarrierConfigManager { + "enterprise:0", "default:1", "mms:2", "supl:2", "dun:2", "hipri:3", "fota:2", + "ims:2", "cbs:2", "ia:2", "emergency:2", "mcx:3", "xcap:3" + }); +- sDefaults.putInt(KEY_NR_ULTRA_WIDEBAND_ICON_SIB2_VALUE, -1); +- sDefaults.putInt(KEY_NR_ULTRA_WIDEBAND_ICON_MIN_BANDWIDTH_VALUE, 0); +- sDefaults.putInt(KEY_NR_ULTRA_WIDEBAND_ICON_MIN_BANDWIDTH_MODE, 0); ++ sDefaults.putInt(KEY_NR_ULTRA_WIDEBAND_ICON_SIB2_VALUE, Integer.MAX_VALUE); ++ sDefaults.putInt(KEY_NR_ULTRA_WIDEBAND_ICON_MIN_BANDWIDTH_VALUE, Integer.MAX_VALUE); ++ sDefaults.putInt(KEY_NR_ULTRA_WIDEBAND_ICON_MIN_BANDWIDTH_MODE, Integer.MAX_VALUE); + sDefaults.putPersistableBundle(KEY_NR_ULTRA_WIDEBAND_ICON_REFRESH_TIMER_MAP, + PersistableBundle.EMPTY); +- sDefaults.putInt(KEY_NR_ULTRA_WIDEBAND_ICON_NSA_BAND_MODE, 0); ++ sDefaults.putInt(KEY_NR_ULTRA_WIDEBAND_ICON_NSA_BAND_MODE, Integer.MAX_VALUE); + sDefaults.putIntArray(KEY_NR_ULTRA_WIDEBAND_ICON_SA_BAND_ARRAY, new int[]{}); +- sDefaults.putInt(KEY_NR_ULTRA_WIDEBAND_ICON_SA_BAND_MODE, 0); ++ sDefaults.putInt(KEY_NR_ULTRA_WIDEBAND_ICON_SA_BAND_MODE, Integer.MAX_VALUE); + sDefaults.putIntArray(KEY_NR_ULTRA_WIDEBAND_ICON_NSA_BAND_ARRAY, new int[]{}); + + // Do not modify the priority unless you know what you are doing. This will have significant +-- +2.25.1 + diff --git a/hardware/xiaomi/0001-Add-dummy-sensors-sub-HAL.patch b/hardware/xiaomi/0001-Add-dummy-sensors-sub-HAL.patch new file mode 100644 index 0000000..600b5b9 --- /dev/null +++ b/hardware/xiaomi/0001-Add-dummy-sensors-sub-HAL.patch @@ -0,0 +1,620 @@ +From 2843c0313a8b5f82fa54b344f3f01cc668db4fe5 Mon Sep 17 00:00:00 2001 +From: Cosmin Tanislav +Date: Wed, 16 Feb 2022 22:14:58 +0200 +Subject: [PATCH 01/10] Add dummy sensors sub HAL + +Change-Id: Ie20ed775344990de3e16e2eefba1754d831027fb +--- + sensors/Android.bp | 30 ++++++ + sensors/Sensor.cpp | 192 ++++++++++++++++++++++++++++++++++++++ + sensors/Sensor.h | 87 +++++++++++++++++ + sensors/SensorsSubHal.cpp | 160 +++++++++++++++++++++++++++++++ + sensors/SensorsSubHal.h | 95 +++++++++++++++++++ + 5 files changed, 564 insertions(+) + create mode 100644 sensors/Sensor.cpp + create mode 100644 sensors/Sensor.h + create mode 100644 sensors/SensorsSubHal.cpp + create mode 100644 sensors/SensorsSubHal.h + +diff --git a/sensors/Android.bp b/sensors/Android.bp +index c897399..d9b1ddc 100644 +--- a/sensors/Android.bp ++++ b/sensors/Android.bp +@@ -4,6 +4,36 @@ + // SPDX-License-Identifier: Apache-2.0 + // + ++cc_library_shared { ++ name: "sensors.xiaomi", ++ defaults: ["hidl_defaults"], ++ srcs: [ ++ "Sensor.cpp", ++ "SensorsSubHal.cpp", ++ ], ++ shared_libs: [ ++ "android.hardware.sensors@1.0", ++ "android.hardware.sensors@2.0", ++ "android.hardware.sensors@2.0-ScopedWakelock", ++ "android.hardware.sensors@2.1", ++ "libcutils", ++ "libfmq", ++ "libhardware", ++ "libhidlbase", ++ "liblog", ++ "libpower", ++ "libutils", ++ ], ++ static_libs: [ ++ "android.hardware.sensors@1.0-convert", ++ "android.hardware.sensors@2.X-multihal", ++ ], ++ cflags: [ ++ "-DLOG_TAG=\"sensors.xiaomi\"", ++ ], ++ vendor: true, ++} ++ + cc_library_shared { + name: "sensors.udfps", + defaults: ["hidl_defaults"], +diff --git a/sensors/Sensor.cpp b/sensors/Sensor.cpp +new file mode 100644 +index 0000000..446a7e9 +--- /dev/null ++++ b/sensors/Sensor.cpp +@@ -0,0 +1,192 @@ ++/* ++ * Copyright (C) 2019 The Android Open Source Project ++ * ++ * Licensed under the Apache License, Version 2.0 (the "License"); ++ * you may not use this file except in compliance with the License. ++ * You may obtain a copy of the License at ++ * ++ * http://www.apache.org/licenses/LICENSE-2.0 ++ * ++ * Unless required by applicable law or agreed to in writing, software ++ * distributed under the License is distributed on an "AS IS" BASIS, ++ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. ++ * See the License for the specific language governing permissions and ++ * limitations under the License. ++ */ ++ ++#include "Sensor.h" ++ ++#include ++#include ++ ++#include ++ ++namespace android { ++namespace hardware { ++namespace sensors { ++namespace V2_1 { ++namespace subhal { ++namespace implementation { ++ ++using ::android::hardware::sensors::V1_0::MetaDataEventType; ++using ::android::hardware::sensors::V1_0::OperationMode; ++using ::android::hardware::sensors::V1_0::Result; ++using ::android::hardware::sensors::V1_0::SensorFlagBits; ++using ::android::hardware::sensors::V1_0::SensorStatus; ++using ::android::hardware::sensors::V2_1::Event; ++using ::android::hardware::sensors::V2_1::SensorInfo; ++using ::android::hardware::sensors::V2_1::SensorType; ++ ++Sensor::Sensor(int32_t sensorHandle, ISensorsEventCallback* callback) ++ : mIsEnabled(false), ++ mSamplingPeriodNs(0), ++ mLastSampleTimeNs(0), ++ mCallback(callback), ++ mMode(OperationMode::NORMAL) { ++ mSensorInfo.sensorHandle = sensorHandle; ++ mSensorInfo.vendor = "The LineageOS Project"; ++ mSensorInfo.version = 1; ++ constexpr float kDefaultMaxDelayUs = 1000 * 1000; ++ mSensorInfo.maxDelay = kDefaultMaxDelayUs; ++ mSensorInfo.fifoReservedEventCount = 0; ++ mSensorInfo.fifoMaxEventCount = 0; ++ mSensorInfo.requiredPermission = ""; ++ mSensorInfo.flags = 0; ++ mRunThread = std::thread(startThread, this); ++} ++ ++Sensor::~Sensor() { ++ // Ensure that lock is unlocked before calling mRunThread.join() or a ++ // deadlock will occur. ++ { ++ std::unique_lock lock(mRunMutex); ++ mStopThread = true; ++ mIsEnabled = false; ++ mWaitCV.notify_all(); ++ } ++ mRunThread.join(); ++} ++ ++const SensorInfo& Sensor::getSensorInfo() const { ++ return mSensorInfo; ++} ++ ++void Sensor::batch(int32_t samplingPeriodNs) { ++ samplingPeriodNs = ++ std::clamp(samplingPeriodNs, mSensorInfo.minDelay * 1000, mSensorInfo.maxDelay * 1000); ++ ++ if (mSamplingPeriodNs != samplingPeriodNs) { ++ mSamplingPeriodNs = samplingPeriodNs; ++ // Wake up the 'run' thread to check if a new event should be generated now ++ mWaitCV.notify_all(); ++ } ++} ++ ++void Sensor::activate(bool enable) { ++ if (mIsEnabled != enable) { ++ std::unique_lock lock(mRunMutex); ++ mIsEnabled = enable; ++ mWaitCV.notify_all(); ++ } ++} ++ ++Result Sensor::flush() { ++ // Only generate a flush complete event if the sensor is enabled and if the sensor is not a ++ // one-shot sensor. ++ if (!mIsEnabled || (mSensorInfo.flags & static_cast(SensorFlagBits::ONE_SHOT_MODE))) { ++ return Result::BAD_VALUE; ++ } ++ ++ // Note: If a sensor supports batching, write all of the currently batched events for the sensor ++ // to the Event FMQ prior to writing the flush complete event. ++ Event ev; ++ ev.sensorHandle = mSensorInfo.sensorHandle; ++ ev.sensorType = SensorType::META_DATA; ++ ev.u.meta.what = MetaDataEventType::META_DATA_FLUSH_COMPLETE; ++ std::vector evs{ev}; ++ mCallback->postEvents(evs, isWakeUpSensor()); ++ ++ return Result::OK; ++} ++ ++void Sensor::startThread(Sensor* sensor) { ++ sensor->run(); ++} ++ ++void Sensor::run() { ++ std::unique_lock runLock(mRunMutex); ++ constexpr int64_t kNanosecondsInSeconds = 1000 * 1000 * 1000; ++ ++ while (!mStopThread) { ++ if (!mIsEnabled || mMode == OperationMode::DATA_INJECTION) { ++ mWaitCV.wait(runLock, [&] { ++ return ((mIsEnabled && mMode == OperationMode::NORMAL) || mStopThread); ++ }); ++ } else { ++ timespec curTime; ++ clock_gettime(CLOCK_REALTIME, &curTime); ++ int64_t now = (curTime.tv_sec * kNanosecondsInSeconds) + curTime.tv_nsec; ++ int64_t nextSampleTime = mLastSampleTimeNs + mSamplingPeriodNs; ++ ++ if (now >= nextSampleTime) { ++ mLastSampleTimeNs = now; ++ nextSampleTime = mLastSampleTimeNs + mSamplingPeriodNs; ++ mCallback->postEvents(readEvents(), isWakeUpSensor()); ++ } ++ ++ mWaitCV.wait_for(runLock, std::chrono::nanoseconds(nextSampleTime - now)); ++ } ++ } ++} ++ ++bool Sensor::isWakeUpSensor() { ++ return mSensorInfo.flags & static_cast(SensorFlagBits::WAKE_UP); ++} ++ ++std::vector Sensor::readEvents() { ++ std::vector events; ++ Event event; ++ event.sensorHandle = mSensorInfo.sensorHandle; ++ event.sensorType = mSensorInfo.type; ++ event.timestamp = ::android::elapsedRealtimeNano(); ++ event.u.vec3.x = 0; ++ event.u.vec3.y = 0; ++ event.u.vec3.z = 0; ++ event.u.vec3.status = SensorStatus::ACCURACY_HIGH; ++ events.push_back(event); ++ return events; ++} ++ ++void Sensor::setOperationMode(OperationMode mode) { ++ if (mMode != mode) { ++ std::unique_lock lock(mRunMutex); ++ mMode = mode; ++ mWaitCV.notify_all(); ++ } ++} ++ ++bool Sensor::supportsDataInjection() const { ++ return mSensorInfo.flags & static_cast(SensorFlagBits::DATA_INJECTION); ++} ++ ++Result Sensor::injectEvent(const Event& event) { ++ Result result = Result::OK; ++ if (event.sensorType == SensorType::ADDITIONAL_INFO) { ++ // When in OperationMode::NORMAL, SensorType::ADDITIONAL_INFO is used to push operation ++ // environment data into the device. ++ } else if (!supportsDataInjection()) { ++ result = Result::INVALID_OPERATION; ++ } else if (mMode == OperationMode::DATA_INJECTION) { ++ mCallback->postEvents(std::vector{event}, isWakeUpSensor()); ++ } else { ++ result = Result::BAD_VALUE; ++ } ++ return result; ++} ++ ++} // namespace implementation ++} // namespace subhal ++} // namespace V2_1 ++} // namespace sensors ++} // namespace hardware ++} // namespace android +diff --git a/sensors/Sensor.h b/sensors/Sensor.h +new file mode 100644 +index 0000000..7923820 +--- /dev/null ++++ b/sensors/Sensor.h +@@ -0,0 +1,87 @@ ++/* ++ * Copyright (C) 2019 The Android Open Source Project ++ * ++ * Licensed under the Apache License, Version 2.0 (the "License"); ++ * you may not use this file except in compliance with the License. ++ * You may obtain a copy of the License at ++ * ++ * http://www.apache.org/licenses/LICENSE-2.0 ++ * ++ * Unless required by applicable law or agreed to in writing, software ++ * distributed under the License is distributed on an "AS IS" BASIS, ++ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. ++ * See the License for the specific language governing permissions and ++ * limitations under the License. ++ */ ++ ++#pragma once ++ ++#include ++ ++#include ++#include ++#include ++#include ++#include ++ ++using ::android::hardware::sensors::V1_0::OperationMode; ++using ::android::hardware::sensors::V1_0::Result; ++using ::android::hardware::sensors::V2_1::Event; ++using ::android::hardware::sensors::V2_1::SensorInfo; ++using ::android::hardware::sensors::V2_1::SensorType; ++ ++namespace android { ++namespace hardware { ++namespace sensors { ++namespace V2_1 { ++namespace subhal { ++namespace implementation { ++ ++class ISensorsEventCallback { ++ public: ++ virtual ~ISensorsEventCallback(){}; ++ virtual void postEvents(const std::vector& events, bool wakeup) = 0; ++}; ++ ++class Sensor { ++ public: ++ Sensor(int32_t sensorHandle, ISensorsEventCallback* callback); ++ virtual ~Sensor(); ++ ++ const SensorInfo& getSensorInfo() const; ++ void batch(int32_t samplingPeriodNs); ++ virtual void activate(bool enable); ++ Result flush(); ++ ++ void setOperationMode(OperationMode mode); ++ bool supportsDataInjection() const; ++ Result injectEvent(const Event& event); ++ ++ protected: ++ void run(); ++ virtual std::vector readEvents(); ++ static void startThread(Sensor* sensor); ++ ++ bool isWakeUpSensor(); ++ ++ bool mIsEnabled; ++ int64_t mSamplingPeriodNs; ++ int64_t mLastSampleTimeNs; ++ SensorInfo mSensorInfo; ++ ++ std::atomic_bool mStopThread; ++ std::condition_variable mWaitCV; ++ std::mutex mRunMutex; ++ std::thread mRunThread; ++ ++ ISensorsEventCallback* mCallback; ++ ++ OperationMode mMode; ++}; ++ ++} // namespace implementation ++} // namespace subhal ++} // namespace V2_1 ++} // namespace sensors ++} // namespace hardware ++} // namespace android +diff --git a/sensors/SensorsSubHal.cpp b/sensors/SensorsSubHal.cpp +new file mode 100644 +index 0000000..6cbcb56 +--- /dev/null ++++ b/sensors/SensorsSubHal.cpp +@@ -0,0 +1,160 @@ ++/* ++ * Copyright (C) 2019 The Android Open Source Project ++ * ++ * Licensed under the Apache License, Version 2.0 (the "License"); ++ * you may not use this file except in compliance with the License. ++ * You may obtain a copy of the License at ++ * ++ * http://www.apache.org/licenses/LICENSE-2.0 ++ * ++ * Unless required by applicable law or agreed to in writing, software ++ * distributed under the License is distributed on an "AS IS" BASIS, ++ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. ++ * See the License for the specific language governing permissions and ++ * limitations under the License. ++ */ ++ ++#include "SensorsSubHal.h" ++ ++#include ++#include ++ ++using ::android::hardware::sensors::V2_1::implementation::ISensorsSubHal; ++using ::android::hardware::sensors::V2_1::subhal::implementation::SensorsSubHal; ++ ++namespace android { ++namespace hardware { ++namespace sensors { ++namespace V2_1 { ++namespace subhal { ++namespace implementation { ++ ++using ::android::hardware::Void; ++using ::android::hardware::sensors::V2_0::implementation::ScopedWakelock; ++ ++SensorsSubHal::SensorsSubHal() : mCallback(nullptr), mNextHandle(1) {} ++ ++Return SensorsSubHal::getSensorsList_2_1(ISensors::getSensorsList_2_1_cb _hidl_cb) { ++ std::vector sensors; ++ for (const auto& sensor : mSensors) { ++ sensors.push_back(sensor.second->getSensorInfo()); ++ } ++ _hidl_cb(sensors); ++ return Void(); ++} ++ ++Return SensorsSubHal::setOperationMode(OperationMode mode) { ++ for (auto sensor : mSensors) { ++ sensor.second->setOperationMode(mode); ++ } ++ mCurrentOperationMode = mode; ++ return Result::OK; ++} ++ ++Return SensorsSubHal::activate(int32_t sensorHandle, bool enabled) { ++ auto sensor = mSensors.find(sensorHandle); ++ if (sensor != mSensors.end()) { ++ sensor->second->activate(enabled); ++ return Result::OK; ++ } ++ return Result::BAD_VALUE; ++} ++ ++Return SensorsSubHal::batch(int32_t sensorHandle, int64_t samplingPeriodNs, ++ int64_t /* maxReportLatencyNs */) { ++ auto sensor = mSensors.find(sensorHandle); ++ if (sensor != mSensors.end()) { ++ sensor->second->batch(samplingPeriodNs); ++ return Result::OK; ++ } ++ return Result::BAD_VALUE; ++} ++ ++Return SensorsSubHal::flush(int32_t sensorHandle) { ++ auto sensor = mSensors.find(sensorHandle); ++ if (sensor != mSensors.end()) { ++ return sensor->second->flush(); ++ } ++ return Result::BAD_VALUE; ++} ++ ++Return SensorsSubHal::injectSensorData_2_1(const Event& event) { ++ auto sensor = mSensors.find(event.sensorHandle); ++ if (sensor != mSensors.end()) { ++ return sensor->second->injectEvent(event); ++ } ++ ++ return Result::BAD_VALUE; ++} ++ ++Return SensorsSubHal::registerDirectChannel(const SharedMemInfo& /* mem */, ++ ISensors::registerDirectChannel_cb _hidl_cb) { ++ _hidl_cb(Result::INVALID_OPERATION, -1 /* channelHandle */); ++ return Return(); ++} ++ ++Return SensorsSubHal::unregisterDirectChannel(int32_t /* channelHandle */) { ++ return Result::INVALID_OPERATION; ++} ++ ++Return SensorsSubHal::configDirectReport(int32_t /* sensorHandle */, ++ int32_t /* channelHandle */, RateLevel /* rate */, ++ ISensors::configDirectReport_cb _hidl_cb) { ++ _hidl_cb(Result::INVALID_OPERATION, 0 /* reportToken */); ++ return Return(); ++} ++ ++Return SensorsSubHal::debug(const hidl_handle& fd, const hidl_vec& args) { ++ if (fd.getNativeHandle() == nullptr || fd->numFds < 1) { ++ ALOGE("%s: missing fd for writing", __FUNCTION__); ++ return Void(); ++ } ++ ++ FILE* out = fdopen(dup(fd->data[0]), "w"); ++ ++ if (args.size() != 0) { ++ fprintf(out, ++ "Note: sub-HAL %s currently does not support args. Input arguments are " ++ "ignored.\n", ++ getName().c_str()); ++ } ++ ++ std::ostringstream stream; ++ stream << "Available sensors:" << std::endl; ++ for (auto sensor : mSensors) { ++ SensorInfo info = sensor.second->getSensorInfo(); ++ stream << "Name: " << info.name << std::endl; ++ stream << "Min delay: " << info.minDelay << std::endl; ++ stream << "Flags: " << info.flags << std::endl; ++ } ++ stream << std::endl; ++ ++ fprintf(out, "%s", stream.str().c_str()); ++ ++ fclose(out); ++ return Return(); ++} ++ ++Return SensorsSubHal::initialize(const sp& halProxyCallback) { ++ mCallback = halProxyCallback; ++ setOperationMode(OperationMode::NORMAL); ++ return Result::OK; ++} ++ ++void SensorsSubHal::postEvents(const std::vector& events, bool wakeup) { ++ ScopedWakelock wakelock = mCallback->createScopedWakelock(wakeup); ++ mCallback->postEvents(events, std::move(wakelock)); ++} ++ ++} // namespace implementation ++} // namespace subhal ++} // namespace V2_1 ++} // namespace sensors ++} // namespace hardware ++} // namespace android ++ ++ISensorsSubHal* sensorsHalGetSubHal_2_1(uint32_t* version) { ++ static SensorsSubHal subHal; ++ *version = SUB_HAL_2_1_VERSION; ++ return &subHal; ++} +diff --git a/sensors/SensorsSubHal.h b/sensors/SensorsSubHal.h +new file mode 100644 +index 0000000..7ac9ac2 +--- /dev/null ++++ b/sensors/SensorsSubHal.h +@@ -0,0 +1,95 @@ ++/* ++ * Copyright (C) 2019 The Android Open Source Project ++ * ++ * Licensed under the Apache License, Version 2.0 (the "License"); ++ * you may not use this file except in compliance with the License. ++ * You may obtain a copy of the License at ++ * ++ * http://www.apache.org/licenses/LICENSE-2.0 ++ * ++ * Unless required by applicable law or agreed to in writing, software ++ * distributed under the License is distributed on an "AS IS" BASIS, ++ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. ++ * See the License for the specific language governing permissions and ++ * limitations under the License. ++ */ ++ ++#pragma once ++ ++#include ++ ++#include "Sensor.h" ++#include "V2_1/SubHal.h" ++ ++namespace android { ++namespace hardware { ++namespace sensors { ++namespace V2_1 { ++namespace subhal { ++namespace implementation { ++ ++using ::android::hardware::sensors::V1_0::OperationMode; ++using ::android::hardware::sensors::V1_0::RateLevel; ++using ::android::hardware::sensors::V1_0::Result; ++using ::android::hardware::sensors::V1_0::SharedMemInfo; ++using ::android::hardware::sensors::V2_1::Event; ++using ::android::hardware::sensors::V2_1::implementation::IHalProxyCallback; ++using ::android::hardware::sensors::V2_1::implementation::ISensorsSubHal; ++ ++class SensorsSubHal : public ISensorsSubHal, public ISensorsEventCallback { ++ public: ++ SensorsSubHal(); ++ ++ Return getSensorsList_2_1(ISensors::getSensorsList_2_1_cb _hidl_cb); ++ Return injectSensorData_2_1(const Event& event); ++ Return initialize(const sp& halProxyCallback); ++ ++ virtual Return setOperationMode(OperationMode mode); ++ ++ OperationMode getOperationMode() const { return mCurrentOperationMode; } ++ ++ Return activate(int32_t sensorHandle, bool enabled); ++ ++ Return batch(int32_t sensorHandle, int64_t samplingPeriodNs, ++ int64_t maxReportLatencyNs); ++ ++ Return flush(int32_t sensorHandle); ++ ++ Return registerDirectChannel(const SharedMemInfo& mem, ++ ISensors::registerDirectChannel_cb _hidl_cb); ++ ++ Return unregisterDirectChannel(int32_t channelHandle); ++ ++ Return configDirectReport(int32_t sensorHandle, int32_t channelHandle, RateLevel rate, ++ ISensors::configDirectReport_cb _hidl_cb); ++ ++ Return debug(const hidl_handle& fd, const hidl_vec& args); ++ ++ const std::string getName() { return "FakeSubHal"; } ++ ++ void postEvents(const std::vector& events, bool wakeup) override; ++ ++ protected: ++ template ++ void AddSensor() { ++ std::shared_ptr sensor = ++ std::make_shared(mNextHandle++ /* sensorHandle */, this /* callback */); ++ mSensors[sensor->getSensorInfo().sensorHandle] = sensor; ++ } ++ ++ std::map> mSensors; ++ ++ sp mCallback; ++ ++ private: ++ OperationMode mCurrentOperationMode = OperationMode::NORMAL; ++ ++ int32_t mNextHandle; ++}; ++ ++} // namespace implementation ++} // namespace subhal ++} // namespace V2_1 ++} // namespace sensors ++} // namespace hardware ++} // namespace android +-- +2.25.1 + diff --git a/hardware/xiaomi/0002-sensors-Make-sensor-batch-function-virtual.patch b/hardware/xiaomi/0002-sensors-Make-sensor-batch-function-virtual.patch new file mode 100644 index 0000000..23f6331 --- /dev/null +++ b/hardware/xiaomi/0002-sensors-Make-sensor-batch-function-virtual.patch @@ -0,0 +1,26 @@ +From e6f404fece4e39b5be00a7e82632b245cd007b2c Mon Sep 17 00:00:00 2001 +From: Cosmin Tanislav +Date: Thu, 17 Feb 2022 01:04:37 +0200 +Subject: [PATCH 02/10] sensors: Make sensor batch function virtual + +Change-Id: I2de1e919234c4893b0b70390c0189cae38dbbe6c +--- + sensors/Sensor.h | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/sensors/Sensor.h b/sensors/Sensor.h +index 7923820..6643083 100644 +--- a/sensors/Sensor.h ++++ b/sensors/Sensor.h +@@ -49,7 +49,7 @@ class Sensor { + virtual ~Sensor(); + + const SensorInfo& getSensorInfo() const; +- void batch(int32_t samplingPeriodNs); ++ virtual void batch(int32_t samplingPeriodNs); + virtual void activate(bool enable); + Result flush(); + +-- +2.25.1 + diff --git a/hardware/xiaomi/0003-sensors-Make-sensor-run-function-virtual.patch b/hardware/xiaomi/0003-sensors-Make-sensor-run-function-virtual.patch new file mode 100644 index 0000000..67ddf99 --- /dev/null +++ b/hardware/xiaomi/0003-sensors-Make-sensor-run-function-virtual.patch @@ -0,0 +1,26 @@ +From 1088f413cc85c735acc652d1b69252a2c1ea2bba Mon Sep 17 00:00:00 2001 +From: Cosmin Tanislav +Date: Thu, 17 Feb 2022 01:04:44 +0200 +Subject: [PATCH 03/10] sensors: Make sensor run function virtual + +Change-Id: Ie50900903bbf4a302baff084f229c37c5c324742 +--- + sensors/Sensor.h | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/sensors/Sensor.h b/sensors/Sensor.h +index 6643083..8a7153a 100644 +--- a/sensors/Sensor.h ++++ b/sensors/Sensor.h +@@ -58,7 +58,7 @@ class Sensor { + Result injectEvent(const Event& event); + + protected: +- void run(); ++ virtual void run(); + virtual std::vector readEvents(); + static void startThread(Sensor* sensor); + +-- +2.25.1 + diff --git a/hardware/xiaomi/0004-sensors-Make-sensor-flush-function-virtual.patch b/hardware/xiaomi/0004-sensors-Make-sensor-flush-function-virtual.patch new file mode 100644 index 0000000..6a05064 --- /dev/null +++ b/hardware/xiaomi/0004-sensors-Make-sensor-flush-function-virtual.patch @@ -0,0 +1,26 @@ +From b856ada4457b884c2890d4ddfbf415c51765787f Mon Sep 17 00:00:00 2001 +From: Cosmin Tanislav +Date: Thu, 17 Feb 2022 01:06:04 +0200 +Subject: [PATCH 04/10] sensors: Make sensor flush function virtual + +Change-Id: I46532fc726d9e0c2073100ff1f6008fcde9e821c +--- + sensors/Sensor.h | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/sensors/Sensor.h b/sensors/Sensor.h +index 8a7153a..3c508c5 100644 +--- a/sensors/Sensor.h ++++ b/sensors/Sensor.h +@@ -51,7 +51,7 @@ class Sensor { + const SensorInfo& getSensorInfo() const; + virtual void batch(int32_t samplingPeriodNs); + virtual void activate(bool enable); +- Result flush(); ++ virtual Result flush(); + + void setOperationMode(OperationMode mode); + bool supportsDataInjection() const; +-- +2.25.1 + diff --git a/hardware/xiaomi/0005-sensors-Make-sensor-set-mode-operation-function-virt.patch b/hardware/xiaomi/0005-sensors-Make-sensor-set-mode-operation-function-virt.patch new file mode 100644 index 0000000..de99009 --- /dev/null +++ b/hardware/xiaomi/0005-sensors-Make-sensor-set-mode-operation-function-virt.patch @@ -0,0 +1,27 @@ +From 012799cb2f69ca2e8a8a6e34b3b191c653da1ae6 Mon Sep 17 00:00:00 2001 +From: Cosmin Tanislav +Date: Sun, 20 Feb 2022 00:51:21 +0200 +Subject: [PATCH 05/10] sensors: Make sensor set mode operation function + virtual + +Change-Id: I62c94a6ad250417162cfc9eaca8cb490ce650d9c +--- + sensors/Sensor.h | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/sensors/Sensor.h b/sensors/Sensor.h +index 3c508c5..7666cb4 100644 +--- a/sensors/Sensor.h ++++ b/sensors/Sensor.h +@@ -53,7 +53,7 @@ class Sensor { + virtual void activate(bool enable); + virtual Result flush(); + +- void setOperationMode(OperationMode mode); ++ virtual void setOperationMode(OperationMode mode); + bool supportsDataInjection() const; + Result injectEvent(const Event& event); + +-- +2.25.1 + diff --git a/hardware/xiaomi/0006-sensors-Move-one-shot-sensor-out-of-main-class.patch b/hardware/xiaomi/0006-sensors-Move-one-shot-sensor-out-of-main-class.patch new file mode 100644 index 0000000..e650c18 --- /dev/null +++ b/hardware/xiaomi/0006-sensors-Move-one-shot-sensor-out-of-main-class.patch @@ -0,0 +1,61 @@ +From 4fe1ac6fb8fe97b2698d09f425627771abbd0625 Mon Sep 17 00:00:00 2001 +From: Cosmin Tanislav +Date: Thu, 17 Feb 2022 01:08:50 +0200 +Subject: [PATCH 06/10] sensors: Move one shot sensor out of main class + +Change-Id: Ib7ac0c55409f2dc7f8fb114167e9f4b2e8859223 +--- + sensors/Sensor.cpp | 9 ++++++++- + sensors/Sensor.h | 9 +++++++++ + 2 files changed, 17 insertions(+), 1 deletion(-) + +diff --git a/sensors/Sensor.cpp b/sensors/Sensor.cpp +index 446a7e9..2b8e1aa 100644 +--- a/sensors/Sensor.cpp ++++ b/sensors/Sensor.cpp +@@ -93,7 +93,7 @@ void Sensor::activate(bool enable) { + Result Sensor::flush() { + // Only generate a flush complete event if the sensor is enabled and if the sensor is not a + // one-shot sensor. +- if (!mIsEnabled || (mSensorInfo.flags & static_cast(SensorFlagBits::ONE_SHOT_MODE))) { ++ if (!mIsEnabled) { + return Result::BAD_VALUE; + } + +@@ -184,6 +184,13 @@ Result Sensor::injectEvent(const Event& event) { + return result; + } + ++OneShotSensor::OneShotSensor(int32_t sensorHandle, ISensorsEventCallback* callback) ++ : Sensor(sensorHandle, callback) { ++ mSensorInfo.minDelay = -1; ++ mSensorInfo.maxDelay = 0; ++ mSensorInfo.flags |= SensorFlagBits::ONE_SHOT_MODE; ++} ++ + } // namespace implementation + } // namespace subhal + } // namespace V2_1 +diff --git a/sensors/Sensor.h b/sensors/Sensor.h +index 7666cb4..b7cd4a5 100644 +--- a/sensors/Sensor.h ++++ b/sensors/Sensor.h +@@ -79,6 +79,15 @@ class Sensor { + OperationMode mMode; + }; + ++class OneShotSensor : public Sensor { ++ public: ++ OneShotSensor(int32_t sensorHandle, ISensorsEventCallback* callback); ++ ++ virtual void batch(int32_t /* samplingPeriodNs */) override {} ++ ++ virtual Result flush() override { return Result::BAD_VALUE; } ++}; ++ + } // namespace implementation + } // namespace subhal + } // namespace V2_1 +-- +2.25.1 + diff --git a/hardware/xiaomi/0007-sensors-Fix-locking-around-setOperationMode-and-acti.patch b/hardware/xiaomi/0007-sensors-Fix-locking-around-setOperationMode-and-acti.patch new file mode 100644 index 0000000..d0596b3 --- /dev/null +++ b/hardware/xiaomi/0007-sensors-Fix-locking-around-setOperationMode-and-acti.patch @@ -0,0 +1,38 @@ +From ae334ea8a2706737212c9e00ff6279cd836af640 Mon Sep 17 00:00:00 2001 +From: Cosmin Tanislav +Date: Sat, 19 Feb 2022 23:34:29 +0200 +Subject: [PATCH 07/10] sensors: Fix locking around setOperationMode and + activate + +Change-Id: I9a09f45f012662c8f92fa40da3a4b9dd691a1b2c +--- + sensors/Sensor.cpp | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +diff --git a/sensors/Sensor.cpp b/sensors/Sensor.cpp +index 2b8e1aa..dcf5b75 100644 +--- a/sensors/Sensor.cpp ++++ b/sensors/Sensor.cpp +@@ -83,8 +83,8 @@ void Sensor::batch(int32_t samplingPeriodNs) { + } + + void Sensor::activate(bool enable) { ++ std::lock_guard lock(mRunMutex); + if (mIsEnabled != enable) { +- std::unique_lock lock(mRunMutex); + mIsEnabled = enable; + mWaitCV.notify_all(); + } +@@ -158,8 +158,8 @@ std::vector Sensor::readEvents() { + } + + void Sensor::setOperationMode(OperationMode mode) { ++ std::lock_guard lock(mRunMutex); + if (mMode != mode) { +- std::unique_lock lock(mRunMutex); + mMode = mode; + mWaitCV.notify_all(); + } +-- +2.25.1 + diff --git a/hardware/xiaomi/0008-sensors-Add-udfps-long-press-sensor.patch b/hardware/xiaomi/0008-sensors-Add-udfps-long-press-sensor.patch new file mode 100644 index 0000000..0f3c978 --- /dev/null +++ b/hardware/xiaomi/0008-sensors-Add-udfps-long-press-sensor.patch @@ -0,0 +1,239 @@ +From 2ab6db384c58652b61c1ff70fc9901b0d4202734 Mon Sep 17 00:00:00 2001 +From: Cosmin Tanislav +Date: Sun, 20 Feb 2022 19:34:44 +0200 +Subject: [PATCH 08/10] sensors: Add udfps long press sensor + +Co-authored-by: LuK1337 +Change-Id: Ie78d7729201836bacd65a57f76e22adb61159192 +--- + sensors/Sensor.cpp | 142 ++++++++++++++++++++++++++++++++++++++ + sensors/Sensor.h | 26 +++++++ + sensors/SensorsSubHal.cpp | 4 +- + 3 files changed, 171 insertions(+), 1 deletion(-) + +diff --git a/sensors/Sensor.cpp b/sensors/Sensor.cpp +index dcf5b75..2982513 100644 +--- a/sensors/Sensor.cpp ++++ b/sensors/Sensor.cpp +@@ -17,10 +17,41 @@ + #include "Sensor.h" + + #include ++#include + #include + + #include + ++namespace { ++ ++static bool readFpState(int fd, int& screenX, int& screenY) { ++ char buffer[512]; ++ int state = 0; ++ int rc; ++ ++ rc = lseek(fd, 0, SEEK_SET); ++ if (rc) { ++ ALOGE("failed to seek: %d", rc); ++ return false; ++ } ++ ++ rc = read(fd, &buffer, sizeof(buffer)); ++ if (rc < 0) { ++ ALOGE("failed to read state: %d", rc); ++ return false; ++ } ++ ++ rc = sscanf(buffer, "%d,%d,%d", &screenX, &screenY, &state); ++ if (rc < 0) { ++ ALOGE("failed to parse fp state: %d", rc); ++ return false; ++ } ++ ++ return state > 0; ++} ++ ++} // anonymous namespace ++ + namespace android { + namespace hardware { + namespace sensors { +@@ -191,6 +222,117 @@ OneShotSensor::OneShotSensor(int32_t sensorHandle, ISensorsEventCallback* callba + mSensorInfo.flags |= SensorFlagBits::ONE_SHOT_MODE; + } + ++UdfpsSensor::UdfpsSensor(int32_t sensorHandle, ISensorsEventCallback* callback) ++ : OneShotSensor(sensorHandle, callback) { ++ mSensorInfo.name = "UDFPS Sensor"; ++ mSensorInfo.type = ++ static_cast(static_cast(SensorType::DEVICE_PRIVATE_BASE) + 1); ++ mSensorInfo.typeAsString = "org.lineageos.sensor.udfps"; ++ mSensorInfo.maxRange = 2048.0f; ++ mSensorInfo.resolution = 1.0f; ++ mSensorInfo.power = 0; ++ mSensorInfo.flags |= SensorFlagBits::WAKE_UP; ++ ++ int rc; ++ ++ rc = pipe(mWaitPipeFd); ++ if (rc < 0) { ++ mWaitPipeFd[0] = -1; ++ mWaitPipeFd[1] = -1; ++ ALOGE("failed to open wait pipe: %d", rc); ++ } ++ ++ mPollFd = open("/sys/devices/virtual/touch/touch_dev/fod_press_status", O_RDONLY); ++ if (mPollFd < 0) { ++ ALOGE("failed to open poll fd: %d", mPollFd); ++ } ++ ++ if (mWaitPipeFd[0] < 0 || mWaitPipeFd[1] < 0 || mPollFd < 0) { ++ mStopThread = true; ++ return; ++ } ++ ++ mPolls[0] = { ++ .fd = mWaitPipeFd[0], ++ .events = POLLIN, ++ }; ++ ++ mPolls[1] = { ++ .fd = mPollFd, ++ .events = POLLERR | POLLPRI, ++ }; ++} ++ ++UdfpsSensor::~UdfpsSensor() { ++ interruptPoll(); ++} ++ ++void UdfpsSensor::activate(bool enable) { ++ std::lock_guard lock(mRunMutex); ++ ++ if (mIsEnabled != enable) { ++ mIsEnabled = enable; ++ ++ interruptPoll(); ++ mWaitCV.notify_all(); ++ } ++} ++ ++void UdfpsSensor::setOperationMode(OperationMode mode) { ++ Sensor::setOperationMode(mode); ++ interruptPoll(); ++} ++ ++void UdfpsSensor::run() { ++ std::unique_lock runLock(mRunMutex); ++ ++ while (!mStopThread) { ++ if (!mIsEnabled || mMode == OperationMode::DATA_INJECTION) { ++ mWaitCV.wait(runLock, [&] { ++ return ((mIsEnabled && mMode == OperationMode::NORMAL) || mStopThread); ++ }); ++ } else { ++ // Cannot hold lock while polling. ++ runLock.unlock(); ++ int rc = poll(mPolls, 2, -1); ++ runLock.lock(); ++ ++ if (rc < 0) { ++ ALOGE("failed to poll: %d", rc); ++ mStopThread = true; ++ continue; ++ } ++ ++ if (mPolls[1].revents == mPolls[1].events && readFpState(mPollFd, mScreenX, mScreenY)) { ++ mIsEnabled = false; ++ mCallback->postEvents(readEvents(), isWakeUpSensor()); ++ } else if (mPolls[0].revents == mPolls[0].events) { ++ char buf; ++ read(mWaitPipeFd[0], &buf, sizeof(buf)); ++ } ++ } ++ } ++} ++ ++std::vector UdfpsSensor::readEvents() { ++ std::vector events; ++ Event event; ++ event.sensorHandle = mSensorInfo.sensorHandle; ++ event.sensorType = mSensorInfo.type; ++ event.timestamp = ::android::elapsedRealtimeNano(); ++ event.u.data[0] = mScreenX; ++ event.u.data[1] = mScreenY; ++ events.push_back(event); ++ return events; ++} ++ ++void UdfpsSensor::interruptPoll() { ++ if (mWaitPipeFd[1] < 0) return; ++ ++ char c = '1'; ++ write(mWaitPipeFd[1], &c, sizeof(c)); ++} ++ + } // namespace implementation + } // namespace subhal + } // namespace V2_1 +diff --git a/sensors/Sensor.h b/sensors/Sensor.h +index b7cd4a5..aa1f194 100644 +--- a/sensors/Sensor.h ++++ b/sensors/Sensor.h +@@ -17,6 +17,9 @@ + #pragma once + + #include ++#include ++#include ++#include + + #include + #include +@@ -88,6 +91,29 @@ class OneShotSensor : public Sensor { + virtual Result flush() override { return Result::BAD_VALUE; } + }; + ++class UdfpsSensor : public OneShotSensor { ++ public: ++ UdfpsSensor(int32_t sensorHandle, ISensorsEventCallback* callback); ++ virtual ~UdfpsSensor() override; ++ ++ virtual void activate(bool enable) override; ++ virtual void setOperationMode(OperationMode mode) override; ++ ++ protected: ++ virtual void run() override; ++ virtual std::vector readEvents(); ++ ++ private: ++ void interruptPoll(); ++ ++ struct pollfd mPolls[2]; ++ int mWaitPipeFd[2]; ++ int mPollFd; ++ ++ int mScreenX; ++ int mScreenY; ++}; ++ + } // namespace implementation + } // namespace subhal + } // namespace V2_1 +diff --git a/sensors/SensorsSubHal.cpp b/sensors/SensorsSubHal.cpp +index 6cbcb56..9306b98 100644 +--- a/sensors/SensorsSubHal.cpp ++++ b/sensors/SensorsSubHal.cpp +@@ -32,7 +32,9 @@ namespace implementation { + using ::android::hardware::Void; + using ::android::hardware::sensors::V2_0::implementation::ScopedWakelock; + +-SensorsSubHal::SensorsSubHal() : mCallback(nullptr), mNextHandle(1) {} ++SensorsSubHal::SensorsSubHal() : mCallback(nullptr), mNextHandle(1) { ++ AddSensor(); ++} + + Return SensorsSubHal::getSensorsList_2_1(ISensors::getSensorsList_2_1_cb _hidl_cb) { + std::vector sensors; +-- +2.25.1 + diff --git a/hardware/xiaomi/0009-sensors-Handle-fod-press-status-without-coordinates.patch b/hardware/xiaomi/0009-sensors-Handle-fod-press-status-without-coordinates.patch new file mode 100644 index 0000000..1c00ddc --- /dev/null +++ b/hardware/xiaomi/0009-sensors-Handle-fod-press-status-without-coordinates.patch @@ -0,0 +1,35 @@ +From 946d086e74452d4c948f8b64afe3b082291c75a5 Mon Sep 17 00:00:00 2001 +From: Arian +Date: Wed, 29 Mar 2023 17:38:34 +0200 +Subject: [PATCH 09/10] sensors: Handle fod press status without coordinates + +Also fix the error handling of sscanf which returns the +number of matched variables on partial success. + +Change-Id: I785c0e3f73e89f79addcf18e1b5111e93e25e430 +--- + sensors/Sensor.cpp | 8 +++++++- + 1 file changed, 7 insertions(+), 1 deletion(-) + +diff --git a/sensors/Sensor.cpp b/sensors/Sensor.cpp +index 2982513..6c1c5e4 100644 +--- a/sensors/Sensor.cpp ++++ b/sensors/Sensor.cpp +@@ -42,7 +42,13 @@ static bool readFpState(int fd, int& screenX, int& screenY) { + } + + rc = sscanf(buffer, "%d,%d,%d", &screenX, &screenY, &state); +- if (rc < 0) { ++ if (rc == 1) { ++ // If only the first variable can be matched assume ++ // that the node only reports the state ++ state = screenX; ++ screenX = 0; ++ screenY = 0; ++ } else if (rc < 3) { + ALOGE("failed to parse fp state: %d", rc); + return false; + } +-- +2.25.1 + diff --git a/hardware/xiaomi/0010-hidl-biometrics-fingerprint-Add-enroll-methods-to-ud.patch b/hardware/xiaomi/0010-hidl-biometrics-fingerprint-Add-enroll-methods-to-ud.patch new file mode 100644 index 0000000..03fbfaf --- /dev/null +++ b/hardware/xiaomi/0010-hidl-biometrics-fingerprint-Add-enroll-methods-to-ud.patch @@ -0,0 +1,61 @@ +From 17c39edbeb39b2a28567c8224608216c90010cda Mon Sep 17 00:00:00 2001 +From: Arian +Date: Wed, 2 Aug 2023 09:36:52 +0200 +Subject: [PATCH 10/10] hidl: biometrics: fingerprint: Add enroll methods to + udfps handler + +Change-Id: I1b73438ae6bf7e2c0b3fe6d2ca7726993604454b +--- + hidl/biometrics/fingerprint/BiometricsFingerprint.cpp | 9 +++++++++ + hidl/biometrics/fingerprint/include/UdfpsHandler.h | 5 +++++ + 2 files changed, 14 insertions(+) + +diff --git a/hidl/biometrics/fingerprint/BiometricsFingerprint.cpp b/hidl/biometrics/fingerprint/BiometricsFingerprint.cpp +index 9303e08..b305f35 100644 +--- a/hidl/biometrics/fingerprint/BiometricsFingerprint.cpp ++++ b/hidl/biometrics/fingerprint/BiometricsFingerprint.cpp +@@ -209,16 +209,25 @@ Return BiometricsFingerprint::setNotify( + } + + Return BiometricsFingerprint::preEnroll() { ++ if (mUdfpsHandler) { ++ mUdfpsHandler->preEnroll(); ++ } + return mDevice->pre_enroll(mDevice); + } + + Return BiometricsFingerprint::enroll(const hidl_array& hat, + uint32_t gid, uint32_t timeoutSec) { ++ if (mUdfpsHandler) { ++ mUdfpsHandler->enroll(); ++ } + const hw_auth_token_t* authToken = reinterpret_cast(hat.data()); + return ErrorFilter(mDevice->enroll(mDevice, authToken, gid, timeoutSec)); + } + + Return BiometricsFingerprint::postEnroll() { ++ if (mUdfpsHandler) { ++ mUdfpsHandler->postEnroll(); ++ } + return ErrorFilter(mDevice->post_enroll(mDevice)); + } + +diff --git a/hidl/biometrics/fingerprint/include/UdfpsHandler.h b/hidl/biometrics/fingerprint/include/UdfpsHandler.h +index 9ae531c..dd05832 100644 +--- a/hidl/biometrics/fingerprint/include/UdfpsHandler.h ++++ b/hidl/biometrics/fingerprint/include/UdfpsHandler.h +@@ -19,6 +19,11 @@ class UdfpsHandler { + + virtual void onAcquired(int32_t result, int32_t vendorCode) = 0; + virtual void cancel() = 0; ++ ++ virtual void preEnroll() = 0; ++ virtual void enroll() = 0; ++ virtual void postEnroll() = 0; ++ + }; + + struct UdfpsHandlerFactory { +-- +2.25.1 + diff --git a/patch.sh b/patch.sh new file mode 100644 index 0000000..83cbb67 --- /dev/null +++ b/patch.sh @@ -0,0 +1,27 @@ + +cd vendor/lineage +git apply ../../patches/vendor/lineage/0001-android-merge_dtbs-Respect-miboard-id-while-merging.patch +cd ../../ + +# cd device/qcom/sepolicy_vndr/sm8450 +# git apply ../../../../patches-21/device/qcom/sepolicy_vndr/sm8450/0001-sepolicy_vndr-update-sepolicy-for-health-HAL-service.patch +# cd ../../../../ + +cd hardware/xiaomi +git apply ../../patches/hardware/xiaomi/0001-Add-dummy-sensors-sub-HAL.patch +git apply ../../patches/hardware/xiaomi/0002-sensors-Make-sensor-batch-function-virtual.patch +git apply ../../patches/hardware/xiaomi/0003-sensors-Make-sensor-run-function-virtual.patch +git apply ../../patches/hardware/xiaomi/0004-sensors-Make-sensor-flush-function-virtual.patch +git apply ../../patches/hardware/xiaomi/0005-sensors-Make-sensor-set-mode-operation-function-virt.patch +git apply ../../patches/hardware/xiaomi/0006-sensors-Move-one-shot-sensor-out-of-main-class.patch +git apply ../../patches/hardware/xiaomi/0007-sensors-Fix-locking-around-setOperationMode-and-acti.patch +git apply ../../patches/hardware/xiaomi/0008-sensors-Add-udfps-long-press-sensor.patch +git apply ../../patches/hardware/xiaomi/0009-sensors-Handle-fod-press-status-without-coordinates.patch +git apply ../../patches/hardware/xiaomi/0010-hidl-biometrics-fingerprint-Add-enroll-methods-to-ud.patch +cd ../../ + +cd frameworks/base +git apply ../../patches/frameworks/base/0001-Add-5G-Ultra-Wideband-icon-carrier-config-keys.patch +git apply ../../patches/frameworks/base/0002-Fix-default-values-for-5G-Ultra-Wideband-icon-carrie.patch + + diff --git a/repopicks.sh b/repopicks.sh new file mode 100644 index 0000000..dcc4bde --- /dev/null +++ b/repopicks.sh @@ -0,0 +1,46 @@ +#!/bin/bash +set -e + +source "build/envsetup.sh"; +source "vendor/lineage/build/envsetup.sh"; + +# device/qcom/sepolicy_vndr/sm8450 +changes=( +383884 # sepolicy_vndr: update sepolicy for health HAL service +) +repopick -P device/qcom/sepolicy_vndr/sm8450 ${changes[@]} + +# hardware/xiaomi +changes=( +352657 # Add dummy sensors sub HAL +352658 # sensors: Make sensor batch function virtual +352659 # sensors: Make sensor run function virtual +352660 # sensors: Make sensor flush function virtual +352661 # sensors: Make sensor set mode operation function virtual +352662 # sensors: Move one shot sensor out of main class +352663 # sensors: Fix locking around setOperationMode and activate +352664 # sensors: Add udfps long press sensor +352665 # sensors: Handle fod_pressed_state without coordinates +363160 # hidl: biometrics: fingerprint: Add enroll methods to udfps handler +) +repopick -P hardware/xiaomi ${changes[@]} + +# frameworks/base +changes=( +386158 # Add 5G Ultra Wideband icon carrier config keys +386159 # Fix default values for 5G Ultra Wideband icon carrier config keys +) +repopick -P frameworks/base ${changes[@]} + +# vendor/lineage +changes=( +367044 # android: merge_dtbs: Respect miboard-id while merging +) +repopick -P vendor/lineage ${changes[@]} + + + +cd hardware/qcom-caf/sm8450/display +git pull https://github.com/LineageOS/android_hardware_qcom_display refs/changes/99/384299/1 +cd ../../../../ + diff --git a/vendor/lineage/0001-android-merge_dtbs-Respect-miboard-id-while-merging.patch b/vendor/lineage/0001-android-merge_dtbs-Respect-miboard-id-while-merging.patch new file mode 100644 index 0000000..3d2258b --- /dev/null +++ b/vendor/lineage/0001-android-merge_dtbs-Respect-miboard-id-while-merging.patch @@ -0,0 +1,204 @@ +From 6a0a02f56cc761f27565c072fe7f3d33514ff9ed Mon Sep 17 00:00:00 2001 +From: Arian +Date: Thu, 14 Jul 2022 18:26:54 +0200 +Subject: [PATCH] android: merge_dtbs: Respect miboard-id while merging + +Change-Id: Ic5b38a122173d8e9ecc1f0f399411cb37acf3150 +--- + build/tools/merge_dtbs.py | 50 ++++++++++++++++++++++++++------------- + 1 file changed, 34 insertions(+), 16 deletions(-) + +diff --git a/build/tools/merge_dtbs.py b/build/tools/merge_dtbs.py +index 898be4cc..a5409317 100755 +--- a/build/tools/merge_dtbs.py ++++ b/build/tools/merge_dtbs.py +@@ -44,10 +44,11 @@ def split_array(array, cells): + return frozenset(tuple(array[i*cells:(i*cells)+cells]) for i in range(len(array) // cells)) + + class DeviceTreeInfo(object): +- def __init__(self, plat, board, pmic): ++ def __init__(self, plat, board, pmic, miboard): + self.plat_id = plat + self.board_id = board + self.pmic_id = pmic ++ self.miboard_id = miboard + + def __str__(self): + s = "" +@@ -57,13 +58,15 @@ class DeviceTreeInfo(object): + s += " board-id = <{}>;".format(" ".join(map(str, self.board_id))) + if self.pmic_id is not None: + s += " pmic-id = <{}>;".format(" ".join(map(str, self.pmic_id))) ++ if self.miboard_id is not None: ++ s += " miboard-id = <{}>;".format(" ".join(map(str, self.miboard_id))) + return s.strip() + + def __repr__(self): + return "<{} {}>".format(self.__class__.__name__, str(self)) + + def has_any_properties(self): +- return self.plat_id is not None or self.board_id is not None or self.pmic_id is not None ++ return self.plat_id is not None or self.board_id is not None or self.pmic_id is not None or self.miboard_id is not None + + def __sub__(self, other): + """ +@@ -71,11 +74,13 @@ class DeviceTreeInfo(object): + msm-id = , + board-id = , + pmic-id = <0, 1> ++ miboard-id = , + + Other has plat, board, pmic are: + msm-id = , + board-id = + pmic-id = <0> ++ miboard-id = , + + (self - other) will split self into a set of devicetrees with different identifers + and meets the following requirements: +@@ -86,11 +91,13 @@ class DeviceTreeInfo(object): + assert self.plat_id is None or isinstance(self.plat_id, (set, frozenset)) + assert self.board_id is None or isinstance(self.board_id, (set, frozenset)) + assert self.pmic_id is None or isinstance(self.pmic_id, (set, frozenset)) ++ assert self.miboard_id is None or isinstance(self.miboard_id, (set, frozenset)) + assert other in self + + new_plat = other.plat_id is not None and self.plat_id != other.plat_id + new_board = other.board_id is not None and self.board_id != other.board_id + new_pmic = other.pmic_id is not None and self.pmic_id != other.pmic_id ++ new_miboard = other.miboard_id is not None and self.miboard_id != other.miboard_id + + res = set() + # Create the devicetree that matches other exactly +@@ -101,13 +108,15 @@ class DeviceTreeInfo(object): + s.board_id = other.board_id + if new_pmic: + s.pmic_id = other.pmic_id ++ if new_miboard: ++ s.miboard_id = other.miboard_id + res.add(s) + + # now create the other possibilities by removing any combination of + # other's plat, board, and/or pmic. Set logic (unique elemnts) handles + # duplicate devicetrees IDs spit out by this loop +- for combo in combinations_with_replacement([True, False], 3): +- if not any((c and n) for (c, n) in zip(combo, (new_plat, new_board, new_pmic))): ++ for combo in combinations_with_replacement([True, False], 4): ++ if not any((c and n) for (c, n) in zip(combo, (new_plat, new_board, new_pmic, new_miboard))): + continue + s = copy.deepcopy(self) + if combo[0] and new_plat: +@@ -116,16 +125,18 @@ class DeviceTreeInfo(object): + s.board_id -= other.board_id + if combo[2] and new_pmic: + s.pmic_id -= other.pmic_id ++ if combo[3] and new_miboard: ++ s.miboard_id -= other.miboard_id + res.add(s) + return res + + def __hash__(self): +- # Hash should only consider msm-id/board-id/pmic-id +- return hash((self.plat_id, self.board_id, self.pmic_id)) ++ # Hash should only consider msm-id/board-id/pmic-id/miboard-id ++ return hash((self.plat_id, self.board_id, self.pmic_id, self.miboard_id)) + + def __and__(self, other): + s = copy.deepcopy(self) +- for prop in ['plat_id', 'board_id', 'pmic_id']: ++ for prop in ['plat_id', 'board_id', 'pmic_id', 'miboard_id']: + if getattr(self, prop) is None or getattr(other, prop) is None: + setattr(s, prop, None) + else: +@@ -141,14 +152,14 @@ class DeviceTreeInfo(object): + + def __eq__(self, other): + """ +- Checks whether other plat_id, board_id, pmic_id matches either identically ++ Checks whether other plat_id, board_id, pmic_id, miboard_id matches either identically + or because the property is none + """ + if not isinstance(other, DeviceTreeInfo): + return False + if not other.has_any_properties(): + return False +- return all(map(lambda p: self._do_equivalent(other, p), ['plat_id', 'board_id', 'pmic_id'])) ++ return all(map(lambda p: self._do_equivalent(other, p), ['plat_id', 'board_id', 'pmic_id', 'miboard_id'])) + + + def _do_gt(self, other, property): +@@ -180,7 +191,7 @@ class DeviceTreeInfo(object): + return False + if not other.has_any_properties(): + return False +- return all(map(lambda p: self._do_gt(other, p), ['plat_id', 'board_id', 'pmic_id'])) ++ return all(map(lambda p: self._do_gt(other, p), ['plat_id', 'board_id', 'pmic_id', 'miboard_id'])) + + + def _do_contains(self, other, property): +@@ -214,7 +225,7 @@ class DeviceTreeInfo(object): + return False + if not other.has_any_properties(): + return False +- return all(map(lambda p: self._do_contains(other, p), ['plat_id', 'board_id', 'pmic_id'])) ++ return all(map(lambda p: self._do_contains(other, p), ['plat_id', 'board_id', 'pmic_id', 'miboard_id'])) + + class DeviceTree(DeviceTreeInfo): + def __init__(self, filename): +@@ -224,7 +235,8 @@ class DeviceTree(DeviceTreeInfo): + # default pmic-id-size is 4 + pmic_id_size = self.get_prop('/', 'qcom,pmic-id-size', check_output=False) or 4 + pmic_id = split_array(self.get_prop('/', 'qcom,pmic-id', check_output=False), pmic_id_size) +- super().__init__(msm_id, board_id, pmic_id) ++ miboard_id = split_array(self.get_prop('/', 'xiaomi,miboard-id', check_output=False), 2) ++ super().__init__(msm_id, board_id, pmic_id, miboard_id) + + if not self.has_any_properties(): + print('WARNING! {} has no properties and may match with any other devicetree'.format(self.filename)) +@@ -260,10 +272,10 @@ class InnerMergedDeviceTree(DeviceTreeInfo): + It has a platform, board, and pmic ID, the "base" devicetree, and some set of add-on + devicetrees + """ +- def __init__(self, filename, plat_id, board_id, pmic_id, techpacks=None): ++ def __init__(self, filename, plat_id, board_id, pmic_id, miboard_id, techpacks=None): + self.base = filename + self.techpacks = techpacks or [] +- super().__init__(plat_id, board_id, pmic_id) ++ super().__init__(plat_id, board_id, pmic_id, miboard_id) + + def try_add(self, techpack): + if not isinstance(techpack, DeviceTree): +@@ -317,6 +329,12 @@ class InnerMergedDeviceTree(DeviceTreeInfo): + print(' {}'.format(' '.join(cmd))) + subprocess.run(cmd, check=True) + ++ if self.miboard_id: ++ board_iter = self.miboard_id if isinstance(self.miboard_id, tuple) else chain.from_iterable(self.miboard_id) ++ cmd = ['fdtput', '-t', 'i', out_file, '/', 'xiaomi,miboard-id'] + list(map(str, board_iter)) ++ print(' {}'.format(' '.join(cmd))) ++ subprocess.run(cmd, check=True) ++ + return DeviceTree(out_file) + + def get_name(self): +@@ -336,7 +354,7 @@ class InnerMergedDeviceTree(DeviceTreeInfo): + + class MergedDeviceTree(object): + def __init__(self, other): +- self.merged_devicetrees = {InnerMergedDeviceTree(other.filename, other.plat_id, other.board_id, other.pmic_id)} ++ self.merged_devicetrees = {InnerMergedDeviceTree(other.filename, other.plat_id, other.board_id, other.pmic_id, other.miboard_id)} + + def try_add(self, techpack): + did_add = False +@@ -395,7 +413,7 @@ def main(): + .format(sys.argv[0])) + sys.exit(1) + +- # 1. Parse the devicetrees -- extract the device info (msm-id, board-id, pmic-id) ++ # 1. Parse the devicetrees -- extract the device info (msm-id, board-id, pmic-id, miboard-id) + bases = parse_dt_files(sys.argv[1]) + techpacks = parse_dt_files(sys.argv[2]) + +-- +2.25.1 +