drivers/virt/vmgenid.c
Source file repositories/reference/linux-study-clean/drivers/virt/vmgenid.c
File Facts
- System
- Linux kernel
- Corpus path
drivers/virt/vmgenid.c- Extension
.c- Size
- 4498 bytes
- Lines
- 182
- Domain
- Driver Families
- Bucket
- drivers/virt
- Inferred role
- Driver Families: implementation source
- Status
- source implementation candidate
Why This File Exists
Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.
- Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.
- Touches IRQ or DMA behavior; this matters for the representative real-device path.
- Allocates kernel memory; connect allocation flags and lifetime to context constraints.
- Defines or uses C structs; map object ownership, embedded links, reference counts, and lock ownership.
Dependency Surface
linux/acpi.hlinux/interrupt.hlinux/kernel.hlinux/module.hlinux/platform_device.hlinux/random.h
Detected Declarations
struct vmgenid_statefunction vmgenid_notifyfunction setup_vmgenid_statefunction vmgenid_acpi_handlerfunction vmgenid_add_acpifunction vmgenid_add_acpifunction vmgenid_of_irq_handlerfunction vmgenid_add_offunction vmgenid_add
Annotated Snippet
struct vmgenid_state {
u8 *next_id;
u8 this_id[VMGENID_SIZE];
};
static void vmgenid_notify(struct device *device)
{
struct vmgenid_state *state = device->driver_data;
u8 old_id[VMGENID_SIZE];
memcpy(old_id, state->this_id, sizeof(old_id));
memcpy(state->this_id, state->next_id, sizeof(state->this_id));
if (!memcmp(old_id, state->this_id, sizeof(old_id)))
return;
add_vmfork_randomness(state->this_id, sizeof(state->this_id));
}
static void setup_vmgenid_state(struct vmgenid_state *state, void *virt_addr)
{
state->next_id = virt_addr;
memcpy(state->this_id, state->next_id, sizeof(state->this_id));
add_device_randomness(state->this_id, sizeof(state->this_id));
}
#ifdef CONFIG_ACPI
static void vmgenid_acpi_handler(acpi_handle __always_unused handle,
u32 __always_unused event, void *dev)
{
vmgenid_notify(dev);
}
static int vmgenid_add_acpi(struct device *dev, struct vmgenid_state *state)
{
struct acpi_device *device = ACPI_COMPANION(dev);
struct acpi_buffer parsed = { ACPI_ALLOCATE_BUFFER };
union acpi_object *obj;
phys_addr_t phys_addr;
acpi_status status;
void *virt_addr;
int ret = 0;
status = acpi_evaluate_object(device->handle, "ADDR", NULL, &parsed);
if (ACPI_FAILURE(status)) {
ACPI_EXCEPTION((AE_INFO, status, "Evaluating ADDR"));
return -ENODEV;
}
obj = parsed.pointer;
if (!obj || obj->type != ACPI_TYPE_PACKAGE || obj->package.count != 2 ||
obj->package.elements[0].type != ACPI_TYPE_INTEGER ||
obj->package.elements[1].type != ACPI_TYPE_INTEGER) {
ret = -EINVAL;
goto out;
}
phys_addr = (obj->package.elements[0].integer.value << 0) |
(obj->package.elements[1].integer.value << 32);
virt_addr = devm_memremap(&device->dev, phys_addr, VMGENID_SIZE, MEMREMAP_WB);
if (IS_ERR(virt_addr)) {
ret = PTR_ERR(virt_addr);
goto out;
}
setup_vmgenid_state(state, virt_addr);
status = acpi_install_notify_handler(device->handle, ACPI_DEVICE_NOTIFY,
vmgenid_acpi_handler, dev);
if (ACPI_FAILURE(status)) {
ret = -ENODEV;
goto out;
}
dev->driver_data = state;
out:
ACPI_FREE(parsed.pointer);
return ret;
}
#else
static int vmgenid_add_acpi(struct device *dev, struct vmgenid_state *state)
{
return -EINVAL;
}
#endif
static irqreturn_t vmgenid_of_irq_handler(int __always_unused irq, void *dev)
{
vmgenid_notify(dev);
return IRQ_HANDLED;
}
static int vmgenid_add_of(struct platform_device *pdev,
Annotation
- Immediate include surface: `linux/acpi.h`, `linux/interrupt.h`, `linux/kernel.h`, `linux/module.h`, `linux/platform_device.h`, `linux/random.h`.
- Detected declarations: `struct vmgenid_state`, `function vmgenid_notify`, `function setup_vmgenid_state`, `function vmgenid_acpi_handler`, `function vmgenid_add_acpi`, `function vmgenid_add_acpi`, `function vmgenid_of_irq_handler`, `function vmgenid_add_of`, `function vmgenid_add`.
- Atlas domain: Driver Families / drivers/virt.
- Implementation status: source implementation candidate.
- IRQ or DMA behavior appears here, which is relevant to the selected PCIe/NVMe device path.
Implementation Notes
- This generated page is the file-by-file coverage layer; curated subsystem chapters should link here when they synthesize a multi-file control flow.
- Core OS pages should be promoted from atlas-only to deep-reviewed when they explain data structures, invariants, locking, lifecycle, and C implementation snippets.
- Driver-family pages are intentionally pattern-oriented unless they are part of the selected PCIe/NVMe representative device path.