1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "https://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/xhtml;charset=UTF-8"/>
<meta http-equiv="X-UA-Compatible" content="IE=9"/>
<meta name="generator" content="Doxygen 1.9.1"/>
<meta name="viewport" content="width=device-width, initial-scale=1"/>
<title>Hardware Locality (hwloc): Thread Safety</title>
<link href="tabs.css" rel="stylesheet" type="text/css"/>
<script type="text/javascript" src="jquery.js"></script>
<script type="text/javascript" src="dynsections.js"></script>
<link href="doxygen.css" rel="stylesheet" type="text/css" />
</head>
<body>
<div id="top"><!-- do not remove this div, it is closed by doxygen! -->
<div id="titlearea">
<table cellspacing="0" cellpadding="0">
<tbody>
<tr style="height: 56px;">
<td id="projectalign" style="padding-left: 0.5em;">
<div id="projectname">Hardware Locality (hwloc)
 <span id="projectnumber">2.4.1</span>
</div>
</td>
</tr>
</tbody>
</table>
</div>
<!-- end header part -->
<!-- Generated by Doxygen 1.9.1 -->
<script type="text/javascript" src="menudata.js"></script>
<script type="text/javascript" src="menu.js"></script>
<script type="text/javascript">
/* @license magnet:?xt=urn:btih:cf05388f2679ee054f2beb29a391d25f4e673ac3&dn=gpl-2.0.txt GPL-v2 */
$(function() {
initMenu('',false,false,'search.php','Search');
});
/* @license-end */</script>
<div id="main-nav"></div>
</div><!-- top -->
<div class="PageDoc"><div class="header">
<div class="headertitle">
<div class="title">Thread Safety </div> </div>
</div><!--header-->
<div class="contents">
<div class="textblock"><p>
<div class="section">
</p>
<p>Like most libraries that mainly fill data structures, hwloc is not thread safe but rather reentrant: all state is held in a <a class="el" href="a00192.html#ga9d1e76ee15a7dee158b786c30b6a6e38" title="Topology context.">hwloc_topology_t</a> instance without mutex protection. That means, for example, that two threads can safely operate on and modify two different <a class="el" href="a00192.html#ga9d1e76ee15a7dee158b786c30b6a6e38" title="Topology context.">hwloc_topology_t</a> instances, but they should not simultaneously invoke functions that modify the <em>same</em> instance. Similarly, one thread should not modify a <a class="el" href="a00192.html#ga9d1e76ee15a7dee158b786c30b6a6e38" title="Topology context.">hwloc_topology_t</a> instance while another thread is reading or traversing it. However, two threads can safely read or traverse the same <a class="el" href="a00192.html#ga9d1e76ee15a7dee158b786c30b6a6e38" title="Topology context.">hwloc_topology_t</a> instance concurrently.</p>
<p>When running in multiprocessor environments, be aware that proper thread synchronization and/or memory coherency protection is needed to pass hwloc data (such as <a class="el" href="a00192.html#ga9d1e76ee15a7dee158b786c30b6a6e38" title="Topology context.">hwloc_topology_t</a> pointers) from one processor to another (e.g., a mutex, semaphore, or a memory barrier). Note that this is not a hwloc-specific requirement, but it is worth mentioning.</p>
<p>For reference, <a class="el" href="a00192.html#ga9d1e76ee15a7dee158b786c30b6a6e38" title="Topology context.">hwloc_topology_t</a> modification operations include (but may not be limited to):</p>
<dl>
<dt>Creation and destruction </dt>
<dd><p class="startdd"><code><a class="el" href="a00192.html#ga03fd4a16d8b9ee1ffc32b25fd2f6bdfa" title="Allocate a topology context.">hwloc_topology_init()</a>, <a class="el" href="a00192.html#gabdf58d87ad77f6615fccdfe0535ff826" title="Build the actual topology.">hwloc_topology_load()</a>, <a class="el" href="a00192.html#ga9f34a640b6fd28d23699d4d084667b15" title="Terminate and free a topology context.">hwloc_topology_destroy()</a></code> (see <a class="el" href="a00192.html">Topology Creation and Destruction</a>) imply major modifications of the structure, including freeing some objects. No other thread cannot access the topology or any of its objects at the same time.</p>
<p class="interdd">Also references to objects inside the topology are not valid anymore after these functions return. </p>
<p class="enddd"></p>
</dd>
<dt>Runtime topology modifications </dt>
<dd><p class="startdd"><code><a class="el" href="a00200.html#gad980782ade737900c5cf208946768c30" title="Add a MISC object as a leaf of the topology.">hwloc_topology_insert_misc_object()</a></code>, <code><a class="el" href="a00200.html#ga4cea4741165faf5323931a9ed8786ef7" title="Allocate a Group object to insert later with hwloc_topology_insert_group_object().">hwloc_topology_alloc_group_object()</a></code>, and <code><a class="el" href="a00200.html#ga1fc6012b3e1c249b83f48cb7bcacaa5b" title="Add more structure to the topology by adding an intermediate Group.">hwloc_topology_insert_group_object()</a></code> (see <a class="el" href="a00200.html">Modifying a loaded Topology</a>) may modify the topology significantly by adding objects inside the tree, changing the topology depth, etc.</p>
<p class="interdd"><code><a class="el" href="a00216.html#gac5a71d96cd86efe31d6f8d282aae3d97" title="Provide a new distance matrix.">hwloc_distances_add()</a></code> and <code><a class="el" href="a00216.html#gac188d9b64d9560255ce5f6d0a20f9c0a" title="Remove all distance matrices from a topology.">hwloc_distances_remove()</a></code> (see <a class="el" href="a00216.html">Add or remove distances between objects</a>) modify the list of distance structures in the topology, and the former may even insert new Group objects.</p>
<p class="interdd"><code><a class="el" href="a00218.html#ga770657d1e44b09e93e09f623936c1e5f" title="Register a new memory attribute.">hwloc_memattr_register()</a></code> and <code><a class="el" href="a00218.html#ga960529c08b25cf15825e0f72ecceb504" title="Set an attribute value for a specific target NUMA node.">hwloc_memattr_set_value()</a></code> (see <a class="el" href="a00218.html">Managing memory attributes</a>) modify the memory attributes of the topology.</p>
<p class="interdd"><code><a class="el" href="a00200.html#ga6db81ed13ac0a9d70cc80372ab537815" title="Restrict the topology to the given CPU set or nodeset.">hwloc_topology_restrict()</a></code> modifies the topology even more dramatically by removing some objects.</p>
<p class="interdd"><code><a class="el" href="a00200.html#ga698ecd640d2b76742bba3829a145cd9a" title="Refresh internal structures after topology modification.">hwloc_topology_refresh()</a></code> updates some internal cached structures. (see below).</p>
<p class="interdd">Although references to former objects <em>may</em> still be valid after insertion or restriction, it is strongly advised to not rely on any such guarantee and always re-consult the topology to reacquire new instances of objects. </p>
<p class="enddd"></p>
</dd>
<dt>Consulting distances </dt>
<dd><p class="startdd"><code><a class="el" href="a00214.html#ga613e6b2a5d0f06626ee8d0c12fa46691" title="Retrieve distance matrices.">hwloc_distances_get()</a></code> and its variants are thread-safe except if the topology was recently modified (because distances may involve objects that were removed).</p>
<p class="interdd">Whenever the topology is modified (see above), <code><a class="el" href="a00200.html#ga698ecd640d2b76742bba3829a145cd9a" title="Refresh internal structures after topology modification.">hwloc_topology_refresh()</a></code> should be called in the same thread-safe context to force the refresh of internal distances structures. A call to <code><a class="el" href="a00214.html#ga613e6b2a5d0f06626ee8d0c12fa46691" title="Retrieve distance matrices.">hwloc_distances_get()</a></code> may also refresh distances-related structures.</p>
<p class="interdd">Once this refresh has been performed, multiple <code><a class="el" href="a00214.html#ga613e6b2a5d0f06626ee8d0c12fa46691" title="Retrieve distance matrices.">hwloc_distances_get()</a></code> may then be performed concurrently by multiple threads. </p>
<p class="enddd"></p>
</dd>
<dt>Consulting memory attributes </dt>
<dd><p class="startdd">Functions consulting memory attributes in <a class="el" href="a00140_source.html">hwloc/memattrs.h</a> are thread-safe except if the topology was recently modified (because memory attributes may involve objects that were removed).</p>
<p class="interdd">Whenever the topology is modified (see above), <code><a class="el" href="a00200.html#ga698ecd640d2b76742bba3829a145cd9a" title="Refresh internal structures after topology modification.">hwloc_topology_refresh()</a></code> should be called in the same thread-safe context to force the refresh of internal memory attribute structures. A call to <code><a class="el" href="a00217.html#ga297e4a9adc2272446a4c7449dacef0df" title="Return an attribute value for a specific target NUMA node.">hwloc_memattr_get_value()</a></code> or <code><a class="el" href="a00218.html#ga3177cc0ab47e4dd1fa69ca1df4c7cb1a" title="Return the target NUMA nodes that have some values for a given attribute.">hwloc_memattr_get_targets()</a></code> may also refresh internal structures for a given memory attribute.</p>
<p class="interdd">Once this refresh has been performed, multiple functions consulting memory attributes may then be performed concurrently by multiple threads. </p>
<p class="enddd"></p>
</dd>
<dt>Locating topologies </dt>
<dd><p class="startdd"><code>hwloc_topology_set_*</code> (see <a class="el" href="a00199.html">Topology Detection Configuration and Query</a>) do not modify the topology directly, but they do modify internal structures describing the behavior of the upcoming invocation of <code><a class="el" href="a00192.html#gabdf58d87ad77f6615fccdfe0535ff826" title="Build the actual topology.">hwloc_topology_load()</a></code>. Hence, all of these functions should not be used concurrently. </p>
<p class="enddd"></p>
</dd>
</dl>
</div></div><!-- contents -->
</div><!-- PageDoc -->
<!-- start footer part -->
<hr class="footer"/><address class="footer"><small>
Generated by <a href="https://www.doxygen.org/index.html"><img class="footer" src="doxygen.svg" width="104" height="31" alt="doxygen"/></a> 1.9.1
</small></address>
</body>
</html>
|