// SPDX-License-Identifier: GPL-2.0-only /* Copyright (c) 2025 Benjamin Tissoires */ #include "vmlinux.h" #include "hid_bpf.h" #include "hid_bpf_helpers.h" #include "hid_report_helpers.h" #include "hid_usages.h" #include HID_BPF_CONFIG( HID_DEVICE(BUS_ANY, HID_GROUP_MULTITOUCH_WIN_8, HID_VID_ANY, HID_PID_ANY), ); EXPORT_UDEV_PROP(HID_DIGITIZER_PAD_TYPE, 32); __u8 hw_req_buf[1024]; /* to be filled by udev-hid-bpf */ struct hid_rdesc_descriptor HID_REPORT_DESCRIPTOR; SEC("syscall") int probe(struct hid_bpf_probe_args *ctx) { struct hid_rdesc_report *pad_type_feature = NULL; struct hid_rdesc_field *pad_type = NULL; struct hid_rdesc_report *feature; struct hid_bpf_ctx *hid_ctx; char *pad_type_str = ""; int ret; hid_bpf_for_each_feature_report(&HID_REPORT_DESCRIPTOR, feature) { struct hid_rdesc_field *field; hid_bpf_for_each_field(feature, field) { if (field->usage_page == HidUsagePage_Digitizers && field->usage_id == HidUsage_Dig_PadType) { pad_type = field; pad_type_feature = feature; break; } } if (pad_type) break; } if (!pad_type || !pad_type_feature) { ctx->retval = -EINVAL; return 0; } hid_ctx = hid_bpf_allocate_context(ctx->hid); if (!hid_ctx) return -1; /* EPERM check */ hw_req_buf[0] = pad_type_feature->report_id; ret = hid_bpf_hw_request(hid_ctx, hw_req_buf, sizeof(hw_req_buf), HID_FEATURE_REPORT, HID_REQ_GET_REPORT); hid_bpf_release_context(hid_ctx); if (ret < 0) { ctx->retval = ret; return 0; } ctx->retval = 0; switch (EXTRACT_BITS(hw_req_buf, pad_type)) { case 0: pad_type_str = "Clickpad"; break; case 1: pad_type_str = "Pressurepad"; break; case 2: pad_type_str = "Discrete"; break; default: pad_type_str = "Unknown"; } UDEV_PROP_SPRINTF(HID_DIGITIZER_PAD_TYPE, "%s", pad_type_str); return 0; } char _license[] SEC("license") = "GPL";