Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-01-18 10:01:16

0001 /*
0002  * Copyright © 2013-2022 Inria.  All rights reserved.
0003  * Copyright © 2016 Cisco Systems, Inc.  All rights reserved.
0004  * See COPYING in top-level directory.
0005  */
0006 
0007 #ifndef HWLOC_PLUGINS_H
0008 #define HWLOC_PLUGINS_H
0009 
0010 /** \file
0011  * \brief Public interface for building hwloc plugins.
0012  */
0013 
0014 struct hwloc_backend;
0015 
0016 #include "hwloc.h"
0017 
0018 #ifdef HWLOC_INSIDE_PLUGIN
0019 /* needed for hwloc_plugin_check_namespace() */
0020 #ifdef HWLOC_HAVE_LTDL
0021 #include <ltdl.h>
0022 #else
0023 #include <dlfcn.h>
0024 #endif
0025 #endif
0026 
0027 
0028 
0029 /** \defgroup hwlocality_disc_components Components and Plugins: Discovery components
0030  *
0031  * \note These structures and functions may change when ::HWLOC_COMPONENT_ABI is modified.
0032  *
0033  * @{
0034  */
0035 
0036 /** \brief Discovery component structure
0037  *
0038  * This is the major kind of components, taking care of the discovery.
0039  * They are registered by generic components, either statically-built or as plugins.
0040  */
0041 struct hwloc_disc_component {
0042   /** \brief Name.
0043    * If this component is built as a plugin, this name does not have to match the plugin filename.
0044    */
0045   const char *name;
0046 
0047   /** \brief Discovery phases performed by this component.
0048    * OR'ed set of ::hwloc_disc_phase_t
0049    */
0050   unsigned phases;
0051 
0052   /** \brief Component phases to exclude, as an OR'ed set of ::hwloc_disc_phase_t.
0053    *
0054    * For a GLOBAL component, this usually includes all other phases (\c ~UL).
0055    *
0056    * Other components only exclude types that may bring conflicting
0057    * topology information. MISC components should likely not be excluded
0058    * since they usually bring non-primary additional information.
0059    */
0060   unsigned excluded_phases;
0061 
0062   /** \brief Instantiate callback to create a backend from the component.
0063    * Parameters data1, data2, data3 are NULL except for components
0064    * that have special enabling routines such as hwloc_topology_set_xml(). */
0065   struct hwloc_backend * (*instantiate)(struct hwloc_topology *topology, struct hwloc_disc_component *component, unsigned excluded_phases, const void *data1, const void *data2, const void *data3);
0066 
0067   /** \brief Component priority.
0068    * Used to sort topology->components, higher priority first.
0069    * Also used to decide between two components with the same name.
0070    *
0071    * Usual values are
0072    * 50 for native OS (or platform) components,
0073    * 45 for x86,
0074    * 40 for no-OS fallback,
0075    * 30 for global components (xml, synthetic),
0076    * 20 for pci,
0077    * 10 for other misc components (opencl etc.).
0078    */
0079   unsigned priority;
0080 
0081   /** \brief Enabled by default.
0082    * If unset, if will be disabled unless explicitly requested.
0083    */
0084   unsigned enabled_by_default;
0085 
0086   /** \private Used internally to list components by priority on topology->components
0087    * (the component structure is usually read-only,
0088    *  the core copies it before using this field for queueing)
0089    */
0090   struct hwloc_disc_component * next;
0091 };
0092 
0093 /** @} */
0094 
0095 
0096 
0097 
0098 /** \defgroup hwlocality_disc_backends Components and Plugins: Discovery backends
0099  *
0100  * \note These structures and functions may change when ::HWLOC_COMPONENT_ABI is modified.
0101  *
0102  * @{
0103  */
0104 
0105 /** \brief Discovery phase */
0106 typedef enum hwloc_disc_phase_e {
0107   /** \brief xml or synthetic, platform-specific components such as bgq.
0108    * Discovers everything including CPU, memory, I/O and everything else.
0109    * A component with a Global phase usually excludes all other phases.
0110    * \hideinitializer */
0111   HWLOC_DISC_PHASE_GLOBAL = (1U<<0),
0112 
0113   /** \brief CPU discovery.
0114    * \hideinitializer */
0115   HWLOC_DISC_PHASE_CPU = (1U<<1),
0116 
0117   /** \brief Attach memory to existing CPU objects.
0118    * \hideinitializer */
0119   HWLOC_DISC_PHASE_MEMORY = (1U<<2),
0120 
0121   /** \brief Attach PCI devices and bridges to existing CPU objects.
0122    * \hideinitializer */
0123   HWLOC_DISC_PHASE_PCI = (1U<<3),
0124 
0125   /** \brief I/O discovery that requires PCI devices (OS devices such as OpenCL, CUDA, etc.).
0126    * \hideinitializer */
0127   HWLOC_DISC_PHASE_IO = (1U<<4),
0128 
0129   /** \brief Misc objects that gets added below anything else.
0130    * \hideinitializer */
0131   HWLOC_DISC_PHASE_MISC = (1U<<5),
0132 
0133   /** \brief Annotating existing objects, adding distances, etc.
0134    * \hideinitializer */
0135   HWLOC_DISC_PHASE_ANNOTATE = (1U<<6),
0136 
0137   /** \brief Final tweaks to a ready-to-use topology.
0138    * This phase runs once the topology is loaded, before it is returned to the topology.
0139    * Hence it may only use the main hwloc API for modifying the topology,
0140    * for instance by restricting it, adding info attributes, etc.
0141    * \hideinitializer */
0142   HWLOC_DISC_PHASE_TWEAK = (1U<<7)
0143 } hwloc_disc_phase_t;
0144 
0145 /** \brief Discovery status flags */
0146 enum hwloc_disc_status_flag_e {
0147   /** \brief The sets of allowed resources were already retrieved \hideinitializer */
0148   HWLOC_DISC_STATUS_FLAG_GOT_ALLOWED_RESOURCES = (1UL<<1)
0149 };
0150 
0151 /** \brief Discovery status structure
0152  *
0153  * Used by the core and backends to inform about what has been/is being done
0154  * during the discovery process.
0155  */
0156 struct hwloc_disc_status {
0157   /** \brief The current discovery phase that is performed.
0158    * Must match one of the phases in the component phases field.
0159    */
0160   hwloc_disc_phase_t phase;
0161 
0162   /** \brief Dynamically excluded phases.
0163    * If a component decides during discovery that some phases are no longer needed.
0164    */
0165   unsigned excluded_phases;
0166 
0167   /** \brief OR'ed set of ::hwloc_disc_status_flag_e */
0168   unsigned long flags;
0169 };
0170 
0171 /** \brief Discovery backend structure
0172  *
0173  * A backend is the instantiation of a discovery component.
0174  * When a component gets enabled for a topology,
0175  * its instantiate() callback creates a backend.
0176  *
0177  * hwloc_backend_alloc() initializes all fields to default values
0178  * that the component may change (except "component" and "next")
0179  * before enabling the backend with hwloc_backend_enable().
0180  *
0181  * Most backends assume that the topology is_thissystem flag is
0182  * set because they talk to the underlying operating system.
0183  * However they may still be used in topologies without the
0184  * is_thissystem flag for debugging reasons.
0185  * In practice, they are usually auto-disabled in such cases
0186  * (excluded by xml or synthetic backends, or by environment
0187  *  variables when changing the Linux fsroot or the x86 cpuid path).
0188  */
0189 struct hwloc_backend {
0190   /** \private Reserved for the core, set by hwloc_backend_alloc() */
0191   struct hwloc_disc_component * component;
0192   /** \private Reserved for the core, set by hwloc_backend_enable() */
0193   struct hwloc_topology * topology;
0194   /** \private Reserved for the core. Set to 1 if forced through envvar, 0 otherwise. */
0195   int envvar_forced;
0196   /** \private Reserved for the core. Used internally to list backends topology->backends. */
0197   struct hwloc_backend * next;
0198 
0199   /** \brief Discovery phases performed by this component, possibly without some of them if excluded by other components.
0200    * OR'ed set of ::hwloc_disc_phase_t
0201    */
0202   unsigned phases;
0203 
0204   /** \brief Backend flags, currently always 0. */
0205   unsigned long flags;
0206 
0207   /** \brief Backend-specific 'is_thissystem' property.
0208    * Set to 0 if the backend disables the thissystem flag for this topology
0209    * (e.g. loading from xml or synthetic string,
0210    *  or using a different fsroot on Linux, or a x86 CPUID dump).
0211    * Set to -1 if the backend doesn't care (default).
0212    */
0213   int is_thissystem;
0214 
0215   /** \brief Backend private data, or NULL if none. */
0216   void * private_data;
0217   /** \brief Callback for freeing the private_data.
0218    * May be NULL.
0219    */
0220   void (*disable)(struct hwloc_backend *backend);
0221 
0222   /** \brief Main discovery callback.
0223    * returns -1 on error, either because it couldn't add its objects ot the existing topology,
0224    * or because of an actual discovery/gathering failure.
0225    * May be NULL.
0226    */
0227   int (*discover)(struct hwloc_backend *backend, struct hwloc_disc_status *status);
0228 
0229   /** \brief Callback to retrieve the locality of a PCI object.
0230    * Called by the PCI core when attaching PCI hierarchy to CPU objects.
0231    * May be NULL.
0232    */
0233   int (*get_pci_busid_cpuset)(struct hwloc_backend *backend, struct hwloc_pcidev_attr_s *busid, hwloc_bitmap_t cpuset);
0234 };
0235 
0236 /** \brief Allocate a backend structure, set good default values, initialize backend->component and topology, etc.
0237  * The caller will then modify whatever needed, and call hwloc_backend_enable().
0238  */
0239 HWLOC_DECLSPEC struct hwloc_backend * hwloc_backend_alloc(struct hwloc_topology *topology, struct hwloc_disc_component *component);
0240 
0241 /** \brief Enable a previously allocated and setup backend. */
0242 HWLOC_DECLSPEC int hwloc_backend_enable(struct hwloc_backend *backend);
0243 
0244 /** @} */
0245 
0246 
0247 
0248 
0249 /** \defgroup hwlocality_generic_components Components and Plugins: Generic components
0250  *
0251  * \note These structures and functions may change when ::HWLOC_COMPONENT_ABI is modified.
0252  *
0253  * @{
0254  */
0255 
0256 /** \brief Generic component type */
0257 typedef enum hwloc_component_type_e {
0258   /** \brief The data field must point to a struct hwloc_disc_component. */
0259   HWLOC_COMPONENT_TYPE_DISC,
0260 
0261   /** \brief The data field must point to a struct hwloc_xml_component. */
0262   HWLOC_COMPONENT_TYPE_XML
0263 } hwloc_component_type_t;
0264 
0265 /** \brief Generic component structure
0266  *
0267  * Generic components structure, either statically listed by configure in static-components.h
0268  * or dynamically loaded as a plugin.
0269  */
0270 struct hwloc_component {
0271   /** \brief Component ABI version, set to ::HWLOC_COMPONENT_ABI */
0272   unsigned abi;
0273 
0274   /** \brief Process-wide component initialization callback.
0275    *
0276    * This optional callback is called when the component is registered
0277    * to the hwloc core (after loading the plugin).
0278    *
0279    * When the component is built as a plugin, this callback
0280    * should call hwloc_check_plugin_namespace()
0281    * and return an negative error code on error.
0282    *
0283    * \p flags is always 0 for now.
0284    *
0285    * \return 0 on success, or a negative code on error.
0286    *
0287    * \note If the component uses ltdl for loading its own plugins,
0288    * it should load/unload them only in init() and finalize(),
0289    * to avoid race conditions with hwloc's use of ltdl.
0290    */
0291   int (*init)(unsigned long flags);
0292 
0293   /** \brief Process-wide component termination callback.
0294    *
0295    * This optional callback is called after unregistering the component
0296    * from the hwloc core (before unloading the plugin).
0297    *
0298    * \p flags is always 0 for now.
0299    *
0300    * \note If the component uses ltdl for loading its own plugins,
0301    * it should load/unload them only in init() and finalize(),
0302    * to avoid race conditions with hwloc's use of ltdl.
0303    */
0304   void (*finalize)(unsigned long flags);
0305 
0306   /** \brief Component type */
0307   hwloc_component_type_t type;
0308 
0309   /** \brief Component flags, unused for now */
0310   unsigned long flags;
0311 
0312   /** \brief Component data, pointing to a struct hwloc_disc_component or struct hwloc_xml_component. */
0313   void * data;
0314 };
0315 
0316 /** @} */
0317 
0318 
0319 
0320 
0321 /** \defgroup hwlocality_components_core_funcs Components and Plugins: Core functions to be used by components
0322  *
0323  * \note These structures and functions may change when ::HWLOC_COMPONENT_ABI is modified.
0324  *
0325  * @{
0326  */
0327 
0328 /** \brief Check whether error messages are hidden.
0329  *
0330  * Callers should print critical error messages
0331  * (e.g. invalid hw topo info, invalid config)
0332  * only if this function returns strictly less than 2.
0333  *
0334  * Callers should print non-critical error messages
0335  * (e.g. failure to initialize CUDA)
0336  * if this function returns 0.
0337  *
0338  * This function return 1 by default (show critical only),
0339  * 0 in lstopo (show all),
0340  * or anything set in HWLOC_HIDE_ERRORS in the environment.
0341  *
0342  * Use macros HWLOC_SHOW_CRITICAL_ERRORS() and HWLOC_SHOW_ALL_ERRORS()
0343  * for clarity.
0344  */
0345 HWLOC_DECLSPEC int hwloc_hide_errors(void);
0346 
0347 #define HWLOC_SHOW_CRITICAL_ERRORS() (hwloc_hide_errors() < 2)
0348 #define HWLOC_SHOW_ALL_ERRORS() (hwloc_hide_errors() == 0)
0349 
0350 /** \brief Add an object to the topology.
0351  *
0352  * Insert new object \p obj in the topology starting under existing object \p root
0353  * (if \c NULL, the topology root object is used).
0354  *
0355  * It is sorted along the tree of other objects according to the inclusion of
0356  * cpusets, to eventually be added as a child of the smallest object including
0357  * this object.
0358  *
0359  * If the cpuset is empty, the type of the object (and maybe some attributes)
0360  * must be enough to find where to insert the object. This is especially true
0361  * for NUMA nodes with memory and no CPUs.
0362  *
0363  * The given object should not have children.
0364  *
0365  * This shall only be called before levels are built.
0366  *
0367  * The caller should check whether the object type is filtered-out before calling this function.
0368  *
0369  * The topology cpuset/nodesets will be enlarged to include the object sets.
0370  *
0371  * \p reason is a unique string identifying where and why this insertion call was performed
0372  * (it will be displayed in case of internal insertion error).
0373  *
0374  * Returns the object on success.
0375  * Returns NULL and frees obj on error.
0376  * Returns another object and frees obj if it was merged with an identical pre-existing object.
0377  */
0378 HWLOC_DECLSPEC hwloc_obj_t
0379 hwloc__insert_object_by_cpuset(struct hwloc_topology *topology, hwloc_obj_t root,
0380                                hwloc_obj_t obj, const char *reason);
0381 
0382 /** \brief Insert an object somewhere in the topology.
0383  *
0384  * It is added as the last child of the given parent.
0385  * The cpuset is completely ignored, so strange objects such as I/O devices should
0386  * preferably be inserted with this.
0387  *
0388  * When used for "normal" children with cpusets (when importing from XML
0389  * when duplicating a topology), the caller should make sure that:
0390  * - children are inserted in order,
0391  * - children cpusets do not intersect.
0392  *
0393  * The given object may have normal, I/O or Misc children, as long as they are in order as well.
0394  * These children must have valid parent and next_sibling pointers.
0395  *
0396  * The caller should check whether the object type is filtered-out before calling this function.
0397  */
0398 HWLOC_DECLSPEC void hwloc_insert_object_by_parent(struct hwloc_topology *topology, hwloc_obj_t parent, hwloc_obj_t obj);
0399 
0400 /** \brief Allocate and initialize an object of the given type and physical index.
0401  *
0402  * If \p os_index is unknown or irrelevant, use \c HWLOC_UNKNOWN_INDEX.
0403  */
0404 HWLOC_DECLSPEC hwloc_obj_t hwloc_alloc_setup_object(hwloc_topology_t topology, hwloc_obj_type_t type, unsigned os_index);
0405 
0406 /** \brief Setup object cpusets/nodesets by OR'ing its children.
0407  *
0408  * Used when adding an object late in the topology.
0409  * Will update the new object by OR'ing all its new children sets.
0410  *
0411  * Used when PCI backend adds a hostbridge parent, when distances
0412  * add a new Group, etc.
0413  */
0414 HWLOC_DECLSPEC int hwloc_obj_add_children_sets(hwloc_obj_t obj);
0415 
0416 /** \brief Request a reconnection of children and levels in the topology.
0417  *
0418  * May be used by backends during discovery if they need arrays or lists
0419  * of object within levels or children to be fully connected.
0420  *
0421  * \p flags is currently unused, must 0.
0422  */
0423 HWLOC_DECLSPEC int hwloc_topology_reconnect(hwloc_topology_t topology, unsigned long flags __hwloc_attribute_unused);
0424 
0425 /** \brief Make sure that plugins can lookup core symbols.
0426  *
0427  * This is a sanity check to avoid lazy-lookup failures when libhwloc
0428  * is loaded within a plugin, and later tries to load its own plugins.
0429  * This may fail (and abort the program) if libhwloc symbols are in a
0430  * private namespace.
0431  *
0432  * \return 0 on success.
0433  * \return -1 if the plugin cannot be successfully loaded. The caller
0434  * plugin init() callback should return a negative error code as well.
0435  *
0436  * Plugins should call this function in their init() callback to avoid
0437  * later crashes if lazy symbol resolution is used by the upper layer that
0438  * loaded hwloc (e.g. OpenCL implementations using dlopen with RTLD_LAZY).
0439  *
0440  * \note The build system must define HWLOC_INSIDE_PLUGIN if and only if
0441  * building the caller as a plugin.
0442  *
0443  * \note This function should remain inline so plugins can call it even
0444  * when they cannot find libhwloc symbols.
0445  */
0446 static __hwloc_inline int
0447 hwloc_plugin_check_namespace(const char *pluginname __hwloc_attribute_unused, const char *symbol __hwloc_attribute_unused)
0448 {
0449 #ifdef HWLOC_INSIDE_PLUGIN
0450   void *sym;
0451 #ifdef HWLOC_HAVE_LTDL
0452   lt_dlhandle handle = lt_dlopen(NULL);
0453 #else
0454   void *handle = dlopen(NULL, RTLD_NOW|RTLD_LOCAL);
0455 #endif
0456   if (!handle)
0457     /* cannot check, assume things will work */
0458     return 0;
0459 #ifdef HWLOC_HAVE_LTDL
0460   sym = lt_dlsym(handle, symbol);
0461   lt_dlclose(handle);
0462 #else
0463   sym = dlsym(handle, symbol);
0464   dlclose(handle);
0465 #endif
0466   if (!sym) {
0467     static int verboseenv_checked = 0;
0468     static int verboseenv_value = 0;
0469     if (!verboseenv_checked) {
0470       const char *verboseenv = getenv("HWLOC_PLUGINS_VERBOSE");
0471       verboseenv_value = verboseenv ? atoi(verboseenv) : 0;
0472       verboseenv_checked = 1;
0473     }
0474     if (verboseenv_value)
0475       fprintf(stderr, "Plugin `%s' disabling itself because it cannot find the `%s' core symbol.\n",
0476           pluginname, symbol);
0477     return -1;
0478   }
0479 #endif /* HWLOC_INSIDE_PLUGIN */
0480   return 0;
0481 }
0482 
0483 /** @} */
0484 
0485 
0486 
0487 
0488 /** \defgroup hwlocality_components_filtering Components and Plugins: Filtering objects
0489  *
0490  * \note These structures and functions may change when ::HWLOC_COMPONENT_ABI is modified.
0491  *
0492  * @{
0493  */
0494 
0495 /** \brief Check whether the given PCI device classid is important.
0496  *
0497  * \return 1 if important, 0 otherwise.
0498  */
0499 static __hwloc_inline int
0500 hwloc_filter_check_pcidev_subtype_important(unsigned classid)
0501 {
0502   unsigned baseclass = classid >> 8;
0503   return (baseclass == 0x03 /* PCI_BASE_CLASS_DISPLAY */
0504       || baseclass == 0x02 /* PCI_BASE_CLASS_NETWORK */
0505       || baseclass == 0x01 /* PCI_BASE_CLASS_STORAGE */
0506       || baseclass == 0x00 /* Unclassified, for Atos/Bull BXI */
0507       || baseclass == 0x0b /* PCI_BASE_CLASS_PROCESSOR */
0508       || classid == 0x0c04 /* PCI_CLASS_SERIAL_FIBER */
0509       || classid == 0x0c06 /* PCI_CLASS_SERIAL_INFINIBAND */
0510           || classid == 0x0502 /* PCI_CLASS_MEMORY_CXL */
0511           || baseclass == 0x06 /* PCI_BASE_CLASS_BRIDGE with non-PCI downstream. the core will drop the useless ones later */
0512       || baseclass == 0x12 /* Processing Accelerators */);
0513 }
0514 
0515 /** \brief Check whether the given OS device subtype is important.
0516  *
0517  * \return 1 if important, 0 otherwise.
0518  */
0519 static __hwloc_inline int
0520 hwloc_filter_check_osdev_subtype_important(hwloc_obj_osdev_type_t subtype)
0521 {
0522   return (subtype != HWLOC_OBJ_OSDEV_DMA);
0523 }
0524 
0525 /** \brief Check whether a non-I/O object type should be filtered-out.
0526  *
0527  * Cannot be used for I/O objects.
0528  *
0529  * \return 1 if the object type should be kept, 0 otherwise.
0530  */
0531 static __hwloc_inline int
0532 hwloc_filter_check_keep_object_type(hwloc_topology_t topology, hwloc_obj_type_t type)
0533 {
0534   enum hwloc_type_filter_e filter = HWLOC_TYPE_FILTER_KEEP_NONE;
0535   hwloc_topology_get_type_filter(topology, type, &filter);
0536   assert(filter != HWLOC_TYPE_FILTER_KEEP_IMPORTANT); /* IMPORTANT only used for I/O */
0537   return filter == HWLOC_TYPE_FILTER_KEEP_NONE ? 0 : 1;
0538 }
0539 
0540 /** \brief Check whether the given object should be filtered-out.
0541  *
0542  * \return 1 if the object type should be kept, 0 otherwise.
0543  */
0544 static __hwloc_inline int
0545 hwloc_filter_check_keep_object(hwloc_topology_t topology, hwloc_obj_t obj)
0546 {
0547   hwloc_obj_type_t type = obj->type;
0548   enum hwloc_type_filter_e filter = HWLOC_TYPE_FILTER_KEEP_NONE;
0549   hwloc_topology_get_type_filter(topology, type, &filter);
0550   if (filter == HWLOC_TYPE_FILTER_KEEP_NONE)
0551     return 0;
0552   if (filter == HWLOC_TYPE_FILTER_KEEP_IMPORTANT) {
0553     if (type == HWLOC_OBJ_PCI_DEVICE)
0554       return hwloc_filter_check_pcidev_subtype_important(obj->attr->pcidev.class_id);
0555     if (type == HWLOC_OBJ_OS_DEVICE)
0556       return hwloc_filter_check_osdev_subtype_important(obj->attr->osdev.type);
0557   }
0558   return 1;
0559 }
0560 
0561 /** @} */
0562 
0563 
0564 
0565 
0566 /** \defgroup hwlocality_components_pcidisc Components and Plugins: helpers for PCI discovery
0567  *
0568  * \note These structures and functions may change when ::HWLOC_COMPONENT_ABI is modified.
0569  *
0570  * @{
0571  */
0572 
0573 /** \brief Return the offset of the given capability in the PCI config space buffer
0574  *
0575  * This function requires a 256-bytes config space. Unknown/unavailable bytes should be set to 0xff.
0576  */
0577 HWLOC_DECLSPEC unsigned hwloc_pcidisc_find_cap(const unsigned char *config, unsigned cap);
0578 
0579 /** \brief Fill linkspeed by reading the PCI config space where PCI_CAP_ID_EXP is at position offset.
0580  *
0581  * Needs 20 bytes of EXP capability block starting at offset in the config space
0582  * for registers up to link status.
0583  */
0584 HWLOC_DECLSPEC int hwloc_pcidisc_find_linkspeed(const unsigned char *config, unsigned offset, float *linkspeed);
0585 
0586 /** \brief Return the hwloc object type (PCI device or Bridge) for the given class and configuration space.
0587  *
0588  * This function requires 16 bytes of common configuration header at the beginning of config.
0589  */
0590 HWLOC_DECLSPEC hwloc_obj_type_t hwloc_pcidisc_check_bridge_type(unsigned device_class, const unsigned char *config);
0591 
0592 /** \brief Fills the attributes of the given PCI bridge using the given PCI config space.
0593  *
0594  * This function requires 32 bytes of common configuration header at the beginning of config.
0595  *
0596  * Returns -1 and destroys /p obj if bridge fields are invalid.
0597  */
0598 HWLOC_DECLSPEC int hwloc_pcidisc_find_bridge_buses(unsigned domain, unsigned bus, unsigned dev, unsigned func,
0599                            unsigned *secondary_busp, unsigned *subordinate_busp,
0600                            const unsigned char *config);
0601 
0602 /** \brief Insert a PCI object in the given PCI tree by looking at PCI bus IDs.
0603  *
0604  * If \p treep points to \c NULL, the new object is inserted there.
0605  */
0606 HWLOC_DECLSPEC void hwloc_pcidisc_tree_insert_by_busid(struct hwloc_obj **treep, struct hwloc_obj *obj);
0607 
0608 /** \brief Add some hostbridges on top of the given tree of PCI objects and attach them to the topology.
0609  *
0610  * Other backends may lookup PCI objects or localities (for instance to attach OS devices)
0611  * by using hwloc_pcidisc_find_by_busid() or hwloc_pcidisc_find_busid_parent().
0612  */
0613 HWLOC_DECLSPEC int hwloc_pcidisc_tree_attach(struct hwloc_topology *topology, struct hwloc_obj *tree);
0614 
0615 /** @} */
0616 
0617 
0618 
0619 
0620 /** \defgroup hwlocality_components_pcifind Components and Plugins: finding PCI objects during other discoveries
0621  *
0622  * \note These structures and functions may change when ::HWLOC_COMPONENT_ABI is modified.
0623  *
0624  * @{
0625  */
0626 
0627 /** \brief Find the object or a parent of a PCI bus ID.
0628  *
0629  * When attaching a new object (typically an OS device) whose locality
0630  * is specified by PCI bus ID, this function returns the PCI object
0631  * to use as a parent for attaching.
0632  *
0633  * If the exact PCI device with this bus ID exists, it is returned.
0634  * Otherwise (for instance if it was filtered out), the function returns
0635  * another object with similar locality (for instance a parent bridge,
0636  * or the local CPU Package).
0637  */
0638 HWLOC_DECLSPEC struct hwloc_obj * hwloc_pci_find_parent_by_busid(struct hwloc_topology *topology, unsigned domain, unsigned bus, unsigned dev, unsigned func);
0639 
0640 /** \brief Find the PCI device or bridge matching a PCI bus ID exactly.
0641  *
0642  * This is useful for adding specific information about some objects
0643  * based on their PCI id. When it comes to attaching objects based on
0644  * PCI locality, hwloc_pci_find_parent_by_busid() should be preferred.
0645  */
0646 HWLOC_DECLSPEC struct hwloc_obj * hwloc_pci_find_by_busid(struct hwloc_topology *topology, unsigned domain, unsigned bus, unsigned dev, unsigned func);
0647 
0648 /** \brief Handle to a new distances structure during its addition to the topology. */
0649 typedef void * hwloc_backend_distances_add_handle_t;
0650 
0651 /** \brief Create a new empty distances structure.
0652  *
0653  * This is identical to hwloc_distances_add_create()
0654  * but this variant is designed for backend inserting
0655  * distances during topology discovery.
0656  */
0657 HWLOC_DECLSPEC hwloc_backend_distances_add_handle_t
0658 hwloc_backend_distances_add_create(hwloc_topology_t topology,
0659                                    const char *name, unsigned long kind,
0660                                    unsigned long flags);
0661 
0662 /** \brief Specify the objects and values in a new empty distances structure.
0663  *
0664  * This is similar to hwloc_distances_add_values()
0665  * but this variant is designed for backend inserting
0666  * distances during topology discovery.
0667  *
0668  * The only semantical difference is that \p objs and \p values
0669  * are not duplicated, but directly attached to the topology.
0670  * On success, these arrays are given to the core and should not
0671  * ever be freed by the caller anymore.
0672  */
0673 HWLOC_DECLSPEC int
0674 hwloc_backend_distances_add_values(hwloc_topology_t topology,
0675                                    hwloc_backend_distances_add_handle_t handle,
0676                                    unsigned nbobjs, hwloc_obj_t *objs,
0677                                    hwloc_uint64_t *values,
0678                                    unsigned long flags);
0679 
0680 /** \brief Commit a new distances structure.
0681  *
0682  * This is similar to hwloc_distances_add_commit()
0683  * but this variant is designed for backend inserting
0684  * distances during topology discovery.
0685  */
0686 HWLOC_DECLSPEC int
0687 hwloc_backend_distances_add_commit(hwloc_topology_t topology,
0688                                    hwloc_backend_distances_add_handle_t handle,
0689                                    unsigned long flags);
0690 
0691 /** @} */
0692 
0693 
0694 
0695 
0696 #endif /* HWLOC_PLUGINS_H */