Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 14e89235 authored by Alex Sarraf's avatar Alex Sarraf
Browse files

input: misc: hbtp_input: Support for Region of Interest/sensors



Add support for sensor and Region of Interest (ROI) events.
Create new ioctl to receive sensor data from userspace.
Create binary sysfs entries to expose data from kernel to
userspace.

Change-Id: Ifa76f08eb293c3da0618c22c07e65976319ea926
Signed-off-by: default avatarAlex Sarraf <asarraf@codeaurora.org>
parent 9898f867
Loading
Loading
Loading
Loading
+103 −1
Original line number Diff line number Diff line

/* Copyright (c) 2014-2016, The Linux Foundation. All rights reserved.
/* Copyright (c) 2014-2017, The Linux Foundation. All rights reserved.
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License version 2 and
@@ -47,6 +47,8 @@ struct hbtp_data {
	struct input_dev *input_dev;
	s32 count;
	struct mutex mutex;
	struct mutex sensormutex;
	struct hbtp_sensor_data *sensor_data;
	bool touch_status[HBTP_MAX_FINGER];
#if defined(CONFIG_FB)
	struct notifier_block fb_notif;
@@ -87,10 +89,14 @@ struct hbtp_data {
	u32 power_on_delay;
	u32 power_off_delay;
	bool manage_pin_ctrl;
	s16 ROI[MAX_ROI_SIZE];
	s16 accelBuffer[MAX_ACCEL_SIZE];
};

static struct hbtp_data *hbtp;

static struct kobject *sensor_kobject;

#if defined(CONFIG_FB)
static int hbtp_fb_suspend(struct hbtp_data *ts);
static int hbtp_fb_early_resume(struct hbtp_data *ts);
@@ -150,6 +156,46 @@ static int fb_notifier_callback(struct notifier_block *self,
}
#endif

static ssize_t hbtp_sensor_roi_show(struct file *dev, struct kobject *kobj,
		struct bin_attribute *attr, char *buf, loff_t pos,
			size_t size) {
	mutex_lock(&hbtp->sensormutex);
	memcpy(buf, hbtp->ROI, size);
	mutex_unlock(&hbtp->sensormutex);

	return size;
}

static ssize_t hbtp_sensor_vib_show(struct file *dev, struct kobject *kobj,
		struct bin_attribute *attr, char *buf, loff_t pos,
			size_t size) {
	mutex_lock(&hbtp->sensormutex);
	memcpy(buf, hbtp->accelBuffer, size);
	mutex_unlock(&hbtp->sensormutex);

	return size;
}

static struct bin_attribute capdata_attr = {
	.attr = {
		.name = "capdata",
		.mode = S_IRUGO,
		},
	.size = 1024,
	.read = hbtp_sensor_roi_show,
	.write = NULL,
};

static struct bin_attribute vibdata_attr = {
	.attr = {
		.name = "vib_data",
		.mode = S_IRUGO,
		},
	.size = MAX_ACCEL_SIZE*sizeof(int16_t),
	.read = hbtp_sensor_vib_show,
	.write = NULL,
};

static int hbtp_input_open(struct inode *inode, struct file *file)
{
	mutex_lock(&hbtp->mutex);
@@ -748,6 +794,22 @@ static long hbtp_input_ioctl_handler(struct file *file, unsigned int cmd,
			return -EINVAL;
		}
		break;

	case HBTP_SET_SENSORDATA:
		if (copy_from_user(hbtp->sensor_data, (void *)arg,
					sizeof(struct hbtp_sensor_data))) {
			pr_err("%s: Error copying data\n", __func__);
			return -EFAULT;
		}
		mutex_lock(&hbtp->sensormutex);
		memcpy(hbtp->ROI, hbtp->sensor_data->ROI, sizeof(hbtp->ROI));
		memcpy(hbtp->accelBuffer, hbtp->sensor_data->accelBuffer,
			sizeof(hbtp->accelBuffer));
		mutex_unlock(&hbtp->sensormutex);

		error = 0;
		break;

	default:
		pr_err("%s: Unsupported ioctl command %u\n", __func__, cmd);
		error = -EINVAL;
@@ -1358,7 +1420,13 @@ static int __init hbtp_init(void)
	if (!hbtp)
		return -ENOMEM;

	hbtp->sensor_data = kzalloc(sizeof(struct hbtp_sensor_data),
			GFP_KERNEL);
	if (!hbtp->sensor_data)
		goto err_sensordata;

	mutex_init(&hbtp->mutex);
	mutex_init(&hbtp->sensormutex);

	error = misc_register(&hbtp_input_misc);
	if (error) {
@@ -1376,6 +1444,28 @@ static int __init hbtp_init(void)
	}
#endif

	sensor_kobject = kobject_create_and_add("hbtpsensor", kernel_kobj);
	if (!sensor_kobject) {
		pr_err("%s: Could not create hbtpsensor kobject\n", __func__);
		goto err_kobject_create;
	}

	error = sysfs_create_bin_file(sensor_kobject, &capdata_attr);
	if (error < 0) {
		pr_err("%s: hbtp capdata sysfs creation failed: %d\n", __func__,
			error);
		goto err_sysfs_create_capdata;
	}
	pr_debug("capdata sysfs creation success\n");

	error = sysfs_create_bin_file(sensor_kobject, &vibdata_attr);
	if (error < 0) {
		pr_err("%s: vibdata sysfs creation failed: %d\n", __func__,
			error);
		goto err_sysfs_create_vibdata;
	}
	pr_debug("vibdata sysfs creation success\n");

	error = platform_driver_register(&hbtp_pdev_driver);
	if (error) {
		pr_err("Failed to register platform driver: %d\n", error);
@@ -1385,12 +1475,20 @@ static int __init hbtp_init(void)
	return 0;

err_platform_drv_reg:
	sysfs_remove_bin_file(sensor_kobject, &vibdata_attr);
err_sysfs_create_vibdata:
	sysfs_remove_bin_file(sensor_kobject, &capdata_attr);
err_sysfs_create_capdata:
	kobject_put(sensor_kobject);
err_kobject_create:
#if defined(CONFIG_FB)
	fb_unregister_client(&hbtp->fb_notif);
err_fb_reg:
#endif
	misc_deregister(&hbtp_input_misc);
err_misc_reg:
	kfree(hbtp->sensor_data);
err_sensordata:
	kfree(hbtp);

	return error;
@@ -1398,6 +1496,9 @@ err_misc_reg:

static void __exit hbtp_exit(void)
{
	sysfs_remove_bin_file(sensor_kobject, &vibdata_attr);
	sysfs_remove_bin_file(sensor_kobject, &capdata_attr);
	kobject_put(sensor_kobject);
	misc_deregister(&hbtp_input_misc);
	if (hbtp->input_dev)
		input_unregister_device(hbtp->input_dev);
@@ -1408,6 +1509,7 @@ static void __exit hbtp_exit(void)

	platform_driver_unregister(&hbtp_pdev_driver);

	kfree(hbtp->sensor_data);
	kfree(hbtp);
}

+9 −0
Original line number Diff line number Diff line
@@ -6,6 +6,8 @@
#define HBTP_MAX_FINGER		20
#define HBTP_ABS_MT_FIRST	ABS_MT_TOUCH_MAJOR
#define HBTP_ABS_MT_LAST	ABS_MT_TOOL_Y
#define MAX_ROI_SIZE		144
#define MAX_ACCEL_SIZE		128

#define HBTP_EVENT_TYPE_DISPLAY	"EVENT_TYPE=HBTP_DISPLAY"

@@ -20,6 +22,11 @@ struct hbtp_input_touch {
	__s32 orientation;
};

struct hbtp_sensor_data {
	__s16 accelBuffer[MAX_ACCEL_SIZE];
	__s16 ROI[MAX_ROI_SIZE];
};

struct hbtp_input_mt {
	__s32 num_touches;
	struct hbtp_input_touch touches[HBTP_MAX_FINGER];
@@ -68,6 +75,8 @@ enum hbtp_afe_power_ctrl {
					enum hbtp_afe_signal)
#define HBTP_SET_POWER_CTRL	_IOW(HBTP_INPUT_IOCTL_BASE, 206, \
					enum hbtp_afe_power_ctrl)
#define HBTP_SET_SENSORDATA	_IOW(HBTP_INPUT_IOCTL_BASE, 207, \
					struct hbtp_sensor_data)

#endif	/* _UAPI_HBTP_INPUT_H */