xref: /linux/Documentation/wmi/driver-development-guide.rst (revision 5ea5880764cbb164afb17a62e76ca75dc371409d)
1.. SPDX-License-Identifier: GPL-2.0-or-later
2
3============================
4WMI driver development guide
5============================
6
7The WMI subsystem provides a rich driver API for implementing WMI drivers,
8documented at Documentation/driver-api/wmi.rst. This document will serve
9as an introductory guide for WMI driver writers using this API. It is supposed
10to be a successor to the original LWN article [1]_ which deals with WMI drivers
11using the deprecated GUID-based WMI interface.
12
13Obtaining WMI device information
14--------------------------------
15
16Before developing an WMI driver, information about the WMI device in question
17must be obtained. The `lswmi <https://pypi.org/project/lswmi>`_ utility can be
18used to extract detailed WMI device information using the following command:
19
20::
21
22  lswmi -V
23
24The resulting output will contain information about all WMI devices available on
25a given machine, plus some extra information.
26
27In order to find out more about the interface used to communicate with a WMI device,
28the `bmfdec <https://github.com/pali/bmfdec>`_ utilities can be used to decode
29the Binary MOF (Managed Object Format) information used to describe WMI devices.
30The ``wmi-bmof`` driver exposes this information to userspace, see
31Documentation/wmi/devices/wmi-bmof.rst.
32
33In order to retrieve the decoded Binary MOF information, use the following command (requires root):
34
35::
36
37  ./bmf2mof /sys/bus/wmi/devices/05901221-D566-11D1-B2F0-00A0C9062910[-X]/bmof
38
39Sometimes, looking at the disassembled ACPI tables used to describe the WMI device
40helps in understanding how the WMI device is supposed to work. The path of the ACPI
41method associated with a given WMI device can be retrieved using the ``lswmi`` utility
42as mentioned above.
43
44If you are attempting to port a driver to Linux and are working on a Windows
45system, `WMIExplorer <https://github.com/vinaypamnani/wmie2>`_ can be useful
46for inspecting available WMI methods and invoking them directly.
47
48Basic WMI driver structure
49--------------------------
50
51The basic WMI driver is build around the struct wmi_driver, which is then bound
52to matching WMI devices using a struct wmi_device_id table:
53
54::
55
56  static const struct wmi_device_id foo_id_table[] = {
57         /* Only use uppercase letters! */
58         { "936DA01F-9ABD-4D9D-80C7-02AF85C822A8", NULL },
59         { }
60  };
61  MODULE_DEVICE_TABLE(wmi, foo_id_table);
62
63  static struct wmi_driver foo_driver = {
64        .driver = {
65                .name = "foo",
66                .probe_type = PROBE_PREFER_ASYNCHRONOUS,        /* recommended */
67                .pm = pm_sleep_ptr(&foo_dev_pm_ops),            /* optional */
68        },
69        .id_table = foo_id_table,
70        .probe = foo_probe,
71        .remove = foo_remove,         /* optional, devres is preferred */
72        .shutdown = foo_shutdown,     /* optional, called during shutdown */
73        .notify_new = foo_notify,     /* optional, for event handling */
74        .min_event_size = X,          /* optional, simplifies event payload size verification */
75        .no_singleton = true,         /* required for new WMI drivers */
76  };
77  module_wmi_driver(foo_driver);
78
79The probe() callback is called when the WMI driver is bound to a matching WMI device. Allocating
80driver-specific data structures and initialising interfaces to other kernel subsystems should
81normally be done in this function.
82
83The remove() callback is then called when the WMI driver is unbound from a WMI device. In order
84to unregister interfaces to other kernel subsystems and release resources, devres should be used.
85This simplifies error handling during probe and often allows to omit this callback entirely, see
86Documentation/driver-api/driver-model/devres.rst for details.
87
88The shutdown() callback is called during shutdown, reboot or kexec. Its sole purpose is to disable
89the WMI device and put it in a well-known state for the WMI driver to pick up later after reboot
90or kexec. Most WMI drivers need no special shutdown handling and can thus omit this callback.
91
92Please note that new WMI drivers are required to be able to be instantiated multiple times,
93and are forbidden from using any deprecated GUID-based or ACPI-based WMI functions. This means
94that the WMI driver should be prepared for the scenario that multiple matching WMI devices are
95present on a given machine.
96
97Because of this, WMI drivers should use the state container design pattern as described in
98Documentation/driver-api/driver-model/design-patterns.rst.
99
100.. warning:: Using both GUID-based and non-GUID-based functions for querying WMI data blocks and
101             handling WMI events simultaneously on the same device is guaranteed to corrupt the
102             WMI device state and might lead to erratic behaviour.
103
104WMI method drivers
105------------------
106
107WMI drivers can call WMI device methods using wmidev_invoke_method(). For each WMI method
108invocation the WMI driver needs to provide the instance number and the method ID, as well as
109a buffer with the method arguments and optionally a buffer for the results. When calling WMI
110methods that do not return any values, wmidev_invoke_procedure() should be used instead.
111
112The layout of said buffers is device-specific and described by the Binary MOF data associated
113with a given WMI device. Said Binary MOF data also describes the method ID of a given WMI method
114with the ``WmiMethodId`` qualifier. WMI devices exposing WMI methods usually expose only a single
115instance (instance number 0), but in theory can expose multiple instances as well. In such a case
116the number of instances can be retrieved using wmidev_instance_count().
117
118Take a look at drivers/platform/x86/intel/wmi/thunderbolt.c for an example WMI method driver.
119
120WMI data block drivers
121----------------------
122
123WMI drivers can query WMI data blocks using wmidev_query_block(), the layout of the returned
124buffer is again device-specific and described by the Binary MOF data. Some WMI data blocks are
125also writeable and can be set using wmidev_set_block(). The number of data block instances can
126again be retrieved using wmidev_instance_count().
127
128Take a look at drivers/platform/x86/intel/wmi/sbl-fw-update.c for an example WMI data block driver.
129
130WMI event drivers
131-----------------
132
133WMI drivers can receive WMI events via the notify_new() callback inside the struct wmi_driver.
134The WMI subsystem will then take care of setting up the WMI event accordingly. Please note that
135the layout of the buffer passed to this callback is device-specific, and freeing of the buffer
136is done by the WMI subsystem itself, not the driver.
137
138The WMI driver core will take care that the notify_new() callback will only be called after
139the probe() callback has been called, and that no events are being received by the driver
140right before and after calling its remove() or shutdown() callback.
141
142However WMI driver developers should be aware that multiple WMI events can be received concurrently,
143so any locking (if necessary) needs to be provided by the WMI driver itself.
144
145The WMI driver can furthermore instruct the WMI driver core to automatically reject WMI events
146that contain a undersized event payload by populating the ``min_event_size`` field inside
147struct wmi_driver. Setting this field to 0 will thus enable the WMI driver to receive WMI events
148without any event payload.
149
150Take a look at drivers/platform/x86/xiaomi-wmi.c for an example WMI event driver.
151
152Exchanging data with the WMI driver core
153----------------------------------------
154
155WMI drivers can exchange data with the WMI driver core using struct wmi_buffer. The internal
156structure of those buffers is device-specific and only known by the WMI driver. Because of this
157the WMI driver itself is responsible for parsing and validating the data received from its
158WMI device.
159
160The structure of said buffers is described by the MOF data associated with the WMI device in
161question. When such a buffer contains multiple data items it usually makes sense to define a
162C structure and use it during parsing. Since the WMI driver core guarantees that all buffers
163received from a WMI device are aligned on an 8-byte boundary, WMI drivers can simply perform
164a cast between the WMI buffer data and this C structure.
165
166This however should only be done after the size of the buffer was verified to be large enough
167to hold the whole C structure. WMI drivers should reject undersized buffers as they are usually
168sent by the WMI device to signal an internal error. Oversized buffers however should be accepted
169to emulate the behavior of the Windows WMI implementation.
170
171When defining a C structure for parsing WMI buffers the alignment of the data items should be
172respected. This is especially important for 64-bit integers as those have different alignments
173on 64-bit (8-byte alignment) and 32-bit (4-byte alignment) architectures. It is thus a good idea
174to manually specify the alignment of such data items or mark the whole structure as packed when
175appropriate. Integer data items in general are little-endian integers and should be marked as
176such using ``__le64`` and friends. When parsing WMI string data items the struct wmi_string should
177be used as WMI strings have a different layout than C strings.
178
179See Documentation/wmi/acpi-interface.rst for more information regarding the binary format
180of WMI data items.
181
182Handling multiple WMI devices at once
183-------------------------------------
184
185There are many cases of firmware vendors using multiple WMI devices to control different aspects
186of a single physical device. This can make developing WMI drivers complicated, as those drivers
187might need to communicate with each other to present a unified interface to userspace.
188
189On such case involves a WMI event device which needs to talk to a WMI data block device or WMI
190method device upon receiving an WMI event. In such a case, two WMI drivers should be developed,
191one for the WMI event device and one for the other WMI device.
192
193The WMI event device driver has only one purpose: to receive WMI events, validate any additional
194event data and invoke a notifier chain. The other WMI driver adds itself to this notifier chain
195during probing and thus gets notified every time a WMI event is received. This WMI driver might
196then process the event further for example by using an input device.
197
198For other WMI device constellations, similar mechanisms can be used.
199
200Things to avoid
201---------------
202
203When developing WMI drivers, there are a couple of things which should be avoided:
204
205- usage of the deprecated GUID-based WMI interface which uses GUIDs instead of WMI device structs
206- usage of the deprecated ACPI-based WMI interface which uses ACPI objects instead of plain buffers
207- bypassing of the WMI subsystem when talking to WMI devices
208- WMI drivers which cannot be instantiated multiple times.
209
210Many older WMI drivers violate one or more points from this list. The reason for
211this is that the WMI subsystem evolved significantly over the last two decades,
212so there is a lot of legacy cruft inside older WMI drivers.
213
214New WMI drivers are also required to conform to the linux kernel coding style as specified in
215Documentation/process/coding-style.rst. The checkpatch utility can catch many common coding style
216violations, you can invoke it with the following command:
217
218::
219
220  ./scripts/checkpatch.pl --strict <path to driver file>
221
222References
223==========
224
225.. [1] https://lwn.net/Articles/391230/
226