// SPDX-License-Identifier: GPL-2.0-or-later
/*
 * USB Synaptics device driver
 *
 *  Copyright (c) 2002 Rob Miller (rob@inpharmatica . co . uk)
 *  Copyright (c) 2003 Ron Lee (ron@debian.org)
 *	cPad driver for kernel 2.4
 *
 *  Copyright (c) 2004 Jan Steinhoff (cpad@jan-steinhoff . de)
 *  Copyright (c) 2004 Ron Lee (ron@debian.org)
 *	rewritten for kernel 2.6
 *
 *  cPad display character device part is not included. It can be found at
 *  http://jan-steinhoff.de/linux/synaptics-usb.html
 *
 * Bases on:	usb_skeleton.c v2.2 by Greg Kroah-Hartman
 *		drivers/hid/usbhid/usbmouse.c by Vojtech Pavlik
 *		drivers/input/mouse/synaptics.c by Peter Osterlund
 *
 * Trademarks are the property of their respective owners.
 */

/*
 * There are three different types of Synaptics USB devices: Touchpads,
 * touchsticks (or trackpoints), and touchscreens. Touchpads are well supported
 * by this driver, touchstick support has not been tested much yet, and
 * touchscreens have not been tested at all.
 *
 * Up to three alternate settings are possible:
 *	setting 0: one int endpoint for relative movement (used by usbhid.ko)
 *	setting 1: one int endpoint for absolute finger position
 *	setting 2 (cPad only): one int endpoint for absolute finger position and
 *		   two bulk endpoints for the display (in/out)
 * This driver uses setting 1.
 */

#include <linux/kernel.h>
#include <linux/slab.h>
#include <linux/module.h>
#include <linux/moduleparam.h>
#include <linux/usb.h>
#include <linux/input.h>
#include <linux/usb/input.h>

#define USB_VENDOR_ID_SYNAPTICS	0x06cb
#define USB_DEVICE_ID_SYNAPTICS_TP	0x0001	/* Synaptics USB TouchPad */
#define USB_DEVICE_ID_SYNAPTICS_INT_TP	0x0002	/* Integrated USB TouchPad */
#define USB_DEVICE_ID_SYNAPTICS_CPAD	0x0003	/* Synaptics cPad */
#define USB_DEVICE_ID_SYNAPTICS_TS	0x0006	/* Synaptics TouchScreen */
#define USB_DEVICE_ID_SYNAPTICS_STICK	0x0007	/* Synaptics USB Styk */
#define USB_DEVICE_ID_SYNAPTICS_WP	0x0008	/* Synaptics USB WheelPad */
#define USB_DEVICE_ID_SYNAPTICS_COMP_TP	0x0009	/* Composite USB TouchPad */
#define USB_DEVICE_ID_SYNAPTICS_WTP	0x0010	/* Wireless TouchPad */
#define USB_DEVICE_ID_SYNAPTICS_DPAD	0x0013	/* DisplayPad */

#define SYNUSB_TOUCHPAD			(1 << 0)
#define SYNUSB_STICK			(1 << 1)
#define SYNUSB_TOUCHSCREEN		(1 << 2)
#define SYNUSB_AUXDISPLAY		(1 << 3) /* For cPad */
#define SYNUSB_COMBO			(1 << 4) /* Composite device (TP + stick) */
#define SYNUSB_IO_ALWAYS		(1 << 5)

