efi: Move to using efi_guid_t in ioctl definitions

Start using efi_guid_t instead of struct uuid in the ioctl
definitions. These are binarily the same, but have different
structure definitions. EFI prefers this form, and to allow more
sharing with EDK2, make this slight addition.

I've not really defined new IOCTLs for this. They are the same
size, but I have defined new function.

Also fix in-kernel uses of uuid to efi_guid_t for anything related to
ioctl.

Sponsored by:		Netflix
Reviewed by:		tsoome, kib
Differential Revision:	https://reviews.freebsd.org/D50057
This commit is contained in:
Warner Losh
2025-05-01 11:53:40 -06:00
parent 915b2336b1
commit 20a860ae3a
5 changed files with 84 additions and 42 deletions
+10 -9
View File
@@ -52,12 +52,13 @@ efidev_ioctl(struct cdev *dev __unused, u_long cmd, caddr_t addr,
switch (cmd) {
case EFIIOC_GET_TABLE:
{
struct efi_get_table_ioc *egtioc =
(struct efi_get_table_ioc *)addr;
struct efi_get_table_ioctl *egtioc =
(struct efi_get_table_ioctl *)addr;
void *buf = NULL;
error = efi_copy_table((efi_guid_t *)&egtioc->uuid, egtioc->buf ? &buf : NULL,
egtioc->buf_len, &egtioc->table_len);
error = efi_copy_table(&egtioc->guid,
egtioc->buf != NULL ? &buf : NULL, egtioc->buf_len,
&egtioc->table_len);
if (error != 0 || egtioc->buf == NULL)
break;
@@ -89,7 +90,7 @@ efidev_ioctl(struct cdev *dev __unused, u_long cmd, caddr_t addr,
}
case EFIIOC_GET_WAKETIME:
{
struct efi_waketime_ioc *wt = (struct efi_waketime_ioc *)addr;
struct efi_waketime_ioctl *wt = (struct efi_waketime_ioctl *)addr;
error = efi_get_waketime(&wt->enabled, &wt->pending,
&wt->waketime);
@@ -97,14 +98,14 @@ efidev_ioctl(struct cdev *dev __unused, u_long cmd, caddr_t addr,
}
case EFIIOC_SET_WAKETIME:
{
struct efi_waketime_ioc *wt = (struct efi_waketime_ioc *)addr;
struct efi_waketime_ioctl *wt = (struct efi_waketime_ioctl *)addr;
error = efi_set_waketime(wt->enabled, &wt->waketime);
break;
}
case EFIIOC_VAR_GET:
{
struct efi_var_ioc *ev = (struct efi_var_ioc *)addr;
struct efi_var_ioctl *ev = (struct efi_var_ioctl *)addr;
void *data;
efi_char *name;
@@ -140,7 +141,7 @@ efidev_ioctl(struct cdev *dev __unused, u_long cmd, caddr_t addr,
}
case EFIIOC_VAR_NEXT:
{
struct efi_var_ioc *ev = (struct efi_var_ioc *)addr;
struct efi_var_ioctl *ev = (struct efi_var_ioctl *)addr;
efi_char *name;
name = malloc(ev->namesize, M_TEMP, M_WAITOK);
@@ -162,7 +163,7 @@ efidev_ioctl(struct cdev *dev __unused, u_long cmd, caddr_t addr,
}
case EFIIOC_VAR_SET:
{
struct efi_var_ioc *ev = (struct efi_var_ioc *)addr;
struct efi_var_ioctl *ev = (struct efi_var_ioctl *)addr;
void *data = NULL;
efi_char *name;
+3 -3
View File
@@ -730,7 +730,7 @@ set_time(struct efi_tm *tm)
}
static int
var_get(efi_char *name, struct uuid *vendor, uint32_t *attrib,
var_get(efi_char *name, efi_guid_t *vendor, uint32_t *attrib,
size_t *datasize, void *data)
{
struct efirt_callinfo ec;
@@ -754,7 +754,7 @@ var_get(efi_char *name, struct uuid *vendor, uint32_t *attrib,
}
static int
var_nextname(size_t *namesize, efi_char *name, struct uuid *vendor)
var_nextname(size_t *namesize, efi_char *name, efi_guid_t *vendor)
{
struct efirt_callinfo ec;
int error;
@@ -775,7 +775,7 @@ var_nextname(size_t *namesize, efi_char *name, struct uuid *vendor)
}
static int
var_set(efi_char *name, struct uuid *vendor, uint32_t attrib,
var_set(efi_char *name, efi_guid_t *vendor, uint32_t attrib,
size_t datasize, void *data)
{
struct efirt_callinfo ec;
+3 -3
View File
@@ -122,7 +122,7 @@ set_time(struct efi_tm *tm)
}
static int
var_get(efi_char *name, struct uuid *vendor, uint32_t *attrib,
var_get(efi_char *name, efi_guid_t *vendor, uint32_t *attrib,
size_t *datasize, void *data)
{
struct xen_platform_op op = {
@@ -151,7 +151,7 @@ var_get(efi_char *name, struct uuid *vendor, uint32_t *attrib,
}
static int
var_nextname(size_t *namesize, efi_char *name, struct uuid *vendor)
var_nextname(size_t *namesize, efi_char *name, efi_guid_t *vendor)
{
struct xen_platform_op op = {
.cmd = XENPF_efi_runtime_call,
@@ -177,7 +177,7 @@ var_nextname(size_t *namesize, efi_char *name, struct uuid *vendor)
}
static int
var_set(efi_char *name, struct uuid *vendor, uint32_t attrib,
var_set(efi_char *name, efi_guid_t *vendor, uint32_t attrib,
size_t datasize, void *data)
{
struct xen_platform_op op = {
+10 -10
View File
@@ -151,7 +151,7 @@ struct efi_esrt_table {
};
struct efi_esrt_entry_v1 {
struct uuid fw_class;
efi_guid_t fw_class;
uint32_t fw_type;
uint32_t fw_version;
uint32_t lowest_supported_fw_version;
@@ -181,11 +181,11 @@ struct efi_rt {
efi_status (*rt_setvirtual)(u_long, u_long, uint32_t,
struct efi_md *) EFIABI_ATTR;
efi_status (*rt_cvtptr)(u_long, void **) EFIABI_ATTR;
efi_status (*rt_getvar)(efi_char *, struct uuid *, uint32_t *,
efi_status (*rt_getvar)(efi_char *, efi_guid_t *, uint32_t *,
u_long *, void *) EFIABI_ATTR;
efi_status (*rt_scanvar)(u_long *, efi_char *, struct uuid *)
efi_status (*rt_scanvar)(u_long *, efi_char *, efi_guid_t *)
EFIABI_ATTR;
efi_status (*rt_setvar)(efi_char *, struct uuid *, uint32_t,
efi_status (*rt_setvar)(efi_char *, efi_guid_t *, uint32_t,
u_long, void *) EFIABI_ATTR;
efi_status (*rt_gethicnt)(uint32_t *) EFIABI_ATTR;
efi_status (*rt_reset)(enum efi_reset, efi_status, u_long,
@@ -267,10 +267,10 @@ struct efi_ops {
int (*get_waketime)(uint8_t *enabled, uint8_t *pending,
struct efi_tm *tm);
int (*set_waketime)(uint8_t enable, struct efi_tm *tm);
int (*var_get)(uint16_t *, struct uuid *, uint32_t *, size_t *,
int (*var_get)(uint16_t *, efi_guid_t *, uint32_t *, size_t *,
void *);
int (*var_nextname)(size_t *, uint16_t *, struct uuid *);
int (*var_set)(uint16_t *, struct uuid *, uint32_t, size_t, void *);
int (*var_nextname)(size_t *, uint16_t *, efi_guid_t *);
int (*var_set)(uint16_t *, efi_guid_t *, uint32_t, size_t, void *);
};
extern const struct efi_ops *active_efi_ops;
@@ -347,7 +347,7 @@ static inline int efi_set_waketime(uint8_t enable, struct efi_tm *tm)
return (active_efi_ops->set_waketime(enable, tm));
}
static inline int efi_var_get(uint16_t *name, struct uuid *vendor,
static inline int efi_var_get(uint16_t *name, efi_guid_t *vendor,
uint32_t *attrib, size_t *datasize, void *data)
{
@@ -357,7 +357,7 @@ static inline int efi_var_get(uint16_t *name, struct uuid *vendor,
}
static inline int efi_var_nextname(size_t *namesize, uint16_t *name,
struct uuid *vendor)
efi_guid_t *vendor)
{
if (active_efi_ops->var_nextname == NULL)
@@ -365,7 +365,7 @@ static inline int efi_var_nextname(size_t *namesize, uint16_t *name,
return (active_efi_ops->var_nextname(namesize, name, vendor));
}
static inline int efi_var_set(uint16_t *name, struct uuid *vendor,
static inline int efi_var_set(uint16_t *name, efi_guid_t *vendor,
uint32_t attrib, size_t datasize, void *data)
{
+58 -17
View File
@@ -30,10 +30,60 @@
#include <sys/uuid.h>
#include <sys/efi.h>
/*
* The EFI world chose not to use the typical uuid_t defines for its global
* universal identifiers. But the textual representation is the same, and we can
* use the uuid_* routines to parse and print them. However, all EFI interfaces
* for this need to be efi_guid_t so we can share code with EDK2, so the *_ioc
* structures in this file are converted to _ioctl structure to transition to
* this new requirement. This library is little used outside of FreeBSD and they
* will be dropped in 16.
*/
_Static_assert(sizeof(struct uuid) == sizeof(efi_guid_t),
"uuid_t and efi_guid_t are same bytes, but different elements");
#if __FreeBSD_version < 1600000 && !defined(_KERNEL)
#define _WANT_EFI_IOC
#endif
struct efi_get_table_ioctl
{
void *buf; /* Pointer to userspace buffer */
efi_guid_t guid; /* GUID to look up */
size_t table_len; /* Table size */
size_t buf_len; /* Size of the buffer */
};
struct efi_var_ioctl
{
efi_char *name; /* User pointer to name, in wide chars */
size_t namesize; /* Number of wide characters in name */
efi_guid_t vendor; /* Vendor's GUID for variable */
uint32_t attrib; /* Attributes */
void *data; /* User pointer to the data */
size_t datasize; /* Number of *bytes* in the data */
};
struct efi_waketime_ioctl
{
struct efi_tm waketime;
uint8_t enabled;
uint8_t pending;
};
#define EFIIOC_GET_TABLE _IOWR('E', 1, struct efi_get_table_ioctl)
#define EFIIOC_GET_TIME _IOR('E', 2, struct efi_tm)
#define EFIIOC_SET_TIME _IOW('E', 3, struct efi_tm)
#define EFIIOC_VAR_GET _IOWR('E', 4, struct efi_var_ioctl)
#define EFIIOC_VAR_NEXT _IOWR('E', 5, struct efi_var_ioctl)
#define EFIIOC_VAR_SET _IOWR('E', 6, struct efi_var_ioctl)
#define EFIIOC_GET_WAKETIME _IOR('E', 7, struct efi_waketime_ioctl)
#define EFIIOC_SET_WAKETIME _IOW('E', 8, struct efi_waketime_ioctl)
#ifdef _WANT_EFI_IOC
struct efi_get_table_ioc
{
void *buf; /* Pointer to userspace buffer */
struct uuid uuid; /* UUID to look up */
struct uuid uuid; /* GUID to look up */
size_t table_len; /* Table size */
size_t buf_len; /* Size of the buffer */
};
@@ -42,26 +92,17 @@ struct efi_var_ioc
{
efi_char *name; /* User pointer to name, in wide chars */
size_t namesize; /* Number of wide characters in name */
struct uuid vendor; /* Vendor's UUID for variable */
struct uuid vendor; /* Vendor's GUID for variable */
uint32_t attrib; /* Attributes */
void *data; /* User pointer to the data */
size_t datasize; /* Number of *bytes* in the data */
};
struct efi_waketime_ioc
{
struct efi_tm waketime;
uint8_t enabled;
uint8_t pending;
};
#define EFIIOC_GET_TABLE _IOWR('E', 1, struct efi_get_table_ioc)
#define EFIIOC_GET_TIME _IOR('E', 2, struct efi_tm)
#define EFIIOC_SET_TIME _IOW('E', 3, struct efi_tm)
#define EFIIOC_VAR_GET _IOWR('E', 4, struct efi_var_ioc)
#define EFIIOC_VAR_NEXT _IOWR('E', 5, struct efi_var_ioc)
#define EFIIOC_VAR_SET _IOWR('E', 6, struct efi_var_ioc)
#define EFIIOC_GET_WAKETIME _IOR('E', 7, struct efi_waketime_ioc)
#define EFIIOC_SET_WAKETIME _IOW('E', 8, struct efi_waketime_ioc)
_Static_assert(sizeof(struct efi_get_table_ioc) == sizeof(struct efi_get_table_ioctl),
"Old and new struct table defines must be the same size");
_Static_assert(sizeof(struct efi_var_ioc) == sizeof(struct efi_var_ioctl),
"Old and new struct var defines must be the same size");
#define efi_waketime_ioc efi_waketime_ioctl
#endif
#endif /* _SYS_EFIIO_H_ */