drivers/input/mouse/trackpoint.c

Source file repositories/reference/linux-study-clean/drivers/input/mouse/trackpoint.c

File Facts

System
Linux kernel
Corpus path
drivers/input/mouse/trackpoint.c
Extension
.c
Size
14240 bytes
Lines
522
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 trackpoint_attr_data {
	size_t field_offset;
	u8 command;
	u8 mask;
	bool inverted;
	u8 power_on_default;
};

static ssize_t trackpoint_show_int_attr(struct psmouse *psmouse,
					void *data, char *buf)
{
	struct trackpoint_data *tp = psmouse->private;
	struct trackpoint_attr_data *attr = data;
	u8 value = *(u8 *)((void *)tp + attr->field_offset);

	if (attr->inverted)
		value = !value;

	return sprintf(buf, "%u\n", value);
}

static ssize_t trackpoint_set_int_attr(struct psmouse *psmouse, void *data,
					const char *buf, size_t count)
{
	struct trackpoint_data *tp = psmouse->private;
	struct trackpoint_attr_data *attr = data;
	u8 *field = (void *)tp + attr->field_offset;
	u8 value;
	int err;

	err = kstrtou8(buf, 10, &value);
	if (err)
		return err;

	*field = value;
	err = trackpoint_write(&psmouse->ps2dev, attr->command, value);

	return err ?: count;
}

#define TRACKPOINT_INT_ATTR(_name, _command, _default)				\
	static struct trackpoint_attr_data trackpoint_attr_##_name = {		\
		.field_offset = offsetof(struct trackpoint_data, _name),	\
		.command = _command,						\
		.power_on_default = _default,					\
	};									\
	PSMOUSE_DEFINE_ATTR(_name, S_IWUSR | S_IRUGO,				\
			    &trackpoint_attr_##_name,				\
			    trackpoint_show_int_attr, trackpoint_set_int_attr)

static ssize_t trackpoint_set_bit_attr(struct psmouse *psmouse, void *data,
					const char *buf, size_t count)
{
	struct trackpoint_data *tp = psmouse->private;
	struct trackpoint_attr_data *attr = data;
	bool *field = (void *)tp + attr->field_offset;
	bool value;
	int err;

	err = kstrtobool(buf, &value);
	if (err)
		return err;

	if (attr->inverted)
		value = !value;

	if (*field != value) {
		*field = value;
		err = trackpoint_toggle_bit(&psmouse->ps2dev,
					    attr->command, attr->mask);
	}

	return err ?: count;
}


#define TRACKPOINT_BIT_ATTR(_name, _command, _mask, _inv, _default)	\
static struct trackpoint_attr_data trackpoint_attr_##_name = {		\
	.field_offset		= offsetof(struct trackpoint_data,	\
					   _name),			\
	.command		= _command,				\
	.mask			= _mask,				\
	.inverted		= _inv,					\
	.power_on_default	= _default,				\
	};								\
PSMOUSE_DEFINE_ATTR(_name, S_IWUSR | S_IRUGO,				\
		    &trackpoint_attr_##_name,				\
		    trackpoint_show_int_attr, trackpoint_set_bit_attr)

TRACKPOINT_INT_ATTR(sensitivity, TP_SENS, TP_DEF_SENS);

Annotation

Implementation Notes