|
||||
File indexing completed on 2025-01-18 10:01:15
0001 /* 0002 * Copyright © 2013-2023 Inria. All rights reserved. 0003 * See COPYING in top-level directory. 0004 */ 0005 0006 /** \file 0007 * \brief Topology differences. 0008 */ 0009 0010 #ifndef HWLOC_DIFF_H 0011 #define HWLOC_DIFF_H 0012 0013 #ifndef HWLOC_H 0014 #error Please include the main hwloc.h instead 0015 #endif 0016 0017 0018 #ifdef __cplusplus 0019 extern "C" { 0020 #elif 0 0021 } 0022 #endif 0023 0024 0025 /** \defgroup hwlocality_diff Topology differences 0026 * 0027 * Applications that manipulate many similar topologies, for instance 0028 * one for each node of a homogeneous cluster, may want to compress 0029 * topologies to reduce the memory footprint. 0030 * 0031 * This file offers a way to manipulate the difference between topologies 0032 * and export/import it to/from XML. 0033 * Compression may therefore be achieved by storing one topology 0034 * entirely while the others are only described by their differences 0035 * with the former. 0036 * The actual topology can be reconstructed when actually needed by 0037 * applying the precomputed difference to the reference topology. 0038 * 0039 * This interface targets very similar nodes. 0040 * Only very simple differences between topologies are actually 0041 * supported, for instance a change in the memory size, the name 0042 * of the object, or some info attribute. 0043 * More complex differences such as adding or removing objects cannot 0044 * be represented in the difference structures and therefore return 0045 * errors. 0046 * Differences between object sets or topology-wide allowed sets, 0047 * cannot be represented either. 0048 * 0049 * It means that there is no need to apply the difference when 0050 * looking at the tree organization (how many levels, how many 0051 * objects per level, what kind of objects, CPU and node sets, etc) 0052 * and when binding to objects. 0053 * However the difference must be applied when looking at object 0054 * attributes such as the name, the memory size or info attributes. 0055 * 0056 * @{ 0057 */ 0058 0059 0060 /** \brief Type of one object attribute difference. 0061 */ 0062 typedef enum hwloc_topology_diff_obj_attr_type_e { 0063 /** \brief The object local memory is modified. 0064 * The union is a hwloc_topology_diff_obj_attr_u::hwloc_topology_diff_obj_attr_uint64_s 0065 * (and the index field is ignored). 0066 */ 0067 HWLOC_TOPOLOGY_DIFF_OBJ_ATTR_SIZE, 0068 0069 /** \brief The object name is modified. 0070 * The union is a hwloc_topology_diff_obj_attr_u::hwloc_topology_diff_obj_attr_string_s 0071 * (and the name field is ignored). 0072 */ 0073 0074 HWLOC_TOPOLOGY_DIFF_OBJ_ATTR_NAME, 0075 /** \brief the value of an info attribute is modified. 0076 * The union is a hwloc_topology_diff_obj_attr_u::hwloc_topology_diff_obj_attr_string_s. 0077 */ 0078 HWLOC_TOPOLOGY_DIFF_OBJ_ATTR_INFO 0079 } hwloc_topology_diff_obj_attr_type_t; 0080 0081 /** \brief One object attribute difference. 0082 */ 0083 union hwloc_topology_diff_obj_attr_u { 0084 struct hwloc_topology_diff_obj_attr_generic_s { 0085 /* each part of the union must start with these */ 0086 hwloc_topology_diff_obj_attr_type_t type; 0087 } generic; 0088 0089 /** \brief Integer attribute modification with an optional index. */ 0090 struct hwloc_topology_diff_obj_attr_uint64_s { 0091 /* used for storing integer attributes */ 0092 hwloc_topology_diff_obj_attr_type_t type; 0093 hwloc_uint64_t index; /* not used for SIZE */ 0094 hwloc_uint64_t oldvalue; 0095 hwloc_uint64_t newvalue; 0096 } uint64; 0097 0098 /** \brief String attribute modification with an optional name */ 0099 struct hwloc_topology_diff_obj_attr_string_s { 0100 /* used for storing name and info pairs */ 0101 hwloc_topology_diff_obj_attr_type_t type; 0102 char *name; /* not used for NAME */ 0103 char *oldvalue; 0104 char *newvalue; 0105 } string; 0106 }; 0107 0108 0109 /** \brief Type of one element of a difference list. 0110 */ 0111 typedef enum hwloc_topology_diff_type_e { 0112 /** \brief An object attribute was changed. 0113 * The union is a hwloc_topology_diff_u::hwloc_topology_diff_obj_attr_s. 0114 */ 0115 HWLOC_TOPOLOGY_DIFF_OBJ_ATTR, 0116 0117 /** \brief The difference is too complex, 0118 * it cannot be represented. The difference below 0119 * this object has not been checked. 0120 * hwloc_topology_diff_build() will return 1. 0121 * 0122 * The union is a hwloc_topology_diff_u::hwloc_topology_diff_too_complex_s. 0123 */ 0124 HWLOC_TOPOLOGY_DIFF_TOO_COMPLEX 0125 } hwloc_topology_diff_type_t; 0126 0127 /** \brief One element of a difference list between two topologies. 0128 */ 0129 typedef union hwloc_topology_diff_u { 0130 struct hwloc_topology_diff_generic_s { 0131 /* each part of the union must start with these */ 0132 hwloc_topology_diff_type_t type; 0133 union hwloc_topology_diff_u * next; /* pointer to the next element of the list, or NULL */ 0134 } generic; 0135 0136 /* A difference in an object attribute. */ 0137 struct hwloc_topology_diff_obj_attr_s { 0138 hwloc_topology_diff_type_t type; /* must be ::HWLOC_TOPOLOGY_DIFF_OBJ_ATTR */ 0139 union hwloc_topology_diff_u * next; 0140 /* List of attribute differences for a single object */ 0141 int obj_depth; 0142 unsigned obj_index; 0143 union hwloc_topology_diff_obj_attr_u diff; 0144 } obj_attr; 0145 0146 /* A difference that is too complex. */ 0147 struct hwloc_topology_diff_too_complex_s { 0148 hwloc_topology_diff_type_t type; /* must be ::HWLOC_TOPOLOGY_DIFF_TOO_COMPLEX */ 0149 union hwloc_topology_diff_u * next; 0150 /* Where we had to stop computing the diff in the first topology */ 0151 int obj_depth; 0152 unsigned obj_index; 0153 } too_complex; 0154 } * hwloc_topology_diff_t; 0155 0156 0157 /** \brief Compute the difference between 2 topologies. 0158 * 0159 * The difference is stored as a list of ::hwloc_topology_diff_t entries 0160 * starting at \p diff. 0161 * It is computed by doing a depth-first traversal of both topology trees 0162 * simultaneously. 0163 * 0164 * If the difference between 2 objects is too complex to be represented 0165 * (for instance if some objects have different types, or different numbers 0166 * of children), a special diff entry of type ::HWLOC_TOPOLOGY_DIFF_TOO_COMPLEX 0167 * is queued. 0168 * The computation of the diff does not continue below these objects. 0169 * So each such diff entry means that the difference between two subtrees 0170 * could not be computed. 0171 * 0172 * \return 0 if the difference can be represented properly. 0173 * 0174 * \return 0 with \p diff pointing to NULL if there is no difference 0175 * between the topologies. 0176 * 0177 * \return 1 if the difference is too complex (see above). Some entries in 0178 * the list will be of type ::HWLOC_TOPOLOGY_DIFF_TOO_COMPLEX. 0179 * 0180 * \return -1 on any other error. 0181 * 0182 * \note \p flags is currently not used. It should be 0. 0183 * 0184 * \note The output diff has to be freed with hwloc_topology_diff_destroy(). 0185 * 0186 * \note The output diff can only be exported to XML or passed to 0187 * hwloc_topology_diff_apply() if 0 was returned, i.e. if no entry of type 0188 * ::HWLOC_TOPOLOGY_DIFF_TOO_COMPLEX is listed. 0189 * 0190 * \note The output diff may be modified by removing some entries from 0191 * the list. The removed entries should be freed by passing them to 0192 * to hwloc_topology_diff_destroy() (possible as another list). 0193 */ 0194 HWLOC_DECLSPEC int hwloc_topology_diff_build(hwloc_topology_t topology, hwloc_topology_t newtopology, unsigned long flags, hwloc_topology_diff_t *diff); 0195 0196 /** \brief Flags to be given to hwloc_topology_diff_apply(). 0197 */ 0198 enum hwloc_topology_diff_apply_flags_e { 0199 /** \brief Apply topology diff in reverse direction. 0200 * \hideinitializer 0201 */ 0202 HWLOC_TOPOLOGY_DIFF_APPLY_REVERSE = (1UL<<0) 0203 }; 0204 0205 /** \brief Apply a topology diff to an existing topology. 0206 * 0207 * \p flags is an OR'ed set of ::hwloc_topology_diff_apply_flags_e. 0208 * 0209 * The new topology is modified in place. hwloc_topology_dup() 0210 * may be used to duplicate it before patching. 0211 * 0212 * If the difference cannot be applied entirely, all previous applied 0213 * elements are unapplied before returning. 0214 * 0215 * \return 0 on success. 0216 * 0217 * \return -N if applying the difference failed while trying 0218 * to apply the N-th part of the difference. For instance -1 0219 * is returned if the very first difference element could not 0220 * be applied. 0221 */ 0222 HWLOC_DECLSPEC int hwloc_topology_diff_apply(hwloc_topology_t topology, hwloc_topology_diff_t diff, unsigned long flags); 0223 0224 /** \brief Destroy a list of topology differences. 0225 * 0226 * \return 0. 0227 */ 0228 HWLOC_DECLSPEC int hwloc_topology_diff_destroy(hwloc_topology_diff_t diff); 0229 0230 /** \brief Load a list of topology differences from a XML file. 0231 * 0232 * If not \c NULL, \p refname will be filled with the identifier 0233 * string of the reference topology for the difference file, 0234 * if any was specified in the XML file. 0235 * This identifier is usually the name of the other XML file 0236 * that contains the reference topology. 0237 * 0238 * \return 0 on success, -1 on error. 0239 * 0240 * \note the pointer returned in refname should later be freed 0241 * by the caller. 0242 */ 0243 HWLOC_DECLSPEC int hwloc_topology_diff_load_xml(const char *xmlpath, hwloc_topology_diff_t *diff, char **refname); 0244 0245 /** \brief Export a list of topology differences to a XML file. 0246 * 0247 * If not \c NULL, \p refname defines an identifier string 0248 * for the reference topology which was used as a base when 0249 * computing this difference. 0250 * This identifier is usually the name of the other XML file 0251 * that contains the reference topology. 0252 * This attribute is given back when reading the diff from XML. 0253 * 0254 * \return 0 on success, -1 on error. 0255 */ 0256 HWLOC_DECLSPEC int hwloc_topology_diff_export_xml(hwloc_topology_diff_t diff, const char *refname, const char *xmlpath); 0257 0258 /** \brief Load a list of topology differences from a XML buffer. 0259 * 0260 * Build a list of differences from the XML memory buffer given 0261 * at \p xmlbuffer and of length \p buflen (including an ending \0). 0262 * This buffer may have been filled earlier with 0263 * hwloc_topology_diff_export_xmlbuffer(). 0264 * 0265 * If not \c NULL, \p refname will be filled with the identifier 0266 * string of the reference topology for the difference file, 0267 * if any was specified in the XML file. 0268 * This identifier is usually the name of the other XML file 0269 * that contains the reference topology. 0270 * 0271 * \return 0 on success, -1 on error. 0272 * 0273 * \note the pointer returned in refname should later be freed 0274 * by the caller. 0275 */ 0276 HWLOC_DECLSPEC int hwloc_topology_diff_load_xmlbuffer(const char *xmlbuffer, int buflen, hwloc_topology_diff_t *diff, char **refname); 0277 0278 /** \brief Export a list of topology differences to a XML buffer. 0279 * 0280 * If not \c NULL, \p refname defines an identifier string 0281 * for the reference topology which was used as a base when 0282 * computing this difference. 0283 * This identifier is usually the name of the other XML file 0284 * that contains the reference topology. 0285 * This attribute is given back when reading the diff from XML. 0286 * 0287 * The returned buffer ends with a \0 that is included in the returned 0288 * length. 0289 * 0290 * \return 0 on success, -1 on error. 0291 * 0292 * \note The XML buffer should later be freed with hwloc_free_xmlbuffer(). 0293 */ 0294 HWLOC_DECLSPEC int hwloc_topology_diff_export_xmlbuffer(hwloc_topology_diff_t diff, const char *refname, char **xmlbuffer, int *buflen); 0295 0296 /** @} */ 0297 0298 0299 #ifdef __cplusplus 0300 } /* extern "C" */ 0301 #endif 0302 0303 0304 #endif /* HWLOC_DIFF_H */
[ Source navigation ] | [ Diff markup ] | [ Identifier search ] | [ general search ] |
This page was automatically generated by the 2.3.7 LXR engine. The LXR team |