summaryrefslogtreecommitdiff
path: root/CMSIS/Documentation/Driver/html/_theory_operation.html
diff options
context:
space:
mode:
Diffstat (limited to 'CMSIS/Documentation/Driver/html/_theory_operation.html')
-rw-r--r--CMSIS/Documentation/Driver/html/_theory_operation.html391
1 files changed, 391 insertions, 0 deletions
diff --git a/CMSIS/Documentation/Driver/html/_theory_operation.html b/CMSIS/Documentation/Driver/html/_theory_operation.html
new file mode 100644
index 0000000..842d128
--- /dev/null
+++ b/CMSIS/Documentation/Driver/html/_theory_operation.html
@@ -0,0 +1,391 @@
+<!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"/>
+<title>Theory of Operation</title>
+<title>CMSIS-Driver: Theory of Operation</title>
+<link href="tabs.css" rel="stylesheet" type="text/css"/>
+<link href="cmsis.css" rel="stylesheet" type="text/css" />
+<script type="text/javascript" src="jquery.js"></script>
+<script type="text/javascript" src="dynsections.js"></script>
+<script type="text/javascript" src="printComponentTabs.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);
+</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="stylsheetf" 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: 46px;">
+ <td id="projectlogo"><img alt="Logo" src="CMSIS_Logo_Final.png"/></td>
+ <td style="padding-left: 0.5em;">
+ <div id="projectname">CMSIS-Driver
+ &#160;<span id="projectnumber">Version 2.04</span>
+ </div>
+ <div id="projectbrief">Peripheral Interface for Middleware and Application Code</div>
+ </td>
+ </tr>
+ </tbody>
+</table>
+</div>
+<!-- end header part -->
+<div id="CMSISnav" class="tabs1">
+ <ul class="tablist">
+ <script type="text/javascript">
+ <!--
+ writeComponentTabs.call(this);
+ //-->
+ </script>
+ </ul>
+</div>
+<!-- Generated by Doxygen 1.8.2 -->
+<script type="text/javascript">
+var searchBox = new SearchBox("searchBox", "search",false,'Search');
+</script>
+ <div id="navrow1" class="tabs">
+ <ul class="tablist">
+ <li><a href="index.html"><span>Main&#160;Page</span></a></li>
+ <li class="current"><a href="pages.html"><span>Usage&#160;and&#160;Description</span></a></li>
+ <li><a href="modules.html"><span>Reference</span></a></li>
+ <li>
+ <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>
+ </li>
+ </ul>
+ </div>
+</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('_theory_operation.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">&#160;</span>All</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(1)"><span class="SelectionMark">&#160;</span>Data Structures</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(2)"><span class="SelectionMark">&#160;</span>Files</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(3)"><span class="SelectionMark">&#160;</span>Functions</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(4)"><span class="SelectionMark">&#160;</span>Variables</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(5)"><span class="SelectionMark">&#160;</span>Typedefs</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(6)"><span class="SelectionMark">&#160;</span>Enumerations</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(7)"><span class="SelectionMark">&#160;</span>Enumerator</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(8)"><span class="SelectionMark">&#160;</span>Macros</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(9)"><span class="SelectionMark">&#160;</span>Groups</a><a class="SelectItem" href="javascript:void(0)" onclick="searchBox.OnSelectItem(10)"><span class="SelectionMark">&#160;</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">Theory of Operation </div> </div>
+</div><!--header-->
+<div class="contents">
+<div class="toc"><h3>Table of Contents</h3>
+<ul><li class="level1"><a href="#DriverFunctions">Common Driver Functions</a><ul><li class="level2"><a href="#ProcessorMode">Cortex-M Processor Mode</a></li>
+</ul>
+</li>
+<li class="level1"><a href="#CallSequence">Function Call Sequence</a><ul><li class="level2"><a href="#CS_start">Start Sequence</a></li>
+<li class="level2"><a href="#CS_stop">Stop Sequence</a></li>
+</ul>
+</li>
+<li class="level1"><a href="#Share_IO">Shared I/O Pins</a></li>
+<li class="level1"><a href="#Data_Xfer_Functions">Data Transfer Functions</a></li>
+<li class="level1"><a href="#AccessStruct">Access Struct</a><ul><li class="level2"><a href="#DriverInstances">Driver Instances</a></li>
+</ul>
+</li>
+<li class="level1"><a href="#DriverConfiguration">Driver Configuration</a></li>
+<li class="level1"><a href="#CodeExample">Code Example</a></li>
+</ul>
+</div>
+<div class="textblock"><p>This section gives an overview of the general operation of CMSIS-Drivers. It explains the <a class="el" href="_theory_operation.html#DriverFunctions">Common Driver Functions</a> that are common in all CMSIS-Drivers along with the <a class="el" href="_theory_operation.html#CallSequence">Function Call Sequence</a>. The topic <a class="el" href="_theory_operation.html#Data_Xfer_Functions">Data Transfer Functions</a> describes how data read/write operations to the peripheral are implemented.</p>
+<p>Each CMSIS-Driver defines an <a class="el" href="_theory_operation.html#AccessStruct">Access Struct</a> for calling the various driver functions and each peripheral (that is accessed via a CMSIS-Driver) has one <a class="el" href="_theory_operation.html#DriverInstances">Driver Instance</a>.</p>
+<h1><a class="anchor" id="DriverFunctions"></a>
+Common Driver Functions</h1>
+<p>Each CMSIS-Driver contains these functions:</p>
+<ul>
+<li><b>GetVersion:</b> can be called at any time to obtain version information of the driver interface.</li>
+</ul>
+<ul>
+<li><b>GetCapabilities:</b> can be called at any time to obtain capabilities of the driver interface.</li>
+</ul>
+<ul>
+<li><b>Initialize:</b> must be called before powering the peripheral using <b>PowerControl</b>. This function performs the following:<ul>
+<li>allocate I/O resources.<ul>
+<li>register an optional <b>SignalEvent</b> callback function.</li>
+</ul>
+</li>
+</ul>
+</li>
+</ul>
+<ul>
+<li><b>SignalEvent:</b> is an optional callback function that is registered with the <b>Initialize</b> function. This callback function is initiated from interrupt service routines and indicates hardware events or the completion of a data block transfer operation.</li>
+</ul>
+<ul>
+<li><b>PowerControl:</b> Controls the power profile of the peripheral and needs to be called after <b>Initialize</b>. Typically, three power options are available:<ul>
+<li><code>ARM_POWER_FULL:</code> Peripheral is turned on and fully operational. The driver initializes the peripheral registers, interrupts, and (optionally) DMA.</li>
+<li><code>ARM_POWER_LOW:</code> (optional) Peripheral is in low power mode and partially operational; usually, it can detect external events and wake-up.</li>
+<li><code>ARM_POWER_OFF:</code> Peripheral is turned off and not operational (pending operations are terminated). This is the state after device reset.</li>
+</ul>
+</li>
+</ul>
+<ul>
+<li><b>Uninitialize:</b> Complementary function to Initialize. Releases the I/O pin resources used by the interface.</li>
+</ul>
+<ul>
+<li><b>Control:</b> Several drivers provide a control function to configure communication parameters or execute miscellaneous control functions.</li>
+</ul>
+<p>The section <a class="el" href="_theory_operation.html#CallSequence">Function Call Sequence</a> contains more information on the operation of each function. Additional functions are specific to each driver interface and are described in the individual sections of each driver.</p>
+<h2><a class="anchor" id="ProcessorMode"></a>
+Cortex-M Processor Mode</h2>
+<p>The CMSIS-Driver functions access peripherals and interrupts and are designed to execute in <b>Privileged</b> mode. When calling CMSIS-Driver functions from RTOS threads, it should be ensure that these threads execute in <b>Privileged</b> mode.</p>
+<h1><a class="anchor" id="CallSequence"></a>
+Function Call Sequence</h1>
+<p>For normal operation of the driver, the API functions <b>GetVersion</b>, <b>GetCapabilities</b>, <b>Initialize</b>, <b>PowerControl</b>, <b>Uninitialize</b> are called in the following order:</p>
+<div align="center">
+<img src="msc_inline_mscgraph_1.png" alt="msc_inline_mscgraph_1" border="0" usemap="#msc_inline_mscgraph_1.map"/>
+<map name="msc_inline_mscgraph_1.map" id="msc_inline_mscgraph_1.map"></map>
+</div>
+<p>The functions <b>GetVersion</b> and <b>GetCapabilities</b> can be called any time to obtain the required information from the driver. These functions return always the same information.</p>
+<h2><a class="anchor" id="CS_start"></a>
+Start Sequence</h2>
+<p>To start working with a peripheral the functions <b>Initialize</b> and <b>PowerControl</b> need to be called in this order: </p>
+<div class="fragment"><div class="line">drv-&gt;Initialize (...); <span class="comment">// Allocate I/O pins</span></div>
+<div class="line">drv-&gt;PowerControl (<a class="code" href="_driver___common_8h.html#ga47d6d7c31f88f3b8ae4aaf9d8444afa5abed52b77a9ce4775570e44a842b1295e" title="Power on: full operation at maximum performance.">ARM_POWER_FULL</a>); <span class="comment">// Power up peripheral, setup IRQ/DMA</span></div>
+</div><!-- fragment --><ul>
+<li><b>Initialize</b> typically allocates the I/O resources (pins) for the peripheral. The function can be called multiple times; if the I/O resources are already initialized it performs no operation and just returns with <a class="el" href="group__execution__status.html#ga85752c5de59e8adeb001e35ff5be6be7">ARM_DRIVER_OK</a>.</li>
+<li><b>PowerControl</b> (<code>ARM_POWER_FULL</code>) sets the peripheral registers including interrupt (NVIC) and optionally DMA. The function can be called multiple times; if the registers are already set it performs no operation and just returns with <a class="el" href="group__execution__status.html#ga85752c5de59e8adeb001e35ff5be6be7">ARM_DRIVER_OK</a>.</li>
+</ul>
+<h2><a class="anchor" id="CS_stop"></a>
+Stop Sequence</h2>
+<p>To stop working with a peripheral the functions <b>PowerControl</b> and <b>Uninitialize</b> need to be called in this order: </p>
+<div class="fragment"><div class="line">drv-&gt;PowerControl (<a class="code" href="_driver___common_8h.html#ga47d6d7c31f88f3b8ae4aaf9d8444afa5ab6f5becc85ebd51c3dd2524a95d2ca35" title="Power off: no operation possible.">ARM_POWER_OFF</a>); <span class="comment">// Terminate any pending transfers, reset IRQ/DMA, power off peripheral</span></div>
+<div class="line">drv-&gt;Uninitialize (...); <span class="comment">// Release I/O pins</span></div>
+</div><!-- fragment --><p> The functions <b>PowerControl</b> and <b>Uninitialize</b> always execute and can be used to put the peripheral into a <b>Safe State</b>, for example after any data transmission errors. To restart the peripheral in a error condition, you should first execute the <a class="el" href="_theory_operation.html#CS_stop">Stop Sequence</a> and then the <a class="el" href="_theory_operation.html#CS_start">Start Sequence</a>.</p>
+<ul>
+<li><b>PowerControl</b> (<code>ARM_POWER_OFF</code>) terminates any pending data transfers with the peripheral, disables the peripheral and leaves it in a defined mode (typically the reset state).<ul>
+<li>when DMA is used it is disabled (including the interrupts)</li>
+<li>peripheral interrupts are disabled on NVIC level</li>
+<li>the peripheral is reset using a dedicated reset mechanism (if available) or by clearing the peripheral registers</li>
+<li>pending peripheral interrupts are cleared on NVIC level</li>
+<li>driver variables are cleared</li>
+</ul>
+</li>
+<li><b>Uninitialize</b> always releases I/O pin resources.</li>
+</ul>
+<h1><a class="anchor" id="Share_IO"></a>
+Shared I/O Pins</h1>
+<p>All CMSIS-Driver provide a <a class="el" href="_theory_operation.html#CS_start">Start Sequence</a> and <a class="el" href="_theory_operation.html#CS_stop">Stop Sequence</a>. Therefore two different drivers can share the same I/O pins, for example UART1 and SPI1 can have overlapping I/O pins. In this case the communication channels can be used as shown below:</p>
+<div class="fragment"><div class="line">SPI1drv-&gt;Initialize (...); <span class="comment">// Start SPI1</span></div>
+<div class="line">SPI1drv-&gt;PowerControl (<a class="code" href="_driver___common_8h.html#ga47d6d7c31f88f3b8ae4aaf9d8444afa5abed52b77a9ce4775570e44a842b1295e" title="Power on: full operation at maximum performance.">ARM_POWER_FULL</a>);</div>
+<div class="line"> ... <span class="comment">// Do operations with SPI1</span></div>
+<div class="line">SPI1drv-&gt;PowerControl (<a class="code" href="_driver___common_8h.html#ga47d6d7c31f88f3b8ae4aaf9d8444afa5ab6f5becc85ebd51c3dd2524a95d2ca35" title="Power off: no operation possible.">ARM_POWER_OFF</a>); <span class="comment">// Stop SPI1</span></div>
+<div class="line">SPI1drv-&gt;Uninitialize ();</div>
+<div class="line"> ...</div>
+<div class="line">USART1drv-&gt;Initialize (...); <span class="comment">// Start USART1</span></div>
+<div class="line">USART1drv-&gt;PowerControl (<a class="code" href="_driver___common_8h.html#ga47d6d7c31f88f3b8ae4aaf9d8444afa5abed52b77a9ce4775570e44a842b1295e" title="Power on: full operation at maximum performance.">ARM_POWER_FULL</a>);</div>
+<div class="line"> ... <span class="comment">// Do operations with USART1</span></div>
+<div class="line">USART1drv-&gt;PowerControl (<a class="code" href="_driver___common_8h.html#ga47d6d7c31f88f3b8ae4aaf9d8444afa5ab6f5becc85ebd51c3dd2524a95d2ca35" title="Power off: no operation possible.">ARM_POWER_OFF</a>); <span class="comment">// Stop USART1</span></div>
+<div class="line">USART1drv-&gt;Uninitialize ();</div>
+</div><!-- fragment --><h1><a class="anchor" id="Data_Xfer_Functions"></a>
+Data Transfer Functions</h1>
+<p>A CMSIS-Driver implements non-blocking functions to transfer data to a peripheral. This means that the driver configures the read or write access to the peripheral and instantly returns to the calling application. The function names for data transfer end with:</p>
+<ul>
+<li><b>Send</b> to write data to a peripheral.</li>
+<li><b>Receive</b> to read data from a peripheral.</li>
+<li><b>Transfer</b> to indicate combined read/write operations to a peripheral.</li>
+</ul>
+<p>During a data transfer, the application can query the number of transferred data items using functions named <b>Get<em>xxx</em>Count</b>. On completion of a data transfer, the driver calls a callback function with a specific event code.</p>
+<p>During the data exchange with the peripheral, the application can decide to:</p>
+<ul>
+<li>Wait (using an RTOS scheduler) for the callback completion event. The RTOS is controlled by the application code which makes the driver itself RTOS independent.</li>
+<li>Use polling functions that return the number of transferred data items to show progress information or partly read or fill data transfer buffers.</li>
+<li>Prepare another data transfer buffer for the next data transfer.</li>
+</ul>
+<p>The following diagram shows the basic communication flow when using the <b>_Send</b> function in an application.</p>
+<div class="image">
+<img src="Non_blocking_transmit_small.png" alt="Non_blocking_transmit_small.png"/>
+<div class="caption">
+Non-blocking Send Function</div></div>
+ <h1><a class="anchor" id="AccessStruct"></a>
+Access Struct</h1>
+<p>A CMSIS-Driver publishes an <a class="el" href="_theory_operation.html#AccessStruct">Access Struct</a> with the data type name ARM_DRIVER_xxxx that gives to access the driver functions.</p>
+<p><b>Code</b> <b>Example:</b> <b>Function</b> <b>Access</b> <b>of</b> <b>the</b> <b>SPI</b> <b>driver</b> </p>
+<div class="fragment"><div class="line"><span class="keyword">typedef</span> <span class="keyword">struct </span>_ARM_DRIVER_SPI {</div>
+<div class="line"> <a class="code" href="group__common__drv__gr.html#struct_a_r_m___d_r_i_v_e_r___v_e_r_s_i_o_n" title="Driver Version.">ARM_DRIVER_VERSION</a> (*GetVersion) (void);</div>
+<div class="line"> <a class="code" href="group__spi__interface__gr.html#struct_a_r_m___s_p_i___c_a_p_a_b_i_l_i_t_i_e_s" title="SPI Driver Capabilities.">ARM_SPI_CAPABILITIES</a> (*GetCapabilities) (void);</div>
+<div class="line"> int32_t (*Initialize) (<a class="code" href="group__spi__interface__gr.html#gafde9205364241ee81290adc0481c6640" title="Pointer to ARM_SPI_SignalEvent : Signal SPI Event.">ARM_SPI_SignalEvent_t</a> cb_event);</div>
+<div class="line"> int32_t (*Uninitialize) (void);</div>
+<div class="line"> int32_t (*PowerControl) (<a class="code" href="group__common__drv__gr.html#ga47d6d7c31f88f3b8ae4aaf9d8444afa5" title="General power states.">ARM_POWER_STATE</a> state);</div>
+<div class="line"> int32_t (*Send) (<span class="keyword">const</span> <span class="keywordtype">void</span> *data, uint32_t num);</div>
+<div class="line"> int32_t (*Receive) ( <span class="keywordtype">void</span> *data, uint32_t num);</div>
+<div class="line"> int32_t (*Transfer) (<span class="keyword">const</span> <span class="keywordtype">void</span> *data_out, <span class="keywordtype">void</span> *data_in, uint32_t num);</div>
+<div class="line"> uint32_t (*GetDataCount) (void);</div>
+<div class="line"> int32_t (*Control) (uint32_t control, uint32_t arg);</div>
+<div class="line"> <a class="code" href="group__spi__interface__gr.html#struct_a_r_m___s_p_i___s_t_a_t_u_s" title="SPI Status.">ARM_SPI_STATUS</a> (*GetStatus) (void);</div>
+<div class="line">} <span class="keyword">const</span> <a class="code" href="group__spi__interface__gr.html#struct_a_r_m___d_r_i_v_e_r___s_p_i" title="Access structure of the SPI Driver.">ARM_DRIVER_SPI</a>;</div>
+</div><!-- fragment --><h2><a class="anchor" id="DriverInstances"></a>
+Driver Instances</h2>
+<p>A device may offer several peripherals of the same type. For such devices, the CMSIS-Driver publishes multiple instances of the <a class="el" href="_theory_operation.html#AccessStruct">Access Struct</a>. The name of each driver instance reflects the names of the peripheral available in the device.</p>
+<p><b>Code</b> <b>Example:</b> <a class="el" href="_theory_operation.html#AccessStruct">Access Struct</a> <b>for</b> <b>three</b> <b>SPIs</b> <b>in</b> <b>a</b> <b>microcontroller</b> <b>device</b>. </p>
+<div class="fragment"><div class="line"><a class="code" href="group__spi__interface__gr.html#struct_a_r_m___d_r_i_v_e_r___s_p_i" title="Access structure of the SPI Driver.">ARM_DRIVER_SPI</a> Driver_SPI1; <span class="comment">// access functions for SPI1 interface</span></div>
+<div class="line"><a class="code" href="group__spi__interface__gr.html#struct_a_r_m___d_r_i_v_e_r___s_p_i" title="Access structure of the SPI Driver.">ARM_DRIVER_SPI</a> Driver_SPI2; <span class="comment">// access functions for SPI2 interface</span></div>
+<div class="line"><a class="code" href="group__spi__interface__gr.html#struct_a_r_m___d_r_i_v_e_r___s_p_i" title="Access structure of the SPI Driver.">ARM_DRIVER_SPI</a> Driver_SPI3; <span class="comment">// access functions for SPI3 interface</span></div>
+</div><!-- fragment --><p>The access functions can be passed to middleware to specify the driver instance that the middleware should use for communication.</p>
+<p><b>Example:</b> </p>
+<div class="fragment"><div class="line"><span class="keywordtype">void</span> init_middleware (<a class="code" href="group__spi__interface__gr.html#struct_a_r_m___d_r_i_v_e_r___s_p_i" title="Access structure of the SPI Driver.">ARM_DRIVER_SPI</a> *Drv_spi) ...</div>
+<div class="line">\\ inside the middleware the SPI driver functions are called with:</div>
+<div class="line">\\ Drv_spi-&gt;function (...);</div>
+</div><!-- fragment --><div class="fragment"><div class="line">\\ setup middleware</div>
+<div class="line">init_middleware (&amp;Driver_SPI1); <span class="comment">// connect middleware to SPI1 interface</span></div>
+<div class="line"> :</div>
+<div class="line">init_middleware (&amp;Driver_SPI2); <span class="comment">// connect middleware to SPI2 interface</span></div>
+</div><!-- fragment --><h1><a class="anchor" id="DriverConfiguration"></a>
+Driver Configuration</h1>
+<p>For a device family, the drivers may be configurable. The <a class="el" href="_reference_implementation.html">Reference Implementation</a> stores configuration options in a central file with the name <b>RTE_Device.h</b>. However, the configuration of the drivers itself is not part of the CMSIS-Driver specification.</p>
+<h1><a class="anchor" id="CodeExample"></a>
+Code Example</h1>
+<p>The following example code shows the usage of the SPI interface.</p>
+<div class="fragment"><div class="line"><span class="preprocessor">#include &quot;<a class="code" href="_driver___s_p_i_8h.html">Driver_SPI.h</a>&quot;</span></div>
+<div class="line"><span class="preprocessor">#include &quot;cmsis_os.h&quot;</span> <span class="comment">// ARM::CMSIS:RTOS:Keil RTX</span></div>
+<div class="line"> </div>
+<div class="line"> </div>
+<div class="line"><span class="keywordtype">void</span> mySPI_Thread(<span class="keywordtype">void</span> <span class="keyword">const</span> *argument);</div>
+<div class="line">osThreadId tid_mySPI_Thread;</div>
+<div class="line"> </div>
+<div class="line"> </div>
+<div class="line"><span class="comment">/* SPI Driver */</span></div>
+<div class="line"><span class="keyword">extern</span> <a class="code" href="group__spi__interface__gr.html#struct_a_r_m___d_r_i_v_e_r___s_p_i" title="Access structure of the SPI Driver.">ARM_DRIVER_SPI</a> Driver_SPI0;</div>
+<div class="line"> </div>
+<div class="line"> </div>
+<div class="line"><span class="keywordtype">void</span> mySPI_callback(uint32_t event)</div>
+<div class="line">{</div>
+<div class="line"> <span class="keywordflow">switch</span> (event)</div>
+<div class="line"> {</div>
+<div class="line"> <span class="keywordflow">case</span> <a class="code" href="group___s_p_i__events.html#gaabdfc9e17641144cd50d36d15511a1b8" title="Data Transfer completed.">ARM_SPI_EVENT_TRANSFER_COMPLETE</a>:</div>
+<div class="line"> <span class="comment">/* Success: Wakeup Thread */</span></div>
+<div class="line"> osSignalSet(tid_mySPI_Thread, 0x01);</div>
+<div class="line"> <span class="keywordflow">break</span>;</div>
+<div class="line"> <span class="keywordflow">case</span> <a class="code" href="group___s_p_i__events.html#ga8e63d99c80ea56de596a8d0a51fd8244" title="Data lost: Receive overflow / Transmit underflow.">ARM_SPI_EVENT_DATA_LOST</a>:</div>
+<div class="line"> <span class="comment">/* Occurs in slave mode when data is requested/sent by master</span></div>
+<div class="line"><span class="comment"> but send/receive/transfer operation has not been started</span></div>
+<div class="line"><span class="comment"> and indicates that data is lost. Occurs also in master mode</span></div>
+<div class="line"><span class="comment"> when driver cannot transfer data fast enough. */</span></div>
+<div class="line"> __breakpoint(0); <span class="comment">/* Error: Call debugger or replace with custom error handling */</span></div>
+<div class="line"> <span class="keywordflow">break</span>;</div>
+<div class="line"> <span class="keywordflow">case</span> <a class="code" href="group___s_p_i__events.html#ga7eaa229003689aa18598273490b3e630" title="Master Mode Fault (SS deactivated when Master)">ARM_SPI_EVENT_MODE_FAULT</a>:</div>
+<div class="line"> <span class="comment">/* Occurs in master mode when Slave Select is deactivated and</span></div>
+<div class="line"><span class="comment"> indicates Master Mode Fault. */</span></div>
+<div class="line"> __breakpoint(0); <span class="comment">/* Error: Call debugger or replace with custom error handling */</span></div>
+<div class="line"> <span class="keywordflow">break</span>;</div>
+<div class="line"> }</div>
+<div class="line">}</div>
+<div class="line"> </div>
+<div class="line"><span class="comment">/* Test data buffers */</span></div>
+<div class="line"><span class="keyword">const</span> uint8_t testdata_out[8] = { 0, 1, 2, 3, 4, 5, 6, 7 }; </div>
+<div class="line">uint8_t testdata_in [8];</div>
+<div class="line"> </div>
+<div class="line"><span class="keywordtype">void</span> mySPI_Thread(<span class="keywordtype">void</span> <span class="keyword">const</span>* arg)</div>
+<div class="line">{</div>
+<div class="line"> <a class="code" href="group__spi__interface__gr.html#struct_a_r_m___d_r_i_v_e_r___s_p_i" title="Access structure of the SPI Driver.">ARM_DRIVER_SPI</a>* SPIdrv = &amp;Driver_SPI0;</div>
+<div class="line"> osEvent evt;</div>
+<div class="line"> </div>
+<div class="line"><span class="preprocessor">#ifdef DEBUG</span></div>
+<div class="line"><span class="preprocessor"></span> <a class="code" href="group__common__drv__gr.html#struct_a_r_m___d_r_i_v_e_r___v_e_r_s_i_o_n" title="Driver Version.">ARM_DRIVER_VERSION</a> version;</div>
+<div class="line"> <a class="code" href="group__spi__interface__gr.html#struct_a_r_m___s_p_i___c_a_p_a_b_i_l_i_t_i_e_s" title="SPI Driver Capabilities.">ARM_SPI_CAPABILITIES</a> drv_capabilities;</div>
+<div class="line"> </div>
+<div class="line"> version = SPIdrv-&gt;<a class="code" href="group__spi__interface__gr.html#a8834b281da48583845c044a81566c1b3" title="Pointer to ARM_SPI_GetVersion : Get driver version.">GetVersion</a>();</div>
+<div class="line"> <span class="keywordflow">if</span> (version.<a class="code" href="group__common__drv__gr.html#ad180da20fbde1d3dafc074af87c19540" title="API version.">api</a> &lt; 0x200) <span class="comment">/* requires at minimum API version 2.00 or higher */</span></div>
+<div class="line"> { <span class="comment">/* error handling */</span></div>
+<div class="line"> <span class="keywordflow">return</span>;</div>
+<div class="line"> }</div>
+<div class="line"> </div>
+<div class="line"> drv_capabilities = SPIdrv-&gt;<a class="code" href="group__spi__interface__gr.html#a065b5fc24d0204692f0f95a44351ac1e" title="Pointer to ARM_SPI_GetCapabilities : Get driver capabilities.">GetCapabilities</a>();</div>
+<div class="line"> <span class="keywordflow">if</span> (drv_capabilities.<a class="code" href="group__spi__interface__gr.html#a309619714f0c4febaa497ebdb9b7e3ca" title="Signal Mode Fault event: ARM_SPI_EVENT_MODE_FAULT.">event_mode_fault</a> == 0)</div>
+<div class="line"> { <span class="comment">/* error handling */</span></div>
+<div class="line"> <span class="keywordflow">return</span>;</div>
+<div class="line"> }</div>
+<div class="line"><span class="preprocessor">#endif</span></div>
+<div class="line"><span class="preprocessor"></span> </div>
+<div class="line"> <span class="comment">/* Initialize the SPI driver */</span></div>
+<div class="line"> SPIdrv-&gt;<a class="code" href="group__spi__interface__gr.html#afac50d0b28860f7b569293e6b713f8a4" title="Pointer to ARM_SPI_Initialize : Initialize SPI Interface.">Initialize</a>(mySPI_callback);</div>
+<div class="line"> <span class="comment">/* Power up the SPI peripheral */</span></div>
+<div class="line"> SPIdrv-&gt;<a class="code" href="group__spi__interface__gr.html#aba8f1c8019af95ffe19c32403e3240ef" title="Pointer to ARM_SPI_PowerControl : Control SPI Interface Power.">PowerControl</a>(<a class="code" href="_driver___common_8h.html#ga47d6d7c31f88f3b8ae4aaf9d8444afa5abed52b77a9ce4775570e44a842b1295e" title="Power on: full operation at maximum performance.">ARM_POWER_FULL</a>);</div>
+<div class="line"> <span class="comment">/* Configure the SPI to Master, 8-bit mode @10000 kBits/sec */</span></div>
+<div class="line"> SPIdrv-&gt;<a class="code" href="group__spi__interface__gr.html#a6e0f47a92f626a971c5197fca6545505" title="Pointer to ARM_SPI_Control : Control SPI Interface.">Control</a>(<a class="code" href="group__spi__mode__ctrls.html#ga3143ef07c1607b9bc57e29df35cf2fa8" title="SPI Master (Output on MOSI, Input on MISO); arg = Bus Speed in bps.">ARM_SPI_MODE_MASTER</a> | <a class="code" href="group__spi__frame__format__ctrls.html#ga7fab572b2fec303e979e47eb2d13ca74" title="Clock Polarity 1, Clock Phase 1.">ARM_SPI_CPOL1_CPHA1</a> | <a class="code" href="group__spi__bit__order__ctrls.html#ga98228a708cbab6e214c7ac696f77dab6" title="SPI Bit order from MSB to LSB (default)">ARM_SPI_MSB_LSB</a> | <a class="code" href="group__spi__slave__select__mode__ctrls.html#gab5e319aa3f9d4d8c9ed92f0fe865f624" title="SPI Slave Select when Master: Software controlled.">ARM_SPI_SS_MASTER_SW</a> | <a class="code" href="group__spi__data__bits__ctrls.html#gaf6c099a1d67256a32010120c66c55250" title="Number of Data bits.">ARM_SPI_DATA_BITS</a>(8), 10000000);</div>
+<div class="line"> </div>
+<div class="line"> <span class="comment">/* SS line = INACTIVE = HIGH */</span></div>
+<div class="line"> SPIdrv-&gt;<a class="code" href="group__spi__interface__gr.html#a6e0f47a92f626a971c5197fca6545505" title="Pointer to ARM_SPI_Control : Control SPI Interface.">Control</a>(<a class="code" href="group__spi__misc__ctrls.html#ga5776272b82decff92da003568540c92f" title="Control Slave Select; arg: 0=inactive, 1=active.">ARM_SPI_CONTROL_SS</a>, <a class="code" href="_driver___s_p_i_8h.html#a335b448e07422e9c25616a693ec581cc" title="SPI Slave Select Signal Inactive.">ARM_SPI_SS_INACTIVE</a>);</div>
+<div class="line"> </div>
+<div class="line"> <span class="comment">/* thread loop */</span></div>
+<div class="line"> <span class="keywordflow">while</span> (1)</div>
+<div class="line"> {</div>
+<div class="line"> <span class="comment">/* SS line = ACTIVE = LOW */</span></div>
+<div class="line"> SPIdrv-&gt;<a class="code" href="group__spi__interface__gr.html#a6e0f47a92f626a971c5197fca6545505" title="Pointer to ARM_SPI_Control : Control SPI Interface.">Control</a>(<a class="code" href="group__spi__misc__ctrls.html#ga5776272b82decff92da003568540c92f" title="Control Slave Select; arg: 0=inactive, 1=active.">ARM_SPI_CONTROL_SS</a>, <a class="code" href="_driver___s_p_i_8h.html#a3f465cdbd1238ddd74f78e14457076c4" title="SPI Slave Select Signal Active.">ARM_SPI_SS_ACTIVE</a>);</div>
+<div class="line"> <span class="comment">/* Transmit some data */</span></div>
+<div class="line"> SPIdrv-&gt;<a class="code" href="group__spi__interface__gr.html#a44eedddf4428cf4b98883b6c27d31922" title="Pointer to ARM_SPI_Send : Start sending data to SPI Interface.">Send</a>(testdata_out, <span class="keyword">sizeof</span>(testdata_out));</div>
+<div class="line"> <span class="comment">/* Wait for completion */</span></div>
+<div class="line"> evt = osSignalWait(0x01, 100);</div>
+<div class="line"> <span class="keywordflow">if</span> (evt.status == osEventTimeout) {</div>
+<div class="line"> __breakpoint(0); <span class="comment">/* Timeout error: Call debugger */</span></div>
+<div class="line"> }</div>
+<div class="line"> <span class="comment">/* SS line = INACTIVE = HIGH */</span></div>
+<div class="line"> SPIdrv-&gt;<a class="code" href="group__spi__interface__gr.html#a6e0f47a92f626a971c5197fca6545505" title="Pointer to ARM_SPI_Control : Control SPI Interface.">Control</a>(<a class="code" href="group__spi__misc__ctrls.html#ga5776272b82decff92da003568540c92f" title="Control Slave Select; arg: 0=inactive, 1=active.">ARM_SPI_CONTROL_SS</a>, <a class="code" href="_driver___s_p_i_8h.html#a335b448e07422e9c25616a693ec581cc" title="SPI Slave Select Signal Inactive.">ARM_SPI_SS_INACTIVE</a>);</div>
+<div class="line"></div>
+<div class="line"> <span class="comment">/* SS line = ACTIVE = LOW */</span></div>
+<div class="line"> SPIdrv-&gt;<a class="code" href="group__spi__interface__gr.html#a6e0f47a92f626a971c5197fca6545505" title="Pointer to ARM_SPI_Control : Control SPI Interface.">Control</a>(<a class="code" href="group__spi__misc__ctrls.html#ga5776272b82decff92da003568540c92f" title="Control Slave Select; arg: 0=inactive, 1=active.">ARM_SPI_CONTROL_SS</a>, <a class="code" href="_driver___s_p_i_8h.html#a3f465cdbd1238ddd74f78e14457076c4" title="SPI Slave Select Signal Active.">ARM_SPI_SS_ACTIVE</a>);</div>
+<div class="line"> <span class="comment">/* Receive 8 bytes of reply */</span></div>
+<div class="line"> SPIdrv-&gt;<a class="code" href="group__spi__interface__gr.html#adb9224a35fe16c92eb0dd103638e4cf3" title="Pointer to ARM_SPI_Receive : Start receiving data from SPI Interface.">Receive</a>(testdata_in, 8);</div>
+<div class="line"> evt = osSignalWait(0x01, 100);</div>
+<div class="line"> <span class="keywordflow">if</span> (evt.status == osEventTimeout) {</div>
+<div class="line"> __breakpoint(0); <span class="comment">/* Timeout error: Call debugger */</span></div>
+<div class="line"> }</div>
+<div class="line"> <span class="comment">/* SS line = INACTIVE = HIGH */</span></div>
+<div class="line"> SPIdrv-&gt;<a class="code" href="group__spi__interface__gr.html#a6e0f47a92f626a971c5197fca6545505" title="Pointer to ARM_SPI_Control : Control SPI Interface.">Control</a>(<a class="code" href="group__spi__misc__ctrls.html#ga5776272b82decff92da003568540c92f" title="Control Slave Select; arg: 0=inactive, 1=active.">ARM_SPI_CONTROL_SS</a>, <a class="code" href="_driver___s_p_i_8h.html#a335b448e07422e9c25616a693ec581cc" title="SPI Slave Select Signal Inactive.">ARM_SPI_SS_INACTIVE</a>);</div>
+<div class="line"> }</div>
+<div class="line">}</div>
+</div><!-- fragment --> </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 Tue Oct 27 2015 14:35:24 for CMSIS-Driver by ARM Ltd. All rights reserved.
+ <!--
+ <a href="http://www.doxygen.org/index.html">
+ <img class="footer" src="doxygen.png" alt="doxygen"/></a> 1.8.2
+ -->
+ </li>
+ </ul>
+</div>
+</body>
+</html>