#define USB_DEVICE_SYNAPTICS(prod, kind)		\
	USB_DEVICE(USB_VENDOR_ID_SYNAPTICS,		\
		   USB_DEVICE_ID_SYNAPTICS_##prod),	\
	.driver_info = (kind),

#define SYNUSB_RECV_SIZE	8

#define XMIN_NOMINAL		1472
#define XMAX_NOMINAL		5472
#define YMIN_NOMINAL		1408
#define YMAX_NOMINAL		4448

struct synusb {
	struct usb_device *udev;
	struct usb_interface *intf;
	struct urb *urb;
	unsigned char *data;

	/* serialize access to open/suspend */
	struct mutex pm_mutex;
	bool is_open;

	/* input device related data structures */
	struct input_dev *input;
	char name[128];
	char phys[64];

	/* characteristics of the device */
	unsigned long flags;
};

static void synusb_report_buttons(struct synusb *synusb)
{
	struct input_dev *input_dev = synusb->input;

	input_report_key(input_dev, BTN_LEFT, synusb->data[1] & 0x04);
	input_report_key(input_dev, BTN_RIGHT, synusb->data[1] & 0x01);
	input_report_key(input_dev, BTN_MIDDLE, synusb->data[1] & 0x02);
}

static void synusb_report_stick(struct synusb *synusb)
{
	struct input_dev *input_dev = synusb->input;
	int x, y;
	unsigned int pressure;

	pressure = synusb->data[6];
	x = (s16)(be16_to_cpup((__be16 *)&synusb->data[2]) << 3) >> 7;
	y = (s16)(be16_to_cpup((__be16 *)&synusb->data[4]) << 3) >> 7;

	if (pressure > 0) {
		input_report_rel(input_dev, REL_X, x);
		input_report_rel(input_dev, REL_Y, -y);
	}

	input_report_abs(input_dev, ABS_PRESSURE, pressure);

	synusb_report_buttons(synusb);

	input_sync(input_dev);
}

static void synusb_report_touchpad(struct synusb *synusb)
{
	struct input_dev *input_dev = synusb->input;
	unsigned int num_fingers, tool_width;
	unsigned int x, y;
	unsigned int pressure, w;

	pressure = synusb->data[6];
	x = be16_to_cpup((__be16 *)&synusb->data[2]);
	y = be16_to_cpup((__be16 *)&synusb->data[4]);
	w = synusb->data[0] & 0x0f;

	if (pressure > 0) {
		num_fingers = 1;
		tool_width = 5;
		switch (w) {
		case 0 ... 1:
			num_fingers = 2 + w;
			break;

		case 2:	                /* pen, pretend its a finger */
			break;

		case 4 ... 15:
			tool_width = w;
			break;
		}
	} else {
		num_fingers = 0;
		tool_width = 0;
	}

	/*
	 * Post events
	 * BTN_TOUCH has to be first as mousedev relies on it when doing
	 * absolute -> relative conversion
	 */

	if (pressure > 30)
		input_report_key(input_dev, BTN_TOUCH, 1);
	if (pressure < 25)
		input_report_key(input_dev, BTN_TOUCH, 0);

	if (num_fingers > 0) {
		input_report_abs(input_dev, ABS_X, x);
		input_report_abs(input_dev, ABS_Y,
				 YMAX_NOMINAL + YMIN_NOMINAL - y);
	}

	input_report_abs(input_dev, ABS_PRESSURE, pressure);
	input_report_abs(input_dev, ABS_TOOL_WIDTH, tool_width);

	input_report_key(input_dev, BTN_TOOL_FINGER, num_fingers == 1);
	input_report_key(input_dev, BTN_TOOL_DOUBLETAP, num_fingers == 2);
	input_report_key(input_dev, BTN_TOOL_TRIPLETAP, num_fingers == 3);

	synusb_report_buttons(synusb);
	if (synusb->flags & SYNUSB_AUXDISPLAY)
		input_report_key(input_dev, BTN_MIDDLE, synusb->data[1] & 0x08);

	input_sync(input_dev);
}

static void synusb_irq(struct urb *urb)
{
	struct synusb *synusb = urb->context;
	int error;

	/* Check our status in case we need to bail out early. */
	switch (urb->status) {
	case 0:
		usb_mark_last_busy(synusb->udev);
		break;

	/* Device went away so don't keep trying to read from it. */
	case -ECONNRESET:
	case -ENOENT:
	case -ESHUTDOWN:
		return;

	default:
		goto resubmit;
		break;
	}

	if (synusb->flags & SYNUSB_STICK)
		synusb_report_stick(synusb);
	else
		synusb_report_touchpad(synusb);

resubmit:
	error = usb_submit_urb(urb, GFP_ATOMIC);
	if (error && error != -EPERM)
		dev_err(&synusb->intf->dev,
			"%s - usb_submit_urb failed with result: %d",
			__func__, error);
}

static struct usb_endpoint_descriptor *
synusb_get_in_endpoint(struct usb_host_interface *iface)
{

	struct usb_endpoint_descriptor *endpoint;
	int i;

	for (i = 0; i < iface->desc.bNumEndpoints; ++i) {
		endpoint = &iface->endpoint[i].desc;

		if (usb_endpoint_is_int_in(endpoint)) {
			/* we found our interrupt in endpoint */
			return endpoint;
		}
	}

	return NULL;
}

static int synusb_open(struct input_dev *dev)
{
	struct synusb *synusb = input_get_drvdata(dev);
	int retval;

	retval = usb_autopm_get_interface(synusb->intf);
	if (retval) {
		dev_err(&synusb->intf->dev,
			"%s - usb_autopm_get_interface failed, error: %d\n",
			__func__, retval);
		return retval;
	}

	mutex_lock(&synusb->pm_mutex);
	retval = usb_submit_urb(synusb->urb, GFP_KERNEL);
	if (retval) {
		dev_err(&synusb->intf->dev,
			"%s - usb_submit_urb failed, error: %d\n",
			__func__, retval);
		retval = -EIO;
		goto out;
	}

	synusb->intf->needs_remote_wakeup = 1;
	synusb->is_open = true;

out:
	mutex_unlock(&synusb->pm_mutex);
	usb_autopm_put_interface(synusb->intf);
	return retval;
}

static void synusb_close(struct input_dev *dev)
{
	struct synusb *synusb = input_get_drvdata(dev);
	int autopm_error;

	autopm_error = usb_autopm_get_interface(synusb->intf);

	mutex_lock(&synusb->pm_mutex);
	usb_kill_urb(synusb->urb);
	synusb->intf->needs_remote_wakeup = 0;
	synusb->is_open = false;
	mutex_unlock(&synusb->pm_mutex);

	if (!autopm_error)
		usb_autopm_put_interface(synusb->intf);
}

static int synusb_probe(struct usb_interface *intf,
			const struct usb_device_id *id)
{
	struct usb_device *udev = interface_to_usbdev(intf);
	struct usb_endpoint_descriptor *ep;
	struct synusb *synusb;
	struct input_dev *input_dev;
	unsigned int intf_num = intf->cur_altsetting->desc.bInterfaceNumber;
	unsigned int altsetting = min(intf->num_altsetting, 1U);
	int error;

	error = usb_set_interface(udev, intf_num, altsetting);
	if (error) {
		dev_err(&udev->dev,
			"Can not set alternate setting to %i, error: %i",
			altsetting, error);
		return error;
	}

	ep = synusb_get_in_endpoint(intf->cur_altsetting);
	if (!ep)
		return -ENODEV;

	synusb = kzalloc(sizeof(*synusb), GFP_KERNEL);
	input_dev = input_allocate_device();
	if (!synusb || !input_dev) {
		error = -ENOMEM;
		goto err_free_mem;
	}

	synusb->udev = udev;
	synusb->intf = intf;
	synusb->input = input_dev;
	mutex_init(&synusb->pm_mutex);

	synusb->flags = id->driver_info;
	if (synusb->flags & SYNUSB_COMBO) {
		/*
		 * This is a combo device, we need to set proper
		 * capability, depending on the interface.
		 */
		synusb->flags |= intf_num == 1 ?
					SYNUSB_STICK : SYNUSB_TOUCHPAD;
	}

	synusb->urb = usb_alloc_urb(0, GFP_KERNEL);
	if (!synusb->urb) {
		error = -ENOMEM;
		goto err_free_mem;
	}

	synusb->data = usb_alloc_coherent(udev, SYNUSB_RECV_SIZE, GFP_KERNEL,
					  &synusb->urb->transfer_dma);
	if (!synusb->data) {
		error = -ENOMEM;
		goto err_free_urb;
	}

	usb_fill_int_urb(synusb->urb, udev,
			 usb_rcvintpipe(udev, ep->bEndpointAddress),
			 synusb->data, SYNUSB_RECV_SIZE,
			 synusb_irq, synusb,
			 ep->bInterval);
	synusb->urb->transfer_flags |= URB_NO_TRANSFER_DMA_MAP;

	if (udev->manufacturer)
		strlcpy(synusb->name, udev->manufacturer,
			sizeof(synusb->name));

	if (udev->product) {
		if (udev->manufacturer)
			strlcat(synusb->name, " ", sizeof(synusb->name));
		strlcat(synusb->name, udev->product, sizeof(synusb->name));
	}

	if (!strlen(synusb->name))
		snprintf(synusb->name, sizeof(synusb->name),
			 "USB Synaptics Device %04x:%04x",
			 le16_to_cpu(udev->descriptor.idVendor),
			 le16_to_cpu(udev->descriptor.idProduct));

	if (synusb->flags & SYNUSB_STICK)
		strlcat(synusb->name, " (Stick)", sizeof(synusb->name));

	usb_make_path(udev, synusb->phys, sizeof(synusb->phys));
	strlcat(synusb->phys, "/input0", sizeof(synusb->phys));

	input_dev->name = synusb->name;
	input_dev->phys = synusb->phys;
	usb_to_input_id(udev, &input_dev->id);
	input_dev->dev.parent = &synusb->intf->dev;

	if (!(synusb->flags & SYNUSB_IO_ALWAYS)) {
		input_dev->open = synusb_open;
		input_dev->close = synusb_close;
	}

	input_set_drvdata(input_dev, synusb);

	__set_bit(EV_ABS, input_dev->evbit);
	__set_bit(EV_KEY, input_dev->evbit);

	if (synusb->flags & SYNUSB_STICK) {
		__set_bit(EV_REL, input_dev->evbit);
		__set_bit(REL_X, input_dev->relbit);
		__set_bit(REL_Y, input_dev->relbit);
		__set_bit(INPUT_PROP_POINTING_STICK, input_dev->propbit);
		input_set_abs_params(input_dev, ABS_PRESSURE, 0, 127, 0, 0);
	} else {
		input_set_abs_params(input_dev, ABS_X,
				     XMIN_NOMINAL, XMAX_NOMINAL, 0, 0);
		input_set_abs_params(input_dev, ABS_Y,
				     YMIN_NOMINAL, YMAX_NOMINAL, 0, 0);
		input_set_abs_params(input_dev, ABS_PRESSURE, 0, 255, 0, 0);
		input_set_abs_params(input_dev, ABS_TOOL_WIDTH, 0, 15, 0, 0);
		__set_bit(BTN_TOUCH, input_dev->keybit);
		__set_bit(BTN_TOOL_FINGER, input_dev->keybit);
		__set_bit(BTN_TOOL_DOUBLETAP, input_dev->keybit);
		__set_bit(BTN_TOOL_TRIPLETAP, input_dev->keybit);
	}

	if (synusb->flags & SYNUSB_TOUCHSCREEN)
		__set_bit(INPUT_PROP_DIRECT, input_dev->propbit);
	else
		__set_bit(INPUT_PROP_POINTER, input_dev->propbit);

	__set_bit(BTN_LEFT, input_dev->keybit);
	__set_bit(BTN_RIGHT, input_dev->keybit);
	__set_bit(BTN_MIDDLE, input_dev->keybit);

	usb_set_intfdata(intf, synusb);

	if (synusb->flags & SYNUSB_IO_ALWAYS) {
		error = synusb_open(input_dev);
		if (error)
			goto err_free_dma;
	}

	error = input_register_device(input_dev);
	if (error) {
		dev_err(&udev->dev,
			"Failed to register input device, error %d\n",
			error);
		goto err_stop_io;
	}

	return 0;

err_stop_io:
	if (synusb->flags & SYNUSB_IO_ALWAYS)
		synusb_close(synusb->input);
err_free_dma:
	usb_free_coherent(udev, SYNUSB_RECV_SIZE, synusb->data,
			  synusb->urb->transfer_dma);
err_free_urb:
	usb_free_urb(synusb->urb);
err_free_mem:
	input_free_device(input_dev);
	kfree(synusb);
	usb_set_intfdata(intf, NULL);

	return error;
}

static void synusb_disconnect(struct usb_interface *intf)
{
	struct synusb *synusb = usb_get_intfdata(intf);
	struct usb_device *udev = interface_to_usbdev(intf);

	if (synusb->flags & SYNUSB_IO_ALWAYS)
		synusb_close(synusb->input);

	input_unregister_device(synusb->input);

	usb_free_coherent(udev, SYNUSB_RECV_SIZE, synusb->data,
			  synusb->urb->transfer_dma);
	usb_free_urb(synusb->urb);
	kfree(synusb);

	usb_set_intfdata(intf, NULL);
}

static int synusb_suspend(struct usb_interface *intf, pm_message_t message)
{
	struct synusb *synusb = usb_get_intfdata(intf);

	mutex_lock(&synusb->pm_mutex);
	usb_kill_urb(synusb->urb);
	mutex_unlock(&synusb->pm_mutex);

	return 0;
}

static int synusb_resume(struct usb_interface *intf)
{
	struct synusb *synusb = usb_get_intfdata(intf);
	int retval = 0;

	mutex_lock(&synusb->pm_mutex);

	if ((synusb->is_open || (synusb->flags & SYNUSB_IO_ALWAYS)) &&
	    usb_submit_urb(synusb->urb, GFP_NOIO) < 0) {
		retval = -EIO;
	}

	mutex_unlock(&synusb->pm_mutex);

	return retval;
}

static int synusb_pre_reset(struct usb_interface *intf)
{
	struct synusb *synusb = usb_get_intfdata(intf);

	mutex_lock(&synusb->pm_mutex);
	usb_kill_urb(synusb->urb);

	return 0;
}

static int synusb_post_reset(struct usb_interface *intf)
{
	struct synusb *synusb = usb_get_intfdata(intf);
	int retval = 0;

	if ((synusb->is_open || (synusb->flags & SYNUSB_IO_ALWAYS)) &&
	    usb_submit_urb(synusb->urb, GFP_NOIO) < 0) {
		retval = -EIO;
	}

	mutex_unlock(&synusb->pm_mutex);

	return retval;
}

static int synusb_reset_resume(struct usb_interface *intf)
{
	return synusb_resume(intf);
}

static const struct usb_device_id synusb_idtable[] = {
	{ USB_DEVICE_SYNAPTICS(TP, SYNUSB_TOUCHPAD) },
	{ USB_DEVICE_SYNAPTICS(INT_TP, SYNUSB_TOUCHPAD) },
	{ USB_DEVICE_SYNAPTICS(CPAD,
		SYNUSB_TOUCHPAD | SYNUSB_AUXDISPLAY | SYNUSB_IO_ALWAYS) },
	{ USB_DEVICE_SYNAPTICS(TS, SYNUSB_TOUCHSCREEN) },
	{ USB_DEVICE_SYNAPTICS(STICK, SYNUSB_STICK) },
	{ USB_DEVICE_SYNAPTICS(WP, SYNUSB_TOUCHPAD) },
	{ USB_DEVICE_SYNAPTICS(COMP_TP, SYNUSB_COMBO) },
	{ USB_DEVICE_SYNAPTICS(WTP, SYNUSB_TOUCHPAD) },
	{ USB_DEVICE_SYNAPTICS(DPAD, SYNUSB_TOUCHPAD) },
	{ }
};
MODULE_DEVICE_TABLE(usb, synusb_idtable);

static struct usb_driver synusb_driver = {
	.name		= "synaptics_usb",
	.probe		= synusb_probe,
	.disconnect	= synusb_disconnect,
	.id_table	= synusb_idtable,
	.suspend	= synusb_suspend,
	.resume		= synusb_resume,
	.pre_reset	= synusb_pre_reset,
	.post_reset	= synusb_post_reset,
	.reset_resume	= synusb_reset_resume,
	.supports_autosuspend = 1,
};

module_usb_driver(synusb_driver);

MODULE_AUTHOR("Rob Miller <rob@inpharmatica.co.uk>, "
              "Ron Lee <ron@debian.org>, "
              "Jan Steinhoff <cpad@jan-steinhoff.de>");
MODULE_DESCRIPTION("Synaptics USB device driver");
MODULE_LICENSE("GPL");
