Skip to content

Commit a6e0868

Browse files
committed
Update backend crash handling to a newer patch by Juergen Gross
1 parent 831204f commit a6e0868

4 files changed

+434
-127
lines changed

0001-xen-xenbus-better-handle-backend-crash.patch

Lines changed: 0 additions & 126 deletions
This file was deleted.
Lines changed: 267 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,267 @@
1+
From be50f0a4041116392864a9acb37315c8b8c076a7 Mon Sep 17 00:00:00 2001
2+
From: Juergen Gross <jgross@suse.com>
3+
Date: Mon, 9 Feb 2026 08:42:06 +0100
4+
Subject: [PATCH 1/2] xenbus: add xenbus_device parameter to
5+
xenbus_read_driver_state()
6+
7+
In order to prepare checking the xenbus device status in
8+
xenbus_read_driver_state(), add the pointer to struct xenbus_device
9+
as a parameter.
10+
11+
Signed-off-by: Juergen Gross <jgross@suse.com>
12+
---
13+
drivers/net/xen-netfront.c | 34 +++++++++++-----------
14+
drivers/pci/xen-pcifront.c | 8 ++---
15+
drivers/scsi/xen-scsifront.c | 2 +-
16+
drivers/xen/xen-pciback/xenbus.c | 10 +++----
17+
drivers/xen/xenbus/xenbus_client.c | 3 +-
18+
drivers/xen/xenbus/xenbus_probe.c | 6 ++--
19+
drivers/xen/xenbus/xenbus_probe_frontend.c | 2 +-
20+
include/xen/xenbus.h | 3 +-
21+
8 files changed, 35 insertions(+), 33 deletions(-)
22+
23+
diff --git a/drivers/net/xen-netfront.c b/drivers/net/xen-netfront.c
24+
index 7c2220366623..e2da977c9c50 100644
25+
--- a/drivers/net/xen-netfront.c
26+
+++ b/drivers/net/xen-netfront.c
27+
@@ -1646,7 +1646,7 @@ static int xennet_xdp_set(struct net_device *dev, struct bpf_prog *prog,
28+
29+
/* avoid the race with XDP headroom adjustment */
30+
wait_event(module_wq,
31+
- xenbus_read_driver_state(np->xbdev->otherend) ==
32+
+ xenbus_read_driver_state(np->xbdev, np->xbdev->otherend) ==
33+
XenbusStateReconfigured);
34+
np->netfront_xdp_enabled = true;
35+
36+
@@ -1764,9 +1764,9 @@ static struct net_device *xennet_create_dev(struct xenbus_device *dev)
37+
do {
38+
xenbus_switch_state(dev, XenbusStateInitialising);
39+
err = wait_event_timeout(module_wq,
40+
- xenbus_read_driver_state(dev->otherend) !=
41+
+ xenbus_read_driver_state(dev, dev->otherend) !=
42+
XenbusStateClosed &&
43+
- xenbus_read_driver_state(dev->otherend) !=
44+
+ xenbus_read_driver_state(dev, dev->otherend) !=
45+
XenbusStateUnknown, XENNET_TIMEOUT);
46+
} while (!err);
47+
48+
@@ -2627,31 +2627,31 @@ static void xennet_bus_close(struct xenbus_device *dev)
49+
{
50+
int ret;
51+
52+
- if (xenbus_read_driver_state(dev->otherend) == XenbusStateClosed)
53+
+ if (xenbus_read_driver_state(dev, dev->otherend) == XenbusStateClosed)
54+
return;
55+
do {
56+
xenbus_switch_state(dev, XenbusStateClosing);
57+
ret = wait_event_timeout(module_wq,
58+
- xenbus_read_driver_state(dev->otherend) ==
59+
- XenbusStateClosing ||
60+
- xenbus_read_driver_state(dev->otherend) ==
61+
- XenbusStateClosed ||
62+
- xenbus_read_driver_state(dev->otherend) ==
63+
- XenbusStateUnknown,
64+
- XENNET_TIMEOUT);
65+
+ xenbus_read_driver_state(dev, dev->otherend) ==
66+
+ XenbusStateClosing ||
67+
+ xenbus_read_driver_state(dev, dev->otherend) ==
68+
+ XenbusStateClosed ||
69+
+ xenbus_read_driver_state(dev, dev->otherend) ==
70+
+ XenbusStateUnknown,
71+
+ XENNET_TIMEOUT);
72+
} while (!ret);
73+
74+
- if (xenbus_read_driver_state(dev->otherend) == XenbusStateClosed)
75+
+ if (xenbus_read_driver_state(dev, dev->otherend) == XenbusStateClosed)
76+
return;
77+
78+
do {
79+
xenbus_switch_state(dev, XenbusStateClosed);
80+
ret = wait_event_timeout(module_wq,
81+
- xenbus_read_driver_state(dev->otherend) ==
82+
- XenbusStateClosed ||
83+
- xenbus_read_driver_state(dev->otherend) ==
84+
- XenbusStateUnknown,
85+
- XENNET_TIMEOUT);
86+
+ xenbus_read_driver_state(dev, dev->otherend) ==
87+
+ XenbusStateClosed ||
88+
+ xenbus_read_driver_state(dev, dev->otherend) ==
89+
+ XenbusStateUnknown,
90+
+ XENNET_TIMEOUT);
91+
} while (!ret);
92+
}
93+
94+
diff --git a/drivers/pci/xen-pcifront.c b/drivers/pci/xen-pcifront.c
95+
index 11636634ae51..cd22bf984024 100644
96+
--- a/drivers/pci/xen-pcifront.c
97+
+++ b/drivers/pci/xen-pcifront.c
98+
@@ -856,7 +856,7 @@ static void pcifront_try_connect(struct pcifront_device *pdev)
99+
int err;
100+
101+
/* Only connect once */
102+
- if (xenbus_read_driver_state(pdev->xdev->nodename) !=
103+
+ if (xenbus_read_driver_state(pdev->xdev, pdev->xdev->nodename) !=
104+
XenbusStateInitialised)
105+
return;
106+
107+
@@ -876,7 +876,7 @@ static int pcifront_try_disconnect(struct pcifront_device *pdev)
108+
enum xenbus_state prev_state;
109+
110+
111+
- prev_state = xenbus_read_driver_state(pdev->xdev->nodename);
112+
+ prev_state = xenbus_read_driver_state(pdev->xdev, pdev->xdev->nodename);
113+
114+
if (prev_state >= XenbusStateClosing)
115+
goto out;
116+
@@ -895,7 +895,7 @@ static int pcifront_try_disconnect(struct pcifront_device *pdev)
117+
118+
static void pcifront_attach_devices(struct pcifront_device *pdev)
119+
{
120+
- if (xenbus_read_driver_state(pdev->xdev->nodename) ==
121+
+ if (xenbus_read_driver_state(pdev->xdev, pdev->xdev->nodename) ==
122+
XenbusStateReconfiguring)
123+
pcifront_connect(pdev);
124+
}
125+
@@ -909,7 +909,7 @@ static int pcifront_detach_devices(struct pcifront_device *pdev)
126+
struct pci_dev *pci_dev;
127+
char str[64];
128+
129+
- state = xenbus_read_driver_state(pdev->xdev->nodename);
130+
+ state = xenbus_read_driver_state(pdev->xdev, pdev->xdev->nodename);
131+
if (state == XenbusStateInitialised) {
132+
dev_dbg(&pdev->xdev->dev, "Handle skipped connect.\n");
133+
/* We missed Connected and need to initialize. */
134+
diff --git a/drivers/scsi/xen-scsifront.c b/drivers/scsi/xen-scsifront.c
135+
index 924025305753..ef74d4da5ab0 100644
136+
--- a/drivers/scsi/xen-scsifront.c
137+
+++ b/drivers/scsi/xen-scsifront.c
138+
@@ -1175,7 +1175,7 @@ static void scsifront_backend_changed(struct xenbus_device *dev,
139+
return;
140+
}
141+
142+
- if (xenbus_read_driver_state(dev->nodename) ==
143+
+ if (xenbus_read_driver_state(dev, dev->nodename) ==
144+
XenbusStateInitialised)
145+
scsifront_do_lun_hotplug(info, VSCSIFRONT_OP_ADD_LUN);
146+
147+
diff --git a/drivers/xen/xen-pciback/xenbus.c b/drivers/xen/xen-pciback/xenbus.c
148+
index b11e401f1b1e..4bd1c7a8957e 100644
149+
--- a/drivers/xen/xen-pciback/xenbus.c
150+
+++ b/drivers/xen/xen-pciback/xenbus.c
151+
@@ -149,12 +149,12 @@ static int xen_pcibk_attach(struct xen_pcibk_device *pdev)
152+
153+
mutex_lock(&pdev->dev_lock);
154+
/* Make sure we only do this setup once */
155+
- if (xenbus_read_driver_state(pdev->xdev->nodename) !=
156+
+ if (xenbus_read_driver_state(pdev->xdev, pdev->xdev->nodename) !=
157+
XenbusStateInitialised)
158+
goto out;
159+
160+
/* Wait for frontend to state that it has published the configuration */
161+
- if (xenbus_read_driver_state(pdev->xdev->otherend) !=
162+
+ if (xenbus_read_driver_state(pdev->xdev, pdev->xdev->otherend) !=
163+
XenbusStateInitialised)
164+
goto out;
165+
166+
@@ -374,7 +374,7 @@ static int xen_pcibk_reconfigure(struct xen_pcibk_device *pdev,
167+
dev_dbg(&pdev->xdev->dev, "Reconfiguring device ...\n");
168+
169+
mutex_lock(&pdev->dev_lock);
170+
- if (xenbus_read_driver_state(pdev->xdev->nodename) != state)
171+
+ if (xenbus_read_driver_state(pdev->xdev, pdev->xdev->nodename) != state)
172+
goto out;
173+
174+
err = xenbus_scanf(XBT_NIL, pdev->xdev->nodename, "num_devs", "%d",
175+
@@ -572,7 +572,7 @@ static int xen_pcibk_setup_backend(struct xen_pcibk_device *pdev)
176+
/* It's possible we could get the call to setup twice, so make sure
177+
* we're not already connected.
178+
*/
179+
- if (xenbus_read_driver_state(pdev->xdev->nodename) !=
180+
+ if (xenbus_read_driver_state(pdev->xdev, pdev->xdev->nodename) !=
181+
XenbusStateInitWait)
182+
goto out;
183+
184+
@@ -662,7 +662,7 @@ static void xen_pcibk_be_watch(struct xenbus_watch *watch,
185+
struct xen_pcibk_device *pdev =
186+
container_of(watch, struct xen_pcibk_device, be_watch);
187+
188+
- switch (xenbus_read_driver_state(pdev->xdev->nodename)) {
189+
+ switch (xenbus_read_driver_state(pdev->xdev, pdev->xdev->nodename)) {
190+
case XenbusStateInitWait:
191+
xen_pcibk_setup_backend(pdev);
192+
break;
193+
diff --git a/drivers/xen/xenbus/xenbus_client.c b/drivers/xen/xenbus/xenbus_client.c
194+
index 2dc874fb5506..6ed0cd8e9676 100644
195+
--- a/drivers/xen/xenbus/xenbus_client.c
196+
+++ b/drivers/xen/xenbus/xenbus_client.c
197+
@@ -936,7 +936,8 @@ static int xenbus_unmap_ring_hvm(struct xenbus_device *dev, void *vaddr)
198+
* Returns: the state of the driver rooted at the given store path, or
199+
* XenbusStateUnknown if no state can be read.
200+
*/
201+
-enum xenbus_state xenbus_read_driver_state(const char *path)
202+
+enum xenbus_state xenbus_read_driver_state(const struct xenbus_device *dev,
203+
+ const char *path)
204+
{
205+
enum xenbus_state result;
206+
int err = xenbus_gather(XBT_NIL, path, "state", "%d", &result, NULL);
207+
diff --git a/drivers/xen/xenbus/xenbus_probe.c b/drivers/xen/xenbus/xenbus_probe.c
208+
index 86fe6e779056..d4f1dbf7cbc4 100644
209+
--- a/drivers/xen/xenbus/xenbus_probe.c
210+
+++ b/drivers/xen/xenbus/xenbus_probe.c
211+
@@ -191,7 +191,7 @@ void xenbus_otherend_changed(struct xenbus_watch *watch,
212+
return;
213+
}
214+
215+
- state = xenbus_read_driver_state(dev->otherend);
216+
+ state = xenbus_read_driver_state(dev, dev->otherend);
217+
218+
dev_dbg(&dev->dev, "state is %d, (%s), %s, %s\n",
219+
state, xenbus_strstate(state), dev->otherend_watch.node, path);
220+
@@ -364,7 +364,7 @@ void xenbus_dev_remove(struct device *_dev)
221+
* closed.
222+
*/
223+
if (!drv->allow_rebind ||
224+
- xenbus_read_driver_state(dev->nodename) == XenbusStateClosing)
225+
+ xenbus_read_driver_state(dev, dev->nodename) == XenbusStateClosing)
226+
xenbus_switch_state(dev, XenbusStateClosed);
227+
}
228+
EXPORT_SYMBOL_GPL(xenbus_dev_remove);
229+
@@ -514,7 +514,7 @@ int xenbus_probe_node(struct xen_bus_type *bus,
230+
size_t stringlen;
231+
char *tmpstring;
232+
233+
- enum xenbus_state state = xenbus_read_driver_state(nodename);
234+
+ enum xenbus_state state = xenbus_read_driver_state(NULL, nodename);
235+
236+
if (state != XenbusStateInitialising) {
237+
/* Device is not new, so ignore it. This can happen if a
238+
diff --git a/drivers/xen/xenbus/xenbus_probe_frontend.c b/drivers/xen/xenbus/xenbus_probe_frontend.c
239+
index 6d1819269cbe..41832994f8b1 100644
240+
--- a/drivers/xen/xenbus/xenbus_probe_frontend.c
241+
+++ b/drivers/xen/xenbus/xenbus_probe_frontend.c
242+
@@ -255,7 +255,7 @@ static int print_device_status(struct device *dev, void *data)
243+
} else if (xendev->state < XenbusStateConnected) {
244+
enum xenbus_state rstate = XenbusStateUnknown;
245+
if (xendev->otherend)
246+
- rstate = xenbus_read_driver_state(xendev->otherend);
247+
+ rstate = xenbus_read_driver_state(xendev, xendev->otherend);
248+
pr_warn("Timeout connecting to device: %s (local state %d, remote state %d)\n",
249+
xendev->nodename, xendev->state, rstate);
250+
}
251+
diff --git a/include/xen/xenbus.h b/include/xen/xenbus.h
252+
index c94caf852aea..15319da65b7f 100644
253+
--- a/include/xen/xenbus.h
254+
+++ b/include/xen/xenbus.h
255+
@@ -228,7 +228,8 @@ int xenbus_unmap_ring_vfree(struct xenbus_device *dev, void *vaddr);
256+
int xenbus_alloc_evtchn(struct xenbus_device *dev, evtchn_port_t *port);
257+
int xenbus_free_evtchn(struct xenbus_device *dev, evtchn_port_t port);
258+
259+
-enum xenbus_state xenbus_read_driver_state(const char *path);
260+
+enum xenbus_state xenbus_read_driver_state(const struct xenbus_device *dev,
261+
+ const char *path);
262+
263+
__printf(3, 4)
264+
void xenbus_dev_error(struct xenbus_device *dev, int err, const char *fmt, ...);
265+
--
266+
2.53.0
267+

0 commit comments

Comments
 (0)