Skip to content

Commit 7b1bcd6

Browse files
Sudan Landgezx2c4
authored andcommitted
virt: vmgenid: add support for devicetree bindings
Extend the vmgenid platform driver to support devicetree bindings. With this support, hypervisors can send vmgenid notifications to the virtual machine without the need to enable ACPI. The bindings are located at: Documentation/devicetree/bindings/rng/microsoft,vmgenid.yaml Since this is no longer ACPI-dependent, remove the dependency from Kconfig and protect the ACPI code with a single ifdef. Signed-off-by: Sudan Landge <sudanl@amazon.com> Reviewed-by: Alexander Graf <graf@amazon.com> Tested-by: Babis Chalios <bchalios@amazon.es> [Jason: - Small style cleanups and refactoring. - Re-work ACPI conditionalization. ] Signed-off-by: Jason A. Donenfeld <Jason@zx2c4.com>
1 parent a4aded1 commit 7b1bcd6

File tree

2 files changed

+51
-3
lines changed

2 files changed

+51
-3
lines changed

drivers/virt/Kconfig

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,6 @@ if VIRT_DRIVERS
1616
config VMGENID
1717
tristate "Virtual Machine Generation ID driver"
1818
default y
19-
depends on ACPI
2019
help
2120
Say Y here to use the hypervisor-provided Virtual Machine Generation ID
2221
to reseed the RNG when the VM is cloned. This is highly recommended if

drivers/virt/vmgenid.c

Lines changed: 51 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,12 +2,13 @@
22
/*
33
* Copyright (C) 2022 Jason A. Donenfeld <Jason@zx2c4.com>. All Rights Reserved.
44
*
5-
* The "Virtual Machine Generation ID" is exposed via ACPI and changes when a
5+
* The "Virtual Machine Generation ID" is exposed via ACPI or DT and changes when a
66
* virtual machine forks or is cloned. This driver exists for shepherding that
77
* information to random.c.
88
*/
99

1010
#include <linux/acpi.h>
11+
#include <linux/interrupt.h>
1112
#include <linux/kernel.h>
1213
#include <linux/module.h>
1314
#include <linux/platform_device.h>
@@ -41,6 +42,7 @@ static void setup_vmgenid_state(struct vmgenid_state *state, void *virt_addr)
4142
add_device_randomness(state->this_id, sizeof(state->this_id));
4243
}
4344

45+
#ifdef CONFIG_ACPI
4446
static void vmgenid_acpi_handler(acpi_handle __always_unused handle,
4547
u32 __always_unused event, void *dev)
4648
{
@@ -92,6 +94,43 @@ static int vmgenid_add_acpi(struct device *dev, struct vmgenid_state *state)
9294
ACPI_FREE(parsed.pointer);
9395
return ret;
9496
}
97+
#else
98+
static int vmgenid_add_acpi(struct device *dev, struct vmgenid_state *state)
99+
{
100+
return -EINVAL;
101+
}
102+
#endif
103+
104+
static irqreturn_t vmgenid_of_irq_handler(int __always_unused irq, void *dev)
105+
{
106+
vmgenid_notify(dev);
107+
return IRQ_HANDLED;
108+
}
109+
110+
static int vmgenid_add_of(struct platform_device *pdev,
111+
struct vmgenid_state *state)
112+
{
113+
void *virt_addr;
114+
int ret;
115+
116+
virt_addr = devm_platform_get_and_ioremap_resource(pdev, 0, NULL);
117+
if (IS_ERR(virt_addr))
118+
return PTR_ERR(virt_addr);
119+
120+
setup_vmgenid_state(state, virt_addr);
121+
122+
ret = platform_get_irq(pdev, 0);
123+
if (ret < 0)
124+
return ret;
125+
126+
ret = devm_request_irq(&pdev->dev, ret, vmgenid_of_irq_handler,
127+
IRQF_SHARED, "vmgenid", &pdev->dev);
128+
if (ret < 0)
129+
return ret;
130+
131+
pdev->dev.driver_data = state;
132+
return 0;
133+
}
95134

96135
static int vmgenid_add(struct platform_device *pdev)
97136
{
@@ -103,13 +142,22 @@ static int vmgenid_add(struct platform_device *pdev)
103142
if (!state)
104143
return -ENOMEM;
105144

106-
ret = vmgenid_add_acpi(dev, state);
145+
if (dev->of_node)
146+
ret = vmgenid_add_of(pdev, state);
147+
else
148+
ret = vmgenid_add_acpi(dev, state);
107149

108150
if (ret < 0)
109151
devm_kfree(dev, state);
110152
return ret;
111153
}
112154

155+
static const struct of_device_id vmgenid_of_ids[] = {
156+
{ .compatible = "microsoft,vmgenid", },
157+
{ },
158+
};
159+
MODULE_DEVICE_TABLE(of, vmgenid_of_ids);
160+
113161
static const struct acpi_device_id vmgenid_acpi_ids[] = {
114162
{ "VMGENCTR", 0 },
115163
{ "VM_GEN_COUNTER", 0 },
@@ -122,6 +170,7 @@ static struct platform_driver vmgenid_plaform_driver = {
122170
.driver = {
123171
.name = "vmgenid",
124172
.acpi_match_table = vmgenid_acpi_ids,
173+
.of_match_table = vmgenid_of_ids,
125174
},
126175
};
127176

0 commit comments

Comments
 (0)