]> git.ipfire.org Git - thirdparty/pciutils.git/commitdiff
libpci is now able to find a specific instance of a capability
authorDaniel Schaefer <git@danielschaefer.me>
Sun, 14 Oct 2018 20:47:53 +0000 (22:47 +0200)
committerMartin Mares <mj@ucw.cz>
Sun, 14 Oct 2018 20:48:33 +0000 (22:48 +0200)
lib/caps.c
lib/libpci.ver
lib/pci.h

index 9a2e0a5f1291cf67cf8a1ac136311bae2ccb7d11..4f415898b045581bf3c49b981e885ff801d0039f 100644 (file)
@@ -103,12 +103,45 @@ pci_free_caps(struct pci_dev *d)
 
 struct pci_cap *
 pci_find_cap(struct pci_dev *d, unsigned int id, unsigned int type)
+{
+  return pci_find_cap_nr(d, id, type, NULL);
+}
+
+/**
+ * Finds a particular capability of a device
+ *
+ * To select one capability if there are more than one with the same id you
+ * can provide a pointer to an unsigned int that contains the index which you
+ * want as cap_number. If you don't care and are fine with the first one you
+ * can supply NULL. To cap_number the acutal number of capablities with that id
+ * will be written.
+ *
+ * @param d          Which device to target
+ * @param id         Capability ID
+ * @param type       PCI_FILL_CAPS or PCI_FILL_EXT_CAPS
+ * @param cap_number Which instance of a capability to target
+ * @returns          pointer to capability structure or NULL if not found
+ */
+struct pci_cap *
+pci_find_cap_nr(struct pci_dev *d, unsigned int id, unsigned int type,
+                unsigned int *cap_number)
 {
   struct pci_cap *c;
+  unsigned int target = 0;
+  if (cap_number != NULL)
+    {
+      target = *cap_number;
+      *cap_number = 0;
+    }
 
-  pci_fill_info_v35(d, ((type == PCI_CAP_NORMAL) ? PCI_FILL_CAPS : PCI_FILL_EXT_CAPS));
+  pci_fill_info_v35(d, ((type == PCI_CAP_NORMAL)
+                        ? PCI_FILL_CAPS
+                        : PCI_FILL_EXT_CAPS));
   for (c=d->first_cap; c; c=c->next)
     if (c->type == type && c->id == id)
-      return c;
+      if (cap_number == NULL || target == *cap_number)
+        return c;
+      else
+       (*cap_number)++;
   return NULL;
 }
index d15e678cbfc6018bf5aeba362fe70b17632efeb1..e20c3f581c711ff9cb55042e62e60c8d7325a065 100644 (file)
@@ -77,3 +77,8 @@ LIBPCI_3.6 {
        global:
                pci_get_string_property;
 };
+
+LIBPCI_3.7 {
+       global:
+               pci_find_cap_nr;
+};
index 548aa69a468dd44179b76149abd811dcfcbeafe7..ae9689ddbbe7d443c976e5c7b6632ff3065e4cfb 100644 (file)
--- a/lib/pci.h
+++ b/lib/pci.h
@@ -211,6 +211,8 @@ struct pci_cap {
 #define PCI_CAP_EXTENDED       2       /* PCIe extended capabilities */
 
 struct pci_cap *pci_find_cap(struct pci_dev *, unsigned int id, unsigned int type) PCI_ABI;
+struct pci_cap *pci_find_cap_nr(struct pci_dev *, unsigned int id, unsigned int type,
+                             unsigned int *cap_number) PCI_ABI;
 
 /*
  *     Filters