Re: [PATCH v3 02/18] iommu: Implement IOMMU Live update FLB callbacks
Ankit Soni <[email protected]> Fri, 31 Jul 2026 05:58:20 +0000
| Newsgroups | dev.linux.lists.iommu,org.kernel.vger.kvm,org.kernel.vger.linux-kernel |
|---|---|
| Message-ID | <fjma5ub62ia4pbcvs4yek52r6jlhut4fidutow3g5uhf6iel3o@iqx3a6bm4q2e> |
On Sun, Jun 14, 2026 at 11:37:12PM +0000, Samiullah Khawaja wrote: > Add liveupdate FLB for IOMMU state preservation. Use KHO preserve memory > alloc/free helper functions to allocate memory for the IOMMU Live update > FLB object and the serialization structs for device, domain and iommu. > > During retrieve, walk through the preserved obj array headers and > restore each folio. Also recreate the FLB obj. > > Signed-off-by: Samiullah Khawaja <[email protected]> > --- > MAINTAINERS | 9 ++ > drivers/iommu/Kconfig | 12 ++ > drivers/iommu/Makefile | 1 + > drivers/iommu/liveupdate.c | 212 +++++++++++++++++++++++++++++++ > include/linux/iommu-liveupdate.h | 18 +++ > include/linux/kho/abi/iommu.h | 207 ++++++++++++++++++++++++++++++ > 6 files changed, 459 insertions(+) > create mode 100644 drivers/iommu/liveupdate.c > create mode 100644 include/linux/iommu-liveupdate.h > create mode 100644 include/linux/kho/abi/iommu.h > ../.. > diff --git a/include/linux/kho/abi/iommu.h b/include/linux/kho/abi/iommu.h > new file mode 100644 > index 000000000000..d06f251a2df4 > --- /dev/null > +++ b/include/linux/kho/abi/iommu.h > @@ -0,0 +1,207 @@ > +/* SPDX-License-Identifier: GPL-2.0 */ > + > +/* > + * Copyright (C) 2026, Google LLC > + * Author: Samiullah Khawaja <[email protected]> > + */ > + > +#ifndef _LINUX_KHO_ABI_IOMMU_H > +#define _LINUX_KHO_ABI_IOMMU_H > + > +#include <linux/mutex_types.h> > +#include <linux/compiler.h> > +#include <linux/types.h> > + > +/** > + * DOC: IOMMU File-Lifecycle Bound (FLB) Live Update ABI > + * > + * This header defines the ABI for preserving IOMMU state across kexec using > + * Live Update File-Lifecycle Bound (FLB) data. > + * > + * This interface is a contract. Any modification to any of the serialization > + * structs defined here constitutes a breaking change. Such changes require > + * incrementing the version number in the IOMMU_LUO_FLB_COMPATIBLE string. > + * > + * Memory Layout of Serialization Structures: > + * ========================================== > + * > + * Each serialized type (IOMMU, Domain, Device) is stored in a linked list of > + * arrays. The first array is allocated initially. When an array is full, a new > + * array is allocated and its physical address is stored in the next_array_phys > + * field of the hdr of the current array. > + * > + * Top Level (struct iommu_flb_ser): > + * +---------------------------+ > + * | - iommu_array_phys | > + * | - iommu_domain_array_phys | > + * | - device_array_phys | > + * +---------------------------+ > + * > + * Each Array contains the serialized objects of the respective type. For > + * example see below the representation of struct iommu_domain_array_ser. > + * > + * +---------------------------+ +---------------------------+ > + * | iommu_domain_array_ser |-->| iommu_domain_array_ser |--> NULL > + * | - hdr.next_array_phys | | - hdr.next_array_phys | > + * | - hdr.nr_objects | | - hdr.nr_objects | > + * | | | | > + * | objects[]: | | objects[]: | > + * | [ iommu_domain_ser ] | | [ iommu_domain_ser ] | > + * | [ iommu_domain_ser ] | | [ iommu_domain_ser ] | > + * | ... | | ... | > + * +---------------------------+ +---------------------------+ > + * > + * Each object in the array starts with a common header (iommu_hdr_ser). > + * For example, the layout of struct iommu_domain_ser is: > + * > + * +-----------------------------+ > + * | iommu_domain_ser | > + * | +-------------------------+ | > + * | | hdr (iommu_hdr_ser) | | > + * | | - ref_count | | > + * | | - deleted / incoming | | > + * | +-------------------------+ | > + * | - top_table_phys | | > + * | - top_level | | > + * | - restored_domain | | > + * +-----------------------------+ > + * > + * This pattern applies identically to iommu_device_ser and iommu_hw_ser. > + */ > + > +#define IOMMU_LUO_FLB_COMPATIBLE "iommu-liveupdate-v1" > + > +/** > + * enum iommu_type_ser - Type of the IOMMU being preserved > + * @IOMMU_INVALID: Invalid type of IOMMU > + * > + * IOMMU type is stored in the IOMMU HW state to differentiate between various > + * IOMMU HWs. > + */ > +enum iommu_type_ser { > + IOMMU_INVALID, > +}; > + > +#define IOMMU_SER_FLAG_DELETED (1 << 0) > +#define IOMMU_SER_FLAG_INCOMING (1 << 1) > + > +/** > + * struct iommu_hdr_ser - Common header for all serialized IOMMU objects > + * @ref_count: Reference count for the object > + * @flags: Bitmask of IOMMU_SER_FLAG_* flags indicating object state > + */ > +struct iommu_hdr_ser { > + u32 ref_count; > + u32 flags; > +} __packed; > + > +/** > + * struct iommu_domain_ser - Serialized state of an IOMMU domain > + * @hdr: Common object header > + * @top_table_phys: Physical address of the top-level page table > + * @top_level: Level of the top-level page table > + * @vasz: Virtual Address Size > + * @sign_extend: FEAT_SIGN_EXTEND is enabled for this domain > + * @restored_domain: Pointer to the restored domain (valid only after restore) > + */ > +struct iommu_domain_ser { > + struct iommu_hdr_ser hdr; > + u64 top_table_phys; > + u64 top_level; > + u32 vasz; > + u32 sign_extend:1; > + struct iommu_domain *restored_domain; > +} __packed; > + Hi, nit, The v3 changelog has "Replace bitfields with u32 flags", but sign_extend:1 looks like it was missed. this is 37 bytes, the only arrayed record in this header that isn't a multiple of 8 (iommu_device_ser is 56, iommu_hw_ser 112). The arrays are strided with pointer arithmetic, so the skew accumulates: from objects[1] onwards none of the u64s are naturally aligned. Looks like a leftover from the bitfield cleanup. -Ankit > +/** > + * struct iommu_dev_map_ser - Serialized mapping between device, domain, > + * and IOMMU instance. > + * @attachment_id: ID of the attachment between device and domain. > + * @domain_phys: Physical address of the domain > + * @iommu_phys: Physical address of the IOMMU > + */ > +struct iommu_dev_map_ser { > + u64 attachment_id; > + u64 domain_phys; > + u64 iommu_phys; > +} __packed; > + > +/** > + * struct iommu_device_ser - Serialized state of a device > + * @hdr: Common object header > + * @devid: Device ID > + * @pci_domain_nr: PCI domain number > + * @domain_iommu_ser: Domain and IOMMU mapping > + */ > +struct iommu_device_ser { > + struct iommu_hdr_ser hdr; > + u32 devid; > + u32 pci_domain_nr; > + struct iommu_dev_map_ser domain_iommu_ser; > +} __packed; > + > +/** > + * struct iommu_hw_ser - Serialized state of an IOMMU instance > + * @hdr: Common object header > + * @token: Unique token for the IOMMU > + * @type: IOMMU type serialized state belongs to > + */ > +struct iommu_hw_ser { > + struct iommu_hdr_ser hdr; > + u64 token; > + u64 type; > +} __packed; > + > +/** > + * struct iommu_array_hdr_ser - Header for an array of serialized objects > + * @next_array_phys: Physical address of the next array of objects > + * @nr_objects: Number of objects in the current array > + */ > +struct iommu_array_hdr_ser { > + u64 next_array_phys; > + u64 nr_objects; > +} __packed; > + > +/** > + * struct iommu_hw_array_ser - An array containing serialized IOMMU HWs > + * @hdr: Array header > + * @objects: Array of serialized IOMMU devices > + */ > +struct iommu_hw_array_ser { > + struct iommu_array_hdr_ser hdr; > + struct iommu_hw_ser objects[]; > +} __packed; > + > +/** > + * struct iommu_domain_array_ser - An array containing serialized domains > + * @hdr: Array header > + * @objects: Array of serialized domains > + */ > +struct iommu_domain_array_ser { > + struct iommu_array_hdr_ser hdr; > + struct iommu_domain_ser objects[]; > +} __packed; > + > +/** > + * struct iommu_device_array_ser - An array containing serialized devices > + * @hdr: Array header > + * @objects: Array of serialized devices > + */ > +struct iommu_device_array_ser { > + struct iommu_array_hdr_ser hdr; > + struct iommu_device_ser objects[]; > +} __packed; > + > +/** > + * struct iommu_flb_ser - Top-level serialization structure > + * @iommu_array_phys: Physical address of the first array of IOMMU HWs > + * @iommu_domain_array_phys: Physical address of the first array of domains > + * @device_array_phys: Physical address of the first array of devices > + */ > +struct iommu_flb_ser { > + u64 iommu_array_phys; > + u64 iommu_domain_array_phys; > + u64 device_array_phys; > +} __packed; > + > +#endif /* _LINUX_KHO_ABI_IOMMU_H */ > -- > 2.54.0.1136.gdb2ca164c4-goog >