bangkk: fingerprint: Switch to IOCTL for HBM

* On newer moto kernels it is possible
  to send a SET_PANEL_FEATURE ioctl to /dev/dri/card0
  to set a panel feature such as HBM. Motorola has
  extended the HBM logic to allow FOD HBM to be set
  in additional to regular HBM. This is done by sending
  "2" with the HBM id through the ioctl.

* Utilize the API provided by Egistec provides via
  vendor.egistec.hardware.fingerprint to send commands
  to the internal handler, this allows us to send
  the finger is on or off the sensor message directly to the
  HAL.

Change-Id: I06ace29567900779e63b9826862964d20b267be6
This commit is contained in:
electimon 2024-01-07 10:51:54 +00:00 committed by Michael Bestas
parent b79d326b12
commit 904a71bb02
No known key found for this signature in database
4 changed files with 67 additions and 59 deletions

View file

@ -4,7 +4,4 @@
// //
soong_namespace { soong_namespace {
imports: [
"hardware/motorola",
],
} }

View file

@ -17,6 +17,7 @@ cc_binary {
"android.hardware.biometrics.fingerprint@2.1", "android.hardware.biometrics.fingerprint@2.1",
"android.hardware.biometrics.fingerprint@2.2", "android.hardware.biometrics.fingerprint@2.2",
"android.hardware.biometrics.fingerprint@2.3", "android.hardware.biometrics.fingerprint@2.3",
"com.motorola.hardware.biometric.fingerprint@1.0", "vendor.egistec.hardware.fingerprint@4.0",
], ],
header_libs: ["generated_kernel_headers"]
} }

View file

