On Wed, 22 Jul 2026, Dave Carey wrote: > The Lenovo Yoga Book 9 14IAH10 ships with a detachable Bluetooth keyboard > that magnetically attaches to the bottom (secondary) screen in one of two > positions. The Embedded Controller tracks the attachment state in a 2-bit > field called BKBD and signals changes via WMI event GUID > 806BD2A2-177B-481D-BFB5-3BA0BB4A2285 (notify ID 0xEB on the WM10 ACPI > device, _UID "GMZN"). > > The device contains embedded BMOF data (WQDD, 20705 bytes) documenting > both WMI interfaces used by this driver: > > LENOVO_BTKBD_EVENT (event GUID): WmiDataId(1) uint32 Status. > The ACPI _WED(0xEB) method returns EC.BKBD directly as an integer, > so the notify callback receives BKBD without a separate query. > > LENOVO_FEATURE_STATUS_DATA (block GUID, WQAF method): returns an > 8-byte buffer {uint32 IDs=0x00060000, uint32 Status=BKBD}. > Used for the initial state read on probe and after resume. > > BKBD encoding: > 0 = keyboard detached > 1 = keyboard docked on top half of bottom screen > 2 = keyboard docked on bottom half of bottom screen > 3 = reserved (not observed in practice) > > This driver registers two WMI drivers sharing a module-level > BLOCKING_NOTIFIER_HEAD: > > - The event driver (LENOVO_BTKBD_EVENT) uses .notify_new() to receive > a pre-parsed wmi_buffer and fires the notifier chain with the BKBD > value extracted from the buffer. > > - The block driver (LENOVO_FEATURE_STATUS_DATA) owns the input_dev in > its per-device private struct. At probe time it registers a > notifier_block on the chain and reads the initial BKBD state via > wmidev_query_block(). The WMI buffer is parsed as > struct lenovo_feature_status { __le32 id; __le32 status; }, and the > ID field is verified before the status is used. > > - SW_TABLET_MODE=1 is reported when the keyboard is detached; > SW_TABLET_MODE=0 when docked in either position (keyboard present). > > - The raw BKBD value is exposed via read-only sysfs attribute > "keyboard_position". > > - BKBD state is re-read via wmidev_query_block() on resume from > suspend or hibernation. > > Tested on: Lenovo Yoga Book 9 14IAH10 (model 83KJ), kernel 7.0. > > Acked-by: Hans de Goede > Reviewed-by: Armin Wolf > Signed-off-by: Dave Carey > --- > v13: > - Resend of v12: patch was corrupted in transit. git-send-email chose > quoted-printable encoding (triggered by non-ASCII in the changelog) > which encoded '=' as '=3D', corrupting the RST table separators in > the ABI doc and breaking git-am. No content changes from v12. > > v12: > - Add #include (for sysfs_emit; Ilpo Järvinen) > - Add #include (for __le32 and __packed; Ilpo Järvinen) > > v11 (addressing Armin Wolf's v10 review): > - ABI doc: correct Date to "June 2027" and KernelVersion to "7.3" > > v10 (addressing Armin Wolf's v9 review): > - Update ABI doc: Date: June 2026, KernelVersion: 6.16 > - Add #include and > - yb9_kbdock_query(): change return to pointer-out u32 *bkbd > - struct yb9_kbdock_data: add spinlock_t lock > - yb9_kbdock_report(): hold lock across input_report_switch + input_sync > - yb9_kbdock_sync(): return int, propagate query error to callers > - yb9_kbdock_resume(), yb9_kbdock_block_probe(): propagate sync error > - struct wmi_buffer out: remove zero-initializer > - yb9_kbdock_notify_new(): drop manual length check; use > .min_event_size = sizeof(__le32) in struct wmi_driver instead > > .../testing/sysfs-driver-lenovo-yb9-kbdock | 19 ++ > MAINTAINERS | 7 + > drivers/platform/x86/lenovo/Kconfig | 14 + > drivers/platform/x86/lenovo/Makefile | 1 + > drivers/platform/x86/lenovo/yb9-kbdock.c | 312 ++++++++++++++++++ > 5 files changed, 353 insertions(+) > create mode 100644 Documentation/ABI/testing/sysfs-driver-lenovo-yb9-kbdock > create mode 100644 drivers/platform/x86/lenovo/yb9-kbdock.c > > diff --git a/Documentation/ABI/testing/sysfs-driver-lenovo-yb9-kbdock b/Documentation/ABI/testing/sysfs-driver-lenovo-yb9-kbdock > new file mode 100644 > index 0000000..ebe713a > --- /dev/null > +++ b/Documentation/ABI/testing/sysfs-driver-lenovo-yb9-kbdock > @@ -0,0 +1,19 @@ > +What: /sys/bus/wmi/drivers/lenovo-yb9-kbdock//keyboard_position > +Date: June 2027 > +KernelVersion: 7.3 > +Contact: Dave Carey > +Description: > + Read-only attribute reporting the current keyboard dock position > + as reported by the Embedded Controller on the Lenovo Yoga Book 9 > + 14IAH10. > + > + Possible values: > + > + == ============================================================= > + 0 keyboard is not docked to any screen (detached) > + 1 keyboard docked on the top half of the bottom screen > + 2 keyboard docked on the bottom half of the bottom screen > + == ============================================================= > + > + SW_TABLET_MODE input events are also emitted: 0 when the keyboard > + is docked (either position), 1 when detached. > diff --git a/MAINTAINERS b/MAINTAINERS > index d1cc0e1..00e8275 100644 > --- a/MAINTAINERS > +++ b/MAINTAINERS > @@ -14479,6 +14479,13 @@ L: platform-driver-x86@vger.kernel.org > S: Maintained > F: drivers/platform/x86/lenovo/wmi-hotkey-utilities.c > > +LENOVO YOGA BOOK 9 KEYBOARD DOCK DRIVER > +M: Dave Carey > +L: platform-driver-x86@vger.kernel.org > +S: Maintained > +F: Documentation/ABI/testing/sysfs-driver-lenovo-yb9-kbdock > +F: drivers/platform/x86/lenovo/yb9-kbdock.c > + > LETSKETCH HID TABLET DRIVER > M: Hans de Goede > L: linux-input@vger.kernel.org > diff --git a/drivers/platform/x86/lenovo/Kconfig b/drivers/platform/x86/lenovo/Kconfig > index 9c48487..938b361 100644 > --- a/drivers/platform/x86/lenovo/Kconfig > +++ b/drivers/platform/x86/lenovo/Kconfig > @@ -43,6 +43,20 @@ config LENOVO_WMI_CAMERA > To compile this driver as a module, choose M here: the module > will be called lenovo-wmi-camera. > > +config LENOVO_YB9_KBDOCK > + tristate "Lenovo Yoga Book 9 keyboard dock detection" > + depends on ACPI_WMI > + depends on DMI > + depends on INPUT > + help > + Say Y here to enable keyboard dock detection on the Lenovo Yoga Book 9 > + 14IAH10. The detachable Bluetooth keyboard magnetically attaches to > + either screen; this driver reports SW_TABLET_MODE input events based > + on the attachment state and exposes the raw position in sysfs. > + > + To compile this driver as a module, choose M here: the module will be > + called lenovo-yb9-kbdock. > + > config LENOVO_YMC > tristate "Lenovo Yoga Tablet Mode Control" > depends on ACPI_WMI > diff --git a/drivers/platform/x86/lenovo/Makefile b/drivers/platform/x86/lenovo/Makefile > index 7b2128e..2842d7d 100644 > --- a/drivers/platform/x86/lenovo/Makefile > +++ b/drivers/platform/x86/lenovo/Makefile > @@ -8,6 +8,7 @@ obj-$(CONFIG_THINKPAD_LMI) += think-lmi.o > obj-$(CONFIG_THINKPAD_ACPI) += thinkpad_acpi.o > > lenovo-target-$(CONFIG_LENOVO_WMI_HOTKEY_UTILITIES) += wmi-hotkey-utilities.o > +lenovo-target-$(CONFIG_LENOVO_YB9_KBDOCK) += yb9-kbdock.o > lenovo-target-$(CONFIG_LENOVO_YMC) += ymc.o > lenovo-target-$(CONFIG_YOGABOOK) += yogabook.o > lenovo-target-$(CONFIG_YT2_1380) += yoga-tab2-pro-1380-fastcharger.o > diff --git a/drivers/platform/x86/lenovo/yb9-kbdock.c b/drivers/platform/x86/lenovo/yb9-kbdock.c > new file mode 100644 > index 0000000..69c68a0 > --- /dev/null > +++ b/drivers/platform/x86/lenovo/yb9-kbdock.c > @@ -0,0 +1,312 @@ > +// SPDX-License-Identifier: GPL-2.0-or-later > +/* > + * Lenovo Yoga Book 9 keyboard-dock detection > + * > + * The Yoga Book 9 ships with a detachable Bluetooth keyboard that magnetically > + * attaches to the bottom screen in one of two positions. The EC tracks > + * attachment state in a 2-bit field called BKBD and signals changes via WMI > + * event 0xEB on the WM10 ACPI device (_UID "GMZN"). > + * > + * BKBD values: > + * 0 = keyboard detached > + * 1 = keyboard docked on the top half of the bottom screen > + * 2 = keyboard docked on the bottom half of the bottom screen > + * 3 = reserved / not observed > + * > + * Two WMI interfaces are used (documented in embedded BMOF, WQDD, 20705 bytes): > + * > + * LENOVO_BTKBD_EVENT (event GUID, 806BD2A2-...) > + * WmiDataId(1) uint32 Status — _WED(0xEB) returns EC.BKBD directly. > + * The notify callback receives BKBD as an integer; no separate query needed. > + * > + * LENOVO_FEATURE_STATUS_DATA (block GUID, E7F300FA-...) > + * WmiDataId(1) uint32 IDs = 0x00060000 (feature selector) > + * WmiDataId(2) uint32 Status = BKBD value > + * Used on probe and resume to read initial state. > + * > + * The event driver (LENOVO_BTKBD_EVENT) fires a notifier chain on each WMI > + * event. The block driver (LENOVO_FEATURE_STATUS_DATA) owns the input_dev > + * and registers a notifier_block to receive those events, eliminating the > + * need for shared global state or a mutex. > + * > + * SW_TABLET_MODE=1 is reported when the keyboard is detached; > + * SW_TABLET_MODE=0 when docked in either position (keyboard present). > + * The raw BKBD value is exposed via the sysfs attribute "keyboard_position". > + * > + * Copyright (C) 2026 Dave Carey > + */ > + > +#include > +#include > +#include > +#include > +#include > +#include > +#include > +#include > +#include > +#include > +#include > +#include Hi, Are you sure you sent the latest version, AFAICT, v12 had this: +#include +#include +#include +#include ... +#include +#include +#include +#include +#include ? -- i.