xref: /illumos-gate/usr/src/man/man9e/ddi_ufm.9e (revision 6523a3aa7f325d64841382707603be7a86e68147)
1.\"
2.\" This file and its contents are supplied under the terms of the
3.\" Common Development and Distribution License ("CDDL"), version 1.0.
4.\" You may only use this file in accordance with the terms of version
5.\" 1.0 of the CDDL.
6.\"
7.\" A full copy of the text of the CDDL should have accompanied this
8.\" source.  A copy of the CDDL is also available via the Internet at
9.\" http://www.illumos.org/license/CDDL.
10.\"
11.\"
12.\" Copyright 2019 Joyent, Inc.
13.\"
14.Dd February 15, 2020
15.Dt DDI_UFM 9E
16.Os
17.Sh NAME
18.Nm ddi_ufm ,
19.Nm ddi_ufm_op_nimages ,
20.Nm ddi_ufm_op_fill_image ,
21.Nm ddi_ufm_op_fill_slot ,
22.Nm ddi_ufm_op_getcaps
23.Nd DDI upgradable firmware module entry points
24.Sh SYNOPSIS
25.Vt typedef struct ddi_ufm_handle ddi_ufm_handle_t
26.Vt typedef struct ddi_ufm_ops ddi_ufm_ops_t
27.In sys/ddi_ufm.h
28.Ft int
29.Fo ddi_ufm_op_getcaps
30.Fa "ddi_ufm_handle_t *uhp"
31.Fa "void *drv_arg"
32.Fa "ddi_ufm_cap_t *caps"
33.Fc
34.Ft int
35.Fo ddi_ufm_op_nimages
36.Fa "ddi_ufm_handle_t *uhp"
37.Fa "void *drv_arg"
38.Fa "uint_t *nimgp"
39.Fc
40.Ft int
41.Fo ddi_ufm_op_fill_image
42.Fa "ddi_ufm_handle_t *uhp"
43.Fa "void *drv_arg"
44.Fa "uint_t imgid"
45.Fa "ddi_ufm_image_t *uip"
46.Fc
47.Ft int
48.Fo ddi_ufm_op_fill_slot
49.Fa "ddi_ufm_handle_t *uhp"
50.Fa "void *drv_arg"
51.Fa "uint_t imgid"
52.Fa "uint_t slotid"
53.Fa "ddi_ufm_slot_t *usp"
54.Fc
55.Sh INTERFACE LEVEL
56.Sy Evolving - This interface is evolving still in illumos. API and ABI stability is not guaranteed.
57.Sh PARAMETERS
58.Bl -tag -width Fa
59.It Fa uhp
60A handle corresponding to the device's UFM handle.
61This is the same value as returned in
62.Xr ddi_ufm_init 9F .
63.It Fa drv_arg
64This is a private value that the driver passed in when calling
65.Xr ddi_ufm_init 9F .
66.It Fa nimgp
67A pointer that the driver should set with a number of images.
68.It Fa nslotp
69A pointer that the driver should set with a number of slots.
70.It Fa imgid
71An integer indicating which image information is being requested for.
72.It Fa uip
73An opaque pointer that represents a UFM image.
74.It Fa slotid
75An integer indicating which slot information is being requested for.
76.It Fa usp
77An opaque pointer that represents a UFM slot.
78.El
79.Sh DESCRIPTION
80Upgradable firmware modules (UFM) are a potential component of many
81devices.
82These interfaces aim to provide a simple series of callbacks
83for a device driver to implement such that it is easy to report
84information and in the future, manipulate firmware modules.
85.Ss UFM Background
86UFMs may come in different flavors and styles ranging from a
87firmware blob, to an EEPROM image, to microcode, and more.
88Take for example a hard drive.
89While it is a field replaceable unit (FRU), it also contains some amount
90of firmware that manages the drive which can be updated independently of
91replacing the drive.
92.Pp
93The motherboard often has a UFM in the form of the BIOS or UEFI.
94The Lights out management controller on a system has a UFM, which is usually
95the entire system image.
96CPUs also have a UFM in the form of microcode.
97.Pp
98An important property of a UFM is that it is a property of the device
99itself.
100For example, many WiFi device drivers are required to send a binary blob of
101firmware to the device after every reset.
102Because these images are not properties of the device and must be upgraded by
103either changing the device driver or related system files, we do not consider
104these UFMs.
105.Pp
106There are also devices that have firmware which is a property of the
107device, but may not be upgradable from the running OS.
108This may be because the vendor doesn't have tooling to upgrade the image or
109because the firmware image itself cannot be upgraded in the field at all.
110For example, a YubiKey has a firmware image that's burned into it in the
111factory, but there is no way to change the firmware on it short of
112replacing the device in its entirety.
113However, because these images are a permanent part of the device, we also
114consider them a UFM.
115.Ss Images and Slots
116A device that supports UFMs is made up of one or more distinct firmware
117images.
118Each image has its own unique purpose.
119For example, a motherboard may have both a BIOS and a CPLD image, each of which
120has independent firmware revisions.
121.Pp
122A given image may have a number of slots.
123A slot represents a particular version of the image.
124Only one slot can be active at a given time.
125Devices support slots such that a firmware image can be downloaded
126to the device without impacting the current device if it fails half-way
127through.
128The slot that's currently in use is referred to as the
129.Em active
130slot.
131.Pp
132The various entry points are designed such that all a driver has to do
133is provide information about the image and its slots to the kernel, it
134does not have to wrangle with how that is marshalled to users and the
135appearance of those structures.
136.Ss Registering with the UFM Subsystem
137During a device driver's
138.Xr attach 9E
139entry point, a device driver should register with the UFM subsystem by
140filling out a UFM operations vector and then calling
141.Xr ddi_ufm_init 9F .
142The driver may pass in a value, usually a pointer to its soft state
143pointer, which it will then receive when its subsequent entry points are
144called.
145.Pp
146Once the driver has finished initializing, it must call
147.Xr ddi_ufm_update 9F
148to indicate that the driver is in a state where it's ready to receive
149calls to the entry points.
150.Pp
151The various UFM entry points may be called from an arbitrary kernel
152context.
153However, they will only ever be called from a single thread at
154a given time.
155.Ss UFM operations vector
156The UFM operations vector is a structure that has the following members:
157.Bd -literal -offset indent
158typedef struct ddi_ufm_ops {
159	int (*ddi_ufm_op_nimages)(ddi_ufm_handle_t *uhp, void *arg,
160	    uint_t *nimgp);
161	int (*ddi_ufm_op_fill_image)(ddi_ufm_handle_t *uhp, void *arg,
162            uint_t imgid, ddi_ufm_image_t *img);
163	int (*ddi_ufm_op_fill_slot)(ddi_ufm_handle_t *uhp, void *arg,
164            int imgid, ddi_ufm_image_t *img, uint_t slotid,
165	    ddi_ufm_slot_t *slotp);
166	int (*ddi_ufm_op_getcaps)(ddi_ufm_handle_t *uhp, void *arg,
167	    ddi_ufm_cap_t *caps);
168} ddi_ufm_ops_t;
169.Ed
170.Pp
171The
172.Fn ddi_ufm_op_nimages
173entry point is optional.
174If a device only has a single image, then there is no reason to implement the
175.Fn ddi_ufm_op_nimages entry point.
176The system will assume that there is only a single image.
177.Pp
178Slots and images are numbered starting at zero.
179If a driver indicates support for multiple images or slots then the images
180or slots will be numbered sequentially going from 0 to the number of images or
181slots minus one.
182These values will be passed to the various entry points to indicate which image
183and slot the system is interested in.
184It is up to the driver to maintain a consistent view of the images and slots
185for a given UFM.
186.Pp
187The members of this structure should be filled in the following ways:
188.Bl -tag -width Fn
189.It Fn ddi_ufm_op_nimages
190The
191.Fn ddi_ufm_op_nimages
192entry point is an optional entry point that answers the question of how
193many different, distinct firmware images are present on the device.
194Once the driver determines how many are present, it should set the value in
195.Fa nimgp to the determined value.
196.Pp
197It is legal for a device to pass in zero for this value, which indicates
198that there are none present.
199.Pp
200Upon successful completion, the driver should return
201.Sy 0 .
202Otherwise, the driver should return the appropriate error number.
203For a full list of error numbers, see
204.Xr Intro 2 .
205Common values are:
206.Bl -tag -width Er -offset width
207.It Er EIO
208An error occurred while communicating with the device to determine the
209number of firmware images.
210.El
211.It Fn ddi_ufm_op_fill_image
212The
213.Fn ddi_ufm_op_fill_image
214entry point is used to fill in information about a given image.
215The value in
216.Fa imgid
217is used to indicate which image the system is asking to fill
218information about.
219If the driver does not recognize the image ID in
220.Fa imgid
221then it should return an error.
222.Pp
223The
224.Ft ddi_ufm_image_t
225structure passed in
226.Fa uip
227is opaque.
228To fill in information about the image, the driver should call the functions
229described in
230.Xr ddi_ufm_image 9F .
231.Pp
232The driver should call the
233.Xr ddi_ufm_image_set_desc 9F
234function to set a description of the image which indicates its purpose.
235This should be a human-readable string.
236The driver may also set any ancillary data that it deems may be useful with the
237.Xr ddi_ufm_image_set_misc 9F function.
238This function takes an nvlist, allowing the driver to set arbitrary keys and values.
239.Pp
240Once the driver has finished setting all of the information about the
241image then the driver should return
242.Sy 0 .
243Otherwise, the driver should return the appropriate error number.
244For a full list of error numbers, see
245.Xr Intro 2 .
246Common values are:
247.Bl -tag -width Er -offset width
248.It Er EINVAL
249The image indicated by
250.Fa imgid
251is unknown.
252.It Er EIO
253An error occurred talking to the device while trying to fill out
254firmware image information.
255.It Er ENOMEM
256The driver was unable to allocate memory while filling out image
257information.
258.El
259.It Fn ddi_ufm_op_fill_slot
260The
261.Fn ddi_ufm_op_fill_slot
262function is used to fill in information about a specific slot for a
263specific image.
264The value in
265.Fa imgid
266indicates the image the system wants slot information for and the value
267in
268.Fa slotid
269indicates which slot of that image the system is interested in.
270If the device driver does not recognize the value in either or
271.Fa imgid
272or
273.Fa slotid ,
274then it should return an error.
275.Pp
276The
277.Ft ddi_ufm_slot_t
278structure passed in
279.Fa usp
280is opaque.
281To fill in information about the image the driver should call the functions
282described in
283.Xr ddi_ufm_slot 9F .
284.Pp
285The driver should call the
286.Xr ddi_ufm_slot_set_version 9F
287function to indicate the version of the UFM.
288The version is a device-specific character string.
289It should contain the current version of the UFM as a human can understand it
290and it should try to match the format used by device vendor.
291.Pp
292The
293.Xr ddi_ufm_slot_set_attrs 9F
294function should be used to set the attributes of the UFM slot.
295These attributes include the following enumeration values:
296.Bl -tag -width Dv
297.It Dv DDI_UFM_ATTR_READABLE
298This attribute indicates that the firmware image in the specified slot
299may be read, even if the device driver does not currently support such
300functionality.
301.It Dv DDI_UFM_ATTR_WRITEABLE
302This attributes indicates that the firmware image in the specified slot
303may be updated, even if the driver does not currently support such
304functionality.
305.It Dv DDI_UFM_ATTR_ACTIVE
306This attributes indicates that the firmware image in the specified slot
307is the active
308.Pq i.e. currently running
309firmware.
310Only one slot should be marked active.
311.It Dv DDI_UFM_ATTR_EMPTY
312This attributes indicates that the specified slot does not currently contain
313any firmware image.
314.El
315.Pp
316Finally, if there are any device-specific key-value pairs that form
317useful, ancillary data, then the driver should assemble an nvlist and
318pass it to the
319.Xr ddi_ufm_set_misc 9F
320function.
321.Pp
322Once the driver has finished setting all of the information about the
323slot then the driver should return
324.Sy 0 .
325Otherwise, the driver should return the appropriate error number.
326For a full list of error numbers, see
327.Xr Intro 2 .
328Common values are:
329.Bl -tag -width Er -offset width
330.It Er EINVAL
331The image or slot indicated by
332.Fa imgid
333and
334.Fa slotid
335is unknown.
336.It Er EIO
337An error occurred talking to the device while trying to fill out
338firmware slot information.
339.It Er ENOMEM
340The driver was unable to allocate memory while filling out slot
341information.
342.El
343.It Fn ddi_ufm_op_getcaps
344The
345.Fn ddi_ufm_op_getcaps
346function is used to indicate which DDI UFM capabilities are supported by this
347driver instance.
348Currently there is only a single capability
349.Pq DDI_UFM_CAP_REPORT
350which indicates that the driver is capable of reporting UFM information for this
351instance.
352Future UFM versions may add additional capabilities such as the ability to
353obtain a raw dump of the firmware image or to upgrade the firmware.
354.Pp
355The driver should indicate the supported capabilities by setting the value in
356the
357.Ft caps
358parameter.
359Once the driver has populated
360.Ft caps
361with an appropriate value, then the driver should return
362.Sy 0 .
363Otherwise, the driver should return the appropriate error number.
364For a full list of error numbers, see
365.Xr Intro 2 .
366Common values are:
367.Bl -tag -width Er -offset width
368.It Er EIO
369An error occurred talking to the device while trying to discover firmware
370capabilities.
371.It Er ENOMEM
372The driver was unable to allocate memory.
373.El
374.El
375.Ss Caching and Updates
376The system will fetch firmware and slot information on an as-needed
377basis.
378Once it obtains some information, it may end up caching this information on
379behalf of the driver.
380Whenever the driver believes that something could have changed -- it need know
381that it has -- then the driver must call
382.Xr ddi_ufm_update 9F .
383.Ss Locking
384All UFM operations on a single UFM handle will always be run serially.
385However, the device driver may still need to apply adequate locking to
386its structure members as other may be accessing the same data structure
387or trying to communicate with the device.
388.Ss Unregistering from the UFM subsystem
389When a device driver is detached, it should unregister from the UFM
390subsystem.
391To do so, the driver should call
392.Xr ddi_ufm_fini 9F .
393By the time this function returns, the driver is guaranteed that no UFM
394entry points will be called.
395However, if there are outstanding UFM related activity, the function will
396block until it is terminated.
397.Ss ioctl Interface
398Userland consumers can access UFM information via a set of ioctls that are
399implemented by the
400.Xr ufm 7D
401driver.
402.Sh CONTEXT
403The various UFM entry points that a device driver must implement will
404always be called from
405.Sy kernel
406context.
407.Sh SEE ALSO
408.Xr Intro 2 ,
409.Xr ufd 7D ,
410.Xr attach 9E ,
411.Xr ddi_ufm_fini 9F ,
412.Xr ddi_ufm_image 9F ,
413.Xr ddi_ufm_image_set_desc 9F ,
414.Xr ddi_ufm_image_set_misc 9F ,
415.Xr ddi_ufm_image_set_nslots 9F ,
416.Xr ddi_ufm_init 9F ,
417.Xr ddi_ufm_slot 9F ,
418.Xr ddi_ufm_slot_set_attrs 9F ,
419.Xr ddi_ufm_slot_set_misc 9F ,
420.Xr ddi_ufm_slot_set_version 9F ,
421.Xr ddi_ufm_update 9F
422