@ -17,19 +17,44 @@
#include "BiometricsFingerprint.h" #include "BiometricsFingerprint.h"
#include <android-base/file.h>
#include <android-base/logging.h> #include <android-base/logging.h>
#include <fcntl.h>
#include <poll.h>
#include <sys/ioctl.h>
#include <sys/stat.h>
#include <chrono>
#include <cmath> #include <cmath>
#include <fstream> #include <fstream>
#include <thread> #include <thread>
#include <fcntl.h> #include <display/drm/sde_drm.h>
#include <poll.h>
#include <sys/stat.h>
#define NOTIFY_FINGER_UP IMotFodEventType::FINGER_UP enum HBM_STATE { OFF = 0, ON = 2 };
#define NOTIFY_FINGER_DOWN IMotFodEventType::FINGER_DOWN
#define FOD_UI_PATH "/sys/devices/platform/soc/soc:qcom,dsi-display-primary/fod_ui" void setHbmState(int state) {
struct panel_param_info param_info;
int32_t node = open("/dev/dri/card0", O_RDWR);
int32_t ret = 0;
if (node < 0) {
LOG(ERROR) << "Failed to get card0!";
return;
}
param_info.param_idx = PARAM_HBM;
param_info.value = state;
ret = ioctl(node, DRM_IOCTL_SET_PANEL_FEATURE, &param_info);
if (ret < 0) {
LOG(ERROR) << "IOCTL call failed with ret = " << ret;
} else {
LOG(INFO) << "HBM state set successfully. New state: " << state;
}
close(node);
}
namespace android { namespace android {
namespace hardware { namespace hardware {
@ -38,52 +63,9 @@ namespace fingerprint {
namespace V2_3 { namespace V2_3 {
namespace implementation { namespace implementation {
static bool readBool(int fd) {
char c;
int rc;
rc = lseek(fd, 0, SEEK_SET);
if (rc) {
LOG(ERROR) << "failed to seek fd, err: " << rc;
return false;
}
rc = read(fd, &c, sizeof(char));
if (rc != 1) {
LOG(ERROR) << "failed to read bool from fd, err: " << rc;
return false;
}
return c != '0';
}
BiometricsFingerprint::BiometricsFingerprint() { BiometricsFingerprint::BiometricsFingerprint() {
biometrics_2_1_service = IBiometricsFingerprint_2_1::getService(); biometrics_2_1_service = IBiometricsFingerprint_2_1::getService();
mMotoFingerprint = IMotoFingerPrint::getService(); rbs_4_0_service = IBiometricsFingerprintRbs::getService();
std::thread([this]() {
int fd = open(FOD_UI_PATH, O_RDONLY);
if (fd < 0) {
LOG(ERROR) << "failed to open fd, err: " << fd;
return;
}
struct pollfd fodUiPoll = {
.fd = fd,
.events = POLLERR | POLLPRI,
.revents = 0,
};
while (true) {
int rc = poll(&fodUiPoll, 1, -1);
if (rc < 0) {
LOG(ERROR) << "failed to poll fd, err: " << rc;
continue;
}
mMotoFingerprint->sendFodEvent(readBool(fd) ? NOTIFY_FINGER_DOWN : NOTIFY_FINGER_UP, {},
[](IMotFodEventResult, const hidl_vec<signed char>&) {});
}
}).detach();
} }
Return<uint64_t> BiometricsFingerprint::setNotify( Return<uint64_t> BiometricsFingerprint::setNotify(
@ -109,6 +91,7 @@ Return<uint64_t> BiometricsFingerprint::getAuthenticatorId() {
} }
Return<RequestStatus> BiometricsFingerprint::cancel() { Return<RequestStatus> BiometricsFingerprint::cancel() {
setHbmState(OFF);
return biometrics_2_1_service->cancel(); return biometrics_2_1_service->cancel();
} }
@ -126,6 +109,7 @@ Return<RequestStatus> BiometricsFingerprint::setActiveGroup(uint32_t gid,
} }
Return<RequestStatus> BiometricsFingerprint::authenticate(uint64_t operationId, uint32_t gid) { Return<RequestStatus> BiometricsFingerprint::authenticate(uint64_t operationId, uint32_t gid) {
setHbmState(OFF);
return biometrics_2_1_service->authenticate(operationId, gid); return biometrics_2_1_service->authenticate(operationId, gid);
} }
@ -134,10 +118,36 @@ Return<bool> BiometricsFingerprint::isUdfps(uint32_t) {
} }
Return<void> BiometricsFingerprint::onFingerDown(uint32_t, uint32_t, float, float) { Return<void> BiometricsFingerprint::onFingerDown(uint32_t, uint32_t, float, float) {
setHbmState(ON);
extraApiWrapper(101);
std::thread([this]() {
std::this_thread::sleep_for(std::chrono::milliseconds(200));
BiometricsFingerprint::onFingerUp();
}).detach();
return Void(); return Void();
} }
Return<void> BiometricsFingerprint::onFingerUp() { Return<void> BiometricsFingerprint::onFingerUp() {
setHbmState(OFF);
extraApiWrapper(102);
return Void();
}
Return<void> BiometricsFingerprint::extraApiWrapper(int cidValue) {
int cid[1] = {cidValue};
// Create a std::vector<uint8_t> to store the data from 'cid'
std::vector<uint8_t> cid_data(reinterpret_cast<uint8_t*>(cid),
reinterpret_cast<uint8_t*>(cid) + sizeof(cid));
// Create the hidl_vec<uint8_t> from the std::vector<uint8_t>
::android::hardware::hidl_vec<uint8_t> hidl_cid = cid_data;
// Call extra_api with the correct input buffer and an empty lambda callback
rbs_4_0_service->extra_api(7, hidl_cid, [](const ::android::hardware::hidl_vec<uint8_t>&) {});
return Void(); return Void();
} }

View file

@ -18,9 +18,9 @@
#define ANDROID_HARDWARE_BIOMETRICS_FINGERPRINT_V2_3_BIOMETRICSFINGERPRINT_H #define ANDROID_HARDWARE_BIOMETRICS_FINGERPRINT_V2_3_BIOMETRICSFINGERPRINT_H
#include <android/hardware/biometrics/fingerprint/2.3/IBiometricsFingerprint.h> #include <android/hardware/biometrics/fingerprint/2.3/IBiometricsFingerprint.h>
#include <com/motorola/hardware/biometric/fingerprint/1.0/IMotoFingerPrint.h>
#include <hidl/MQDescriptor.h> #include <hidl/MQDescriptor.h>
#include <hidl/Status.h> #include <hidl/Status.h>
#include <vendor/egistec/hardware/fingerprint/4.0/IBiometricsFingerprintRbs.h>
namespace android { namespace android {
namespace hardware { namespace hardware {
@ -40,9 +40,7 @@ using ::android::hardware::Return;
using ::android::hardware::Void; using ::android::hardware::Void;
using ::android::hardware::biometrics::fingerprint::V2_1::IBiometricsFingerprintClientCallback; using ::android::hardware::biometrics::fingerprint::V2_1::IBiometricsFingerprintClientCallback;
using ::android::hardware::biometrics::fingerprint::V2_1::RequestStatus; using ::android::hardware::biometrics::fingerprint::V2_1::RequestStatus;
using ::com::motorola::hardware::biometric::fingerprint::V1_0::IMotFodEventResult; using ::vendor::egistec::hardware::fingerprint::V4_0::IBiometricsFingerprintRbs;
using ::com::motorola::hardware::biometric::fingerprint::V1_0::IMotFodEventType;
using ::com::motorola::hardware::biometric::fingerprint::V1_0::IMotoFingerPrint;
struct BiometricsFingerprint : public IBiometricsFingerprint { struct BiometricsFingerprint : public IBiometricsFingerprint {
BiometricsFingerprint(); BiometricsFingerprint();
@ -65,9 +63,11 @@ struct BiometricsFingerprint : public IBiometricsFingerprint {
Return<void> onFingerDown(uint32_t x, uint32_t y, float minor, float major) override; Return<void> onFingerDown(uint32_t x, uint32_t y, float minor, float major) override;
Return<void> onFingerUp() override; Return<void> onFingerUp() override;
Return<void> extraApiWrapper(int cidValue);
private: private:
sp<IBiometricsFingerprint_2_1> biometrics_2_1_service; sp<IBiometricsFingerprint_2_1> biometrics_2_1_service;
sp<IMotoFingerPrint> mMotoFingerprint; sp<IBiometricsFingerprintRbs> rbs_4_0_service;
}; };
} // namespace implementation } // namespace implementation