drivers/input/touchscreen/wacom_w8001.c

Source file repositories/reference/linux-study-clean/drivers/input/touchscreen/wacom_w8001.c

File Facts

System
Linux kernel
Corpus path
drivers/input/touchscreen/wacom_w8001.c
Extension
.c
Size
16958 bytes
Lines
705
Domain
Driver Families
Bucket
drivers/input
Inferred role
Driver Families: implementation source
Status
source implementation candidate

Why This File Exists

Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.

Dependency Surface

Detected Declarations

Annotated Snippet

struct w8001_coord {
	u8 rdy;
	u8 tsw;
	u8 f1;
	u8 f2;
	u16 x;
	u16 y;
	u16 pen_pressure;
	u8 tilt_x;
	u8 tilt_y;
};

/* touch query reply packet */
struct w8001_touch_query {
	u16 x;
	u16 y;
	u8 panel_res;
	u8 capacity_res;
	u8 sensor_id;
};

/*
 * Per-touchscreen data.
 */

struct w8001 {
	struct input_dev *pen_dev;
	struct input_dev *touch_dev;
	struct serio *serio;
	struct completion cmd_done;
	int id;
	int idx;
	unsigned char response_type;
	unsigned char response[W8001_MAX_LENGTH];
	unsigned char data[W8001_MAX_LENGTH];
	char phys[W8001_MAX_PHYS];
	int type;
	unsigned int pktlen;
	u16 max_touch_x;
	u16 max_touch_y;
	u16 max_pen_x;
	u16 max_pen_y;
	char pen_name[64];
	char touch_name[64];
	int open_count;
	struct mutex mutex;
};

static void parse_pen_data(u8 *data, struct w8001_coord *coord)
{
	memset(coord, 0, sizeof(*coord));

	coord->rdy = data[0] & 0x20;
	coord->tsw = data[0] & 0x01;
	coord->f1 = data[0] & 0x02;
	coord->f2 = data[0] & 0x04;

	coord->x = (data[1] & 0x7F) << 9;
	coord->x |= (data[2] & 0x7F) << 2;
	coord->x |= (data[6] & 0x60) >> 5;

	coord->y = (data[3] & 0x7F) << 9;
	coord->y |= (data[4] & 0x7F) << 2;
	coord->y |= (data[6] & 0x18) >> 3;

	coord->pen_pressure = data[5] & 0x7F;
	coord->pen_pressure |= (data[6] & 0x07) << 7 ;

	coord->tilt_x = data[7] & 0x7F;
	coord->tilt_y = data[8] & 0x7F;
}

static void parse_single_touch(u8 *data, struct w8001_coord *coord)
{
	coord->x = (data[1] << 7) | data[2];
	coord->y = (data[3] << 7) | data[4];
	coord->tsw = data[0] & 0x01;
}

static void scale_touch_coordinates(struct w8001 *w8001,
				    unsigned int *x, unsigned int *y)
{
	if (w8001->max_pen_x && w8001->max_touch_x)
		*x = *x * w8001->max_pen_x / w8001->max_touch_x;

	if (w8001->max_pen_y && w8001->max_touch_y)
		*y = *y * w8001->max_pen_y / w8001->max_touch_y;
}

static void parse_multi_touch(struct w8001 *w8001)

Annotation

Implementation Notes