<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" media="screen" href="/~d/styles/rss2full.xsl"?><?xml-stylesheet type="text/css" media="screen" href="http://feeds.feedburner.com/~d/styles/itemcontent.css"?><rss xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:sy="http://purl.org/rss/1.0/modules/syndication/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/" xmlns:series="http://unfoldingneurons.com/" xmlns:feedburner="http://rssnamespace.org/feedburner/ext/1.0" version="2.0">

<channel>
	<title>Pete Vidler</title>
	
	<link>http://petevidler.com</link>
	<description>Software development and technology in general</description>
	<lastBuildDate>Sat, 02 Apr 2011 17:34:45 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.3</generator>
		<atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" type="application/rss+xml" href="http://feeds.feedburner.com/PeteVidler" /><feedburner:info uri="petevidler" /><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="hub" href="http://pubsubhubbub.appspot.com/" /><item>
		<title>Handling Delays without Blocking</title>
		<link>http://feedproxy.google.com/~r/PeteVidler/~3/woUb03hNtcA/</link>
		<comments>http://petevidler.com/2011/03/handling-delays-without-blocking/#comments</comments>
		<pubDate>Thu, 31 Mar 2011 20:03:43 +0000</pubDate>
		<dc:creator>Pete</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[C++]]></category>
		<category><![CDATA[Embedded Systems]]></category>
		<category><![CDATA[RTOS]]></category>
		<category><![CDATA[Software]]></category>

		<guid isPermaLink="false">http://petevidler.com/?p=339</guid>
		<description><![CDATA[In an earlier article we looked at the design and implementation of a time-triggered scheduler, but we didn’t consider the implications of actually using it. This can take some getting used to if you have never used such a system before. Imagine that we wanted to create a simple traffic light system… in a more [...]]]></description>
			<content:encoded><![CDATA[<div class="wp-caption alignright"><img title="RTOS Alternatives" src="http://petevidler.com/wp-content/uploads/2010/06/rtos-alt-series.png" alt="RTOS Alternatives" width="155" height="119" /></div>

<p>In an <a href="http://petevidler.com/2011/03/simple-co-operative-scheduling/" title="Simple Co-Operative Scheduling">earlier article</a> we looked at the design and implementation of a time-triggered scheduler, but we didn’t consider the implications of actually using it.  This can take some getting used to if you have never used such a system before.  Imagine that we wanted to create a simple <a href="http://en.wikipedia.org/wiki/File:Traffic_light.gif" title="Traffic light animation at Wikipedia">traffic light system</a>… in a more traditional event-triggered design, it might look something like this:</p>

<div class="codecolorer-container c mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br />13<br />14<br />15<br />16<br />17<br />18<br />19<br />20<br /></div></td><td><div class="c codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #993333;">typedef</span> <span style="color: #000000; font-weight: bold;">enum</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; LIGHT_RED<span style="color: #339933;">,</span><br />
&nbsp; &nbsp; LIGHT_RED_AMBER<span style="color: #339933;">,</span><br />
&nbsp; &nbsp; LIGHT_GREEN<span style="color: #339933;">,</span><br />
&nbsp; &nbsp; LIGHT_AMBER<br />
<span style="color: #009900;">&#125;</span> traffic_light_state<span style="color: #339933;">;</span><br />
<br />
<span style="color: #666666; font-style: italic;">// Event triggered RTOS version.</span><br />
<span style="color: #993333;">void</span> Traffic_Light_Controller<span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span> <span style="color: #339933;">*</span>parameters<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; <span style="color: #b1b100;">while</span> <span style="color: #009900;">&#40;</span><span style="color: #0000dd;">1</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Set_Lights<span style="color: #009900;">&#40;</span>LIGHT_RED<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Delay<span style="color: #009900;">&#40;</span><span style="color: #0000dd;">15000</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #666666; font-style: italic;">// wait 15 seconds</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Set_Lights<span style="color: #009900;">&#40;</span>LIGHT_RED_AMBER<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Delay<span style="color: #009900;">&#40;</span><span style="color: #0000dd;">2000</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #666666; font-style: italic;">// wait 2 seconds</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Set_Lights<span style="color: #009900;">&#40;</span>LIGHT_GREEN<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Delay<span style="color: #009900;">&#40;</span><span style="color: #0000dd;">15000</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Set_Lights<span style="color: #009900;">&#40;</span>LIGHT_AMBER<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Delay<span style="color: #009900;">&#40;</span><span style="color: #0000dd;">2000</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #009900;">&#125;</span><br />
<span style="color: #009900;">&#125;</span></div></td></tr></tbody></table></div>

<p>In a typical RTOS, calling the <code>Delay</code> function will cause the task to become <em>blocked</em> for the given duration (it is often hard to tell from the documentation if the delay is <em>up to</em> or <em>at least</em> the value — I have seen both).  Blocking a task involves removing it from the list of tasks that the scheduler can execute (the <em>ready list</em>) and using a context switch to resume another task instead.  Obviously this functionality is not available in our simple scheduler, as we do not have the ability to save and restore contexts (which generally requires platform-specific assembly code).</p>

<p><span id="more-339"></span></p>

<p>If we cannot block tasks, actually implementing a delay will involve <em>spinning</em> — sitting in an empty loop for the specified amount of time.  This prevents any other task from running for that time, which in this example is up to 15 seconds!  Obviously with other tasks in the system, this would not be acceptable — between the delays and the infinite loop they would never get to run.  One alternative is to use a <a href="http://en.wikipedia.org/wiki/Finite-state_machine" title="Finite State Machine article at Wikipedia">Finite State Machine</a> (FSM).</p>

<h3>Switch-Based Finite State Machines</h3>

<p>In C, state machines are often implemented with a switch statement.  We just store the current state in a variable and switch on it every time the task function is called, updating the state variable whenever the state must change.  In practice, this means setting the task period to something sensible and using a counter to determine if it is time to change state, which can be implemented as follows:</p>

<div class="codecolorer-container c mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br />13<br />14<br />15<br />16<br />17<br />18<br />19<br />20<br /></div></td><td><div class="c codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #666666; font-style: italic;">// Called once per second by the scheduler.</span><br />
<span style="color: #993333;">void</span> Traffic_Light_Update<span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; <span style="color: #666666; font-style: italic;">// Initial values that immediately change to LIGHT_RED.</span><br />
&nbsp; &nbsp; <span style="color: #993333;">static</span> traffic_light_state current_state <span style="color: #339933;">=</span> LIGHT_AMBER<span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #993333;">static</span> <span style="color: #993333;">int32_t</span> time_left <span style="color: #339933;">=</span> <span style="color: #0000dd;">1</span><span style="color: #339933;">;</span><br />
<br />
&nbsp; &nbsp; <span style="color: #b1b100;">if</span> <span style="color: #009900;">&#40;</span><span style="color: #339933;">--</span>time_left <span style="color: #339933;">&gt;</span> <span style="color: #0000dd;">0</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #b1b100;">return</span><span style="color: #339933;">;</span> <span style="color: #666666; font-style: italic;">// Not ready for a state change yet.</span><br />
&nbsp; &nbsp; <span style="color: #009900;">&#125;</span><br />
<br />
&nbsp; &nbsp; <span style="color: #b1b100;">switch</span> <span style="color: #009900;">&#40;</span>current_state<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #b1b100;">case</span> LIGHT_RED <span style="color: #339933;">:</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; current_state <span style="color: #339933;">=</span> LIGHT_RED_AMBER<span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; time_left <span style="color: #339933;">=</span> <span style="color: #0000dd;">2</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #000000; font-weight: bold;">break</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #666666; font-style: italic;">// And so on for the other states...</span><br />
&nbsp; &nbsp; <span style="color: #009900;">&#125;</span><br />
<br />
&nbsp; &nbsp; Set_Lights<span style="color: #009900;">&#40;</span>current_state<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
<span style="color: #009900;">&#125;</span></div></td></tr></tbody></table></div>

<p>The code above is quite simple and a switch statement works well for an FSM with few states, but even in this case — with all the states filled in — it is quite excessive when compared to the original blocking version.  A common way to reduce the amount of code we need to write is to use a table-based implementation.</p>

<h3>Table-Based Finite State Machines</h3>

<p>The state machine shown above is mostly concerned with data — the actual functionality of the state is carried out by the call to <code>Set_Lights</code> on each transition;  this is the same for every state, so all we really need to concern ourselves with is the nature of the states themselves.  For each state, we need to know:</p>

<ol>
<li>which state it transitions to; and</li>
<li>how long it remains in the state.</li>
</ol>

<p>This information can be wrapped up in a structure and stored in an array, indexed by the enumeration that we defined earlier:</p>

<div class="codecolorer-container c mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br /></div></td><td><div class="c codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #993333;">typedef</span> <span style="color: #993333;">struct</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; traffic_light_state next_state<span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #993333;">int32_t</span> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; state_time<span style="color: #339933;">;</span><br />
<span style="color: #009900;">&#125;</span> traffic_light_type<span style="color: #339933;">;</span><br />
<br />
<span style="color: #993333;">static</span> <span style="color: #993333;">const</span> traffic_light_type state_table<span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span> <span style="color: #339933;">=</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; <span style="color: #009900;">&#123;</span> .<span style="color: #202020;">next_state</span> <span style="color: #339933;">=</span> LIGHT_RED_AMBER<span style="color: #339933;">,</span> .<span style="color: #202020;">state_time</span> <span style="color: #339933;">=</span> <span style="color: #0000dd;">15</span> <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span><br />
&nbsp; &nbsp; <span style="color: #009900;">&#123;</span> .<span style="color: #202020;">next_state</span> <span style="color: #339933;">=</span> LIGHT_GREEN<span style="color: #339933;">,</span> &nbsp; &nbsp; .<span style="color: #202020;">state_time</span> <span style="color: #339933;">=</span> &nbsp;<span style="color: #0000dd;">2</span> <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span><br />
&nbsp; &nbsp; <span style="color: #009900;">&#123;</span> .<span style="color: #202020;">next_state</span> <span style="color: #339933;">=</span> LIGHT_AMBER<span style="color: #339933;">,</span> &nbsp; &nbsp; .<span style="color: #202020;">state_time</span> <span style="color: #339933;">=</span> <span style="color: #0000dd;">15</span> <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span><br />
&nbsp; &nbsp; <span style="color: #009900;">&#123;</span> .<span style="color: #202020;">next_state</span> <span style="color: #339933;">=</span> LIGHT_RED<span style="color: #339933;">,</span> &nbsp; &nbsp; &nbsp; .<span style="color: #202020;">state_time</span> <span style="color: #339933;">=</span> &nbsp;<span style="color: #0000dd;">2</span> <span style="color: #009900;">&#125;</span><br />
<span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span></div></td></tr></tbody></table></div>

<p>With the above table in hand, writing the actual task function is now a trivial exercise:</p>

<div class="codecolorer-container c mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br /></div></td><td><div class="c codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #666666; font-style: italic;">// Called once per second by the scheduler.</span><br />
<span style="color: #993333;">void</span> Traffic_Light_Update<span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; <span style="color: #666666; font-style: italic;">// Initial values that immediately change to LIGHT_RED.</span><br />
&nbsp; &nbsp; <span style="color: #993333;">static</span> traffic_light_state current_state <span style="color: #339933;">=</span> LIGHT_AMBER<span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #993333;">static</span> <span style="color: #993333;">int32_t</span> time_left <span style="color: #339933;">=</span> <span style="color: #0000dd;">1</span><span style="color: #339933;">;</span><br />
<br />
&nbsp; &nbsp; <span style="color: #b1b100;">if</span> <span style="color: #009900;">&#40;</span><span style="color: #339933;">--</span>time_left <span style="color: #339933;">&lt;=</span> <span style="color: #0000dd;">0</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; current_state <span style="color: #339933;">=</span> state_table<span style="color: #009900;">&#91;</span>current_state<span style="color: #009900;">&#93;</span>.<span style="color: #202020;">next_state</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; time_left <span style="color: #339933;">=</span> state_table<span style="color: #009900;">&#91;</span>current_state<span style="color: #009900;">&#93;</span>.<span style="color: #202020;">state_time</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Set_Lights<span style="color: #009900;">&#40;</span>current_state<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #009900;">&#125;</span><br />
<span style="color: #009900;">&#125;</span></div></td></tr></tbody></table></div>

<p>That is much less code than the switch example for a data-driven and time-triggered state machine, but this only works here because we have the <code>Set_Lights</code> function that takes the current state as a parameter.  How might this work if we had to use, say, a separate function for each light (<code>Set_Red_Light</code>, <code>Set_Amber_Light</code> and <code>Set_Green_Light</code>)?</p>

<p>In the RTOS example at the beginning of this article, it would be easy — I can just call the functions as needed.  For the switch-based state machine it is equally easy, but still results in a lot of excess boilerplate for state transitions and the switch itself.  Can it be done with a table-based approach?  I can think of at least two ways, off the top of my head:</p>

<ol>
<li>We can add the data for individual lights to the state table and use it to call all three of the light-setting functions.</li>
<li>We can include a function pointer in the state table and call it to carry out the state’s operation.</li>
</ol>

<p>The first method is less work, but also less interesting.  The second method is far more generic — you could write any time-triggered state machine with just a function pointer, an index to the next state and a time value in the structure.  That means that both the structure and the state changing code could be reused as necessary… in fact, you don’t even need the next state information if the function can return it:</p>

<div class="codecolorer-container c mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br />13<br />14<br />15<br />16<br />17<br />18<br /></div></td><td><div class="c codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #993333;">typedef</span> <span style="color: #993333;">struct</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; <span style="color: #993333;">uint32_t</span> <span style="color: #009900;">&#40;</span><span style="color: #339933;">*</span>transition<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #993333;">int32_t</span> &nbsp; &nbsp;<a href="http://www.opengroup.org/onlinepubs/009695399/functions/time.html"><span style="color: #000066;">time</span></a><span style="color: #339933;">;</span><br />
<span style="color: #009900;">&#125;</span> state_type<span style="color: #339933;">;</span><br />
<br />
<span style="color: #666666; font-style: italic;">// Call this periodically to execute a state machine.</span><br />
<span style="color: #993333;">void</span> State_Update<span style="color: #009900;">&#40;</span><span style="color: #993333;">const</span> state_type <span style="color: #339933;">*</span>states<span style="color: #339933;">,</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #993333;">int32_t</span> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;<span style="color: #339933;">*</span>current_time<span style="color: #339933;">,</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #993333;">uint32_t</span> &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #339933;">*</span>current_state<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; <a href="http://www.opengroup.org/onlinepubs/009695399/functions/assert.html"><span style="color: #000066;">assert</span></a><span style="color: #009900;">&#40;</span>states <span style="color: #339933;">!=</span> NULL<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <a href="http://www.opengroup.org/onlinepubs/009695399/functions/assert.html"><span style="color: #000066;">assert</span></a><span style="color: #009900;">&#40;</span>current_time <span style="color: #339933;">!=</span> NULL<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <a href="http://www.opengroup.org/onlinepubs/009695399/functions/assert.html"><span style="color: #000066;">assert</span></a><span style="color: #009900;">&#40;</span>current_state <span style="color: #339933;">!=</span> NULL<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
<br />
&nbsp; &nbsp; <span style="color: #b1b100;">if</span> <span style="color: #009900;">&#40;</span><span style="color: #339933;">--*</span>current_time <span style="color: #339933;">&lt;=</span> <span style="color: #0000dd;">0</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #339933;">*</span>current_time <span style="color: #339933;">=</span> states<span style="color: #009900;">&#91;</span><span style="color: #339933;">*</span>current_state<span style="color: #009900;">&#93;</span>.<a href="http://www.opengroup.org/onlinepubs/009695399/functions/time.html"><span style="color: #000066;">time</span></a><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #339933;">*</span>current_state <span style="color: #339933;">=</span> states<span style="color: #009900;">&#91;</span><span style="color: #339933;">*</span>current_state<span style="color: #009900;">&#93;</span>.<span style="color: #202020;">transition</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #009900;">&#125;</span><br />
<span style="color: #009900;">&#125;</span></div></td></tr></tbody></table></div>

<p>You might be wondering why I bothered with all the assertions this time, when I left them out of the previous examples.  The answer is simply that this is a generic function that may be reused months or years down the line — it’s helpful both to check the parameters for correctness and as informal documentation of the function’s preconditions.</p>

<p>I also made the first parameter <code>const</code>, which is always useful but which I rarely bother with in examples like this.  I did it this time because the array that we pass in will probably be declared as <code>static</code> <code>const</code> and I wanted to avoid casting that ‘const-ness’ away… your compiler will almost certainly issue a warning if this is left out anyway.</p>

<p>As a side note:  declaring an array as <code>static</code> <code>const</code> is the best way to ensure that the compiler and linker place it in a read-only memory section, which is very helpful in embedded systems where it will be placed into <a href="http://en.wikipedia.org/wiki/Flash_memory" title="Flash memory article at Wikipedia">flash memory</a> and kept out of our more limited (and therefore precious) RAM.</p>

<p>Using the generic state machine code is now quite simple:</p>

<div class="codecolorer-container c mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br />13<br />14<br />15<br />16<br />17<br />18<br />19<br />20<br /></div></td><td><div class="c codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #993333;">uint32_t</span> Enter_Red_State<span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; Set_Red_Light<span style="color: #009900;">&#40;</span>TRUE<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; Set_Amber_Light<span style="color: #009900;">&#40;</span>FALSE<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; Set_Green_Light<span style="color: #009900;">&#40;</span>FALSE<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
<br />
&nbsp; &nbsp; <span style="color: #666666; font-style: italic;">// Return the next state to transition to.</span><br />
&nbsp; &nbsp; <span style="color: #b1b100;">return</span> LIGHT_RED_AMBER<span style="color: #339933;">;</span><br />
<span style="color: #009900;">&#125;</span><br />
<br />
<span style="color: #993333;">static</span> <span style="color: #993333;">const</span> state_type state_table<span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span> <span style="color: #339933;">=</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; <span style="color: #009900;">&#123;</span> .<span style="color: #202020;">transition</span> <span style="color: #339933;">=</span> Enter_Red_State<span style="color: #339933;">,</span> .<a href="http://www.opengroup.org/onlinepubs/009695399/functions/time.html"><span style="color: #000066;">time</span></a> <span style="color: #339933;">=</span> <span style="color: #0000dd;">15</span> <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span><br />
&nbsp; &nbsp; <span style="color: #666666; font-style: italic;">// ... the other states go here.</span><br />
<span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span><br />
<br />
<span style="color: #993333;">void</span> Traffic_Light_Update<span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; <span style="color: #666666; font-style: italic;">// Initial values that immediately change to LIGHT_RED.</span><br />
&nbsp; &nbsp; <span style="color: #993333;">static</span> traffic_light_state current_state <span style="color: #339933;">=</span> LIGHT_AMBER<span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #993333;">static</span> <span style="color: #993333;">int32_t</span> time_left <span style="color: #339933;">=</span> <span style="color: #0000dd;">1</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; State_Update<span style="color: #009900;">&#40;</span>state_table<span style="color: #339933;">,</span> <span style="color: #339933;">&amp;</span>current_time<span style="color: #339933;">,</span> <span style="color: #339933;">&amp;</span>current_state<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
<span style="color: #009900;">&#125;</span></div></td></tr></tbody></table></div>

<p>This allows us to easily split up our state transition code into separate functions, with just the state table and a simple three line function as overhead.  The design is as capable as the switch-based approach, but without the messy boilerplate code that can easily get mixed in with the actual state operations.  Of course, we still haven’t reached the level of simplicity shown in the RTOS example — I know of at least one method of achieving such simplicity without platform-specific context switching, but this article is already too long, so I’ll leave it for another time.</p>

<p>In this article we discussed a few different approaches to implementing time delays without blocking; next time, I will be looking at how to handle tasks with long execution times that hog the CPU.</p>
<img src="http://feeds.feedburner.com/~r/PeteVidler/~4/woUb03hNtcA" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://petevidler.com/2011/03/handling-delays-without-blocking/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
	
		<series:name><![CDATA[RTOS Alternatives]]></series:name>
	<feedburner:origLink>http://petevidler.com/2011/03/handling-delays-without-blocking/</feedburner:origLink></item>
		<item>
		<title>Simple Co-Operative Scheduling</title>
		<link>http://feedproxy.google.com/~r/PeteVidler/~3/C-tkXhDqdls/</link>
		<comments>http://petevidler.com/2011/03/simple-co-operative-scheduling/#comments</comments>
		<pubDate>Wed, 16 Mar 2011 10:12:39 +0000</pubDate>
		<dc:creator>Pete</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[C++]]></category>
		<category><![CDATA[Embedded Systems]]></category>
		<category><![CDATA[RTOS]]></category>
		<category><![CDATA[Software]]></category>

		<guid isPermaLink="false">http://petevidler.com/?p=238</guid>
		<description><![CDATA[Last time, I looked at some of the simplest alternatives to using a Real-Time Operating System. The problem is, as soon as you need both accurate timing and prioritised tasks, you are out of luck — a foreground/background system would need a separate interrupt source per task priority, which can bring its own problems to [...]]]></description>
			<content:encoded><![CDATA[<div class="wp-caption alignright"><img title="RTOS Alternatives" src="http://petevidler.com/wp-content/uploads/2010/06/rtos-alt-series.png" alt="RTOS Alternatives" width="155" height="119" /></div>

<p><a href="http://petevidler.com/2010/06/superloop-foreground-background-scheduling/" title="Super Loops, Sandwich Delays and Foreground/Background Scheduling">Last time</a>, I looked at some of the simplest alternatives to using a Real-Time Operating System.  The problem is, as soon as you need both accurate timing and prioritised tasks, you are out of luck — a foreground/background system would need a separate interrupt source per task priority, which can bring its own problems to the table:</p>

<div><img class="aligncenter" src="http://petevidler.com/wp-content/uploads/2010/06/int-sources.png" alt="Graph of predictability and functionality against number of interrupt sources" title="Graph of predictability and functionality against number of interrupt sources" width="550" height="350" /></div>

<p>In order to meet our requirements and avoid these issues, we really need a scheduler… luckily, they aren’t too hard to write.  The simplest of all schedulers is the Time-Triggered Co-operative (TTC) scheduler, in which tasks are released by a single timer interrupt (hitting the green ‘sweet spot’ on the above graph).  This differs from foreground/background scheduling in that tasks are actually executed from the <code class="codecolorer c mac-classic"><span class="c">main</span></code> function and not from the interrupt handler itself.</p>

<p><span id="more-238"></span></p>

<h3>Time-Triggered Systems</h3>

<p>Before delving into the scheduler implementation, it’s probably worth taking a short detour through time-triggered systems.  If you’re not familiar with them, they are a subset of the more widely used <a href="http://en.wikipedia.org/wiki/Event-driven_programming" title="Event-driven programming article at Wikipedia">event-driven programming</a> technique.  The difference is that the only ‘events’ we are allowed to use are those whose timing is known in advance.  This typically means just having one timer interrupt as the event source — which, as some will already have guessed — often leads to a technique known as <a href="http://en.wikipedia.org/wiki/Polling_(computer_science)" title="Polling article at Wikipedia">polling</a>.</p>

<p>Polling has a poor reputation in most software development circles, and for good reason.  As soon as you start polling on more than a few frequent (but aperiodic) events, the time taken to continually check for the event can be costly in terms of processor utilisation.  Then there’s the problem of long tasks, which — in a co-operatively scheduled system — can delay polling activities and potentially cause events to be missed.</p>

<p>Despite these issues, the idea of knowing <em>exactly</em> what your system is doing at any given instant is very compelling.  So, in this article we will look at building a co-operative scheduler and in future articles we will look at ways of coping with the shortcomings of this approach.  Perhaps in time I might even get as far as writing about pre-emptive schedulers!</p>

<h3>The Anatomy of a Task</h3>

<p>For systems written in C, a task is usually represented as a function. The average RTOS will not allow the task function to return, instead forcing us to wrap the code in an infinite loop. Having the task perform operations periodically — as in a time-triggered system — is done by calling <em>blocking</em> functions provided by the RTOS, similar to the following:</p>

<div class="codecolorer-container c mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br />13<br />14<br /></div></td><td><div class="c codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #666666; font-style: italic;">// Called in the main function:</span><br />
Create_Task<span style="color: #009900;">&#40;</span>RTOS_Task<span style="color: #339933;">,</span> <span style="color: #666666; font-style: italic;">// Task function.</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #0000dd;">512</span><span style="color: #339933;">,</span> &nbsp; &nbsp; &nbsp; <span style="color: #666666; font-style: italic;">// Bytes of stack to allocate.</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; NULL<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> &nbsp; &nbsp; <span style="color: #666666; font-style: italic;">// No parameters to pass.</span><br />
<br />
<span style="color: #666666; font-style: italic;">// Never called directly, runs only through context switching.</span><br />
<span style="color: #993333;">void</span> RTOS_Task<span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span> <span style="color: #339933;">*</span>parameters<span style="color: #009900;">&#41;</span><br />
<span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; <span style="color: #666666; font-style: italic;">// Tasks may never return!</span><br />
&nbsp; &nbsp; <span style="color: #b1b100;">while</span> <span style="color: #009900;">&#40;</span><span style="color: #0000dd;">1</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Do_Something<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Delay<span style="color: #009900;">&#40;</span><span style="color: #0000dd;">5</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #009900;">&#125;</span><br />
<span style="color: #009900;">&#125;</span></div></td></tr></tbody></table></div>

<p>Notice how similar this is to the super loop example from <a href="http://petevidler.com/2010/06/superloop-foreground-background-scheduling/" title="Super Loops, Sandwich Delays and Foreground/Background Scheduling">last time</a>?  It suffers from many of the same problems too, but we won’t get into that now.  Instead, let’s look at a roughly equivalent task for a time-triggered, co-operative scheduler:</p>

<div class="codecolorer-container c mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br /></div></td><td><div class="c codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #666666; font-style: italic;">// Called in the main function:</span><br />
Create_Task<span style="color: #009900;">&#40;</span>Scheduled_Task<span style="color: #339933;">,</span> <span style="color: #666666; font-style: italic;">// Task function.</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #0000dd;">5</span><span style="color: #339933;">,</span> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;<span style="color: #666666; font-style: italic;">// Task period, in ticks.</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #0000dd;">0</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #666666; font-style: italic;">// Delay before first run, in ticks.</span><br />
<br />
<span style="color: #666666; font-style: italic;">// Called directly and periodically by the scheduler.</span><br />
<span style="color: #993333;">void</span> Scheduled_Task<span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span><span style="color: #009900;">&#41;</span><br />
<span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; Do_Something<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
<span style="color: #009900;">&#125;</span></div></td></tr></tbody></table></div>

<p>Notice that the function is allowed to return, and that we specify a period and delay for the task. The scheduler will be responsible for calling the task function at the appropriate times — we do not control this inside the task itself.  Note also that the task function is called directly without context switching, and so does not require a stack of its own.</p>

<p>The scheduler implementation will need a data structure to store this information; to keep things simple, we can use the following:</p>

<div class="codecolorer-container c mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br /></div></td><td><div class="c codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #993333;">typedef</span> <span style="color: #993333;">struct</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; <span style="color: #993333;">void</span> &nbsp; <span style="color: #009900;">&#40;</span><span style="color: #339933;">*</span>task<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #666666; font-style: italic;">// Pointer to the task function.</span><br />
&nbsp; &nbsp; <span style="color: #993333;">uint32_t</span> period<span style="color: #339933;">;</span> &nbsp; &nbsp; &nbsp;<span style="color: #666666; font-style: italic;">// Period to execute with.</span><br />
&nbsp; &nbsp; <span style="color: #993333;">uint32_t</span> delay<span style="color: #339933;">;</span> &nbsp; &nbsp; &nbsp; <span style="color: #666666; font-style: italic;">// Delay before first call.</span><br />
<span style="color: #009900;">&#125;</span> task_type<span style="color: #339933;">;</span></div></td></tr></tbody></table></div>

<p>The above structure is effectively minimal for a time-triggered scheduler, containing just the function pointer and timing data needed to call the task at the appropriate times.  Note that the implementation is easiest if the period and delay are in units of ‘ticks’, which correspond to a (single) periodically repeating timer interrupt.</p>

<h3>Implementing a Simple Scheduler</h3>

<p>Time is obviously going to be the most important factor in a time-triggered system.  To build the scheduler, we will need — as a minimum — the ability to configure a hardware timer such that it generates an interrupt at the desired frequency.  This is platform dependent and I will not go into detail here — see the datasheet or user manuals for your architecture for more information.</p>

<p>In the terminology introduced <a href="http://petevidler.com/2010/06/superloop-foreground-background-scheduling/" title="Super Loops, Sandwich Delays and Foreground/Background Scheduling">last time</a>, all tasks in our co-operative scheduler are going to be ‘background’ tasks.  In other words, the interrupt handler is not responsible for actually running tasks; instead it will just keep track of time for us:</p>

<div class="codecolorer-container c mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br /></div></td><td><div class="c codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #666666; font-style: italic;">// Count the number of ticks yet to be processed.</span><br />
<span style="color: #993333;">volatile</span> <span style="color: #993333;">uint32_t</span> elapsed_ticks <span style="color: #339933;">=</span> <span style="color: #0000dd;">0</span><span style="color: #339933;">;</span><br />
<br />
<span style="color: #993333;">void</span> Timer_ISR<span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span><span style="color: #009900;">&#41;</span><br />
<span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">++</span>elapsed_ticks<span style="color: #339933;">;</span><br />
<span style="color: #009900;">&#125;</span></div></td></tr></tbody></table></div>

<p>It’s that simple — all the real work will be done outside of the ISR, in a dispatcher that can be called over and over again from the <code>main</code> function.  All we really need to do is wait until the <code>elapsed_ticks</code> variable is greater than zero, then decrement the delay of every task and execute any that reach zero.  The task’s <code>delay</code> variable can then be reloaded with the period.</p>

<p>Note that the <code>elapsed_ticks</code> variable must be made <code>volatile</code>, as it is accessed both inside and outside of an ISR.  This is not to ensure atomic access — which is good, because it doesn’t — but instead prevents some <a href="http://en.wikipedia.org/wiki/Volatile_variable#Example_of_MMIO_In_C" title="Volatile variable article at Wikipedia">potentially harmful compiler optimisations</a> (however unlikely).  We must take further steps to ensure atomic access, and in this case I have opted for a heavy handed application of disabled interrupts:</p>

<div class="codecolorer-container c mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br />13<br />14<br />15<br />16<br />17<br />18<br />19<br /></div></td><td><div class="c codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">task_type tasks<span style="color: #009900;">&#91;</span>NUM_TASKS<span style="color: #009900;">&#93;</span><span style="color: #339933;">;</span><br />
<br />
<span style="color: #993333;">void</span> Dispatch_Tasks<span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span><span style="color: #009900;">&#41;</span><br />
<span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; Disable_Interrupts<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #b1b100;">while</span> <span style="color: #009900;">&#40;</span>elapsed_ticks <span style="color: #339933;">&gt;</span> <span style="color: #0000dd;">0</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span> <span style="color: #666666; font-style: italic;">// TRUE only if the ISR ran.</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #b1b100;">for</span> <span style="color: #009900;">&#40;</span><span style="color: #993333;">uint32_t</span> i <span style="color: #339933;">=</span> <span style="color: #0000dd;">0</span><span style="color: #339933;">;</span> i <span style="color: #339933;">&lt;</span> NUM_TASKS<span style="color: #339933;">;</span> i<span style="color: #339933;">++</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #b1b100;">if</span> <span style="color: #009900;">&#40;</span><span style="color: #339933;">--</span>tasks<span style="color: #009900;">&#91;</span>i<span style="color: #009900;">&#93;</span>.<span style="color: #202020;">delay</span> <span style="color: #339933;">==</span> <span style="color: #0000dd;">0</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; tasks<span style="color: #009900;">&#91;</span>i<span style="color: #009900;">&#93;</span>.<span style="color: #202020;">delay</span> <span style="color: #339933;">=</span> tasks<span style="color: #009900;">&#91;</span>i<span style="color: #009900;">&#93;</span>.<span style="color: #202020;">period</span><span style="color: #339933;">;</span><br />
<br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; Enable_Interrupts<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; tasks<span style="color: #009900;">&#91;</span>i<span style="color: #009900;">&#93;</span>.<span style="color: #202020;">task</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #666666; font-style: italic;">// Execute the task!</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; Disable_Interrupts<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;">&#125;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #009900;">&#125;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #339933;">--</span>elapsed_ticks<span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #009900;">&#125;</span><br />
&nbsp; &nbsp; Enable_Interrupts<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
<span style="color: #009900;">&#125;</span></div></td></tr></tbody></table></div>

<p>Reading the above code, you might notice that the first call to the dispatcher will (probably) jump past the outer loop and exit almost immediately.  This is not a disaster — if the function is called repeatedly as intended then it will still operate correctly — but it is not ideal.</p>

<h3>Initialisation and Usage</h3>

<p>We can improve efficiency by making use of the microcontroller’s idle mode:</p>

<div class="codecolorer-container c mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br />13<br />14<br />15<br />16<br /></div></td><td><div class="c codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #993333;">int</span> main<span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span><span style="color: #009900;">&#41;</span><br />
<span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; Initialise_Timer<span style="color: #009900;">&#40;</span> <span style="color: #808080; font-style: italic;">/* ... */</span> <span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
<br />
&nbsp; &nbsp; <span style="color: #666666; font-style: italic;">// Note the tasks from the last post.</span><br />
&nbsp; &nbsp; Create_Task<span style="color: #009900;">&#40;</span>Task_1<span style="color: #339933;">,</span> <span style="color: #0000dd;">10</span><span style="color: #339933;">,</span> <span style="color: #0000dd;">0</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; Create_Task<span style="color: #009900;">&#40;</span>Task_2<span style="color: #339933;">,</span> <span style="color: #0000dd;">10</span><span style="color: #339933;">,</span> <span style="color: #0000dd;">5</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
<br />
&nbsp; &nbsp; Start_Timer<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
<br />
&nbsp; &nbsp; <span style="color: #b1b100;">while</span> <span style="color: #009900;">&#40;</span><span style="color: #0000dd;">1</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; <span style="color: #666666; font-style: italic;">// Sleep until the next interrupt.</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Enter_Idle_Mode<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Dispatch_Tasks<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #009900;">&#125;</span><br />
<span style="color: #009900;">&#125;</span></div></td></tr></tbody></table></div>

<p>Line <code>13</code> effectively puts the microcontroller to sleep until the next interrupt occurs; once again, this function is highly architecture-dependent and you will have to write it yourself.  The trouble with using idle mode is what happens when an interrupt occurs immediately before this line is reached — the <code>elapsed_ticks</code> variable will still be incremented, but the dispatcher will not run until the <em>following</em> tick (i.e. one tick will be ‘missed’).</p>

<p>We can assume that the timer interrupt will not fire between lines <code>9</code> and <code>13</code> above, but there is still the possibility of this happening between the end of <code>Dispatch_Tasks</code> and entering idle mode.  Actually, there is another problem with this code — the dispatcher decrements the delay before testing it and we are setting the initial delay to zero, so how do we avoid underflow (or subtraction overflow if you prefer)?</p>

<div class="codecolorer-container c mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br /></div></td><td><div class="c codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #993333;">void</span> Create_Task<span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span> <span style="color: #009900;">&#40;</span><span style="color: #339933;">*</span>function_pointer<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;<span style="color: #993333;">uint32_t</span> period<span style="color: #339933;">,</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;<span style="color: #993333;">uint32_t</span> delay<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; <span style="color: #993333;">static</span> <span style="color: #993333;">uint32_t</span> index <span style="color: #339933;">=</span> <span style="color: #0000dd;">0</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <a href="http://www.opengroup.org/onlinepubs/009695399/functions/assert.html"><span style="color: #000066;">assert</span></a><span style="color: #009900;">&#40;</span>index <span style="color: #339933;">&lt;</span> NUM_TASKS<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
<br />
&nbsp; &nbsp; tasks<span style="color: #009900;">&#91;</span>index<span style="color: #009900;">&#93;</span>.<span style="color: #202020;">task</span> <span style="color: #339933;">=</span> function_pointer<span style="color: #339933;">;</span><br />
&nbsp; &nbsp; tasks<span style="color: #009900;">&#91;</span>index<span style="color: #009900;">&#93;</span>.<span style="color: #202020;">period</span> <span style="color: #339933;">=</span> period<span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #666666; font-style: italic;">// Avoid underflow in the dispatcher.</span><br />
&nbsp; &nbsp; tasks<span style="color: #009900;">&#91;</span>index<span style="color: #009900;">&#93;</span>.<span style="color: #202020;">delay</span> <span style="color: #339933;">=</span> delay <span style="color: #339933;">+</span> <span style="color: #0000dd;">1</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #339933;">++</span>index<span style="color: #339933;">;</span><br />
<span style="color: #009900;">&#125;</span></div></td></tr></tbody></table></div>

<p>That’s it for the implementation… let’s take a look at how it works with the two-task example from <a href="http://petevidler.com/2010/06/superloop-foreground-background-scheduling/" title="Super Loops, Sandwich Delays and Foreground/Background Scheduling">last time</a>:</p>

<div><img class="aligncenter" src="http://petevidler.com/wp-content/uploads/2011/03/scheduler-timing.png" alt="Timing of the scheduler example" title="Timing of the scheduler example" width="440" height="155" /></div>

<p>So, we now have access to priorities — based on the order of the task array — as well as a simple way of getting accurate timing.  Next time, we’ll look at some of the problems inherent in both co-operative and time-triggered schedulers and some ways of working around them.</p>
<img src="http://feeds.feedburner.com/~r/PeteVidler/~4/C-tkXhDqdls" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://petevidler.com/2011/03/simple-co-operative-scheduling/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
	
		<series:name><![CDATA[RTOS Alternatives]]></series:name>
	<feedburner:origLink>http://petevidler.com/2011/03/simple-co-operative-scheduling/</feedburner:origLink></item>
		<item>
		<title>Super Loops, Sandwich Delays and Foreground/Background Scheduling</title>
		<link>http://feedproxy.google.com/~r/PeteVidler/~3/cVGcxmXcoA0/</link>
		<comments>http://petevidler.com/2010/06/superloop-foreground-background-scheduling/#comments</comments>
		<pubDate>Sun, 13 Jun 2010 16:02:59 +0000</pubDate>
		<dc:creator>Pete</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[C++]]></category>
		<category><![CDATA[Embedded Systems]]></category>
		<category><![CDATA[RTOS]]></category>
		<category><![CDATA[Software]]></category>

		<guid isPermaLink="false">http://petevidler.com/?p=190</guid>
		<description><![CDATA[As microcontrollers increase in speed and capacity, it’s becoming much more tempting to simply fit a full Real-Time Operating System (RTOS) into a design, without considering other options. This is a shame, because over time a number of alternatives have been developed that can be simple and effective. In this series, I will be discussing [...]]]></description>
			<content:encoded><![CDATA[<div class="wp-caption alignright"><img title="RTOS Alternatives" src="http://petevidler.com/wp-content/uploads/2010/06/rtos-alt-series.png" alt="RTOS Alternatives" width="155" height="119" /></div>

<p>As microcontrollers increase in speed and capacity, it’s becoming much more tempting to simply fit a full Real-Time Operating System (RTOS) into a design, without considering other options.  This is a shame, because over time a number of alternatives have been developed that can be simple and effective.  In this series, I will be discussing some of these, starting with the very simplest — the super loop.</p>

<p><span id="more-190"></span></p>

<h3>Super Loops</h3>

<p>Without an operating system to fall back on, the application is responsible for executing any tasks that must run.  The easiest way to do this is just to keep calling task functions repeatedly in an infinite (super) loop:</p>

<div class="codecolorer-container c mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br /></div></td><td><div class="c codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #993333;">int</span> main<span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span><span style="color: #009900;">&#41;</span><br />
<span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; <span style="color: #b1b100;">while</span> <span style="color: #009900;">&#40;</span><span style="color: #0000dd;">1</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Task_1<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Task_2<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #009900;">&#125;</span><br />
<span style="color: #009900;">&#125;</span></div></td></tr></tbody></table></div>

<p>Note that we need an infinite loop in the main function because there is no OS to return to.</p>

<p>The solution above has the advantage of utter simplicity; it will run the two tasks, one after the other, as fast as they can be run.  The disadvantages are that there will be no pre-emption and no accuracy to the timing of the tasks.</p>

<p>Timing can be an important issue for many tasks, such as debouncing a button press, sampling data from an ADC, or executing a control algorithm.  These tasks are usually required to run with a fixed period, which we might be able to accomplish in a super loop.  Suppose we want to run the tasks above every ten milliseconds, with five milliseconds between them:</p>

<div class="codecolorer-container c mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br />13<br />14<br />15<br />16<br /></div></td><td><div class="c codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #993333;">void</span> Delay<span style="color: #009900;">&#40;</span><span style="color: #993333;">uint32_t</span> milliseconds<span style="color: #009900;">&#41;</span><br />
<span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; <span style="color: #666666; font-style: italic;">// Setup a hardware timer for the given time</span><br />
&nbsp; &nbsp; <span style="color: #666666; font-style: italic;">// Loop until the delay has been reached.</span><br />
<span style="color: #009900;">&#125;</span><br />
<br />
<span style="color: #993333;">int</span> main<span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span><span style="color: #009900;">&#41;</span><br />
<span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; <span style="color: #b1b100;">while</span> <span style="color: #009900;">&#40;</span><span style="color: #0000dd;">1</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Task_1<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Delay<span style="color: #009900;">&#40;</span><span style="color: #0000dd;">5</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
<br />
&nbsp; &nbsp; &nbsp; &nbsp; Task_2<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Delay<span style="color: #009900;">&#40;</span><span style="color: #0000dd;">5</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #009900;">&#125;</span><br />
<span style="color: #009900;">&#125;</span></div></td></tr></tbody></table></div>

<p>This might work as described, but only if the two tasks are extremely short.  The problem here is the delay can only begin after the associated task has finished.  If the tasks each had a constant Worst-Case Execution Time (WCET), then we could simply reduce the delay values appropriately, but this is exceptionally rare and not very practical (any change to the tasks or optimisation settings could invalidate the delay).  The problem is shown here, where we assume that both tasks take around two milliseconds to complete:</p>

<div><img class="aligncenter" src="http://petevidler.com/wp-content/uploads/2010/06/superloop-timing.png" alt="Timing of the super loop example" title="Timing of the super loop example" width="545" height="127" /></div>

<p>Clearly we don’t want the task’s period to be tied to its execution time.  If the problem is that the delay only starts after the task finishes, can we find a way to start it before the task runs?  A sandwich delay does precisely that.</p>

<h3>Sandwich Delays</h3>

<p>The goal of a sandwich delay is to achieve a delay that is constant from the <em>beginning</em> of the task.  The delay function used previously started a timer and looped until the desired time had passed; this time, we can simply try starting the timer before the task runs:</p>

<div class="codecolorer-container c mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br /></div></td><td><div class="c codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #993333;">int</span> main<span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span><span style="color: #009900;">&#41;</span><br />
<span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; <span style="color: #b1b100;">while</span> <span style="color: #009900;">&#40;</span><span style="color: #0000dd;">1</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Start_Timer<span style="color: #009900;">&#40;</span><span style="color: #0000dd;">5</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Task_1<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Wait_For_Timer<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
<br />
&nbsp; &nbsp; &nbsp; &nbsp; Start_Timer<span style="color: #009900;">&#40;</span><span style="color: #0000dd;">5</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Task_2<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Wait_For_Timer<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #009900;">&#125;</span><br />
<span style="color: #009900;">&#125;</span></div></td></tr></tbody></table></div>

<p>It should be obvious where the name comes from — the task is sandwiched by the two delay calls.  The timing behaviour is also greatly improved, now providing the ten millisecond periods that we were looking for:</p>

<div><img class="aligncenter" src="http://petevidler.com/wp-content/uploads/2010/06/sandwich-timing.png" alt="Timing of the sandwich delay example" title="Timing of the sandwich delay example" width="440" height="124" /></div>

<p>We have the periodic behaviour that we were looking for, but what about the lack of pre-emption?  I will address this point at length later in the series, but for now consider what happens if some of our tasks are very long and others are very frequent.  In the example above, what if we also needed a task run every millisecond at a higher priority (e.g. to acquire a sample from an ADC)?</p>

<p>A simple sandwich delay cannot provide this behaviour.  In fact, we have no support for higher priorities at all;  this is where foreground/background scheduling comes into play.</p>

<h3>Foreground/Background Scheduling</h3>

<p>Foreground/background scheduling is simply the practice of using interrupt handlers to carry out the most important work in your system.  Tasks run from the super loop in the main function become the background tasks, while the interrupt handlers become the foreground (higher priority) tasks:</p>

<div class="codecolorer-container c mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br />13<br />14<br />15<br />16<br />17<br />18<br />19<br />20<br /></div></td><td><div class="c codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #666666; font-style: italic;">// Run by hardware, every millisecond</span><br />
<span style="color: #993333;">void</span> Timer_ISR<span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span><span style="color: #009900;">&#41;</span><br />
<span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; sample_buffer<span style="color: #009900;">&#91;</span>index<span style="color: #339933;">++</span><span style="color: #009900;">&#93;</span> <span style="color: #339933;">=</span> ADC_Get_Data<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
<span style="color: #009900;">&#125;</span><br />
<br />
<span style="color: #993333;">void</span> main<span style="color: #009900;">&#40;</span><span style="color: #993333;">void</span><span style="color: #009900;">&#41;</span><br />
<span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; Init_ISR<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
<br />
&nbsp; &nbsp; <span style="color: #b1b100;">while</span> <span style="color: #009900;">&#40;</span><span style="color: #0000dd;">1</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Start_Timer<span style="color: #009900;">&#40;</span><span style="color: #0000dd;">5</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Background_Task_1<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Wait_For_Timer<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
<br />
&nbsp; &nbsp; &nbsp; &nbsp; Start_Timer<span style="color: #009900;">&#40;</span><span style="color: #0000dd;">5</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Background_Task_2<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp; Wait_For_Timer<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><br />
&nbsp; &nbsp; <span style="color: #009900;">&#125;</span><br />
<span style="color: #009900;">&#125;</span></div></td></tr></tbody></table></div>

<p>In the above example, we still have both of our tasks — which now run in the ‘background’.  In the foreground we have added a new task that retrieves a sample from an ADC, which should run every millisecond.  Because the new task is actually triggered directly in an interrupt handler, it has the ability to pre-empt any background task:</p>

<div><img class="aligncenter" src="http://petevidler.com/wp-content/uploads/2010/06/back-fore-timing.png" alt="Timing of the foreground/background example" title="Timing of the foreground/background example" width="465" height="126" /></div>

<p>So now we have two priorities and some pre-emption going on.  It’s possible to have more than two priorities if you have other interrupts and associated handlers; many systems can do nesting and prioritisation of interrupt handlers.  That doesn’t make it a good idea!  Having many different interrupt sources just doesn’t scale well — in my experience, predictability drops off rapidly with each additional source beyond the basic system tick timer.</p>

<div><img class="aligncenter" src="http://petevidler.com/wp-content/uploads/2010/06/int-sources.png" alt="Graph of predictability and functionality against number of interrupt sources" title="Graph of predictability and functionality against number of interrupt sources" width="550" height="350" /></div>

<p>What we really want is a way to get prioritisation and accurate timing for background tasks as well, ideally without sacrificing predictability, simplicity, performance or memory usage in the process.  We can do this — easily — with a simple scheduler, which is the topic of the next article in this series.</p>
<img src="http://feeds.feedburner.com/~r/PeteVidler/~4/cVGcxmXcoA0" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://petevidler.com/2010/06/superloop-foreground-background-scheduling/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
	
		<series:name><![CDATA[RTOS Alternatives]]></series:name>
	<feedburner:origLink>http://petevidler.com/2010/06/superloop-foreground-background-scheduling/</feedburner:origLink></item>
		<item>
		<title>Software Team Trade-Offs</title>
		<link>http://feedproxy.google.com/~r/PeteVidler/~3/uglRHUVfyRg/</link>
		<comments>http://petevidler.com/2010/04/software-team-compromis/#comments</comments>
		<pubDate>Sat, 17 Apr 2010 10:17:39 +0000</pubDate>
		<dc:creator>Pete</dc:creator>
				<category><![CDATA[Elsewhere]]></category>
		<category><![CDATA[Software]]></category>
		<category><![CDATA[Teams]]></category>

		<guid isPermaLink="false">http://petevidler.com/?p=184</guid>
		<description><![CDATA[A quote from Rands about the interaction in software development teams: Time. Quality. Features. It’s usually described as a triangle, which somehow represents the state of your product or your feature. I believe the idea is that in a perfect and unattainable world, this triangle is perfect, equilateral, and seemingly at rest. There is balance [...]]]></description>
			<content:encoded><![CDATA[<p>A quote from <a href="http://www.randsinrepose.com/">Rands</a> about the <a href="http://www.randsinrepose.com/archives/2010/03/29/bits_features_and_truth.html">interaction in software development teams</a>:</p>

<blockquote>
  <p>Time. Quality. Features. It’s usually described as a triangle, which somehow represents the state
  of your product or your feature. I believe the idea is that in a perfect and unattainable world, this triangle
  is perfect, equilateral, and seemingly at rest. There is balance among the time you have to release, the
  quality you are seeking to attain, and the features you want to ship.</p>
  
  <p>In reality, this triangle is never at rest. It’s constantly shifting and, well, I don’t think it’s actually a
  triangle. It’s just a mental model that gives you just enough ammunition to lie.</p>
</blockquote>

<p>The whole article is worth reading — I like the concept of “Bits”, “Features” and “Truth” as roles for certain people on the team.  It seems more approachable than the traditional engineering manager, product manager and program manager titles.</p>

<p>“I’m the Bits” does sound wrong, though.</p>
<img src="http://feeds.feedburner.com/~r/PeteVidler/~4/uglRHUVfyRg" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://petevidler.com/2010/04/software-team-compromis/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://petevidler.com/2010/04/software-team-compromis/</feedburner:origLink></item>
		<item>
		<title>The Case Against File Comments</title>
		<link>http://feedproxy.google.com/~r/PeteVidler/~3/fOVFTYR4Ej8/</link>
		<comments>http://petevidler.com/2010/04/case-against-file-comment/#comments</comments>
		<pubDate>Sun, 04 Apr 2010 20:01:56 +0000</pubDate>
		<dc:creator>Pete</dc:creator>
				<category><![CDATA[Elsewhere]]></category>
		<category><![CDATA[C++]]></category>
		<category><![CDATA[Code Generation]]></category>
		<category><![CDATA[Software]]></category>

		<guid isPermaLink="false">http://petevidler.com/?p=180</guid>
		<description><![CDATA[Ville Laurikari, in an older post that recently made the Hacker News front page, talks about the evils of source-code templates: Most projects have some kind of standard source code template which has the copyright and license text and placeholders for things like a description. All I have to say is: You don’t need a [...]]]></description>
			<content:encoded><![CDATA[<p><a href="http://hackerboss.com/">Ville Laurikari</a>, in an older post that recently made the <a href="http://news.ycombinator.com/">Hacker News</a> front page, talks about the <a href="http://hackerboss.com/get-rid-of-templates/" title="Get Rid of Source Code Templates">evils of source-code templates</a>:</p>

<blockquote>
  <p>Most projects have some kind of standard source code template which has the copyright and license text and placeholders for things like a description.  All I have to say is: <strong>You don’t need a template.  Stop using it.</strong></p>
</blockquote>

<p>He’s referring to things like this, found at the top of most source-code files:</p>

<div class="codecolorer-container c mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br /></div></td><td><div class="c codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #808080; font-style: italic;">/*<br />
&nbsp;* File: filename.c<br />
&nbsp;* Author: Peter J. Vidler<br />
&nbsp;* Copyright (c) 2010. &nbsp;All rights reserved.<br />
&nbsp;*/</span></div></td></tr></tbody></table></div>

<p>Actually, that one’s fairly trivial — see the actual post for <a href="http://hackerboss.com/get-rid-of-templates/" title="Get Rid of Source Code Templates">a <em>much</em> worse example</a>.  His post actually seems to be about file-level comments, rather than comment templates, but it’s still worth a read.</p>
<img src="http://feeds.feedburner.com/~r/PeteVidler/~4/fOVFTYR4Ej8" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://petevidler.com/2010/04/case-against-file-comment/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://petevidler.com/2010/04/case-against-file-comment/</feedburner:origLink></item>
		<item>
		<title>Central Repositories in Mercurial</title>
		<link>http://feedproxy.google.com/~r/PeteVidler/~3/GQ38u5ExSXU/</link>
		<comments>http://petevidler.com/2010/04/central-repositories-mercurial/#comments</comments>
		<pubDate>Fri, 02 Apr 2010 16:08:27 +0000</pubDate>
		<dc:creator>Pete</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Mercurial]]></category>

		<guid isPermaLink="false">http://petevidler.com/?p=148</guid>
		<description><![CDATA[As a distributed version control system, Mercurial allows us to push and pull changes between any two repositories in an ad hoc manner. In reality, most projects can benefit from a central server (even if it’s just a repository on the lead developer’s machine) — somewhere accessible to keep an authoritative copy of the project. [...]]]></description>
			<content:encoded><![CDATA[<div class="wp-caption alignright"><img title="Bite-Sized Mercurial" src="http://petevidler.com/wp-content/uploads/2010/03/hg-series.png" alt="Bite-Sized Mercurial" width="90" height="100" /></div>

<p>As a distributed version control system, Mercurial allows us to push and pull changes between any two repositories in an ad hoc manner.  In reality, most projects can benefit from a central server (even if it’s just a repository on the lead developer’s machine) — somewhere accessible to keep an <em>authoritative</em> copy of the project.</p>

<p>In this article, I’ll look at <em>one</em> way to work with a remote central repository in order to share code with other developers.</p>

<p><span id="more-148"></span></p>

<p><a href="http://petevidler.com/2010/03/mercurial-release-management/" title="Release Management in Mercurial">Last time</a>, Joe managed to create and merge branches for both his cutting-edge development and the bug fixes he made to the released software.  But what about his colleague, <a href="http://petevidler.com/2010/03/bite-sized-mercurial-intro/" title="Introduction to Bite-Sized Mercurial">Dan</a>?  He’s going to need a copy of Joe’s changes and he’s going to need to share some changes of his own.  As mentioned in <a href="http://petevidler.com/2010/03/bite-sized-mercurial-intro/" title="Introduction to Bite-Sized Mercurial">the introduction</a>, Joe can use the <em>push</em> command to send his changes to a remote repository… except we don’t have one yet.</p>

<p>To create a new repository, Joe can use the <em>init</em> command with a parameter indicating the working directory (or none for the current directory).  To add files to a new repository, Joe will add them to the working directory and then use the <em>add</em> command to tell the repository about their existence (without parameters, this will add all files in the working directory and recurse through all subdirectories).  This can all be done on a remote server over <a href="http://en.wikipedia.org/wiki/Secure_Shell" title="Wikipedia page for the Secure Shell">SSH</a>.</p>

<div class="codecolorer-container bash mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br /></div></td><td><div class="bash codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #666666; font-style: italic;"># Joe, working on the server:</span><br />
hg init new_repo<br />
<span style="color: #7a0874; font-weight: bold;">cd</span> new_repo<br />
<span style="color: #666666; font-style: italic;"># ... Joe copies files into the working directory ...</span><br />
hg add<br />
hg commit <span style="color: #660033;">-m</span> <span style="color: #ff0000;">'Initial import to the new repository'</span></div></td></tr></tbody></table></div>

<p>Mercurial can push from one local repository to another, or to a remote repository through SSH, HTTP or even to a shared drive.  It even comes with a built-in <a href="http://mercurial.selenic.com/wiki/hgserve" title="The Mercurial wiki about the built-in server">standalone web-server</a> for ad hoc sharing.  Whichever method is used, the push command will allow Joe to add his changes from last time into the repository on the central server.  Dan can get a copy of the repository on his computer by <em>cloning</em> the server’s copy.</p>

<div class="codecolorer-container bash mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br /></div></td><td><div class="bash codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap"><span style="color: #666666; font-style: italic;"># Joe, working on his local repository:</span><br />
hg push ssh:<span style="color: #000000; font-weight: bold;">//</span>username<span style="color: #000000; font-weight: bold;">@</span>repository_address<br />
<br />
<span style="color: #666666; font-style: italic;"># Dan, working on his local machine</span><br />
hg clone ssh:<span style="color: #000000; font-weight: bold;">//</span>username<span style="color: #000000; font-weight: bold;">@</span>repository_address</div></td></tr></tbody></table></div>

<p>Now they both have up-to-date copies of the repository, Joe and Dan can start making changes simultaneously.  If Joe finishes first and pushes his changes, what will happen when Dan tries to do the same?  Simply put, he won’t be able to.  Mercurial will complain that the push will create multiple heads — which would effectively be two anonymous branches.</p>

<p>On encountering this error, Dan can pull Joe’s changes into his own repository, creating the multiple heads there instead.  Dan could follow the steps from <a href="http://petevidler.com/2010/03/mercurial-release-management/" title="Release Management in Mercurial">last time</a> and merge the heads before committing and pushing the merge changeset.  From what I can tell, this is usually the recommended approach in Mercurial; I don’t like it because it results in littering the central repository’s history with useless commit messages from merge operations.</p>

<p>The alternative approach, which is often used in that <a href="http://git-scm.com/" title="The main homepage for the Git version control system">other version control system</a>, is to <em>rebase</em> the local changes on top of the ones we have just pulled in.  This is actually a multi-step process that first copies the changesets from one head onto the other (this actually <a href="http://mercurial.selenic.com/wiki/RebasePlan" title="Inner workings of the rebase extension">works by merging</a>), then deletes the old changesets (indeed, the entire anonymous branch):</p>

<div><img class="aligncenter" src="http://petevidler.com/wp-content/uploads/2010/04/hg-repo-rebase.png" alt="Diagram of Mercurial repository throughout a rebase" title="Mercurial repository rebasing" width="536" height="308" /></div>

<p>Generally, this approach goes against the Mercurial philosophy that the history should be immutable (to avoid losing data), but it is just so much cleaner than the alternative of having merge-commits all over the place.  If every developer follows this workflow, then the only time we will see merges should be when working with <a href="http://petevidler.com/2010/03/mercurial-release-management/" title="Release Management in Mercurial">named release branches</a>, which is useful.</p>

<p>There is one small problem here though:  <strong>do not rebase changes that have already been pushed</strong>.  If you do, you only delete the old changes locally and other repositories may end up having two copies of your changesets.  This can get messy and should therefore be avoided — I recommend a simple “pull, rebase, push” workflow only for local changes to avoid this kind of mess.  Note also that in Mercurial, rebasing is done by an extension that must be enabled before we can use it.  See <a href="http://mercurial.selenic.com/wiki/RebaseExtension" title="Documentation for Mercurial's Rebase extension">the documentation</a> for details.</p>

<p>That’s it for this time.  So far the workflow I’ve discussed is mainly suitable for small-scale projects; next time I’ll look at how we can scale things up to larger projects with more developers.  Meanwhile, here’s a quick summary of the new Mercurial commands used in this article:</p>

<table>
<thead>
<tr>
  <th>Command</th>
  <th>Effect</th>
</tr>
</thead>
<tbody>
<tr>
  <td>init</td>
  <td>initialises a new repository</td>
</tr>
<tr>
  <td>add</td>
  <td>adds new files to the repository</td>
</tr>
<tr>
  <td>clone</td>
  <td>makes a copy of another repository</td>
</tr>
<tr>
  <td>rebase</td>
  <td>moves changesets from one head to another</td>
</tr>
</tbody>
</table>
<img src="http://feeds.feedburner.com/~r/PeteVidler/~4/GQ38u5ExSXU" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://petevidler.com/2010/04/central-repositories-mercurial/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
	
		<series:name><![CDATA[Bite-Sized Mercurial]]></series:name>
	<feedburner:origLink>http://petevidler.com/2010/04/central-repositories-mercurial/</feedburner:origLink></item>
		<item>
		<title>The C++ Confidence Curve</title>
		<link>http://feedproxy.google.com/~r/PeteVidler/~3/b8aVV2kfqK8/</link>
		<comments>http://petevidler.com/2010/03/cpp-confidence-curve/#comments</comments>
		<pubDate>Mon, 29 Mar 2010 22:08:16 +0000</pubDate>
		<dc:creator>Pete</dc:creator>
				<category><![CDATA[Elsewhere]]></category>
		<category><![CDATA[C++]]></category>
		<category><![CDATA[Interviewing]]></category>

		<guid isPermaLink="false">http://petevidler.com/?p=138</guid>
		<description><![CDATA[Louis Brandy on why you should never trust a programmer who says he knows C++: Programmers (especially those coming from C) can very quickly get up to speed in C++ and feel quite proficient. These programmers will tell you that they know C++. They are lying. As a programmer continues in C++, he goes through [...]]]></description>
			<content:encoded><![CDATA[<p><a href="http://lbrandy.com/blog/">Louis Brandy</a> on why you should <a href="http://lbrandy.com/blog/2010/03/never-trust-a-programmer-who-says-he-knows-c/">never trust a programmer who says he knows C++</a>:</p>

<blockquote>
  <p>Programmers (especially those coming from C) can very quickly get up to speed in C++ and feel quite proficient. These programmers will tell you that they know C++. They are lying. As a programmer continues in C++, he goes through this valley of frustration where he fully comes to terms with the full complexity of the language.</p>
</blockquote>

<p>Very true, and worth a look just for the diagram.</p>
<img src="http://feeds.feedburner.com/~r/PeteVidler/~4/b8aVV2kfqK8" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://petevidler.com/2010/03/cpp-confidence-curve/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://petevidler.com/2010/03/cpp-confidence-curve/</feedburner:origLink></item>
		<item>
		<title>Issues with the Ogg Container Format</title>
		<link>http://feedproxy.google.com/~r/PeteVidler/~3/ioTljAzHZZo/</link>
		<comments>http://petevidler.com/2010/03/issues-with-ogg/#comments</comments>
		<pubDate>Mon, 29 Mar 2010 12:00:07 +0000</pubDate>
		<dc:creator>Pete</dc:creator>
				<category><![CDATA[Elsewhere]]></category>
		<category><![CDATA[H.264]]></category>
		<category><![CDATA[Ogg Theora]]></category>
		<category><![CDATA[Video]]></category>

		<guid isPermaLink="false">http://petevidler.com/?p=132</guid>
		<description><![CDATA[With all the recent talk about Ogg Theora, H.264 and patent issues, it’s nice to read an article about the Ogg container format itself that is focussed entirely on technical details: The Ogg container format is being promoted by the Xiph Foundation for use with its Vorbis and Theora codecs. Unfortunately, a number of technical [...]]]></description>
			<content:encoded><![CDATA[<p>With all the recent talk about <a href="http://www.theora.org/">Ogg Theora</a>, <a href="http://en.wikipedia.org/wiki/H.264/MPEG-4_AVC">H.264</a> and patent issues, it’s nice to read an <a href="http://ffmpeg.org/~mru/hardwarebug.org/2010/03/03/ogg-objections/">article about the Ogg container format</a> itself that is focussed entirely on technical details:</p>

<blockquote>
  <p>The Ogg container format is being promoted by the Xiph Foundation for use with its Vorbis and Theora codecs. Unfortunately, a number of technical shortcomings in the format render it ill-suited to most, if not all, use cases.</p>
</blockquote>

<p>I have no idea how accurate the article is, but it was certainly refreshing.</p>
<img src="http://feeds.feedburner.com/~r/PeteVidler/~4/ioTljAzHZZo" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://petevidler.com/2010/03/issues-with-ogg/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://petevidler.com/2010/03/issues-with-ogg/</feedburner:origLink></item>
		<item>
		<title>Release Management in Mercurial</title>
		<link>http://feedproxy.google.com/~r/PeteVidler/~3/YUMnCg6JYic/</link>
		<comments>http://petevidler.com/2010/03/mercurial-release-management/#comments</comments>
		<pubDate>Wed, 24 Mar 2010 22:15:46 +0000</pubDate>
		<dc:creator>Pete</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Mercurial]]></category>

		<guid isPermaLink="false">http://petevidler.com/?p=82</guid>
		<description><![CDATA[As I discussed previously there are many possible workflows to use with Mercurial; I will only be looking at some very specific scenarios. For example, it’s often the case that we want to separate work being done on cutting edge development from bug-fixes that get applied to the latest stable release. This is often done [...]]]></description>
			<content:encoded><![CDATA[<div class="wp-caption alignright"><img title="Bite-Sized Mercurial" src="http://petevidler.com/wp-content/uploads/2010/03/hg-series.png" alt="Bite-Sized Mercurial" width="90" height="100" /></div>

<p>As I <a href="http://petevidler.com/2010/03/bite-sized-mercurial-intro/" title="Introduction to Bite-Sized Mercurial">discussed previously</a> there are many possible workflows to use with <a href="http://mercurial.selenic.com/" title="The main Mercurial site">Mercurial</a>; I will only be looking at some very specific scenarios.  For example, it’s often the case that we want to separate work being done on cutting edge development from bug-fixes that get applied to the latest stable release.  This is often done with <em>branching</em> — you have a main development branch and a separate branch for every significant release.</p>

<p>As with everything else, there are <a href="http://stevelosh.com/blog/2009/08/a-guide-to-branching-in-mercurial/" title="Steve Losh's guide to branching in Mercurial">many ways to branch</a> in Mercurial.  I’ll start in this article by looking specifically at the use of <a href="http://mercurial.selenic.com/wiki/NamedBranches" title="Named branches in the Mercurial wiki">named branches</a>.</p>

<p><span id="more-82"></span></p>

<p>Remember Joe from <a href="http://petevidler.com/2010/03/bite-sized-mercurial-intro/" title="Introduction to Bite-Sized Mercurial">last time</a>?  Let’s take a closer look at his repository:</p>

<div><img class="aligncenter" src="http://petevidler.com/wp-content/uploads/2010/03/hg-repo-internal.png" alt="Diagram of Mercurial repository internals" title="Mercurial repository internals" width="465" height="240" /></div>

<p>Joe has made and committed some changes to the local repository; on the right we can see his <a href="http://mercurial.selenic.com/wiki/ChangeSet"><em>changesets</em></a>, each representing a set of changes that were committed together.  Changesets in Mercurial have two identifiers — the small number on the left is a local identifier that is <em>only</em> valid within the repository.  On the right is a global identifier that may be used across different repositories.</p>

<p>The current state of the working directory can be thought of as a <em>potential</em> changeset.  It doesn’t yet exist in the repository or have an identifier of its own, but it could if it were committed immediately.</p>

<p>Suppose Joe had released the version at changeset <code>0</code> as his first major release.  If a user has a problem with this release, it’s useful to be able to get back to the exact version that they were using and fix the bug there.  To do this, Joe can tag the exact version that he released and use a branch for any ongoing bug-fixes.  First, he must update his working directory to the relevant version:</p>

<div class="codecolorer-container bash mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br /></div></td><td><div class="bash codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">hg update <span style="color: #660033;">-r</span> <span style="color: #000000;">0</span><br />
hg branch branch-<span style="color: #000000;">1</span><br />
hg tag version-<span style="color: #000000;">1.0</span></div></td></tr></tbody></table></div>

<p>Tags are stored in a file inside the repository that is itself kept under version control, so using the tag command also results in a commit.  By contrast, the branch command provides a branch name for the <em>next</em> commit, which is why Joe used it first — to put the tag on the release’s branch.</p>

<p>So if Joe had to make some bug-fixes to the released version at this point, he could update to the tagged revision, make his changes and commit them back to the repository:</p>

<div class="codecolorer-container bash mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br /></div></td><td><div class="bash codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">hg update branch-<span style="color: #000000;">1</span><br />
<span style="color: #666666; font-style: italic;"># ... Joe makes some changes ...</span><br />
hg commit <span style="color: #660033;">-m</span> <span style="color: #ff0000;">&quot;Another bug bites the dust&quot;</span></div></td></tr></tbody></table></div>

<p>Joe’s working directory is still based on the bug-fix to the first release.  But this commit was built on top of the new branch, so what does Joe’s repository look like now?  Something like this:</p>

<div><img class="aligncenter" src="http://petevidler.com/wp-content/uploads/2010/03/hg-repo-branch.png" alt="Diagram of Mercurial repository internals after branching" title="Mercurial repository branching" width="483" height="210" /></div>

<p>Now that Joe has a branch for the first release of his product, how can he get those bug fixes back into the development branch?  The answer is <em>merging</em>, where one branch is merged into another.  The main branch that we use for development is called <em>default</em>, so first Joe must update to it and then he simply merges in all changes from the stable branch:</p>

<div class="codecolorer-container bash mac-classic" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br /></div></td><td><div class="bash codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">hg update default<br />
hg merge branch-<span style="color: #000000;">1</span><br />
<span style="color: #666666; font-style: italic;"># ... Joe fixes any merge conflicts ...</span><br />
hg resolve <span style="color: #660033;">-m</span> <span style="color: #660033;">-a</span><br />
hg commit <span style="color: #660033;">-m</span> <span style="color: #ff0000;">&quot;Merged bug-fixes from branch-1&quot;</span></div></td></tr></tbody></table></div>

<p>If there are conflicts during the merge, then Joe will need to resolve them manually.  Usually this is a simple task of editing the file to include only the desired changes, but a graphical diff tool can make this task even easier.  Joe uses the <em>resolve</em> command (with the <code>-m</code> and <code>-a</code> options) to indicate to Mercurial that all the conflicts have been resolved successfully.</p>

<p>Finally, as the merge is itself a change, it must be committed to the repository.  Joe’s repository will now look like this:</p>

<div><img class="aligncenter" src="http://petevidler.com/wp-content/uploads/2010/03/hg-repo-merge.png" alt="Diagram of Mercurial repository during a merge" title="Mercurial repository merging" width="298" height="259" /></div>

<p>Using named branches and tags like this works very well for tracking and managing releases.  I would strongly recommend using one named branch for each major stable release, then tagging at every minor release.  It’s then trivial to use Mercurial’s update command to switch the working directory to the head of any given branch.</p>

<p>That’s it for now; next time I’ll be looking at how we can deal with remote repositories and how to avoid littering our history with merges.  Here’s a quick summary of the new Mercurial commands used in this article:</p>

<table>
<thead>
<tr>
  <th>Command</th>
  <th>Effect</th>
</tr>
</thead>
<tbody>
<tr>
  <td>tag</td>
  <td>names the current revision, commits the change</td>
</tr>
<tr>
  <td>branch</td>
  <td>sets a branch name for future commits</td>
</tr>
<tr>
  <td>merge</td>
  <td>merges another changeset into the working directory</td>
</tr>
<tr>
  <td>resolve</td>
  <td>marks merge conflicts as manually resolved</td>
</tr>
</tbody>
</table>
<img src="http://feeds.feedburner.com/~r/PeteVidler/~4/YUMnCg6JYic" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://petevidler.com/2010/03/mercurial-release-management/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
	
		<series:name><![CDATA[Bite-Sized Mercurial]]></series:name>
	<feedburner:origLink>http://petevidler.com/2010/03/mercurial-release-management/</feedburner:origLink></item>
		<item>
		<title>Force Field Armour?</title>
		<link>http://feedproxy.google.com/~r/PeteVidler/~3/stsd_QNralU/</link>
		<comments>http://petevidler.com/2010/03/force-field-armour/#comments</comments>
		<pubDate>Tue, 23 Mar 2010 21:16:46 +0000</pubDate>
		<dc:creator>Pete</dc:creator>
				<category><![CDATA[Elsewhere]]></category>
		<category><![CDATA[Science Fiction]]></category>

		<guid isPermaLink="false">http://petevidler.com/?p=77</guid>
		<description><![CDATA[According to the Telegraph, the Defence Science and Technology Laboratory are developing a new type of armour for vehicles: When a threat from incoming fire is detected by the vehicle, the energy stored in the supercapacitor can be rapidly dumped onto the metal plating on the outside of the vehicle, producing a strong electromagnetic field. [...]]]></description>
			<content:encoded><![CDATA[<p><a href="http://www.telegraph.co.uk/technology/news/7487740/Star-Trek-style-force-field-armour-being-developed-by-military-scientists.html">According to the Telegraph</a>, the Defence Science and Technology Laboratory are developing a new type of armour for vehicles:</p>

<blockquote>
  <p>When a threat from incoming fire is detected by the vehicle, the energy stored in the supercapacitor can be rapidly dumped onto the metal plating on the outside of the vehicle, producing a strong electromagnetic field.</p>
</blockquote>

<p><a href="http://memory-alpha.org/en/wiki/Polarized_hull_plating">Polarise the hull plating?</a></p>
<img src="http://feeds.feedburner.com/~r/PeteVidler/~4/stsd_QNralU" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://petevidler.com/2010/03/force-field-armour/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		<feedburner:origLink>http://petevidler.com/2010/03/force-field-armour/</feedburner:origLink></item>
	</channel>
</rss><!-- Dynamic page generated in 2.538 seconds. --><!-- Cached page generated by WP-Super-Cache on 2012-03-11 16:39:34 --><!-- Compression = gzip -->

