mirror of
https://github.com/ps1x/onexplayer-superxcontrol.git
synced 2026-09-10 17:28:10 +00:00
Archive Super X rotation upstream submissions
This commit is contained in:
parent
93eb81e853
commit
e75643f2c4
9 changed files with 768 additions and 0 deletions
78
contrib/upstream-rotation/README.md
Normal file
78
contrib/upstream-rotation/README.md
Normal file
|
|
@ -0,0 +1,78 @@
|
|||
# OneXPlayer Super X automatic rotation upstream submissions
|
||||
|
||||
Automatic rotation on the OneXPlayer Super X needs two independent pieces of
|
||||
upstream support:
|
||||
|
||||
1. Linux must report tablet posture when the pogo-pin keyboard is detached.
|
||||
2. systemd's sensor hardware database must map the BMI260 axes to the display.
|
||||
|
||||
The patches in this directory are based on current upstream sources and are
|
||||
intended for their respective projects. They should not be combined into one
|
||||
submission.
|
||||
|
||||
## Linux kernel
|
||||
|
||||
Patch:
|
||||
|
||||
- `linux/0001-platform-x86-oxpec-report-tablet-mode-on-super-x.patch`
|
||||
|
||||
Base commit:
|
||||
|
||||
- `f5098b6bae761e346ebcd9da7f95622c04733cff`
|
||||
|
||||
The Super X pogo-pin keyboard enumerates as USB `1a86:1305`. The patch extends
|
||||
the existing DMI-matched `oxpec` platform driver with a persistent
|
||||
`SW_TABLET_MODE` input switch:
|
||||
|
||||
- keyboard present: laptop mode (`SW_TABLET_MODE=0`)
|
||||
- keyboard absent: tablet mode (`SW_TABLET_MODE=1`)
|
||||
|
||||
Other USB and Bluetooth keyboards do not affect the switch.
|
||||
|
||||
Suggested recipients, generated by `scripts/get_maintainer.pl`:
|
||||
|
||||
- Hans de Goede `<hansg@kernel.org>`
|
||||
- Ilpo Jarvinen `<ilpo.jarvinen@linux.intel.com>`
|
||||
- Antheas Kapenekakis `<lkml@antheas.dev>`
|
||||
- Derek John Clark `<derekjohn.clark@gmail.com>`
|
||||
- Joaquin Ignacio Aramendia `<samsagax@gmail.com>`
|
||||
- `platform-driver-x86@vger.kernel.org`
|
||||
- `linux-kernel@vger.kernel.org`
|
||||
|
||||
Validation:
|
||||
|
||||
- compiled the exact patched upstream `oxpec.c` against Fedora kernel
|
||||
`7.1.3-100.fc43.x86_64` headers
|
||||
- `scripts/checkpatch.pl --no-tree`: zero errors and zero warnings
|
||||
- tested pogo keyboard attach and detach on the hardware
|
||||
- verified Mutter `PanelOrientationManaged` changes `false -> true -> false`
|
||||
|
||||
## systemd hwdb
|
||||
|
||||
Patch:
|
||||
|
||||
- `systemd/0001-hwdb-add-super-x-accelerometer-matrix.patch`
|
||||
|
||||
Base commit:
|
||||
|
||||
- `7412c16ef8e60ec201839a46a459950cd1328962`
|
||||
|
||||
The tested matrix is:
|
||||
|
||||
```text
|
||||
0, -1, 0; 1, 0, 0; 0, 0, 1
|
||||
```
|
||||
|
||||
Validation:
|
||||
|
||||
- systemd's `test/hwdb-test.sh` passes
|
||||
- strict hwdb compilation passes
|
||||
- querying the compiled database with the complete machine modalias returns
|
||||
the expected `ACCEL_MOUNT_MATRIX`
|
||||
- tested with iio-sensor-proxy 3.8 and Mutter 49.7
|
||||
- verified native landscape and both portrait orientations on the hardware
|
||||
|
||||
## AI assistance disclosure
|
||||
|
||||
Development of both patches used assistance from ChatGPT 5.6 sol. The same
|
||||
disclosure is included in each patch's commit message.
|
||||
|
|
@ -0,0 +1,202 @@
|
|||
From a71833601fc441460bb02e6ec07e95b29f553865 Mon Sep 17 00:00:00 2001
|
||||
From: Alexander Egorov <begeebe@gmail.com>
|
||||
Date: Mon, 27 Jul 2026 22:45:52 +0300
|
||||
Subject: [PATCH] platform/x86: oxpec: Report tablet mode on OneXPlayer Super X
|
||||
|
||||
The OneXPlayer Super X has a detachable pogo-pin keyboard which
|
||||
enumerates as USB device 1a86:1305. The firmware does not expose a
|
||||
tablet-mode input switch.
|
||||
|
||||
Without SW_TABLET_MODE, userspace treats the built-in controller and
|
||||
other pointer devices as evidence that the system is in laptop mode.
|
||||
Mutter consequently leaves automatic display rotation disabled after
|
||||
the keyboard is detached.
|
||||
|
||||
On the Super X DMI match, register a persistent input device and report
|
||||
SW_TABLET_MODE according to the pogo keyboard USB hotplug state. Report
|
||||
laptop mode while the keyboard is present and tablet mode while it is
|
||||
absent. Other USB and Bluetooth keyboards do not affect the switch.
|
||||
|
||||
Tested on a OneXPlayer Super X with keyboard attach and detach events.
|
||||
Mutter changes PanelOrientationManaged in both directions and applies
|
||||
accelerometer-driven display transforms only while the pogo keyboard is
|
||||
absent.
|
||||
|
||||
Development of this patch used assistance from ChatGPT 5.6 sol.
|
||||
|
||||
Signed-off-by: Alexander Egorov <begeebe@gmail.com>
|
||||
---
|
||||
drivers/platform/x86/Kconfig | 7 ++-
|
||||
drivers/platform/x86/oxpec.c | 110 +++++++++++++++++++++++++++++++++++
|
||||
2 files changed, 115 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/drivers/platform/x86/Kconfig b/drivers/platform/x86/Kconfig
|
||||
index b54b521..3e30127 100644
|
||||
--- a/drivers/platform/x86/Kconfig
|
||||
+++ b/drivers/platform/x86/Kconfig
|
||||
@@ -1055,11 +1055,14 @@ config OXP_EC
|
||||
depends on ACPI_EC
|
||||
depends on ACPI_BATTERY
|
||||
depends on HWMON
|
||||
+ depends on INPUT
|
||||
+ depends on USB
|
||||
depends on X86
|
||||
help
|
||||
Enables support for the platform EC of OneXPlayer and AOKZOE
|
||||
- handheld devices. This includes fan speed, fan controls, and
|
||||
- disabling the default TDP behavior of the device.
|
||||
+ handheld devices. This includes fan speed, fan controls, disabling
|
||||
+ the default TDP behavior of the device, and tablet mode reporting
|
||||
+ on supported detachable models.
|
||||
|
||||
source "drivers/platform/x86/tuxedo/Kconfig"
|
||||
|
||||
diff --git a/drivers/platform/x86/oxpec.c b/drivers/platform/x86/oxpec.c
|
||||
index 99c0dfc..e64ae54 100644
|
||||
--- a/drivers/platform/x86/oxpec.c
|
||||
+++ b/drivers/platform/x86/oxpec.c
|
||||
@@ -18,10 +18,12 @@
|
||||
#include <linux/dmi.h>
|
||||
#include <linux/hwmon.h>
|
||||
#include <linux/init.h>
|
||||
+#include <linux/input.h>
|
||||
#include <linux/kernel.h>
|
||||
#include <linux/module.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/processor.h>
|
||||
+#include <linux/usb.h>
|
||||
#include <acpi/battery.h>
|
||||
|
||||
/* Handle ACPI lock mechanism */
|
||||
@@ -55,6 +57,14 @@ enum oxp_board {
|
||||
static enum oxp_board board;
|
||||
static struct device *oxp_dev;
|
||||
|
||||
+struct oxp_platform_data {
|
||||
+ struct input_dev *tablet_mode_input;
|
||||
+ struct notifier_block usb_notifier;
|
||||
+};
|
||||
+
|
||||
+#define OXP_SUPER_X_KEYBOARD_VID 0x1a86
|
||||
+#define OXP_SUPER_X_KEYBOARD_PID 0x1305
|
||||
+
|
||||
/* Fan reading and PWM */
|
||||
#define OXP_SENSOR_FAN_REG 0x76 /* Fan reading is 2 registers long */
|
||||
#define OXP_2_SENSOR_FAN_REG 0x58 /* Fan reading is 2 registers long */
|
||||
@@ -292,6 +302,94 @@ static const struct dmi_system_id dmi_table[] = {
|
||||
{},
|
||||
};
|
||||
|
||||
+static bool oxp_is_super_x_keyboard(const struct usb_device *udev)
|
||||
+{
|
||||
+ return le16_to_cpu(udev->descriptor.idVendor) == OXP_SUPER_X_KEYBOARD_VID &&
|
||||
+ le16_to_cpu(udev->descriptor.idProduct) == OXP_SUPER_X_KEYBOARD_PID;
|
||||
+}
|
||||
+
|
||||
+static void oxp_report_keyboard_attached(struct oxp_platform_data *data,
|
||||
+ bool attached)
|
||||
+{
|
||||
+ /* SW_TABLET_MODE is set when the detachable keyboard is absent. */
|
||||
+ input_report_switch(data->tablet_mode_input, SW_TABLET_MODE, !attached);
|
||||
+ input_sync(data->tablet_mode_input);
|
||||
+}
|
||||
+
|
||||
+static int oxp_find_super_x_keyboard(struct usb_device *udev, void *data)
|
||||
+{
|
||||
+ bool *attached = data;
|
||||
+
|
||||
+ if (oxp_is_super_x_keyboard(udev))
|
||||
+ *attached = true;
|
||||
+
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+static int oxp_usb_notify(struct notifier_block *nb,
|
||||
+ unsigned long action, void *notify_data)
|
||||
+{
|
||||
+ struct oxp_platform_data *data =
|
||||
+ container_of(nb, struct oxp_platform_data, usb_notifier);
|
||||
+ struct usb_device *udev = notify_data;
|
||||
+
|
||||
+ if (!oxp_is_super_x_keyboard(udev))
|
||||
+ return NOTIFY_DONE;
|
||||
+
|
||||
+ switch (action) {
|
||||
+ case USB_DEVICE_ADD:
|
||||
+ oxp_report_keyboard_attached(data, true);
|
||||
+ break;
|
||||
+ case USB_DEVICE_REMOVE:
|
||||
+ oxp_report_keyboard_attached(data, false);
|
||||
+ break;
|
||||
+ default:
|
||||
+ return NOTIFY_DONE;
|
||||
+ }
|
||||
+
|
||||
+ return NOTIFY_OK;
|
||||
+}
|
||||
+
|
||||
+static void oxp_unregister_usb_notifier(void *notify_block)
|
||||
+{
|
||||
+ usb_unregister_notify(notify_block);
|
||||
+}
|
||||
+
|
||||
+static int oxp_register_super_x_tablet_switch(struct device *dev,
|
||||
+ struct oxp_platform_data *data)
|
||||
+{
|
||||
+ bool keyboard_attached = false;
|
||||
+ struct input_dev *input;
|
||||
+ int ret;
|
||||
+
|
||||
+ input = devm_input_allocate_device(dev);
|
||||
+ if (!input)
|
||||
+ return -ENOMEM;
|
||||
+
|
||||
+ input->name = "OneXPlayer Super X Tablet Mode Switch";
|
||||
+ input->phys = "oxp-platform/input0";
|
||||
+ input->id.bustype = BUS_HOST;
|
||||
+ input_set_capability(input, EV_SW, SW_TABLET_MODE);
|
||||
+
|
||||
+ ret = input_register_device(input);
|
||||
+ if (ret)
|
||||
+ return ret;
|
||||
+
|
||||
+ data->tablet_mode_input = input;
|
||||
+ data->usb_notifier.notifier_call = oxp_usb_notify;
|
||||
+ usb_register_notify(&data->usb_notifier);
|
||||
+
|
||||
+ ret = devm_add_action_or_reset(dev, oxp_unregister_usb_notifier,
|
||||
+ &data->usb_notifier);
|
||||
+ if (ret)
|
||||
+ return ret;
|
||||
+
|
||||
+ usb_for_each_dev(&keyboard_attached, oxp_find_super_x_keyboard);
|
||||
+ oxp_report_keyboard_attached(data, keyboard_attached);
|
||||
+
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
/* Helper functions to handle EC read/write */
|
||||
static int read_from_ec(u8 reg, int size, long *val)
|
||||
{
|
||||
@@ -954,6 +1052,18 @@ static int oxp_platform_probe(struct platform_device *pdev)
|
||||
return ret;
|
||||
}
|
||||
|
||||
+ if (dmi_match(DMI_BOARD_NAME, "ONEXPLAYER SUPER X")) {
|
||||
+ struct oxp_platform_data *data;
|
||||
+
|
||||
+ data = devm_kzalloc(dev, sizeof(*data), GFP_KERNEL);
|
||||
+ if (!data)
|
||||
+ return -ENOMEM;
|
||||
+
|
||||
+ ret = oxp_register_super_x_tablet_switch(dev, data);
|
||||
+ if (ret)
|
||||
+ return ret;
|
||||
+ }
|
||||
+
|
||||
return 0;
|
||||
}
|
||||
|
||||
--
|
||||
2.55.0
|
||||
|
||||
19
contrib/upstream-rotation/linux/send-email.txt
Normal file
19
contrib/upstream-rotation/linux/send-email.txt
Normal file
|
|
@ -0,0 +1,19 @@
|
|||
Subject: [PATCH] platform/x86: oxpec: Report tablet mode on OneXPlayer Super X
|
||||
|
||||
The formatted patch already contains the complete problem statement, hardware
|
||||
identity, behavior, testing evidence, Signed-off-by trailer, and AI assistance
|
||||
disclosure.
|
||||
|
||||
Suggested command from a Linux kernel checkout:
|
||||
|
||||
git send-email \
|
||||
--to='platform-driver-x86@vger.kernel.org' \
|
||||
--cc='hansg@kernel.org' \
|
||||
--cc='ilpo.jarvinen@linux.intel.com' \
|
||||
--cc='lkml@antheas.dev' \
|
||||
--cc='derekjohn.clark@gmail.com' \
|
||||
--cc='samsagax@gmail.com' \
|
||||
--cc='linux-kernel@vger.kernel.org' \
|
||||
0001-platform-x86-oxpec-report-tablet-mode-on-super-x.patch
|
||||
|
||||
Development of this patch used assistance from ChatGPT 5.6 sol.
|
||||
23
contrib/upstream-rotation/linux/v2/send-v2.txt
Normal file
23
contrib/upstream-rotation/linux/v2/send-v2.txt
Normal file
|
|
@ -0,0 +1,23 @@
|
|||
# Source this file, then explicitly run `send_v2`.
|
||||
# Keeping the command in a function prevents an accidental resend merely from
|
||||
# sourcing these instructions.
|
||||
send_v2() {
|
||||
repo_dir=$(git rev-parse --show-toplevel 2>/dev/null) || return
|
||||
cd "$repo_dir" || return
|
||||
git send-email \
|
||||
--to='platform-driver-x86@vger.kernel.org' \
|
||||
--cc='hansg@kernel.org' \
|
||||
--cc='ilpo.jarvinen@linux.intel.com' \
|
||||
--cc='lkml@antheas.dev' \
|
||||
--cc='derekjohn.clark@gmail.com' \
|
||||
--cc='samsagax@gmail.com' \
|
||||
--cc='linux-kernel@vger.kernel.org' \
|
||||
--in-reply-to='<20260727215947.118292-1-begeebe@gmail.com>' \
|
||||
contrib/upstream-rotation/linux/v2/v2-0000-cover-letter.patch \
|
||||
contrib/upstream-rotation/linux/v2/v2-0001-platform-x86-oxpec-Distinguish-OneXPlayer-Super-X.patch \
|
||||
contrib/upstream-rotation/linux/v2/v2-0002-platform-x86-oxpec-Report-tablet-mode-on-OneXPlay.patch
|
||||
}
|
||||
|
||||
# This sends three messages in the existing v1 thread: one cover letter and
|
||||
# the two patches. At the SMTP password prompt, paste the Gmail app password
|
||||
# and press Enter.
|
||||
|
|
@ -0,0 +1,51 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Alexander Egorov <begeebe@gmail.com>
|
||||
Date: Tue, 28 Jul 2026 11:31:01 +0300
|
||||
Subject: [PATCH v2 0/2] platform/x86: oxpec: Report tablet mode on
|
||||
OneXPlayer detachables
|
||||
|
||||
The OneXPlayer X1 family and Super X do not expose a firmware tablet-mode
|
||||
switch. Add one based on their detachable pogo-pin keyboard devices.
|
||||
|
||||
I checked the EC alternative suggested in review. The Super X ACPI EC
|
||||
operation region covers the complete 0x00-0xff register map. I captured 30
|
||||
maps with the keyboard attached, 30 detached, and 30 reattached. There were
|
||||
no stable attached-detached-reattached changes. The named ACPI fields KBFG
|
||||
and SYSK did not change either. USB hotplug is therefore the only
|
||||
attachment state exposed by this Super X firmware.
|
||||
|
||||
The X1 keyboard ID was taken from public hardware information. X1, X1 Pro,
|
||||
and X1 Mini systems show the HAILUCK 258a:001e folio keyboard:
|
||||
|
||||
https://wiki.archlinux.org/title/OnexPlayer_X1_A
|
||||
https://linux-hardware.org/?probe=517a6d5085
|
||||
https://linux-hardware.org/?probe=98267565ff
|
||||
https://linux-hardware.org/?probe=21f49ac935
|
||||
|
||||
The X1 family is included, but has not been tested by me because I only
|
||||
have the Super X. G1 is deliberately deferred because of its different
|
||||
keyboard layout.
|
||||
|
||||
Ilpo, comments on whether oxpec is the right home for this functionality are
|
||||
welcome.
|
||||
|
||||
Changes in v2:
|
||||
- add the requested Assisted-by trailer;
|
||||
- split Super X from the shared G1 AMD board ID in a preceding patch;
|
||||
- support the X1 and X1 Mini family using their folio keyboard ID;
|
||||
- use driver globals and board switches instead of platform data and DMI;
|
||||
- keep only the USB scan and notifier callbacks, with matching and reporting
|
||||
inlined;
|
||||
- use generic keyboard vendor names and place the IDs beside their users;
|
||||
- document the complete EC map comparison.
|
||||
|
||||
Alexander Egorov (2):
|
||||
platform/x86: oxpec: Distinguish OneXPlayer Super X board
|
||||
platform/x86: oxpec: Report tablet mode on OneXPlayer detachables
|
||||
|
||||
drivers/platform/x86/Kconfig | 2 +
|
||||
drivers/platform/x86/oxpec.c | 116 ++++++++++++++++++++++++++++++++++-
|
||||
2 files changed, 117 insertions(+), 1 deletion(-)
|
||||
|
||||
--
|
||||
2.55.0
|
||||
|
|
@ -0,0 +1,123 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Alexander Egorov <begeebe@gmail.com>
|
||||
Date: Tue, 28 Jul 2026 10:41:56 +0300
|
||||
Subject: [PATCH v2 1/2] platform/x86: oxpec: Distinguish OneXPlayer Super X
|
||||
board
|
||||
|
||||
The Super X currently shares the oxp_g1_a board identifier because its
|
||||
existing EC functionality matches the G1 AMD.
|
||||
|
||||
Give it a dedicated identifier so model-specific functionality can be
|
||||
selected without also enabling it on the G1. Preserve the existing G1
|
||||
AMD behavior for the new identifier.
|
||||
|
||||
Assisted-by: Codex:gpt-5.6
|
||||
Signed-off-by: Alexander Egorov <begeebe@gmail.com>
|
||||
---
|
||||
drivers/platform/x86/oxpec.c | 13 ++++++++++++-
|
||||
1 file changed, 12 insertions(+), 1 deletion(-)
|
||||
|
||||
diff --git a/drivers/platform/x86/oxpec.c b/drivers/platform/x86/oxpec.c
|
||||
index 99c0dfc..df29e41 100644
|
||||
--- a/drivers/platform/x86/oxpec.c
|
||||
+++ b/drivers/platform/x86/oxpec.c
|
||||
@@ -50,6 +50,7 @@ enum oxp_board {
|
||||
oxp_x1,
|
||||
oxp_g1_i,
|
||||
oxp_g1_a,
|
||||
+ oxp_super_x,
|
||||
};
|
||||
|
||||
static enum oxp_board board;
|
||||
@@ -210,7 +211,7 @@ static const struct dmi_system_id dmi_table[] = {
|
||||
DMI_MATCH(DMI_BOARD_VENDOR, "ONE-NETBOOK"),
|
||||
DMI_EXACT_MATCH(DMI_BOARD_NAME, "ONEXPLAYER SUPER X"),
|
||||
},
|
||||
- .driver_data = (void *)oxp_g1_a,
|
||||
+ .driver_data = (void *)oxp_super_x,
|
||||
},
|
||||
{
|
||||
.matches = {
|
||||
@@ -345,6 +346,7 @@ static umode_t tt_toggle_is_visible(struct kobject *kobj,
|
||||
case oxp_x1:
|
||||
case oxp_g1_i:
|
||||
case oxp_g1_a:
|
||||
+ case oxp_super_x:
|
||||
return attr->mode;
|
||||
default:
|
||||
break;
|
||||
@@ -374,6 +376,7 @@ static ssize_t tt_toggle_store(struct device *dev,
|
||||
case oxp_fly:
|
||||
case oxp_mini_amd_pro:
|
||||
case oxp_g1_a:
|
||||
+ case oxp_super_x:
|
||||
reg = OXP_TURBO_SWITCH_REG;
|
||||
mask = OXP_TURBO_TAKE_VAL;
|
||||
break;
|
||||
@@ -420,6 +423,7 @@ static ssize_t tt_toggle_show(struct device *dev,
|
||||
case oxp_fly:
|
||||
case oxp_mini_amd_pro:
|
||||
case oxp_g1_a:
|
||||
+ case oxp_super_x:
|
||||
reg = OXP_TURBO_SWITCH_REG;
|
||||
mask = OXP_TURBO_TAKE_VAL;
|
||||
break;
|
||||
@@ -516,6 +520,7 @@ static bool oxp_psy_ext_supported(void)
|
||||
case oxp_x1:
|
||||
case oxp_g1_i:
|
||||
case oxp_g1_a:
|
||||
+ case oxp_super_x:
|
||||
case oxp_fly:
|
||||
return true;
|
||||
default:
|
||||
@@ -649,6 +654,7 @@ static int oxp_pwm_enable(void)
|
||||
case oxp_x1:
|
||||
case oxp_g1_i:
|
||||
case oxp_g1_a:
|
||||
+ case oxp_super_x:
|
||||
return write_to_ec(OXP_SENSOR_PWM_ENABLE_REG, PWM_MODE_MANUAL);
|
||||
default:
|
||||
return -EINVAL;
|
||||
@@ -669,6 +675,7 @@ static int oxp_pwm_disable(void)
|
||||
case oxp_x1:
|
||||
case oxp_g1_i:
|
||||
case oxp_g1_a:
|
||||
+ case oxp_super_x:
|
||||
return write_to_ec(OXP_SENSOR_PWM_ENABLE_REG, PWM_MODE_AUTO);
|
||||
default:
|
||||
return -EINVAL;
|
||||
@@ -689,6 +696,7 @@ static int oxp_pwm_read(long *val)
|
||||
case oxp_x1:
|
||||
case oxp_g1_i:
|
||||
case oxp_g1_a:
|
||||
+ case oxp_super_x:
|
||||
return read_from_ec(OXP_SENSOR_PWM_ENABLE_REG, 1, val);
|
||||
default:
|
||||
return -EOPNOTSUPP;
|
||||
@@ -725,6 +733,7 @@ static int oxp_pwm_fan_speed(long *val)
|
||||
case oxp_mini_amd_a07:
|
||||
case oxp_mini_amd_pro:
|
||||
case oxp_g1_a:
|
||||
+ case oxp_super_x:
|
||||
return read_from_ec(OXP_SENSOR_FAN_REG, 2, val);
|
||||
default:
|
||||
return -EOPNOTSUPP;
|
||||
@@ -757,6 +766,7 @@ static int oxp_pwm_input_write(long val)
|
||||
case oxp_fly:
|
||||
case oxp_mini_amd_pro:
|
||||
case oxp_g1_a:
|
||||
+ case oxp_super_x:
|
||||
return write_to_ec(OXP_SENSOR_PWM_REG, val);
|
||||
default:
|
||||
return -EOPNOTSUPP;
|
||||
@@ -796,6 +806,7 @@ static int oxp_pwm_input_read(long *val)
|
||||
case oxp_fly:
|
||||
case oxp_mini_amd_pro:
|
||||
case oxp_g1_a:
|
||||
+ case oxp_super_x:
|
||||
default:
|
||||
ret = read_from_ec(OXP_SENSOR_PWM_REG, 1, val);
|
||||
if (ret)
|
||||
--
|
||||
2.55.0
|
||||
|
||||
|
|
@ -0,0 +1,199 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Alexander Egorov <begeebe@gmail.com>
|
||||
Date: Tue, 28 Jul 2026 10:44:54 +0300
|
||||
Subject: [PATCH v2 2/2] platform/x86: oxpec: Report tablet mode on OneXPlayer
|
||||
detachables
|
||||
|
||||
The OneXPlayer X1 family and Super X have detachable pogo-pin
|
||||
keyboards. The firmware does not expose a tablet-mode input switch.
|
||||
|
||||
The Super X keyboard enumerates as 1a86:1305. The X1 family folio
|
||||
keyboard enumerates as 258a:001e.
|
||||
|
||||
Register an input device on these boards and report SW_TABLET_MODE from
|
||||
the model-specific pogo keyboard USB hotplug state. Other USB and
|
||||
Bluetooth keyboards do not affect the switch.
|
||||
|
||||
A complete dump of the 256-byte Super X EC register map was compared
|
||||
with the keyboard attached, detached, and reattached. No register
|
||||
changed predictably with the attachment state.
|
||||
|
||||
Tested on a OneXPlayer Super X. Mutter enables accelerometer-driven
|
||||
display rotation only while the pogo keyboard is absent.
|
||||
|
||||
Assisted-by: Codex:gpt-5.6
|
||||
Signed-off-by: Alexander Egorov <begeebe@gmail.com>
|
||||
---
|
||||
drivers/platform/x86/Kconfig | 2 +
|
||||
drivers/platform/x86/oxpec.c | 103 +++++++++++++++++++++++++++++++++++
|
||||
2 files changed, 105 insertions(+)
|
||||
|
||||
diff --git a/drivers/platform/x86/Kconfig b/drivers/platform/x86/Kconfig
|
||||
index b54b521..3bcbd49 100644
|
||||
--- a/drivers/platform/x86/Kconfig
|
||||
+++ b/drivers/platform/x86/Kconfig
|
||||
@@ -1055,6 +1055,8 @@ config OXP_EC
|
||||
depends on ACPI_EC
|
||||
depends on ACPI_BATTERY
|
||||
depends on HWMON
|
||||
+ depends on INPUT
|
||||
+ depends on USB
|
||||
depends on X86
|
||||
help
|
||||
Enables support for the platform EC of OneXPlayer and AOKZOE
|
||||
diff --git a/drivers/platform/x86/oxpec.c b/drivers/platform/x86/oxpec.c
|
||||
index df29e41..5c07a35 100644
|
||||
--- a/drivers/platform/x86/oxpec.c
|
||||
+++ b/drivers/platform/x86/oxpec.c
|
||||
@@ -18,10 +18,12 @@
|
||||
#include <linux/dmi.h>
|
||||
#include <linux/hwmon.h>
|
||||
#include <linux/init.h>
|
||||
+#include <linux/input.h>
|
||||
#include <linux/kernel.h>
|
||||
#include <linux/module.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/processor.h>
|
||||
+#include <linux/usb.h>
|
||||
#include <acpi/battery.h>
|
||||
|
||||
/* Handle ACPI lock mechanism */
|
||||
@@ -55,6 +57,8 @@ enum oxp_board {
|
||||
|
||||
static enum oxp_board board;
|
||||
static struct device *oxp_dev;
|
||||
+static struct input_dev *oxp_tablet_mode_input;
|
||||
+static struct notifier_block oxp_usb_notifier;
|
||||
|
||||
/* Fan reading and PWM */
|
||||
#define OXP_SENSOR_FAN_REG 0x76 /* Fan reading is 2 registers long */
|
||||
@@ -293,6 +297,74 @@ static const struct dmi_system_id dmi_table[] = {
|
||||
{},
|
||||
};
|
||||
|
||||
+#define OXP_KEYBOARD_VID_QINHENG 0x1a86
|
||||
+#define OXP_KEYBOARD_PID_K2445 0x1305
|
||||
+#define OXP_KEYBOARD_VID_HAILUCK 0x258a
|
||||
+#define OXP_KEYBOARD_PID_HAILUCK 0x001e
|
||||
+
|
||||
+static int oxp_find_keyboard(struct usb_device *udev, void *data)
|
||||
+{
|
||||
+ bool *keyboard_attached = data;
|
||||
+ u16 vid = le16_to_cpu(udev->descriptor.idVendor);
|
||||
+ u16 pid = le16_to_cpu(udev->descriptor.idProduct);
|
||||
+
|
||||
+ switch (board) {
|
||||
+ case oxp_x1:
|
||||
+ if (vid == OXP_KEYBOARD_VID_HAILUCK &&
|
||||
+ pid == OXP_KEYBOARD_PID_HAILUCK)
|
||||
+ *keyboard_attached = true;
|
||||
+ break;
|
||||
+ case oxp_super_x:
|
||||
+ if (vid == OXP_KEYBOARD_VID_QINHENG &&
|
||||
+ pid == OXP_KEYBOARD_PID_K2445)
|
||||
+ *keyboard_attached = true;
|
||||
+ break;
|
||||
+ default:
|
||||
+ break;
|
||||
+ }
|
||||
+
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+static int oxp_usb_notify(struct notifier_block *nb,
|
||||
+ unsigned long action, void *data)
|
||||
+{
|
||||
+ struct usb_device *udev = data;
|
||||
+ u16 vid = le16_to_cpu(udev->descriptor.idVendor);
|
||||
+ u16 pid = le16_to_cpu(udev->descriptor.idProduct);
|
||||
+ bool keyboard = false;
|
||||
+
|
||||
+ switch (board) {
|
||||
+ case oxp_x1:
|
||||
+ keyboard = vid == OXP_KEYBOARD_VID_HAILUCK &&
|
||||
+ pid == OXP_KEYBOARD_PID_HAILUCK;
|
||||
+ break;
|
||||
+ case oxp_super_x:
|
||||
+ keyboard = vid == OXP_KEYBOARD_VID_QINHENG &&
|
||||
+ pid == OXP_KEYBOARD_PID_K2445;
|
||||
+ break;
|
||||
+ default:
|
||||
+ break;
|
||||
+ }
|
||||
+
|
||||
+ if (!keyboard)
|
||||
+ return NOTIFY_DONE;
|
||||
+
|
||||
+ switch (action) {
|
||||
+ case USB_DEVICE_ADD:
|
||||
+ input_report_switch(oxp_tablet_mode_input, SW_TABLET_MODE, false);
|
||||
+ break;
|
||||
+ case USB_DEVICE_REMOVE:
|
||||
+ input_report_switch(oxp_tablet_mode_input, SW_TABLET_MODE, true);
|
||||
+ break;
|
||||
+ default:
|
||||
+ return NOTIFY_DONE;
|
||||
+ }
|
||||
+
|
||||
+ input_sync(oxp_tablet_mode_input);
|
||||
+ return NOTIFY_OK;
|
||||
+}
|
||||
+
|
||||
/* Helper functions to handle EC read/write */
|
||||
static int read_from_ec(u8 reg, int size, long *val)
|
||||
{
|
||||
@@ -948,6 +1020,7 @@ static const struct hwmon_chip_info oxp_ec_chip_info = {
|
||||
/* Initialization logic */
|
||||
static int oxp_platform_probe(struct platform_device *pdev)
|
||||
{
|
||||
+ bool keyboard_attached = false;
|
||||
struct device *dev = &pdev->dev;
|
||||
struct device *hwdev;
|
||||
int ret;
|
||||
@@ -965,6 +1038,33 @@ static int oxp_platform_probe(struct platform_device *pdev)
|
||||
return ret;
|
||||
}
|
||||
|
||||
+ switch (board) {
|
||||
+ case oxp_x1:
|
||||
+ case oxp_super_x:
|
||||
+ oxp_tablet_mode_input = devm_input_allocate_device(dev);
|
||||
+ if (!oxp_tablet_mode_input)
|
||||
+ return -ENOMEM;
|
||||
+
|
||||
+ oxp_tablet_mode_input->name = "OneXPlayer Tablet Mode Switch";
|
||||
+ oxp_tablet_mode_input->phys = "oxp-platform/input0";
|
||||
+ oxp_tablet_mode_input->id.bustype = BUS_HOST;
|
||||
+ input_set_capability(oxp_tablet_mode_input, EV_SW, SW_TABLET_MODE);
|
||||
+
|
||||
+ ret = input_register_device(oxp_tablet_mode_input);
|
||||
+ if (ret)
|
||||
+ return ret;
|
||||
+
|
||||
+ oxp_usb_notifier.notifier_call = oxp_usb_notify;
|
||||
+ usb_register_notify(&oxp_usb_notifier);
|
||||
+ usb_for_each_dev(&keyboard_attached, oxp_find_keyboard);
|
||||
+ input_report_switch(oxp_tablet_mode_input, SW_TABLET_MODE,
|
||||
+ !keyboard_attached);
|
||||
+ input_sync(oxp_tablet_mode_input);
|
||||
+ break;
|
||||
+ default:
|
||||
+ break;
|
||||
+ }
|
||||
+
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -1005,6 +1105,9 @@ static int __init oxp_platform_init(void)
|
||||
|
||||
static void __exit oxp_platform_exit(void)
|
||||
{
|
||||
+ if (board == oxp_x1 || board == oxp_super_x)
|
||||
+ usb_unregister_notify(&oxp_usb_notifier);
|
||||
+
|
||||
platform_device_unregister(oxp_platform_device);
|
||||
platform_driver_unregister(&oxp_platform_driver);
|
||||
}
|
||||
--
|
||||
2.55.0
|
||||
|
||||
|
|
@ -0,0 +1,40 @@
|
|||
From 013bac321b12c8c4485019e55bbfa0c595b53a27 Mon Sep 17 00:00:00 2001
|
||||
From: Alexander Egorov <begeebe@gmail.com>
|
||||
Date: Mon, 27 Jul 2026 22:47:03 +0300
|
||||
Subject: [PATCH] hwdb: Add accelerometer matrix for OneXPlayer Super X
|
||||
|
||||
The BMI260 accelerometer in the OneXPlayer Super X is exposed through
|
||||
the ACPI BMI0160 ID. Its X and Y axes do not match the built-in display
|
||||
axes, and no firmware mount matrix is provided.
|
||||
|
||||
Add an exact vendor and product DMI match with the matrix verified on
|
||||
the hardware. The matrix keeps the native landscape position normal and
|
||||
maps both portrait rotations to the corresponding display orientation.
|
||||
|
||||
Tested with iio-sensor-proxy 3.8 and Mutter 49.7 in all display
|
||||
orientations. The compiled hwdb entry also matches the complete modalias
|
||||
reported by the device.
|
||||
|
||||
Development of this patch used assistance from ChatGPT 5.6 sol.
|
||||
---
|
||||
hwdb.d/60-sensor.hwdb | 4 ++++
|
||||
1 file changed, 4 insertions(+)
|
||||
|
||||
diff --git a/hwdb.d/60-sensor.hwdb b/hwdb.d/60-sensor.hwdb
|
||||
index 7b57c18..8d6e521 100644
|
||||
--- a/hwdb.d/60-sensor.hwdb
|
||||
+++ b/hwdb.d/60-sensor.hwdb
|
||||
@@ -876,6 +876,10 @@ sensor:modalias:acpi:BOSC0200:*:dmi:bvnAmericanMegatrendsInc.:bvr5.12:bd07/17/20
|
||||
sensor:modalias:acpi:BMI0160:*:dmi:*:rnONEXPLAYER:rvrV01:*
|
||||
ACCEL_MOUNT_MATRIX=-1, 0, 0; 0, 1, 0; 0, 0, -1
|
||||
|
||||
+# One-Netbook OneXPlayer Super X
|
||||
+sensor:modalias:acpi:BMI0160:*:dmi:*:svnONE-NETBOOK:pnONEXPLAYERSUPERX:*
|
||||
+ ACCEL_MOUNT_MATRIX=0, -1, 0; 1, 0, 0; 0, 0, 1
|
||||
+
|
||||
#########################################
|
||||
# OrangePi
|
||||
#########################################
|
||||
--
|
||||
2.55.0
|
||||
|
||||
33
contrib/upstream-rotation/systemd/pr-description.md
Normal file
33
contrib/upstream-rotation/systemd/pr-description.md
Normal file
|
|
@ -0,0 +1,33 @@
|
|||
## Summary
|
||||
|
||||
Add the accelerometer mounting matrix for the One-Netbook OneXPlayer Super X.
|
||||
|
||||
The device contains a BMI260 accelerometer exposed using the ACPI `BMI0160`
|
||||
identifier. Firmware does not provide a mount matrix, and the sensor X/Y axes
|
||||
do not match the built-in display axes. Without this entry,
|
||||
`iio-sensor-proxy` reports incorrect screen orientations.
|
||||
|
||||
The entry uses the exact system vendor and product DMI fields:
|
||||
|
||||
```text
|
||||
svnONE-NETBOOK:pnONEXPLAYERSUPERX
|
||||
```
|
||||
|
||||
The tested matrix is:
|
||||
|
||||
```text
|
||||
0, -1, 0; 1, 0, 0; 0, 0, 1
|
||||
```
|
||||
|
||||
## Validation
|
||||
|
||||
- Passed `test/hwdb-test.sh` using systemd-hwdb 258.
|
||||
- Passed strict hwdb compilation.
|
||||
- Queried the compiled database with the complete machine modalias and
|
||||
received the expected `ACCEL_MOUNT_MATRIX`.
|
||||
- Tested with iio-sensor-proxy 3.8 and Mutter 49.7.
|
||||
- Verified native landscape and both portrait orientations on the hardware.
|
||||
|
||||
## AI assistance disclosure
|
||||
|
||||
Development of this patch used assistance from ChatGPT 5.6 sol.
|
||||
Loading…
Add table
Reference in a new issue