From: "José Expósito" <jose.exposito89@gmail.com>
To: jikos@kernel.org
Cc: benjamin.tissoires@redhat.com, spbnick@gmail.com,
linux-input@vger.kernel.org, linux-kernel@vger.kernel.org,
"José Expósito" <jose.exposito89@gmail.com>
Subject: [PATCH 4/7] HID: uclogic: Split pen and frame raw event handling
Date: Thu, 10 Feb 2022 20:04:34 +0100 [thread overview]
Message-ID: <20220210190437.50152-5-jose.exposito89@gmail.com> (raw)
In-Reply-To: <20220210190437.50152-1-jose.exposito89@gmail.com>
From: Nikolai Kondrashov <spbnick@gmail.com>
In order to avoid ending up with a big uclogic_raw_event function,
split it in two smaller functions: uclogic_raw_event_pen for the pen
events and uclogic_raw_event_frame for the pad events.
Signed-off-by: Nikolai Kondrashov <spbnick@gmail.com>
Signed-off-by: José Expósito <jose.exposito89@gmail.com>
---
drivers/hid/hid-uclogic-core.c | 195 ++++++++++++++++++++-------------
1 file changed, 120 insertions(+), 75 deletions(-)
diff --git a/drivers/hid/hid-uclogic-core.c b/drivers/hid/hid-uclogic-core.c
index 850c660ec2ab..9187fd835a46 100644
--- a/drivers/hid/hid-uclogic-core.c
+++ b/drivers/hid/hid-uclogic-core.c
@@ -246,6 +246,123 @@ static int uclogic_resume(struct hid_device *hdev)
}
#endif
+/**
+ * uclogic_raw_event_pen - handle raw pen events (pen HID reports).
+ *
+ * @drvdata: Driver data.
+ * @data: Report data buffer, can be modified.
+ * @size: Report data size, bytes.
+ *
+ * Returns:
+ * Negative value on error (stops event delivery), zero for success.
+ */
+static int uclogic_raw_event_pen(struct uclogic_drvdata *drvdata,
+ u8 *data, int size)
+{
+ struct uclogic_params *params = &drvdata->params;
+
+ WARN_ON(drvdata == NULL);
+ WARN_ON(data == NULL && size != 0);
+
+ /* If in-range reports are inverted */
+ if (params->pen.inrange ==
+ UCLOGIC_PARAMS_PEN_INRANGE_INVERTED) {
+ /* Invert the in-range bit */
+ data[1] ^= 0x40;
+ }
+ /*
+ * If report contains fragmented high-resolution pen
+ * coordinates
+ */
+ if (size >= 10 && params->pen.fragmented_hires) {
+ u8 pressure_low_byte;
+ u8 pressure_high_byte;
+
+ /* Lift pressure bytes */
+ pressure_low_byte = data[6];
+ pressure_high_byte = data[7];
+ /*
+ * Move Y coord to make space for high-order X
+ * coord byte
+ */
+ data[6] = data[5];
+ data[5] = data[4];
+ /* Move high-order X coord byte */
+ data[4] = data[8];
+ /* Move high-order Y coord byte */
+ data[7] = data[9];
+ /* Place pressure bytes */
+ data[8] = pressure_low_byte;
+ data[9] = pressure_high_byte;
+ }
+ /* If we need to emulate in-range detection */
+ if (params->pen.inrange == UCLOGIC_PARAMS_PEN_INRANGE_NONE) {
+ /* Set in-range bit */
+ data[1] |= 0x40;
+ /* (Re-)start in-range timeout */
+ mod_timer(&drvdata->inrange_timer,
+ jiffies + msecs_to_jiffies(100));
+ }
+ /* If we report tilt and Y direction is flipped */
+ if (size >= 12 && params->pen.tilt_y_flipped)
+ data[11] = -data[11];
+
+ return 0;
+}
+
+/**
+ * uclogic_raw_event_frame - handle raw frame events (frame HID reports).
+ *
+ * @drvdata: Driver data.
+ * @data: Report data buffer, can be modified.
+ * @size: Report data size, bytes.
+ *
+ * Returns:
+ * Negative value on error (stops event delivery), zero for success.
+ */
+static int uclogic_raw_event_frame(struct uclogic_drvdata *drvdata,
+ u8 *data, int size)
+{
+ struct uclogic_params *params = &drvdata->params;
+
+ WARN_ON(drvdata == NULL);
+ WARN_ON(data == NULL && size != 0);
+
+ /* If need to, and can, set pad device ID for Wacom drivers */
+ if (params->frame.dev_id_byte > 0 &&
+ params->frame.dev_id_byte < size) {
+ data[params->frame.dev_id_byte] = 0xf;
+ }
+ /* If need to, and can, read rotary encoder state change */
+ if (params->frame.re_lsb > 0 &&
+ params->frame.re_lsb / 8 < size) {
+ unsigned int byte = params->frame.re_lsb / 8;
+ unsigned int bit = params->frame.re_lsb % 8;
+
+ u8 change;
+ u8 prev_state = drvdata->re_state;
+ /* Read Gray-coded state */
+ u8 state = (data[byte] >> bit) & 0x3;
+ /* Encode state change into 2-bit signed integer */
+ if ((prev_state == 1 && state == 0) ||
+ (prev_state == 2 && state == 3)) {
+ change = 1;
+ } else if ((prev_state == 2 && state == 0) ||
+ (prev_state == 1 && state == 3)) {
+ change = 3;
+ } else {
+ change = 0;
+ }
+ /* Write change */
+ data[byte] = (data[byte] & ~((u8)3 << bit)) |
+ (change << bit);
+ /* Remember state */
+ drvdata->re_state = state;
+ }
+
+ return 0;
+}
+
static int uclogic_raw_event(struct hid_device *hdev,
struct hid_report *report,
u8 *data, int size)
@@ -265,85 +382,13 @@ static int uclogic_raw_event(struct hid_device *hdev,
data[0] = params->frame.id;
return 0;
}
- /* If in-range reports are inverted */
- if (params->pen.inrange ==
- UCLOGIC_PARAMS_PEN_INRANGE_INVERTED) {
- /* Invert the in-range bit */
- data[1] ^= 0x40;
- }
- /*
- * If report contains fragmented high-resolution pen
- * coordinates
- */
- if (size >= 10 && params->pen.fragmented_hires) {
- u8 pressure_low_byte;
- u8 pressure_high_byte;
-
- /* Lift pressure bytes */
- pressure_low_byte = data[6];
- pressure_high_byte = data[7];
- /*
- * Move Y coord to make space for high-order X
- * coord byte
- */
- data[6] = data[5];
- data[5] = data[4];
- /* Move high-order X coord byte */
- data[4] = data[8];
- /* Move high-order Y coord byte */
- data[7] = data[9];
- /* Place pressure bytes */
- data[8] = pressure_low_byte;
- data[9] = pressure_high_byte;
- }
- /* If we need to emulate in-range detection */
- if (params->pen.inrange == UCLOGIC_PARAMS_PEN_INRANGE_NONE) {
- /* Set in-range bit */
- data[1] |= 0x40;
- /* (Re-)start in-range timeout */
- mod_timer(&drvdata->inrange_timer,
- jiffies + msecs_to_jiffies(100));
- }
- /* If we report tilt and Y direction is flipped */
- if (size >= 12 && params->pen.tilt_y_flipped)
- data[11] = -data[11];
+ return uclogic_raw_event_pen(drvdata, data, size);
}
/* Tweak frame control reports, if necessary */
if ((report->type == HID_INPUT_REPORT) &&
- (report->id == params->frame.id)) {
- /* If need to, and can, set pad device ID for Wacom drivers */
- if (params->frame.dev_id_byte > 0 &&
- params->frame.dev_id_byte < size) {
- data[params->frame.dev_id_byte] = 0xf;
- }
- /* If need to, and can, read rotary encoder state change */
- if (params->frame.re_lsb > 0 &&
- params->frame.re_lsb / 8 < size) {
- unsigned int byte = params->frame.re_lsb / 8;
- unsigned int bit = params->frame.re_lsb % 8;
-
- u8 change;
- u8 prev_state = drvdata->re_state;
- /* Read Gray-coded state */
- u8 state = (data[byte] >> bit) & 0x3;
- /* Encode state change into 2-bit signed integer */
- if ((prev_state == 1 && state == 0) ||
- (prev_state == 2 && state == 3)) {
- change = 1;
- } else if ((prev_state == 2 && state == 0) ||
- (prev_state == 1 && state == 3)) {
- change = 3;
- } else {
- change = 0;
- }
- /* Write change */
- data[byte] = (data[byte] & ~((u8)3 << bit)) |
- (change << bit);
- /* Remember state */
- drvdata->re_state = state;
- }
- }
+ (report->id == params->frame.id))
+ return uclogic_raw_event_frame(drvdata, data, size);
return 0;
}
--
2.25.1
next prev parent reply other threads:[~2022-02-10 19:05 UTC|newest]
Thread overview: 9+ messages / expand[flat|nested] mbox.gz Atom feed top
2022-02-10 19:04 [PATCH 0/7] DIGImend patches, part one José Expósito
2022-02-10 19:04 ` [PATCH 1/7] HID: uclogic: Support Huion tilt reporting José Expósito
2022-02-10 19:04 ` [PATCH 2/7] HID: uclogic: Rename Huion HS64 PID to Huion Tablet 2 José Expósito
2022-02-10 19:04 ` [PATCH 3/7] HID: uclogic: Support Huion 13th frame button José Expósito
2022-02-10 19:04 ` José Expósito [this message]
2022-02-10 19:04 ` [PATCH 5/7] HID: uclogic: Access pen/frame params directly in raw_event handling José Expósito
2022-02-10 19:04 ` [PATCH 6/7] HID: uclogic: Skip non-input raw events earlier José Expósito
2022-02-10 19:04 ` [PATCH 7/7] HID: uclogic: Handle virtual frame reports José Expósito
2022-02-16 15:43 ` [PATCH 0/7] DIGImend patches, part one Jiri Kosina
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20220210190437.50152-5-jose.exposito89@gmail.com \
--to=jose.exposito89@gmail.com \
--cc=benjamin.tissoires@redhat.com \
--cc=jikos@kernel.org \
--cc=linux-input@vger.kernel.org \
--cc=linux-kernel@vger.kernel.org \
--cc=spbnick@gmail.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox
all inboxes | Powered by JetHome®