NULL,
NULL,
#endif
+#if defined(PCI_HAVE_PM_ECAM)
+ &pm_ecam,
+#else
+ NULL,
+#endif
};
// If PCI_ACCESS_AUTO is selected, we probe the access methods in this order
PCI_ACCESS_WIN32_KLDBG,
PCI_ACCESS_WIN32_SYSDBG,
// Low-level methods poking the hardware directly
+ PCI_ACCESS_ECAM,
PCI_ACCESS_I386_TYPE1,
PCI_ACCESS_I386_TYPE2,
PCI_ACCESS_MMIO_TYPE1_EXT,
* directory, hence something completely different. So prepend missing
* "\\\\?\\" prefix to make path valid again.
* Reproduce: CreateProcessW("\\??\\UNC\\10.0.2.4\\qemu\\lspci.exe", ...)
+ *
+ * If path starts with DOS drive letter and with appended PCI_IDS is
+ * longer than 260 bytes and is without "\\\\?\\" prefix then append it.
+ * This prefix is required for paths and file names with DOS drive letter
+ * longer than 260 bytes.
*/
if (strncmp(path, "\\UNC\\", 5) == 0 ||
- strncmp(path, "UNC\\", 4) == 0)
+ strncmp(path, "UNC\\", 4) == 0 ||
+ (((path[0] >= 'a' && path[0] <= 'z') || (path[0] >= 'A' && path[0] <= 'Z')) &&
+ len + sizeof(PCI_IDS) >= 260))
{
memmove(path+4, path, len);
memcpy(path, "\\\\?\\", 4);
return a;
}
-void
-pci_init_v35(struct pci_access *a)
+int
+pci_init_internal(struct pci_access *a, int skip_method)
{
if (!a->error)
a->error = pci_generic_error;
if (!a->debugging)
a->debug = pci_null_debug;
- if (a->method)
+ if (a->method != PCI_ACCESS_AUTO)
{
if (a->method >= PCI_ACCESS_MAX || !pci_methods[a->method])
a->error("This access method is not supported.");
struct pci_methods *m = pci_methods[probe_sequence[i]];
if (!m)
continue;
+ if (skip_method == probe_sequence[i])
+ continue;
a->debug("Trying method %s...", m->name);
if (m->detect(a))
{
a->debug("...No.\n");
}
if (!a->methods)
- a->error("Cannot find any working access method.");
+ return 0;
}
a->debug("Decided to use %s\n", a->methods->name);
a->methods->init(a);
+ return 1;
+}
+
+void
+pci_init_v35(struct pci_access *a)
+{
+ if (!pci_init_internal(a, -1))
+ a->error("Cannot find any working access method.");
}
STATIC_ALIAS(void pci_init(struct pci_access *a), pci_init_v35(a));
SYMBOL_VERSION(pci_init_v30, pci_init@LIBPCI_3.0);
SYMBOL_VERSION(pci_init_v35, pci_init@@LIBPCI_3.5);
+struct pci_access *
+pci_clone_access(struct pci_access *a)
+{
+ struct pci_access *b = pci_alloc();
+
+ b->writeable = a->writeable;
+ b->buscentric = a->buscentric;
+ b->debugging = a->debugging;
+ b->error = a->error;
+ b->warning = a->warning;
+ b->debug = a->debug;
+
+ return b;
+}
+
void
pci_cleanup(struct pci_access *a)
{