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 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159
|
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://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.8.6"/>
<title>ViennaCL - The Vienna Computing Library: Configuring OpenCL Contexts and Devices</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="navtree.css" rel="stylesheet" type="text/css"/>
<script type="text/javascript" src="resize.js"></script>
<script type="text/javascript" src="navtree.js"></script>
<script type="text/javascript">
$(document).ready(initResizable);
$(window).load(resizeHeight);
</script>
<link href="search/search.css" rel="stylesheet" type="text/css"/>
<script type="text/javascript" src="search/search.js"></script>
<script type="text/javascript">
$(document).ready(function() { searchBox.OnSelectItem(0); });
</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 style="padding-left: 0.5em;">
<div id="projectname">ViennaCL - The Vienna Computing Library
 <span id="projectnumber">1.7.1</span>
</div>
<div id="projectbrief">Free open-source GPU-accelerated linear algebra and solver library.</div>
</td>
<td> <div id="MSearchBox" class="MSearchBoxInactive">
<span class="left">
<img id="MSearchSelect" src="search/mag_sel.png"
onmouseover="return searchBox.OnSearchSelectShow()"
onmouseout="return searchBox.OnSearchSelectHide()"
alt=""/>
<input type="text" id="MSearchField" value="Search" accesskey="S"
onfocus="searchBox.OnSearchFieldFocus(true)"
onblur="searchBox.OnSearchFieldFocus(false)"
onkeyup="searchBox.OnSearchFieldChange(event)"/>
</span><span class="right">
<a id="MSearchClose" href="javascript:searchBox.CloseResultsWindow()"><img id="MSearchCloseImg" border="0" src="search/close.png" alt=""/></a>
</span>
</div>
</td>
</tr>
</tbody>
</table>
</div>
<!-- end header part -->
<!-- Generated by Doxygen 1.8.6 -->
<script type="text/javascript">
var searchBox = new SearchBox("searchBox", "search",false,'Search');
</script>
</div><!-- top -->
<div id="side-nav" class="ui-resizable side-nav-resizable">
<div id="nav-tree">
<div id="nav-tree-contents">
<div id="nav-sync" class="sync"></div>
</div>
</div>
<div id="splitbar" style="-moz-user-select:none;"
class="ui-resizable-handle">
</div>
</div>
<script type="text/javascript">
$(document).ready(function(){initNavTree('manual-multi-device.html','');});
</script>
<div id="doc-content">
<!-- window showing the filter options -->
<div id="MSearchSelectWindow"
onmouseover="return searchBox.OnSearchSelectShow()"
onmouseout="return searchBox.OnSearchSelectHide()"
onkeydown="return searchBox.OnSearchSelectKey(event)">
<a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(0)"><span class="SelectionMark"> </span>All</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(1)"><span class="SelectionMark"> </span>Classes</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(2)"><span class="SelectionMark"> </span>Namespaces</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(3)"><span class="SelectionMark"> </span>Files</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(4)"><span class="SelectionMark"> </span>Functions</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(5)"><span class="SelectionMark"> </span>Variables</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(6)"><span class="SelectionMark"> </span>Typedefs</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(7)"><span class="SelectionMark"> </span>Enumerations</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(8)"><span class="SelectionMark"> </span>Enumerator</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(9)"><span class="SelectionMark"> </span>Friends</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(10)"><span class="SelectionMark"> </span>Macros</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(11)"><span class="SelectionMark"> </span>Pages</a></div>
<!-- iframe showing the search results (closed by default) -->
<div id="MSearchResultsWindow">
<iframe src="javascript:void(0)" frameborder="0"
name="MSearchResults" id="MSearchResults">
</iframe>
</div>
<div class="header">
<div class="headertitle">
<div class="title">Configuring OpenCL Contexts and Devices </div> </div>
</div><!--header-->
<div class="contents">
<div class="textblock"><p>Support for multiple devices was officially added in OpenCL 1.1. Among other things, this allows for e.g. using all CPUs in a multi-socket CPU mainboard as a single OpenCL compute device. Nevertheless, the efficient use of multiple OpenCL devices is far from trivial, because algorithms have to be designed such that they take distributed memory and synchronization issues into account.</p>
<dl class="section note"><dt>Note</dt><dd>There is no native support for automatically executing operations over multiple GPUs in ViennaCL. Partition of data is left to the user.</dd></dl>
<h1><a class="anchor" id="manual-multi-device-context"></a>
Context Setup</h1>
<p>Unless specified otherwise (see <a class="el" href="manual-custom-contexts.html">User-Provided OpenCL Contexts</a>), ViennaCL silently creates its own context and adds all available default devices with a single queue per device to it. All operations are then carried out on this (or the user-provided) context, which can be obtained with the call </p>
<div class="fragment"><div class="line"><a class="code" href="namespaceviennacl_1_1ocl.html#a16fc917445ce2010e7b16fbc968771b7">viennacl::ocl::current_context</a>();</div>
</div><!-- fragment --><p> This default context is identified by the ID <code>0</code> (of type <code>long</code>). ViennaCL uses the first platform returned by the OpenCL backend for the context. If a different platform should be used on a machine with multiple platforms available, this can be achieved with </p>
<div class="fragment"><div class="line"><a class="code" href="namespaceviennacl_1_1ocl.html#aba4b534b1464fc21143f0c6aaae89a40">viennacl::ocl::set_context_platform_index</a>(<span class="keywordtype">id</span>, platform_index);</div>
</div><!-- fragment --><p> where the context ID is <code>id</code> and <code>platform_index</code> refers to the array index of the platform as returned by <code>clGetPlatformIDs()</code>.</p>
<p>By default, only the first device in the context is used for all operations. This device can be obtained via </p>
<div class="fragment"><div class="line"><a class="code" href="namespaceviennacl_1_1ocl.html#a16fc917445ce2010e7b16fbc968771b7">viennacl::ocl::current_context</a>().<a class="code" href="classviennacl_1_1ocl_1_1context.html#ab4d9064422cc8c183a14ad77c2a7b49b">current_device</a>();</div>
<div class="line"><a class="code" href="namespaceviennacl_1_1ocl.html#ac54d59a74deaccec81f64e738b856348">viennacl::ocl::current_device</a>(); <span class="comment">//equivalent to above</span></div>
</div><!-- fragment --><p> A user may wish to use multiple OpenCL contexts, where each context consists of a subset of the available devices. To setup a context with ID <code>id</code> with a particular device type only, the user has to specify this <em>prior</em> to any other ViennaCL related statements: </p>
<div class="fragment"><div class="line"><span class="comment">// use only GPUs:</span></div>
<div class="line"><a class="code" href="namespaceviennacl_1_1ocl.html#a11349d9bbd1691595c6ac23d03b294fd">viennacl::ocl::set_context_device_type</a>(<span class="keywordtype">id</span>, <a class="code" href="structviennacl_1_1ocl_1_1gpu__tag.html">viennacl::ocl::gpu_tag</a>());</div>
<div class="line"><span class="comment">// use only CPUs:</span></div>
<div class="line"><a class="code" href="namespaceviennacl_1_1ocl.html#a11349d9bbd1691595c6ac23d03b294fd">viennacl::ocl::set_context_device_type</a>(<span class="keywordtype">id</span>, <a class="code" href="structviennacl_1_1ocl_1_1cpu__tag.html">viennacl::ocl::cpu_tag</a>());</div>
<div class="line"><span class="comment">// use only the default device type</span></div>
<div class="line"><a class="code" href="namespaceviennacl_1_1ocl.html#a11349d9bbd1691595c6ac23d03b294fd">viennacl::ocl::set_context_device_type</a>(<span class="keywordtype">id</span>, <a class="code" href="structviennacl_1_1ocl_1_1default__tag.html">viennacl::ocl::default_tag</a>());</div>
<div class="line"><span class="comment">// use only accelerators:</span></div>
<div class="line"><a class="code" href="namespaceviennacl_1_1ocl.html#a11349d9bbd1691595c6ac23d03b294fd">viennacl::ocl::set_context_device_type</a>(<span class="keywordtype">id</span>, <a class="code" href="structviennacl_1_1ocl_1_1accelerator__tag.html">viennacl::ocl::accelerator_tag</a>());</div>
</div><!-- fragment --><p> Instead of using the tag classes, the respective OpenCL constants <code>CL_DEVICE_TYPE_GPU</code> etc. can be supplied as second argument.</p>
<p>Another possibility is to query all devices from the current platform: </p>
<div class="fragment"><div class="line">std::vector< viennacl::ocl::device > devices = <a class="code" href="classviennacl_1_1ocl_1_1platform.html">viennacl::ocl::platform</a>().<a class="code" href="classviennacl_1_1ocl_1_1platform.html#afaa563522ebe9ce7b80ef02c40e7fe31">devices</a>();</div>
</div><!-- fragment --><p> and create a custom subset of devices, which is then passed to the context setup routine: </p>
<div class="fragment"><div class="line"><span class="comment">// take the first and the third available device from 'devices'</span></div>
<div class="line">std::vector< viennacl::ocl::device > my_devices;</div>
<div class="line">my_devices.push_back(devices[0]);</div>
<div class="line">my_devices.push_back(devices[2]);</div>
<div class="line"></div>
<div class="line"><span class="comment">// Initialize the context with ID 'id' with these devices:</span></div>
<div class="line"><a class="code" href="namespaceviennacl_1_1ocl.html#add1725d48cfd159ce187e287369d1cdb">viennacl::ocl::setup_context</a>(<span class="keywordtype">id</span>, my_devices);</div>
</div><!-- fragment --><p> Similarly, contexts with other IDs can be set up.</p>
<dl class="section note"><dt>Note</dt><dd>For details on how to initialize ViennaCL with already existing contexts, see <a class="el" href="manual-custom-contexts.html">User-Provided OpenCL Contexts</a>.</dd></dl>
<p>The user is reminded that memory objects within an OpenCL context are allocated for all devices within a context. Thus, setting up contexts with one device each is optimal in terms of memory usage, because each memory object is then bound to a single device only. However, memory transfer between contexts (and thus devices) has to be done manually by the library user then. Moreover, the user has to keep track in which context the individual ViennaCL objects have been created, because all operands are assumed to be in the currently active context.</p>
<h1><a class="anchor" id="manual-multi-device-switching"></a>
Switching Contexts and Devices</h1>
<p>ViennaCL always uses the currently active OpenCL context with the currently active device to enqueue compute kernels. The default context is identified by ID <code>0</code>. The context with ID <code>id</code> can be set as active context with the line. </p>
<div class="fragment"><div class="line"><a class="code" href="namespaceviennacl_1_1ocl.html#acc1a7460a9ff237b7c0306c32c3d34c6">viennacl::ocl::switch_context</a>(<span class="keywordtype">id</span>);</div>
</div><!-- fragment --><p> Subsequent kernels are then enqueued on the active device for that particular context.</p>
<p>Similar to setting contexts active, the active device can be set for each context. For example, setting the second device in the context to be the active device, the lines </p>
<div class="fragment"><div class="line"><a class="code" href="namespaceviennacl_1_1ocl.html#a16fc917445ce2010e7b16fbc968771b7">viennacl::ocl::current_context</a>().<a class="code" href="classviennacl_1_1ocl_1_1context.html#a85373fa81be824eef324579bf429d201">switch_device</a>(1);</div>
</div><!-- fragment --><p> are required. In some circumstances one may want to pass the device object directly, e.g. to set the second device of the platform active: </p>
<div class="fragment"><div class="line">std::vector<viennacl::ocl::device> <span class="keyword">const</span> & devices = <a class="code" href="classviennacl_1_1ocl_1_1platform.html">viennacl::ocl::platform</a>().<a class="code" href="classviennacl_1_1ocl_1_1platform.html#afaa563522ebe9ce7b80ef02c40e7fe31">devices</a>();</div>
<div class="line"><a class="code" href="namespaceviennacl_1_1ocl.html#a16fc917445ce2010e7b16fbc968771b7">viennacl::ocl::current_context</a>().<a class="code" href="classviennacl_1_1ocl_1_1context.html#a85373fa81be824eef324579bf429d201">switch_device</a>(devices[1]);</div>
</div><!-- fragment --><p> If the supplied device is not part of the context, an error message is printed and the active device remains unchanged.</p>
<h1><a class="anchor" id="manual-multi-device-compiler"></a>
Setting OpenCL Compiler Flags</h1>
<p>Each OpenCL context provides a member function <code>.build_options()</code>, which can be used to pass OpenCL compiler flags <em>prior</em> to compilation. Flags need to be passed to the context prior to the compilation of the respective kernels, i.e. prior the first instantiation of the respective matrix or vector types.</p>
<p>To pass the <code>-cl-mad-enable</code> flag to the current context, the line </p>
<div class="fragment"><div class="line"><a class="code" href="namespaceviennacl_1_1ocl.html#a16fc917445ce2010e7b16fbc968771b7">viennacl::ocl::current_context</a>().<a class="code" href="classviennacl_1_1ocl_1_1context.html#a4f0b8c81dad769f6efffe2d2069101f8">build_options</a>(<span class="stringliteral">"-cl-mad-enable"</span>);</div>
</div><!-- fragment --><p> is sufficient. Confer to the OpenCL standard for a full list of flags.</p>
<dl class="section note"><dt>Note</dt><dd>Our experience is that performance is usually not affected significantly by additional OpenCL compiler flags. </dd></dl>
</div></div><!-- contents -->
</div><!-- doc-content -->
<!-- start footer part -->
<div id="nav-path" class="navpath"><!-- id is needed for treeview function! -->
<ul>
<li class="footer">Generated on Wed Jan 20 2016 22:32:44 for ViennaCL - The Vienna Computing Library by
<a href="http://www.doxygen.org/index.html">
<img class="footer" src="doxygen.png" alt="doxygen"/></a> 1.8.6 </li>
</ul>
</div>
</body>
</html>
|