<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom"><channel><title>opensource | Craig Hesling</title><link>https://new.craighesling.com/tag/opensource/</link><atom:link href="https://new.craighesling.com/tag/opensource/index.xml" rel="self" type="application/rss+xml"/><description>opensource</description><generator>Wowchemy (https://wowchemy.com)</generator><language>en-us</language><lastBuildDate>Sun, 03 Jun 2018 07:46:59 -0500</lastBuildDate><image><url>https://new.craighesling.com/media/icon_hud2fdbe3c21f96e183bc7961971f91459_788_512x512_fill_lanczos_center_3.png</url><title>opensource</title><link>https://new.craighesling.com/tag/opensource/</link></image><item><title>SafetyFast</title><link>https://new.craighesling.com/project/safetyfast/</link><pubDate>Sun, 03 Jun 2018 07:46:59 -0500</pubDate><guid>https://new.craighesling.com/project/safetyfast/</guid><description>&lt;p>Put thread-safety first, with the performance of safety last.&lt;/p>
&lt;p>
&lt;figure >
&lt;div class="d-flex justify-content-center">
&lt;div class="w-100" >&lt;img src="https://new.craighesling.com/img/SafetyFast_Preview.png" alt="Example SafetyFast Atomic usage" loading="lazy" data-zoomable />&lt;/div>
&lt;/div>&lt;/figure>
&lt;/p>
&lt;p>This is a Go library that implements synchronization primitives over
&lt;a href="https://en.wikipedia.org/wiki/Transactional_Synchronization_Extensions" target="_blank" rel="noopener">Intel TSX&lt;/a> (Intel&amp;rsquo;s hardware transactional primitives).
The library exposes interfaces to make use of Intel HLE and Intel RTM.&lt;/p>
&lt;h1 id="usage-patterns">Usage Patterns&lt;/h1>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-shell" data-lang="shell">&lt;span class="line">&lt;span class="cl">go get github.com/linux4life798/safetyfast
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h2 id="rtm-context">RTM Context&lt;/h2>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-go" data-lang="go">&lt;span class="line">&lt;span class="cl">&lt;span class="kn">package&lt;/span> &lt;span class="nx">main&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="kn">import&lt;/span> &lt;span class="s">&amp;#34;github.com/linux4life798/safetyfast&amp;#34;&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="kd">func&lt;/span> &lt;span class="nf">main&lt;/span>&lt;span class="p">()&lt;/span> &lt;span class="p">{&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="nx">r&lt;/span> &lt;span class="o">:=&lt;/span> &lt;span class="nx">safetyfast&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nf">NewRTMContexDefault&lt;/span>&lt;span class="p">()&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="nx">r&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nf">Atomic&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="kd">func&lt;/span>&lt;span class="p">()&lt;/span> &lt;span class="p">{&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="nx">btc&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nf">Touch&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="nx">index&lt;/span>&lt;span class="p">)&lt;/span> &lt;span class="c1">// Any action
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="p">})&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="p">}&lt;/span>
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h2 id="hle-spin-lock">HLE Spin Lock&lt;/h2>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-go" data-lang="go">&lt;span class="line">&lt;span class="cl">&lt;span class="kn">package&lt;/span> &lt;span class="nx">main&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="kn">import&lt;/span> &lt;span class="p">(&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="s">&amp;#34;sync&amp;#34;&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="s">&amp;#34;github.com/linux4life798/safetyfast&amp;#34;&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="p">)&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="kd">func&lt;/span> &lt;span class="nf">main&lt;/span>&lt;span class="p">()&lt;/span> &lt;span class="p">{&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="kd">var&lt;/span> &lt;span class="nx">m&lt;/span> &lt;span class="nx">sync&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nx">Locker&lt;/span> &lt;span class="p">=&lt;/span> &lt;span class="nb">new&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="nx">safetyfast&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nx">SpinHLEMutex&lt;/span>&lt;span class="p">)&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="nx">m&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nf">Lock&lt;/span>&lt;span class="p">()&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="nx">btc&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nf">Touch&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="nx">index&lt;/span>&lt;span class="p">)&lt;/span> &lt;span class="c1">// Any action
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="nx">m&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nf">Unlock&lt;/span>&lt;span class="p">()&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="p">}&lt;/span>
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h1 id="poster">Poster&lt;/h1>
&lt;a href="https://craighesling.com/files/SafetyFast_Poster.pdf">Download PDF&lt;/a>
&lt;p>A preview of the PDF should appear below. If it does not show up soon, please refresh the page.&lt;/p>
&lt;iframe src="https://docs.google.com/gview?url=https%3a%2f%2fcraighesling.com%2ffiles%2fSafetyFast_Poster.pdf&amp;embedded=true" style="width:100%; height:600px;" frameborder="0">
This browser does not support PDFs. Please download the PDF to view it: &lt;a href="https://craighesling.com/files/SafetyFast_Poster.pdf">Download PDF&lt;/a>
&lt;/iframe>
&lt;h2 id="links">Links&lt;/h2>
&lt;ul>
&lt;li>&lt;a href="https://github.com/linux4life798/safetyfast" target="_blank" rel="noopener">SafetyFast on Github&lt;/a>&lt;/li>
&lt;li>&lt;a href="https://en.wikipedia.org/wiki/Transactional_Synchronization_Extensions" target="_blank" rel="noopener">Intel TSX&lt;/a>&lt;/li>
&lt;/ul></description></item><item><title>GOBF</title><link>https://new.craighesling.com/post/gobf/</link><pubDate>Fri, 04 May 2018 00:00:00 +0000</pubDate><guid>https://new.craighesling.com/post/gobf/</guid><description>&lt;h2 id="intro">Intro&lt;/h2>
&lt;p>I have always been fascinated by compilers.
I think the idea of representing one language&amp;rsquo;s structure inside
of another language is just downright cool.
Furthermore, the ability to analyze another language and optimize it really peaks my interest.&lt;/p>
&lt;p>Recently, I worked on a project that would allow you to more precisely manage
which processor core a set of Goroutines would run on.
The idea was that Goroutines that communicate more than they process independently
would benefit from sharing that same processor core&amp;rsquo;s cache. I called them
M-Groups. The implementation called for modifying the &lt;code>runtime&lt;/code> package
and the Go scheduler.
While ripping through the Go internals, I stumbled upon quite a bit of the Go
compiler code, including the SSA library. As I ripped into it more,
I started to form an itch to make my own compiler of some kind.&lt;/p>
&lt;p>Fast forward a few months and I found myself staring at some examples of
my favorite simple esoteric language, &lt;a href="https://en.wikipedia.org/wiki/Brainfuck" target="_blank" rel="noopener">BF&lt;/a>.
BF is the perfect language to write a compiler / optimizer for because of its
extremely minimal syntax.
It only has 8 possible syntax items(called commands), &lt;code>&amp;lt;&amp;gt;+-.,[]&lt;/code>, but
those simple syntax items quickly form complex programs
(not in the sense of awesome functionality).&lt;/p>
&lt;p>Here is Hello World in BF&lt;/p>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-brainfuck" data-lang="brainfuck">&lt;span class="line">&lt;span class="cl">&lt;span class="nb">++++++++&lt;/span>&lt;span class="k">[&lt;/span>&lt;span class="nv">&amp;gt;&lt;/span>&lt;span class="nb">++++&lt;/span>&lt;span class="k">[&lt;/span>&lt;span class="nv">&amp;gt;&lt;/span>&lt;span class="nb">++&lt;/span>&lt;span class="nv">&amp;gt;&lt;/span>&lt;span class="nb">+++&lt;/span>&lt;span class="nv">&amp;gt;&lt;/span>&lt;span class="nb">+++&lt;/span>&lt;span class="nv">&amp;gt;&lt;/span>&lt;span class="nb">+&lt;/span>&lt;span class="nv">&amp;lt;&amp;lt;&amp;lt;&amp;lt;&lt;/span>&lt;span class="nb">-&lt;/span>&lt;span class="k">]&lt;/span>&lt;span class="nv">&amp;gt;&lt;/span>&lt;span class="nb">+&lt;/span>&lt;span class="nv">&amp;gt;&lt;/span>&lt;span class="nb">+&lt;/span>&lt;span class="nv">&amp;gt;&lt;/span>&lt;span class="nb">-&lt;/span>&lt;span class="nv">&amp;gt;&amp;gt;&lt;/span>&lt;span class="nb">+&lt;/span>&lt;span class="k">[&lt;/span>&lt;span class="nv">&amp;lt;&lt;/span>&lt;span class="k">]&lt;/span>&lt;span class="nv">&amp;lt;&lt;/span>&lt;span class="nb">-&lt;/span>&lt;span class="k">]&lt;/span>&lt;span class="nv">&amp;gt;&amp;gt;&lt;/span>&lt;span class="nt">.&lt;/span>&lt;span class="nv">&amp;gt;&lt;/span>&lt;span class="nb">---&lt;/span>&lt;span class="nt">.&lt;/span>&lt;span class="nb">+++++++&lt;/span>&lt;span class="nt">..&lt;/span>&lt;span class="nb">+++&lt;/span>&lt;span class="nt">.&lt;/span>&lt;span class="nv">&amp;gt;&amp;gt;&lt;/span>&lt;span class="nt">.&lt;/span>&lt;span class="nv">&amp;lt;&lt;/span>&lt;span class="nb">-&lt;/span>&lt;span class="nt">.&lt;/span>&lt;span class="nv">&amp;lt;&lt;/span>&lt;span class="nt">.&lt;/span>&lt;span class="nb">+++&lt;/span>&lt;span class="nt">.&lt;/span>&lt;span class="nb">------&lt;/span>&lt;span class="nt">.&lt;/span>&lt;span class="nb">--------&lt;/span>&lt;span class="nt">.&lt;/span>&lt;span class="nv">&amp;gt;&amp;gt;&lt;/span>&lt;span class="nb">+&lt;/span>&lt;span class="nt">.&lt;/span>&lt;span class="nv">&amp;gt;&lt;/span>&lt;span class="nb">++&lt;/span>&lt;span class="nt">.&lt;/span>&lt;span class="c">
&lt;/span>&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h2 id="gobf-overview">GOBF Overview&lt;/h2>
&lt;p>Introducing GOBF, an interpreter/optimizer/compiler/code_generator for the BF language.
It has two primary modes of operation, interpreting/running (as-is) and
converting BF to optimized Go code.&lt;/p>
&lt;h3 id="interpreting">Interpreting&lt;/h3>
&lt;p>Interpreting and running was the first mode of operation that really just
served to solidify my understanding of the BF language.
It simply sets up a virtual environment for the BF program and acts on each
syntax item as they come. There is no optimization here.&lt;/p>
&lt;h3 id="optimizing--compiling">Optimizing / Compiling&lt;/h3>
&lt;p>Next, I wanted to focus on how I would be able to generate super fast
binaries from my BF programs.
I considered lots of approaches, but the two most prominent ones were to
directly assemble a binary from the BF commands and convert BF to equivalent Go code.&lt;/p>
&lt;p>Directly assemble an x86 binary from the the BF commands seems like a natural
extension, since BF forces the programmer to act somewhat like a state machine.
The downside to this approach is that it would lack portability and would loose
out on further architectural optimizations that are found in modern compilers.&lt;/p>
&lt;p>I ultimately chose the ladder solution, where I convert the BF commands into
equivalent Go code.
Although it seems like a bulky implementation strategy, the program&amp;rsquo;s
functionality is quite limited and we gain the builtin compiler inlining.&lt;/p>
&lt;p>I have designed GOBF to parse BF programs and generate a internal
intermediate representation(IR) that resembles a tree.
The next major observation that BF contains lots of repetitive actions,
like &lt;code>++++++++&lt;/code>, which increments the local accumulator eight times, only to
save the value &lt;code>8&lt;/code>.
These repetitive actions can easily be smashed into a single operation, which
can yield massive speedups.
The GOBF optimizer traverses the IR tree and coalesces these
repetitive actions into a more descriptive single action.&lt;/p>
&lt;p>When the optimizer finishes, GOBF generates Go code from the IR
and optionally compiles it.&lt;/p>
&lt;h2 id="benchmarking">Benchmarking&lt;/h2>
&lt;p>I ran some of the typical BF programs you can find on the internet.&lt;/p>
&lt;table>
&lt;thead>
&lt;tr>
&lt;th>BF Program&lt;/th>
&lt;th>Run Time&lt;/th>
&lt;/tr>
&lt;/thead>
&lt;tbody>
&lt;tr>
&lt;td>mandelbrot.b&lt;/td>
&lt;td>8.162s&lt;/td>
&lt;/tr>
&lt;tr>
&lt;td>hanoi.b&lt;/td>
&lt;td>5.401s&lt;/td>
&lt;/tr>
&lt;tr>
&lt;td>helloworld.b&lt;/td>
&lt;td>0.003s&lt;/td>
&lt;/tr>
&lt;/tbody>
&lt;/table>
&lt;div class="alert alert-note">
&lt;div>
Running on an Intel(R) Xeon(R) CPU E3-1505M v5 @ 2.80GHz
&lt;/div>
&lt;/div>
&lt;h2 id="future-work">Future Work&lt;/h2>
&lt;p>I would like to create a reverse code generator that takes a high-level
language, such as Go, and generates BF.&lt;/p>
&lt;h3 id="links">Links&lt;/h3>
&lt;p>&lt;a href="https://github.com/linux4life798/gobf" target="_blank" rel="noopener">GOBF on Github&lt;/a>&lt;/p></description></item><item><title>dproto</title><link>https://new.craighesling.com/project/dproto/</link><pubDate>Sun, 03 Dec 2017 07:46:59 -0500</pubDate><guid>https://new.craighesling.com/project/dproto/</guid><description>&lt;p>
&lt;figure >
&lt;div class="d-flex justify-content-center">
&lt;div class="w-100" >&lt;img src="https://new.craighesling.com/img/dproto_initialization.jpg" alt="Basic dproto usage" loading="lazy" data-zoomable />&lt;/div>
&lt;/div>&lt;/figure>
&lt;/p>
&lt;p>An on the fly Google protobuf decoder/encoder library.&lt;/p>
&lt;h2 id="summary">Summary&lt;/h2>
&lt;p>This library allows you to use Protobufs (Google Protocol Buffers) without needing to
generate protobuf code and compile it into your project.
This means you don&amp;rsquo;t need to compile .proto files.&lt;/p>
&lt;p>This library is designed for marshaling and unmarshalling protobufs in a &lt;em>dynamic&lt;/em> way.
It is designed to interface with any standard protobuf library and is tested against
the official protobuf C++ and Golang bindings, in addition to the C
&lt;a href="https://github.com/nanopb/nanopb" target="_blank" rel="noopener">Nanopdb&lt;/a> library.&lt;/p>
&lt;p>The intent of this library was to allow creating long running services that can
interpret and interface with clients using new/unknown protobuf messages.&lt;/p>
&lt;p>The basic idea is that you construct a &lt;code>ProtoFieldMap&lt;/code> that contains any protobuf
field number to protobuf type associations you are interested in and then you
call &lt;code>DecodeBUffer&lt;/code> on the protobuf payload.
&lt;code>DecodeBuffer&lt;/code> returns an array of &lt;code>FieldValue&lt;/code>s that it decoded from the payload.
Each &lt;code>FieldValue&lt;/code> specifies the protobuf field number and value decoded as a Golang
primitive(must be inside a &lt;code>interface{}&lt;/code>).&lt;/p>
&lt;h2 id="example-usage">Example Usage&lt;/h2>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-go" data-lang="go">&lt;span class="line">&lt;span class="cl">&lt;span class="c1">// Encodes and Decodes a protobuf buffer that would interface with
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">// a .proto file message containing &amp;#34;bool status =1;&amp;#34; and
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">// &amp;#34;int64 intensity = 2;&amp;#34;.
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span>&lt;span class="kd">func&lt;/span> &lt;span class="nf">ExampleNewProtoFieldMap&lt;/span>&lt;span class="p">()&lt;/span> &lt;span class="p">{&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="c1">// Setup the ProtoFieldMap to interface with the
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="c1">// following .proto file:
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="c1">// message LightStatus {
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="c1">// bool status = 1;
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="c1">// int64 intensity = 2;
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="c1">// }
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="c1">// Setup a FieldMap that holds the type-fieldnumber association
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="c1">// This is effectively the information held in a .proto file
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="nx">fm&lt;/span> &lt;span class="o">:=&lt;/span> &lt;span class="nx">dproto&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nf">NewProtoFieldMap&lt;/span>&lt;span class="p">()&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="c1">// Add Protobuf bool as field 1 (&amp;#34;bool status = 1;&amp;#34;)
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="k">if&lt;/span> &lt;span class="p">!&lt;/span>&lt;span class="nx">fm&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nf">Add&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="mi">1&lt;/span>&lt;span class="p">,&lt;/span> &lt;span class="nx">descriptor&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nx">FieldDescriptorProto_TYPE_BOOL&lt;/span>&lt;span class="p">)&lt;/span> &lt;span class="p">{&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="nb">panic&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="s">&amp;#34;Failed to add bool field 1&amp;#34;&lt;/span>&lt;span class="p">)&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="p">}&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="c1">// Add Protobuf int64 as field 2 (&amp;#34;int64 intensity = 2;&amp;#34;)
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="k">if&lt;/span> &lt;span class="p">!&lt;/span>&lt;span class="nx">fm&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nf">Add&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="mi">2&lt;/span>&lt;span class="p">,&lt;/span> &lt;span class="nx">descriptor&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nx">FieldDescriptorProto_TYPE_INT64&lt;/span>&lt;span class="p">)&lt;/span> &lt;span class="p">{&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="nb">panic&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="s">&amp;#34;Failed to add bool field 1&amp;#34;&lt;/span>&lt;span class="p">)&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="p">}&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="c1">// Provide some values for our &amp;#34;status&amp;#34; and &amp;#34;intensity&amp;#34;
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="nx">values&lt;/span> &lt;span class="o">:=&lt;/span> &lt;span class="p">[]&lt;/span>&lt;span class="nx">dproto&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nx">FieldValue&lt;/span>&lt;span class="p">{&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="nx">dproto&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nx">FieldValue&lt;/span>&lt;span class="p">{&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="nx">Field&lt;/span>&lt;span class="p">:&lt;/span> &lt;span class="mi">1&lt;/span>&lt;span class="p">,&lt;/span> &lt;span class="c1">// status field number
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="nx">Value&lt;/span>&lt;span class="p">:&lt;/span> &lt;span class="nb">bool&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="kc">true&lt;/span>&lt;span class="p">),&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="p">},&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="nx">dproto&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nx">FieldValue&lt;/span>&lt;span class="p">{&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="nx">Field&lt;/span>&lt;span class="p">:&lt;/span> &lt;span class="mi">2&lt;/span>&lt;span class="p">,&lt;/span> &lt;span class="c1">// intensity field number
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="nx">Value&lt;/span>&lt;span class="p">:&lt;/span> &lt;span class="nb">int64&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="mi">10&lt;/span>&lt;span class="p">),&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="p">},&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="p">}&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="c1">// Encode out values into the protobuf message described in fm
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="nx">bytes&lt;/span>&lt;span class="p">,&lt;/span> &lt;span class="nx">err&lt;/span> &lt;span class="o">:=&lt;/span> &lt;span class="nx">fm&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nf">EncodeBuffer&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="nx">values&lt;/span>&lt;span class="p">)&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="k">if&lt;/span> &lt;span class="nx">err&lt;/span> &lt;span class="o">!=&lt;/span> &lt;span class="kc">nil&lt;/span> &lt;span class="p">{&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="nb">panic&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="s">&amp;#34;Error Encoding: &amp;#34;&lt;/span> &lt;span class="o">+&lt;/span> &lt;span class="nx">err&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nf">Error&lt;/span>&lt;span class="p">())&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="p">}&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="nx">fmt&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nf">Printf&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="s">&amp;#34;ProtobufBinary: [ %# x ]\n&amp;#34;&lt;/span>&lt;span class="p">,&lt;/span> &lt;span class="nx">bytes&lt;/span>&lt;span class="p">)&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="c1">// Decode all protobuf fields
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="nx">decodedValues&lt;/span>&lt;span class="p">,&lt;/span> &lt;span class="nx">err&lt;/span> &lt;span class="o">:=&lt;/span> &lt;span class="nx">fm&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nf">DecodeBuffer&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="nx">bytes&lt;/span>&lt;span class="p">)&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="k">if&lt;/span> &lt;span class="nx">err&lt;/span> &lt;span class="o">!=&lt;/span> &lt;span class="kc">nil&lt;/span> &lt;span class="p">{&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="nb">panic&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="s">&amp;#34;Error Decoding: &amp;#34;&lt;/span> &lt;span class="o">+&lt;/span> &lt;span class="nx">err&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nf">Error&lt;/span>&lt;span class="p">())&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="p">}&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="k">for&lt;/span> &lt;span class="nx">_&lt;/span>&lt;span class="p">,&lt;/span> &lt;span class="nx">val&lt;/span> &lt;span class="o">:=&lt;/span> &lt;span class="k">range&lt;/span> &lt;span class="nx">decodedValues&lt;/span> &lt;span class="p">{&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="nx">fmt&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nf">Printf&lt;/span>&lt;span class="p">(&lt;/span>&lt;span class="s">&amp;#34;%v: %v\n&amp;#34;&lt;/span>&lt;span class="p">,&lt;/span> &lt;span class="nx">val&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nx">Field&lt;/span>&lt;span class="p">,&lt;/span> &lt;span class="nx">val&lt;/span>&lt;span class="p">.&lt;/span>&lt;span class="nx">Value&lt;/span>&lt;span class="p">)&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="p">}&lt;/span>
&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl"> &lt;span class="c1">// Unordered output:
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="c1">// ProtobufBinary: [ 0x08 0x01 0x10 0x0a ]
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="c1">// 1: true
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span> &lt;span class="c1">// 2: 10
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span>&lt;span class="p">}&lt;/span>
&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;h2 id="links">Links&lt;/h2>
&lt;ul>
&lt;li>&lt;a href="https://github.com/linux4life798/dproto" target="_blank" rel="noopener">Dproto on Github&lt;/a>&lt;/li>
&lt;li>&lt;a href="https://developers.google.com/protocol-buffers/" target="_blank" rel="noopener">Google Protobufs&lt;/a>&lt;/li>
&lt;/ul></description></item><item><title>Easybits Serialization Service</title><link>https://new.craighesling.com/project/easybits/</link><pubDate>Sun, 03 Dec 2017 07:46:59 -0500</pubDate><guid>https://new.craighesling.com/project/easybits/</guid><description>&lt;p>
&lt;figure >
&lt;div class="d-flex justify-content-center">
&lt;div class="w-100" >&lt;img src="https://new.craighesling.com/img/easybits_config_example3.png" alt="Example Easybits device configuration" loading="lazy" data-zoomable />&lt;/div>
&lt;/div>&lt;/figure>
&lt;/p>
&lt;h2 id="summary">Summary&lt;/h2>
&lt;p>Easybits is an on-the-fly Google protobuf stream decoder/encoder for
&lt;a href="https://new.craighesling.com/project/openchirp/">OpenChirp&lt;/a>.
This service is one of the core services that an embedded device may
need in it&amp;rsquo;s OpenChirp data pipeline.&lt;/p>
&lt;p>The idea is that your device would use Google Protobufs to serialize
(and deserialize) it&amp;rsquo;s data and sends it to OpenChirp.
The Easybits service is then invoked, which deserializes your data and
publishes human readable values back to OpenChirp.&lt;/p>
&lt;p>Easybits just needs the user to describe what protobuf types were declared
and where to place the data.&lt;/p>
&lt;h2 id="how-it-works">How it works&lt;/h2>
&lt;p>Google Protobufs are great for creating compact serialized data packets for
typical sensor values.&lt;/p>
&lt;p>Protobufs requires you to create a &lt;code>.proto&lt;/code> file that
describes what data you intend to send back and forth. It then compiles this
&lt;code>.proto&lt;/code> file into a set of language specific interface files, which
containing functions and objects to represent and aggregate your data.&lt;/p>
&lt;blockquote>
&lt;p>Here is an example &lt;code>.proto&lt;/code> file description for a smart light bulb.&lt;/p>
&lt;/blockquote>
&lt;div class="highlight">&lt;pre tabindex="0" class="chroma">&lt;code class="language-protobuf" data-lang="protobuf">&lt;span class="line">&lt;span class="cl">&lt;span class="c1">// SmartBulb.proto
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="c1">&lt;/span>&lt;span class="n">syntax&lt;/span> &lt;span class="o">=&lt;/span> &lt;span class="s">&amp;#34;proto3&amp;#34;&lt;/span>&lt;span class="p">;&lt;/span>&lt;span class="err">
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="err">&lt;/span>&lt;span class="kd">message&lt;/span> &lt;span class="nc">LightStatus&lt;/span> &lt;span class="p">{&lt;/span>&lt;span class="err">
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="err">&lt;/span> &lt;span class="kt">bool&lt;/span> &lt;span class="n">status&lt;/span> &lt;span class="o">=&lt;/span> &lt;span class="mi">1&lt;/span>&lt;span class="p">;&lt;/span>&lt;span class="err">
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="err">&lt;/span> &lt;span class="kt">int64&lt;/span> &lt;span class="n">intensity&lt;/span> &lt;span class="o">=&lt;/span> &lt;span class="mi">2&lt;/span>&lt;span class="p">;&lt;/span>&lt;span class="err">
&lt;/span>&lt;/span>&lt;/span>&lt;span class="line">&lt;span class="cl">&lt;span class="err">&lt;/span>&lt;span class="p">}&lt;/span>&lt;span class="err">
&lt;/span>&lt;/span>&lt;/span>&lt;/code>&lt;/pre>&lt;/div>&lt;p>Due to this native language integration, protobufs are easy for end users to
pack up and send data messages, but it is non-trivial to create long running
services that can interpret all possible custom protobuf messages, without
recompilation.&lt;/p>
&lt;p>To get around the Protobuf constraint of recompiling for every new protobuf
message, Easybits uses &lt;a href="https://new.craighesling.com/project/dproto/">dproto&lt;/a> to adapt to new user
described messages, without even restarting.&lt;/p>
&lt;h2 id="links">Links&lt;/h2>
&lt;p>&lt;a href="https://github.com/OpenChirp/easybits-service" target="_blank" rel="noopener">Easybits on Github&lt;/a>&lt;/p></description></item><item><title>OpenChirp</title><link>https://new.craighesling.com/project/openchirp/</link><pubDate>Sun, 03 Dec 2017 07:46:59 -0500</pubDate><guid>https://new.craighesling.com/project/openchirp/</guid><description>
&lt;div class="gallery">
&lt;a data-fancybox="gallery-main" data-caption="Gateway 1" href="https://new.craighesling.com/project/openchirp/GSIA_GW_hu8af566d35e172a1448aad7b439b9ad98_1089158_1920x0_resize_q75_lanczos.jpg">
&lt;img alt="GSIA_GW.jpg" src="https://new.craighesling.com/project/openchirp/GSIA_GW_hu8af566d35e172a1448aad7b439b9ad98_1089158_1920x0_resize_q15_lanczos.jpg">
&lt;/a>
&lt;a data-fancybox="gallery-main" data-caption="OpenChirp Logo" href="https://new.craighesling.com/project/openchirp/OCStickerDark.svg">
&lt;img alt="OCStickerDark.svg" src="https://new.craighesling.com/project/openchirp/OCStickerDark.svg">
&lt;/a>
&lt;a data-fancybox="gallery-main" data-caption="A gateway up-close" href="https://new.craighesling.com/project/openchirp/OnGround_Wean_GW_hu2ae3da5a428bf1047e2250f9a743cb87_3037040_3024x0_resize_q75_lanczos.jpg">
&lt;img alt="OnGround_Wean_GW.jpg" src="https://new.craighesling.com/project/openchirp/OnGround_Wean_GW_hu2ae3da5a428bf1047e2250f9a743cb87_3037040_3024x0_resize_q15_lanczos.jpg">
&lt;/a>
&lt;a data-fancybox="gallery-main" data-caption="Gateway 2" href="https://new.craighesling.com/project/openchirp/SouthCraig_GW_hu3c1fbb5776c28c3856df7474a5b76c50_1314334_3120x0_resize_q75_lanczos.jpg">
&lt;img alt="SouthCraig_GW.jpg" src="https://new.craighesling.com/project/openchirp/SouthCraig_GW_hu3c1fbb5776c28c3856df7474a5b76c50_1314334_3120x0_resize_q15_lanczos.jpg">
&lt;/a>
&lt;a data-fancybox="gallery-main" data-caption="Gateway 3" href="https://new.craighesling.com/project/openchirp/Wean_GW_hu9b7bdac86ca23d1aa5a7028c80665157_715377_3120x0_resize_q75_lanczos.jpg">
&lt;img alt="Wean_GW.jpg" src="https://new.craighesling.com/project/openchirp/Wean_GW_hu9b7bdac86ca23d1aa5a7028c80665157_715377_3120x0_resize_q15_lanczos.jpg">
&lt;/a>
&lt;/div>
&lt;h2 id="summary">Summary&lt;/h2>
&lt;p>We are creating a community-driven low-power wireless connectivity solution for
IoT.&lt;/p>
&lt;h2 id="my-contributions">My Contributions&lt;/h2>
&lt;ul>
&lt;li>Designed, built, and installed outdoor gateways&lt;/li>
&lt;li>Created custom Debian packages for gateway software and configuration - &lt;a href="https://github.com/OpenChirp/ocgw" target="_blank" rel="noopener">ocgw&lt;/a>&lt;/li>
&lt;li>Created gateway system monitoring service - &lt;a href="https://github.com/OpenChirp/sysmonitor-device" target="_blank" rel="noopener">SysMonitor Device&lt;/a>&lt;/li>
&lt;li>Created the Golang framework for Users, Devices, and Services - &lt;a href="https://github.com/OpenChirp/framework" target="_blank" rel="noopener">framework&lt;/a> and &lt;a href="https://github.com/OpenChirp/example-service" target="_blank" rel="noopener">Example Service&lt;/a>&lt;/li>
&lt;li>Created the LoRaWAN integration service&lt;/li>
&lt;li>Created data serialization/deserialization services - &lt;a href="https://github.com/OpenChirp/bytetranslator-service" target="_blank" rel="noopener">ByteTranslator Service&lt;/a> and &lt;a href="https://new.craighesling.com/project/easybits">Easybits Service&lt;/a>&lt;/li>
&lt;li>Created prototype trigger service - &lt;a href="https://github.com/OpenChirp/trigger-service" target="_blank" rel="noopener">Trigger Service&lt;/a>&lt;/li>
&lt;li>Designed and built ultra low-power LoRaWAN client devices - &lt;a href="https://new.craighesling.com/project/lorabug">The LoRaBug&lt;/a>&lt;/li>
&lt;li>Created the hardware abstraction layer and adapted the necessary firmware stacks for the LoRaBug - &lt;a href="https://new.craighesling.com/project/lorabug/#software">LoRaBug Software&lt;/a>&lt;/li>
&lt;li>Created serial bootloader tool to flash the LoRaBug over micro USB - &lt;a href="https://new.craighesling.com/post/cc2538-cc26xx-bootloader/">ccbootutil&lt;/a>&lt;/li>
&lt;/ul>
&lt;p>Checkout the &lt;a href="http://OpenChirp.io" target="_blank" rel="noopener">OpenChirp.io Website&lt;/a>&lt;/p></description></item><item><title>The GridBallast Controller</title><link>https://new.craighesling.com/project/gridballast/gridballast/</link><pubDate>Sun, 03 Dec 2017 07:46:59 -0500</pubDate><guid>https://new.craighesling.com/project/gridballast/gridballast/</guid><description>&lt;p>FIXME - Add the gallery line back here.&lt;/p>
&lt;h2 id="summary">Summary&lt;/h2>
&lt;p>This is a modular demand response controller for household or commercial
appliances that tend to consume a lot of power.
The original goal was to intelligently control water heaters.&lt;/p>
&lt;p>Water heaters tax the power grid heavily during peek times
(morning and afternoon), when people are using the most hot water.
These spikes in power consumption require power providers to plan ahead
and preemptively start up temporary power plant that may not meet the
typical efficiency and cleanliness standards.&lt;/p>
&lt;p>Fortunately, water heaters store enough hot water
for most normal household tasks, including taking a shower. Whether they turn
on during your morning shower or not, makes no noticeable difference.
Unfortunately, hot water heaters are controlled by mechanical switches
that activate the water heaters when the internal water temperature drops
below a certain point. This causes the heaters to activate during events like
your shower in the morning, when it might not be necessary.
If the water heater was to delay it&amp;rsquo;s activation to some random time during
the middle of the day, we could alleviate this peak demand issue.
This controller is designed to monitor the water heater vitals, observe it&amp;rsquo;s usage patterns, and intelligently control it&amp;rsquo;s activation.&lt;/p>
&lt;h2 id="schematic-and-board">Schematic and Board&lt;/h2>
&lt;h3 id="the-controller">The Controller&lt;/h3>
&lt;a href="https://cdn.rawgit.com/WiseLabCMU/gridballast/1d7e381e/Hardware/Controller/Info/ControllerV1.1.pdf">Download PDF&lt;/a>
&lt;p>A preview of the PDF should appear below. If it does not show up soon, please refresh the page.&lt;/p>
&lt;iframe src="https://docs.google.com/gview?url=https%3a%2f%2fcdn.rawgit.com%2fWiseLabCMU%2fgridballast%2f1d7e381e%2fHardware%2fController%2fInfo%2fControllerV1.1.pdf&amp;embedded=true" style="width:100%; height:600px;" frameborder="0">
This browser does not support PDFs. Please download the PDF to view it: &lt;a href="https://cdn.rawgit.com/WiseLabCMU/gridballast/1d7e381e/Hardware/Controller/Info/ControllerV1.1.pdf">Download PDF&lt;/a>
&lt;/iframe>
&lt;h3 id="the-cta2045-adapter">The CTA2045 Adapter&lt;/h3>
&lt;a href="https://cdn.rawgit.com/WiseLabCMU/gridballast/1d7e381e/Hardware/CTA2045/Info/CTA2045v1.pdf">Download PDF&lt;/a>
&lt;p>A preview of the PDF should appear below. If it does not show up soon, please refresh the page.&lt;/p>
&lt;iframe src="https://docs.google.com/gview?url=https%3a%2f%2fcdn.rawgit.com%2fWiseLabCMU%2fgridballast%2f1d7e381e%2fHardware%2fCTA2045%2fInfo%2fCTA2045v1.pdf&amp;embedded=true" style="width:100%; height:600px;" frameborder="0">
This browser does not support PDFs. Please download the PDF to view it: &lt;a href="https://cdn.rawgit.com/WiseLabCMU/gridballast/1d7e381e/Hardware/CTA2045/Info/CTA2045v1.pdf">Download PDF&lt;/a>
&lt;/iframe>
&lt;h2 id="simulation">Simulation&lt;/h2>
&lt;p>This board required some custom analog design.
I simulated some of the more complex circuits in &lt;a href="http://www.linear.com/designtools/software/#LTspice" target="_blank" rel="noopener">LTspice&lt;/a>.
The circuits and simulation are shown on the GitHub &lt;a href="https://github.com/WiseLabCMU/gridballast/tree/master/Hardware/Controller/Info/Simulations" target="_blank" rel="noopener">Simulations Page&lt;/a>.&lt;/p>
&lt;h2 id="links">Links&lt;/h2>
&lt;ul>
&lt;li>&lt;a href="https://github.com/WiseLabCMU/gridballast/tree/master/Hardware/Controller/Info/Simulations" target="_blank" rel="noopener">Simulations&lt;/a>&lt;/li>
&lt;li>&lt;a href="https://github.com/WiseLabCMU/gridballast" target="_blank" rel="noopener">GridBallast on Github&lt;/a>&lt;/li>
&lt;li>&lt;a href="https://sites.google.com/view/gridballast/home" target="_blank" rel="noopener">GridBallast Website&lt;/a>&lt;/li>
&lt;/ul></description></item><item><title>System Monitor Device (for OpenChirp)</title><link>https://new.craighesling.com/post/sysmonitor-device/</link><pubDate>Mon, 06 Nov 2017 00:00:00 +0000</pubDate><guid>https://new.craighesling.com/post/sysmonitor-device/</guid><description>&lt;h2 id="summary">Summary&lt;/h2>
&lt;h2 id="how-it-works">How it works&lt;/h2>
&lt;h2 id="links">Links&lt;/h2>
&lt;p>&lt;a href="https://github.com/OpenChirp/sysmonitor-device" target="_blank" rel="noopener">sysmonitor-device on Github&lt;/a>&lt;/p></description></item><item><title>The LoRaBug</title><link>https://new.craighesling.com/project/lorabug/</link><pubDate>Sat, 03 Dec 2016 07:46:59 -0500</pubDate><guid>https://new.craighesling.com/project/lorabug/</guid><description>
&lt;div class="gallery">
&lt;a data-fancybox="gallery-main" data-caption="Fully built LoRaBugs with the environmental sensor board v1" href="https://new.craighesling.com/project/lorabug/Fully_Enclosed_hue365703db40798d641f7c145346ab307_1531989_4160x0_resize_q75_lanczos.jpg">
&lt;img alt="Fully_Enclosed.jpg" src="https://new.craighesling.com/project/lorabug/Fully_Enclosed_hue365703db40798d641f7c145346ab307_1531989_4160x0_resize_q15_lanczos.jpg">
&lt;/a>
&lt;a data-fancybox="gallery-main" data-caption="Altium 3D rendering" href="https://new.craighesling.com/project/lorabug/LoRaBugBoardV3.1_3D_hu78434072f4b03f97a69451697241d2b9_446129_1030x0_resize_q75_lanczos_3.png">
&lt;img alt="LoRaBugBoardV3.1_3D.png" src="https://new.craighesling.com/project/lorabug/LoRaBugBoardV3.1_3D_hu78434072f4b03f97a69451697241d2b9_446129_1030x0_resize_q20_lanczos_3.png">
&lt;/a>
&lt;a data-fancybox="gallery-main" data-caption="The extremely low power consumption of the LoRaBug while sleep" href="https://new.craighesling.com/project/lorabug/LoRaBug_Exteme_Sleep_hua80e3be80af02d69f9ee4704be305725_1356728_4160x0_resize_q75_lanczos.jpg">
&lt;img alt="LoRaBug_Exteme_Sleep.jpg" src="https://new.craighesling.com/project/lorabug/LoRaBug_Exteme_Sleep_hua80e3be80af02d69f9ee4704be305725_1356728_4160x0_resize_q15_lanczos.jpg">
&lt;/a>
&lt;a data-fancybox="gallery-main" data-caption="The LoRaBug controlling LED accent lighting" href="https://new.craighesling.com/project/lorabug/LoRaBug_LED_Controller_hu1b844f0a393381480f4920e09890ee47_1248524_3088x0_resize_q75_lanczos.jpg">
&lt;img alt="LoRaBug_LED_Controller.jpg" src="https://new.craighesling.com/project/lorabug/LoRaBug_LED_Controller_hu1b844f0a393381480f4920e09890ee47_1248524_3088x0_resize_q15_lanczos.jpg">
&lt;/a>
&lt;/div>
&lt;h2 id="summary">Summary&lt;/h2>
&lt;p>The LoRaBug is a general purpose low-power sensor platform.
It tightly integrates an ARM Cortex M3 based MCU, BLE, and a LoRa radio.&lt;/p>
&lt;p>Checkout the &lt;a href="https://github.com/OpenChirp/LoRaBug" target="_blank" rel="noopener">Github repository&lt;/a> for more
detail.&lt;/p>
&lt;h2 id="key-features">Key Features&lt;/h2>
&lt;ul>
&lt;li>TI CC2650 MCU/Transciever - ARM Cortex M3, Bluetooth+BLE, and 2.4GHz 802.15.4&lt;/li>
&lt;li>Semtech SX1276 radio - 137MHz to 1020MHz supporting LoRa, FSK, GFSK, MSK, GMSK, and OOK&lt;/li>
&lt;li>Micro USB - Bootloading and Console&lt;/li>
&lt;li>Onboard 500mA 3.3V regulator&lt;/li>
&lt;/ul>
&lt;h2 id="software">Software&lt;/h2>
&lt;ul>
&lt;li>I have adapted the HAL of the official LoRaWAN stack for the CC2650 with TI-RTOS - &lt;a href="https://github.com/OpenChirp/LoRaMac-node/tree/lorabug" target="_blank" rel="noopener">LoRaWAN MAC&lt;/a>&lt;/li>
&lt;li>A spinoff from my example firmware can be found - &lt;a href="https://github.com/OpenChirp/LoRaBug_Firmware" target="_blank" rel="noopener">LoRaBug_Firmware&lt;/a>.&lt;/li>
&lt;li>I have created a cross-platform serial bootloader tool that allows you to flash the LoRaBug using just a micro usb cable - &lt;a href="https://new.craighesling.com/post/cc2538-cc26xx-bootloader/">ccbootutil&lt;/a>&lt;/li>
&lt;/ul>
&lt;h2 id="schematic-and-board">Schematic and Board&lt;/h2>
&lt;a href="https://cdn.rawgit.com/OpenChirp/LoRaBug/ec3e2fa6/Info/LoRaBugBoardV3.1.pdf">Download PDF&lt;/a>
&lt;p>A preview of the PDF should appear below. If it does not show up soon, please refresh the page.&lt;/p>
&lt;iframe src="https://docs.google.com/gview?url=https%3a%2f%2fcdn.rawgit.com%2fOpenChirp%2fLoRaBug%2fec3e2fa6%2fInfo%2fLoRaBugBoardV3.1.pdf&amp;embedded=true" style="width:100%; height:600px;" frameborder="0">
This browser does not support PDFs. Please download the PDF to view it: &lt;a href="https://cdn.rawgit.com/OpenChirp/LoRaBug/ec3e2fa6/Info/LoRaBugBoardV3.1.pdf">Download PDF&lt;/a>
&lt;/iframe></description></item></channel></rss>