Page MenuHomeFreeBSD

D31241.diff
No OneTemporary

D31241.diff

Index: usr.sbin/bhyve/pci_emul.h
===================================================================
--- usr.sbin/bhyve/pci_emul.h
+++ usr.sbin/bhyve/pci_emul.h
@@ -159,6 +159,7 @@
struct msix_table_entry *table; /* allocated at runtime */
void *pba_page;
int pba_page_offset;
+ void *table_page;
} pi_msix;
void *pi_arg; /* devemu-private data */
Index: usr.sbin/bhyve/pci_passthru.c
===================================================================
--- usr.sbin/bhyve/pci_passthru.c
+++ usr.sbin/bhyve/pci_passthru.c
@@ -327,13 +327,14 @@
return (data);
}
+ /* Should make this an assert. */
if (offset < pi->pi_msix.table_offset)
return (-1);
offset -= pi->pi_msix.table_offset;
index = offset / MSIX_TABLE_ENTRY_SIZE;
if (index >= pi->pi_msix.table_count)
- return (-1);
+ goto readbar;
entry = &pi->pi_msix.table[index];
entry_offset = offset % MSIX_TABLE_ENTRY_SIZE;
@@ -360,6 +361,33 @@
}
return (data);
+
+readbar:
+ if (pi->pi_msix.table_page != NULL && offset < 4096) {
+ switch(size) {
+ case 1:
+ src8 = (uint8_t *)(pi->pi_msix.table_page + offset);
+ data = *src8;
+ break;
+ case 2:
+ src16 = (uint16_t *)(pi->pi_msix.table_page + offset);
+ data = *src16;
+ break;
+ case 4:
+ src32 = (uint32_t *)(pi->pi_msix.table_page + offset);
+ data = *src32;
+ break;
+ case 8:
+ src64 = (uint64_t *)(pi->pi_msix.table_page + offset);
+ data = *src64;
+ break;
+ default:
+ return (-1);
+ }
+ return (data);
+ }
+
+ return (-1);
}
static void
@@ -406,13 +434,14 @@
return;
}
+ /* Should make this an assert. */
if (offset < pi->pi_msix.table_offset)
return;
offset -= pi->pi_msix.table_offset;
index = offset / MSIX_TABLE_ENTRY_SIZE;
if (index >= pi->pi_msix.table_count)
- return;
+ goto writebar;
entry = &pi->pi_msix.table[index];
entry_offset = offset % MSIX_TABLE_ENTRY_SIZE;
@@ -435,6 +464,31 @@
entry->msg_data, entry->vector_control);
}
}
+
+writebar:
+ if (pi->pi_msix.table_page != NULL && offset < 4096) {
+ switch(size) {
+ case 1:
+ dest8 = (uint8_t *)(pi->pi_msix.table_page + offset);
+ *dest8 = data;
+ break;
+ case 2:
+ dest16 = (uint16_t *)(pi->pi_msix.table_page + offset);
+ *dest16 = data;
+ break;
+ case 4:
+ dest32 = (uint32_t *)(pi->pi_msix.table_page + offset);
+ *dest32 = data;
+ break;
+ case 8:
+ dest64 = (uint64_t *)(pi->pi_msix.table_page + offset);
+ *dest64 = data;
+ break;
+ default:
+ break;
+ }
+ return;
+ }
}
static int
@@ -470,6 +524,21 @@
start = pi->pi_bar[idx].addr;
remaining = pi->pi_bar[idx].size;
+ /*
+ * Some device (against better documentation of the spec)
+ * are mapping other usable address space into the same page
+ * as the end of the MSI-X tables.
+ * At least Intel AX200 being one of them apparently.
+ * Map the page and fall back to it for any reads/writes outside
+ * the MSI-X table in msix_table_{read,write}.
+ */
+ pi->pi_msix.table_page = mmap(NULL, 4096, PROT_READ | PROT_WRITE,
+ MAP_SHARED, memfd, sc->psc_bar[idx].addr + table_offset);
+ if (pi->pi_msix.table_page == MAP_FAILED) {
+ warn("Failed to map table page for MSI-X on %d/%d/%d", b, s, f);
+ return (-1);
+ }
+
if (pi->pi_msix.pba_bar == pi->pi_msix.table_bar) {
pba_offset = pi->pi_msix.pba_offset;
pba_size = pi->pi_msix.pba_size;

File Metadata

Mime Type
text/plain
Expires
Sun, Dec 21, 12:39 AM (2 h, 51 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
27103710
Default Alt Text
D31241.diff (3 KB)

Event Timeline