NetBSD-Bugs archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

kern/57023: amd64 QEMU virtio-net not able to pxeboot.



>Number:         57023
>Category:       kern
>Synopsis:       amd64 QEMU virtio-net not able to pxeboot.
>Confidential:   no
>Severity:       serious
>Priority:       high
>Responsible:    kern-bug-people
>State:          open
>Class:          sw-bug
>Submitter-Id:   net
>Arrival-Date:   Sat Sep 24 17:30:00 +0000 2022
>Originator:     Martin Kjellstrand
>Release:        NetBSD netbsd 9.99.100
>Organization:
-
>Environment:
NetBSD netbsd 9.99.100 NetBSD 9.99.100 (GENERIC) #32: Sat Sep 24 16:37:21 CEST 2022  mad@plupp:/home/mad/co/netbsd/sys/arch/amd64/compile/obj/GENERIC amd64
>Description:
Running NetBSD under QEMU, using the virtio-net-pci driver, the system is not able to perform pxeboot:

...
[   1.0039800] virtio0 at pci0 dev 2 function 0
[   1.0039800] virtio0: Virtio Network Device (rev. 0x00)
[   1.0039800] vioif0 at virtio0: Features: 0x11070020<INDIRECT_DESC,NOTIFY_ON_EMPTY,CTRL_RX,CTRL_VQ,STATUS,MAC>
[   1.0039800] vioif0: Ethernet address 52:54:00:12:34:56
...
[   1.0039800] findroot: netboot interface not found.
[   1.0039800] findroot: netboot interface not found.
[   1.0039800] boot device: <unknown>
[   1.0039800] root device: 

[   1.9426149] use one of: vioif0 vioif1 ddb halt reboot


Using e1000 emulation instead of virtio-net-pci boots properly.

Thanks to tnn@ for help with debugging this issue.
>How-To-Repeat:
Run NetBSD under QEMU, using the virtio-net-pci driver for pxebooting.
>Fix:
Please find patch suggestion below which corrects this issue.

diff --git a/sys/arch/x86/pci/pci_machdep.c b/sys/arch/x86/pci/pci_machdep.c
index 68e6d7a93..7919070c0 100644
--- a/sys/arch/x86/pci/pci_machdep.c
+++ b/sys/arch/x86/pci/pci_machdep.c
@@ -1214,6 +1214,12 @@ device_pci_register(device_t dev, void *aux)
 					return dev;
 			}
 #endif
+		} else if (bin->bus == BI_BUS_PCI && device_is_a(parent, "virtio")) {
+			prop_dictionary_t prop = device_properties(parent);
+			uint tag;
+			if (prop_dictionary_get_uint(prop, "pxeboot-tag", &tag) &&
+			    bin->addr.tag == tag)
+				return dev;
 		}
 	}
 	if (parent && device_is_a(parent, "pci") &&
diff --git a/sys/dev/pci/virtio_pci.c b/sys/dev/pci/virtio_pci.c
index 08b63114b..153a38cf6 100644
--- a/sys/dev/pci/virtio_pci.c
+++ b/sys/dev/pci/virtio_pci.c
@@ -292,6 +292,16 @@ virtio_pci_attach(device_t parent, device_t self, void *aux)
 	virtio_set_status(sc, VIRTIO_CONFIG_DEVICE_STATUS_ACK);
 	virtio_set_status(sc, VIRTIO_CONFIG_DEVICE_STATUS_DRIVER);
 
+#if defined(__i386__) || defined(__amd64__)
+	/* device_pci_register() needs this for us to pxeboot */
+	if (PCI_CLASS(pa->pa_class) == PCI_CLASS_NETWORK) {
+		int b, d, f;
+		pci_decompose_tag(pc, tag, &b, &d, &f);
+		prop_dictionary_t prop = device_properties(self);
+		prop_dictionary_set_uint(prop, "pxeboot-tag", ((b << 8) | (d << 3) | f));
+	}
+#endif
+
 	sc->sc_childdevid = id;
 	sc->sc_child = NULL;
 	virtio_pci_rescan(self, NULL, NULL);



Home | Main Index | Thread Index | Old Index