Skip to content

Commit 8ae980d

Browse files
jfrakerkuba-moo
authored andcommitted
gve: Deprecate adminq_pfn for pci revision 0x1.
adminq_pfn assumes a page size of 4k, causing this mechanism to break in kernels compiled with different page sizes. A new PCI device revision was needed for the device to be able to communicate with the driver how to set up the admin queue prior to having access to the admin queue. Signed-off-by: Jordan Kimbrough <jrkim@google.com> Signed-off-by: John Fraker <jfraker@google.com> Reviewed-by: Willem de Bruijn <willemb@google.com> Link: https://lore.kernel.org/r/20231128002648.320892-3-jfraker@google.com Signed-off-by: Jakub Kicinski <kuba@kernel.org>
1 parent 955f4d3 commit 8ae980d

File tree

2 files changed

+44
-13
lines changed

2 files changed

+44
-13
lines changed

drivers/net/ethernet/google/gve/gve_adminq.c

Lines changed: 35 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -225,9 +225,20 @@ int gve_adminq_alloc(struct device *dev, struct gve_priv *priv)
225225
priv->adminq_get_ptype_map_cnt = 0;
226226

227227
/* Setup Admin queue with the device */
228-
iowrite32be(priv->adminq_bus_addr / PAGE_SIZE,
229-
&priv->reg_bar0->adminq_pfn);
230-
228+
if (priv->pdev->revision < 0x1) {
229+
iowrite32be(priv->adminq_bus_addr / PAGE_SIZE,
230+
&priv->reg_bar0->adminq_pfn);
231+
} else {
232+
iowrite16be(GVE_ADMINQ_BUFFER_SIZE,
233+
&priv->reg_bar0->adminq_length);
234+
#ifdef CONFIG_ARCH_DMA_ADDR_T_64BIT
235+
iowrite32be(priv->adminq_bus_addr >> 32,
236+
&priv->reg_bar0->adminq_base_address_hi);
237+
#endif
238+
iowrite32be(priv->adminq_bus_addr,
239+
&priv->reg_bar0->adminq_base_address_lo);
240+
iowrite32be(GVE_DRIVER_STATUS_RUN_MASK, &priv->reg_bar0->driver_status);
241+
}
231242
gve_set_admin_queue_ok(priv);
232243
return 0;
233244
}
@@ -237,16 +248,27 @@ void gve_adminq_release(struct gve_priv *priv)
237248
int i = 0;
238249

239250
/* Tell the device the adminq is leaving */
240-
iowrite32be(0x0, &priv->reg_bar0->adminq_pfn);
241-
while (ioread32be(&priv->reg_bar0->adminq_pfn)) {
242-
/* If this is reached the device is unrecoverable and still
243-
* holding memory. Continue looping to avoid memory corruption,
244-
* but WARN so it is visible what is going on.
245-
*/
246-
if (i == GVE_MAX_ADMINQ_RELEASE_CHECK)
247-
WARN(1, "Unrecoverable platform error!");
248-
i++;
249-
msleep(GVE_ADMINQ_SLEEP_LEN);
251+
if (priv->pdev->revision < 0x1) {
252+
iowrite32be(0x0, &priv->reg_bar0->adminq_pfn);
253+
while (ioread32be(&priv->reg_bar0->adminq_pfn)) {
254+
/* If this is reached the device is unrecoverable and still
255+
* holding memory. Continue looping to avoid memory corruption,
256+
* but WARN so it is visible what is going on.
257+
*/
258+
if (i == GVE_MAX_ADMINQ_RELEASE_CHECK)
259+
WARN(1, "Unrecoverable platform error!");
260+
i++;
261+
msleep(GVE_ADMINQ_SLEEP_LEN);
262+
}
263+
} else {
264+
iowrite32be(GVE_DRIVER_STATUS_RESET_MASK, &priv->reg_bar0->driver_status);
265+
while (!(ioread32be(&priv->reg_bar0->device_status)
266+
& GVE_DEVICE_STATUS_DEVICE_IS_RESET)) {
267+
if (i == GVE_MAX_ADMINQ_RELEASE_CHECK)
268+
WARN(1, "Unrecoverable platform error!");
269+
i++;
270+
msleep(GVE_ADMINQ_SLEEP_LEN);
271+
}
250272
}
251273
gve_clear_device_rings_ok(priv);
252274
gve_clear_device_resources_ok(priv);

drivers/net/ethernet/google/gve/gve_register.h

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,11 +18,20 @@ struct gve_registers {
1818
__be32 adminq_event_counter;
1919
u8 reserved[3];
2020
u8 driver_version;
21+
__be32 adminq_base_address_hi;
22+
__be32 adminq_base_address_lo;
23+
__be16 adminq_length;
2124
};
2225

2326
enum gve_device_status_flags {
2427
GVE_DEVICE_STATUS_RESET_MASK = BIT(1),
2528
GVE_DEVICE_STATUS_LINK_STATUS_MASK = BIT(2),
2629
GVE_DEVICE_STATUS_REPORT_STATS_MASK = BIT(3),
30+
GVE_DEVICE_STATUS_DEVICE_IS_RESET = BIT(4),
31+
};
32+
33+
enum gve_driver_status_flags {
34+
GVE_DRIVER_STATUS_RUN_MASK = BIT(0),
35+
GVE_DRIVER_STATUS_RESET_MASK = BIT(1),
2736
};
2837
#endif /* _GVE_REGISTER_H_ */

0 commit comments

Comments
 (0)