<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
  <channel>
    <title>Nodejs on bramp.net</title>
    <link>https://blog.bramp.net/</link>
    <description>Recent content in Nodejs on bramp.net</description>
    <generator>Hugo -- gohugo.io</generator>
    <language>en-GB</language>
    <lastBuildDate>Sun, 21 Dec 2014 00:00:00 +0000</lastBuildDate>
    <atom:link href="https://blog.bramp.net/tags/nodejs/" rel="self" type="application/rss+xml" />
    
    <item>
      <title>NationJS talk on NodeJs now on Vimeo</title>
      <link>https://blog.bramp.net/post/2014/12/21/nationjs-talk-on-nodejs-now-on-vimeo/</link>
      <pubDate>Sun, 21 Dec 2014 00:00:00 +0000</pubDate>
      
      <guid>https://blog.bramp.net/post/2014/12/21/nationjs-talk-on-nodejs-now-on-vimeo/</guid>
      <description><p>It&rsquo;s a bit late, but finally my NationJS talk is on Vimeo:</p>
<iframe src="//player.vimeo.com/video/93754470" width="500" height="281" frameborder="0" webkitallowfullscreen mozallowfullscreen allowfullscreen></iframe><br>
[Node.js + WebSockets + Wiimote = Fun][1] from Andrew Brampton on [Vimeo][2].
<p>Slides here: <a href="https://bramp.github.io/nodewii-talk/">https://bramp.github.io/nodewii-talk/</a></p>
</description>
    </item>
    
    <item>
      <title>Invalid IP range checking defeated by DNS</title>
      <link>https://blog.bramp.net/post/2012/11/27/invalid-ip-range-checking-defeated-by-dns/</link>
      <pubDate>Tue, 27 Nov 2012 00:00:00 +0000</pubDate>
      
      <guid>https://blog.bramp.net/post/2012/11/27/invalid-ip-range-checking-defeated-by-dns/</guid>
      <description><p>I’ve seen a particular kind of vulnerability in a few different applications but I’m not sure of an appropriate name for it. So I thought I’d write about it, and informally call it the “DNS defeated IP address check”. Basically, if you have an application that can be used as a proxy, or can be instructed to make web request, you don’t want it fetching files from internal services.</p>
<p>For example, there is a simple proxy called <a href="https://github.com/atmos/camo">Camo</a>, which is used to fetch third party images when you need to display them on a SSL secure site. (Read more about Camo on the <a href="https://github.com/blog/743-sidejack-prevention-phase-3-ssl-proxied-assets">GitHub blog</a>).</p>
<p>This kind of application can be incorrectly setup such that the application has access to internal servers and resources that wouldn’t normally be exposed to the Internet. This make the proxy application a good way a hacker could gain information about a private network. However Camo tries to address this issue by forbidding URLs that contain private IP addresses. It does a check like so:</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-coffeescript" data-lang="coffeescript"><span class="line"><span class="cl"><span class="nv">RESTRICTED_IPS = </span><span class="sr">/^((10\.)|(127\.)|(169\.254)|(192\.168)|(172\.((1[6-9])|(2[0-9])|(3[0-1]))))/</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="k">if</span> <span class="p">(</span><span class="nx">url</span><span class="p">.</span><span class="nx">host</span><span class="p">.</span><span class="nx">match</span><span class="p">(</span><span class="nx">RESTRICTED_IPS</span><span class="p">))</span>
</span></span><span class="line"><span class="cl">  <span class="k">return</span> <span class="nx">four_oh_four</span><span class="p">(</span><span class="nx">resp</span><span class="p">,</span> <span class="s">&#34;Hitting excluded hostnames&#34;</span><span class="p">)</span>
</span></span></code></pre></div><p>This code (written for <a href="http://nodejs.org/">Node.js</a> in <a href="http://coffeescript.org/">CoffeeScript</a>) is taking a <a href="http://nodejs.org/api/url.html">url object</a> and checking the hostname doesn’t match a restricted address. This works great against URLs such as <a href="http://127.0.0.1/">http://127.0.0.1/</a>, or <a href="http://10.0.0.1/">http://10.0.0.1/</a>, however this check can easily be defeated. If you create a domain name, such as localhost.bramp.net, which resolves to 127.0.0.1, and ask the proxy to fetch <a href="http://localhost.bramp.net/">http://localhost.bramp.net/</a>, then it won’t be caught by that check. Now the proxy will continue to try and fetch a resource from 127.0.0.1.</p>
<p>The solution to this problem is to do that IP address check <strong>after</strong> the DNS name has been resolved. This can also be problematic if you use a standard library for making web requests, as they will do the DNS lookup for you, and don’t give you the fine grain control you need. For example, I’ve seen this be a problem for a Java application using the <a href="http://hc.apache.org/httpclient-3.x/">Apache HTTP Client</a>.</p>
<p>One might naively assume they could do a DNS check, and then hand the processing to a HTTP library to make the actual request. The issue here is that the DNS record the HTTP library uses might not be the same as the one you checked against with the DNS check. For example, many domains have multiple A records, and some DNS servers can be configured to round robin DNS records. If you can’t be sure the HTTP library will do another DNS requests, then you’d be vulnerable.</p>
<p>Luckily, in Camo’s case the fix was relatively easy (see my <a href="https://github.com/atmos/camo/pull/19">pull request</a>).</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-coffeescript" data-lang="coffeescript"><span class="line"><span class="cl"><span class="c1"># We do DNS lookup ourselves
</span></span></span><span class="line"><span class="cl"><span class="nx">Dns</span><span class="p">.</span><span class="nx">lookup</span> <span class="nx">url</span><span class="p">.</span><span class="nx">host</span><span class="p">,</span> <span class="nf">(err, address, family) -&gt;</span>
</span></span><span class="line"><span class="cl">  <span class="k">if</span> <span class="nx">address</span><span class="p">.</span><span class="nx">match</span><span class="p">(</span><span class="nx">RESTRICTED_IPS</span><span class="p">)</span>
</span></span><span class="line"><span class="cl">    <span class="k">return</span> <span class="nx">four_oh_four</span><span class="p">(</span><span class="nx">resp</span><span class="p">,</span> <span class="s">&#34;Hitting excluded hostnames&#34;</span><span class="p">)</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="c1"># We connect to the IP address, not hostname
</span></span></span><span class="line"><span class="cl">  <span class="nv">src = </span><span class="nx">Http</span><span class="p">.</span><span class="nx">createClient</span> <span class="nx">url</span><span class="p">.</span><span class="nx">port</span> <span class="o">||</span> <span class="mi">80</span><span class="p">,</span> <span class="nx">address</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="c1"># We add a host header, so the request will work
</span></span></span><span class="line"><span class="cl">  <span class="nv">headers = </span>
</span></span><span class="line"><span class="cl">    <span class="s">&#34;Host&#39; : url.host
</span></span></span><span class="line"><span class="cl"><span class="s">
</span></span></span><span class="line"><span class="cl"><span class="s">  # Boom, we make the request
</span></span></span><span class="line"><span class="cl"><span class="s">  srcReq = src.request &#39;GET&#39;, query_path, headers
</span></span></span></code></pre></div><p>The above code was simplified a little from the real code, but basically we do the DNS lookup, check the returned address is good, and then make a HTTP request to that IP address with a <code>Host:</code> header to ensure the request will work.</p>
<p>Really though, the correct solution to this is to configure a suitably paranoid firewall to stop requests from the proxy machine to anything internal. However, as with all security, the more <a href="http://en.wikipedia.org/wiki/Swiss_cheese_model">layers of protection</a> you have the better, and you should never depend on just one.</p></description>
    </item>
    
    <item>
      <title>Nodewii talk at Node DC</title>
      <link>https://blog.bramp.net/post/2012/11/14/nodewii-talk-at-node-dc/</link>
      <pubDate>Wed, 14 Nov 2012 00:00:00 +0000</pubDate>
      
      <guid>https://blog.bramp.net/post/2012/11/14/nodewii-talk-at-node-dc/</guid>
      <description><p>Last night I gave a short talk at <a href="http://nodedc.github.com/">NodeDC</a>, on how to use Node.js with a wiimote. The offical title was “Controlling Node.js with a wiimote – My experiences with developing multi-threaded nodejs addon”. I’d like to thank the NodeDC guys for arranging everything last night, it was a great night, with some great talks.</p>
<div class="text-center">
    <a href="https://bramp.github.io/nodewii-talk/">
		<img src="nodewii-talk.png" alt="" title="nodewii-talk" width="981" height="763"/>
	</a>
</div>
The slides can be found here: [https://bramp.github.io/nodewii-talk/][2]
</description>
    </item>
    
    <item>
      <title>My experiences with developing multi-threaded nodejs addon</title>
      <link>https://blog.bramp.net/post/2011/10/17/my-experiences-with-developing-multi-threaded-nodejs-addon/</link>
      <pubDate>Mon, 17 Oct 2011 00:00:00 +0000</pubDate>
      
      <guid>https://blog.bramp.net/post/2011/10/17/my-experiences-with-developing-multi-threaded-nodejs-addon/</guid>
      <description><p>I’ve been modifying an <a href="https://github.com/tbranyen/nodewii">existing nodejs extension</a>, that wraps <a href="http://abstrakraft.org/cwiid/wiki/libcwiid">libcwiid</a> (a C library written to interface with a <a href="http://en.wikipedia.org/wiki/Wii_Remote">Wiimote</a>). This extension uses polling to check if the state of the Wiimote has changed (such as a button being pressed). Libcwiid however provides a callback mechanism to be alerted as soon as a state change occurs. This has the benefit of being instantaneous, instead of at the polling interval.</p>
<p>While adapting <a href="https://github.com/bramp/nodewii">nodewii</a> to use this callback mechanism I learnt a couple of things about developing multi-threaded nodejs extensions that I thought I’d share.</p>
<h4 id="1-all-v8-operations-must-run-from-the-main-thread">1) All V8 operations must run from the main thread</h4>
<p><a href="http://nodejs.org/">Nodejs</a> uses a single thread for executing the <a href="http://code.google.com/p/v8/">V8 JavaScript engine</a>, and multiple worker threads to execute longer running non-JavaScript blocking tasks. Because V8 is not thread safe, all V8 operations must be executed from this single V8 thread. That means you are not allowed to create V8 objects, integers, strings, etc, from any other thread. If you try, race conditions happen, memory get corrupted and nodejs is likely to crash. Helpfully, nodejs does provide a mechanism to simplify using these threads:</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-c++" data-lang="c++"><span class="line"><span class="cl"><span class="n">eio_custom</span><span class="p">(</span><span class="n">eio_cb</span> <span class="n">execute</span><span class="p">,</span> <span class="kt">int</span> <span class="n">pri</span><span class="p">,</span> <span class="n">eio_cb</span> <span class="n">cb</span><span class="p">,</span> <span class="kt">void</span> <span class="o">*</span><span class="n">data</span><span class="p">);</span>
</span></span></code></pre></div><p>This function allows you to execute a blocking task in a worker thread. Once that task is finished another callback is called on the main JavaScript thread. Multiple extensions use it, and this is the basis for how nodejs provides it’s callback mechanism. Here is a very short example (adapted from <a href="https://github.com/bramp/nodewii/blob/master/src/wiimote.cc">wiimote.cc</a>) of how to use eio_custom.</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-c++" data-lang="c++"><span class="line"><span class="cl"><span class="n">Handle</span><span class="o">&amp;</span><span class="n">lt</span><span class="p">;</span><span class="n">Value</span><span class="o">&amp;</span><span class="n">gt</span><span class="p">;</span> <span class="n">WiiMote</span><span class="o">::</span><span class="n">Connect</span><span class="p">(</span><span class="k">const</span> <span class="n">Arguments</span><span class="o">&amp;</span> <span class="n">args</span><span class="p">)</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl">  <span class="n">WiiMote</span><span class="o">*</span> <span class="n">wiimote</span> <span class="o">=</span> <span class="n">ObjectWrap</span><span class="o">::</span><span class="n">Unwrap</span><span class="o">&amp;</span><span class="n">lt</span><span class="p">;</span><span class="n">WiiMote</span><span class="o">&amp;</span><span class="n">gt</span><span class="p">;(</span><span class="n">args</span><span class="p">.</span><span class="n">This</span><span class="p">());</span>
</span></span><span class="line"><span class="cl">  <span class="n">Local</span><span class="o">&amp;</span><span class="n">lt</span><span class="p">;</span><span class="n">Function</span><span class="o">&amp;</span><span class="n">gt</span><span class="p">;</span> <span class="n">callback</span><span class="p">;</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="n">HandleScope</span> <span class="n">scope</span><span class="p">;</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="c1">// Pass the arguments like you would any other method
</span></span></span><span class="line"><span class="cl">  <span class="k">if</span><span class="p">(</span><span class="n">args</span><span class="p">.</span><span class="n">Length</span><span class="p">()</span> <span class="o">==</span> <span class="mi">0</span> <span class="o">||</span> <span class="o">!</span><span class="n">args</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">IsFunction</span><span class="p">())</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl">    <span class="k">return</span> <span class="nf">ThrowException</span><span class="p">(</span>
</span></span><span class="line"><span class="cl">      <span class="n">Exception</span><span class="o">::</span><span class="n">Error</span><span class="p">(</span><span class="n">String</span><span class="o">::</span><span class="n">New</span><span class="p">(</span><span class="s">&#34;Callback is required and must be a Function.&#34;</span><span class="p">))</span>
</span></span><span class="line"><span class="cl">    <span class="p">);</span>
</span></span><span class="line"><span class="cl">  <span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="n">callback</span> <span class="o">=</span> <span class="n">Local</span><span class="o">&amp;</span><span class="n">lt</span><span class="p">;</span><span class="n">Function</span><span class="o">&amp;</span><span class="n">gt</span><span class="p">;</span><span class="o">::</span><span class="n">Cast</span><span class="p">(</span><span class="n">args</span><span class="p">[</span><span class="mi">0</span><span class="p">]);</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="c1">// Create a struct to pass into worker thread
</span></span></span><span class="line"><span class="cl">  <span class="n">connect_request</span><span class="o">*</span> <span class="n">ar</span> <span class="o">=</span> <span class="k">new</span> <span class="n">connect_request</span><span class="p">();</span>
</span></span><span class="line"><span class="cl">  <span class="n">ar</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">wiimote</span> <span class="o">=</span> <span class="n">wiimote</span><span class="p">;</span>
</span></span><span class="line"><span class="cl">  <span class="n">ar</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">callback</span> <span class="o">=</span> <span class="n">Persistent</span><span class="o">&amp;</span><span class="n">lt</span><span class="p">;</span><span class="n">Function</span><span class="o">&amp;</span><span class="n">gt</span><span class="p">;</span><span class="o">::</span><span class="n">New</span><span class="p">(</span><span class="n">callback</span><span class="p">);</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="c1">// Add a reference to the wiimote, so it isn&#39;t garbage collected between now
</span></span></span><span class="line"><span class="cl">  <span class="c1">// and the callback being run
</span></span></span><span class="line"><span class="cl">  <span class="n">wiimote</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">Ref</span><span class="p">();</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="c1">// Add reference to the EV (JavaScript) thread
</span></span></span><span class="line"><span class="cl">  <span class="n">ev_ref</span><span class="p">(</span><span class="n">EV_DEFAULT_UC</span><span class="p">);</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="c1">// Schedule the Connect function to be called.
</span></span></span><span class="line"><span class="cl">  <span class="n">eio_custom</span><span class="p">(</span><span class="n">Connect</span><span class="p">,</span> <span class="n">EIO_PRI_DEFAULT</span><span class="p">,</span> <span class="n">AfterConnect</span><span class="p">,</span> <span class="n">ar</span><span class="p">);</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="k">return</span> <span class="nf">Undefined</span><span class="p">();</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kt">int</span> <span class="n">WiiMote</span><span class="o">::</span><span class="n">Connect</span><span class="p">(</span><span class="n">eio_req</span><span class="o">*</span> <span class="n">req</span><span class="p">)</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl">  <span class="c1">// This method is running in a worker thread, and NOT the main nodejs
</span></span></span><span class="line"><span class="cl">  <span class="c1">// thread. This mean you can&#39;t use any V8 methods.
</span></span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="n">connect_request</span><span class="o">*</span> <span class="n">ar</span> <span class="o">=</span> <span class="k">static_cast</span><span class="o">&amp;</span><span class="n">lt</span><span class="p">;</span><span class="n">connect_request</span><span class="o">*</span> <span class="o">&amp;</span><span class="n">gt</span><span class="p">;(</span><span class="n">req</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">data</span><span class="p">);</span>
</span></span><span class="line"><span class="cl">  <span class="c1">// Do some work with the connect_request, and put the results back into the struct
</span></span></span><span class="line"><span class="cl">  <span class="p">...</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="k">return</span> <span class="mi">0</span><span class="p">;</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kt">int</span> <span class="n">WiiMote</span><span class="o">::</span><span class="n">AfterConnect</span><span class="p">(</span><span class="n">eio_req</span><span class="o">*</span> <span class="n">req</span><span class="p">)</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl">  <span class="c1">// Once the &#34;Connect&#34; method has finished, this method will be called on
</span></span></span><span class="line"><span class="cl">  <span class="c1">// the main nodejs thread. This means we can now use normal V8 methods.
</span></span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="n">HandleScope</span> <span class="n">scope</span><span class="p">;</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="c1">// Retrieve the info from the request
</span></span></span><span class="line"><span class="cl">  <span class="n">connect_request</span><span class="o">*</span> <span class="n">ar</span> <span class="o">=</span> <span class="k">static_cast</span><span class="o">&amp;</span><span class="n">lt</span><span class="p">;</span><span class="n">connect_request</span><span class="o">*</span> <span class="o">&amp;</span><span class="n">gt</span><span class="p">;(</span><span class="n">req</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">data</span><span class="p">);</span>
</span></span><span class="line"><span class="cl">  <span class="n">WiiMote</span> <span class="o">*</span> <span class="n">wiimote</span> <span class="o">=</span> <span class="n">ar</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">wiimote</span><span class="p">;</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="c1">// We no longer need a reference to the follow things
</span></span></span><span class="line"><span class="cl">  <span class="n">ev_ref</span><span class="p">(</span><span class="n">EV_DEFAULT_UC</span><span class="p">);</span>
</span></span><span class="line"><span class="cl">  <span class="n">wiimote</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">Unref</span><span class="p">();</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="c1">// Create some JavaScript objects, and call the callback
</span></span></span><span class="line"><span class="cl">  <span class="n">Local</span><span class="o">&amp;</span><span class="n">lt</span><span class="p">;</span><span class="n">Value</span><span class="o">&amp;</span><span class="n">gt</span><span class="p">;</span> <span class="n">argv</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span> <span class="o">=</span> <span class="p">{</span> <span class="n">Integer</span><span class="o">::</span><span class="n">New</span><span class="p">(</span><span class="n">ar</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">err</span><span class="p">)</span> <span class="p">};</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="n">TryCatch</span> <span class="n">try_catch</span><span class="p">;</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="n">ar</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">callback</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">Call</span><span class="p">(</span><span class="n">Context</span><span class="o">::</span><span class="n">GetCurrent</span><span class="p">()</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">Global</span><span class="p">(),</span> <span class="mi">1</span><span class="p">,</span> <span class="n">argv</span><span class="p">);</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="k">if</span><span class="p">(</span><span class="n">try_catch</span><span class="p">.</span><span class="n">HasCaught</span><span class="p">())</span>
</span></span><span class="line"><span class="cl">    <span class="n">FatalException</span><span class="p">(</span><span class="n">try_catch</span><span class="p">);</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="c1">// Now cleanup!
</span></span></span><span class="line"><span class="cl">  <span class="n">ar</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">callback</span><span class="p">.</span><span class="n">Dispose</span><span class="p">();</span>
</span></span><span class="line"><span class="cl">  <span class="k">delete</span> <span class="n">ar</span><span class="p">;</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="k">return</span> <span class="mi">0</span><span class="p">;</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span></code></pre></div><p>This simple pattern makes writing callback code relatively simple. However, this only works well if you are in control of creating the callback.</p>
<h4 id="2-how-to-run-something-on-the-main-thread-without-eio_custom">2) How to run something on the main thread without eio_custom</h4>
<p>Libcwiid creates it’s own thread, which is uses to read data from the wiimote. When data is received, it invokes a callback function passing this new data. This callback function is run on the libcwiid thread. This restricts us from interacting with V8. We ideally need this callback function running in the context of the main thread. The answer to this problem is:</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-c++" data-lang="c++"><span class="line"><span class="cl"><span class="n">eio_req</span> <span class="o">*</span><span class="nf">eio_nop</span>       <span class="p">(</span><span class="kt">int</span> <span class="n">pri</span><span class="p">,</span> <span class="n">eio_cb</span> <span class="n">cb</span><span class="p">,</span> <span class="kt">void</span> <span class="o">*</span><span class="n">data</span><span class="p">);</span>
</span></span></code></pre></div><p>It is safe to call this function from any thread. It will place the eio_cb callback task on the main event queue. This task is then eventually executed on the V8′s thread. An example of this follows:</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-c++" data-lang="c++"><span class="line"><span class="cl"><span class="kt">void</span> <span class="n">WiiMote</span><span class="o">::</span><span class="n">HandleMessages</span><span class="p">(</span><span class="n">cwiid_wiimote_t</span> <span class="o">*</span><span class="n">wiimote</span><span class="p">,</span> <span class="kt">int</span> <span class="n">len</span><span class="p">,</span> <span class="k">union</span> <span class="nc">cwiid_mesg</span> <span class="n">mesgs</span><span class="p">[])</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl">  <span class="c1">// This thread is running on the libcwiid&#39;s thread, and thus we can not use V8 operations
</span></span></span><span class="line"><span class="cl">  <span class="n">WiiMote</span> <span class="o">*</span><span class="n">self</span> <span class="o">=</span> <span class="k">const_cast</span><span class="o">&amp;</span><span class="n">lt</span><span class="p">;</span><span class="n">WiiMote</span><span class="o">*&amp;</span><span class="n">gt</span><span class="p">;(</span><span class="k">static_cast</span><span class="o">&amp;</span><span class="n">lt</span><span class="p">;</span><span class="k">const</span> <span class="n">WiiMote</span><span class="o">*&amp;</span><span class="n">gt</span><span class="p">;(</span><span class="n">cwiid_get_data</span><span class="p">(</span><span class="n">wiimote</span><span class="p">)));</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="c1">// Create a struct to pass to the V8 thread
</span></span></span><span class="line"><span class="cl">  <span class="k">struct</span> <span class="nc">message_request</span> <span class="o">*</span> <span class="n">req</span> <span class="o">=</span> <span class="p">(</span><span class="k">struct</span> <span class="nc">message_request</span> <span class="o">*</span><span class="p">)</span><span class="n">malloc</span><span class="p">(</span> <span class="k">sizeof</span><span class="p">(</span><span class="o">*</span><span class="n">req</span><span class="p">)</span> <span class="o">+</span> <span class="k">sizeof</span><span class="p">(</span><span class="n">req</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">mesgs</span><span class="p">)</span> <span class="o">*</span> <span class="p">(</span><span class="n">len</span> <span class="o">-</span> <span class="mi">1</span><span class="p">)</span> <span class="p">);</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="c1">// Copy all the data into this struct
</span></span></span><span class="line"><span class="cl">  <span class="n">req</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">wiimote</span> <span class="o">=</span> <span class="n">self</span><span class="p">;</span>
</span></span><span class="line"><span class="cl">  <span class="n">req</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">len</span> <span class="o">=</span> <span class="n">len</span><span class="p">;</span>
</span></span><span class="line"><span class="cl">  <span class="n">memcpy</span><span class="p">(</span><span class="n">req</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">mesgs</span><span class="p">,</span> <span class="n">mesgs</span><span class="p">,</span> <span class="n">len</span> <span class="o">*</span> <span class="k">sizeof</span><span class="p">(</span><span class="k">union</span> <span class="nc">cwiid_mesg</span><span class="p">));</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="c1">// Now pass this over to the main V8 thread
</span></span></span><span class="line"><span class="cl">  <span class="n">eio_nop</span> <span class="p">(</span><span class="n">EIO_PRI_DEFAULT</span><span class="p">,</span> <span class="n">WiiMote</span><span class="o">::</span><span class="n">HandleMessagesAfter</span><span class="p">,</span> <span class="n">req</span><span class="p">);</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kt">int</span> <span class="n">WiiMote</span><span class="o">::</span><span class="n">HandleMessagesAfter</span><span class="p">(</span><span class="n">eio_req</span> <span class="o">*</span><span class="n">req</span><span class="p">)</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl">  <span class="c1">// We are now running in the V8 thread.
</span></span></span><span class="line"><span class="cl">  <span class="n">message_request</span><span class="o">*</span> <span class="n">r</span> <span class="o">=</span> <span class="k">static_cast</span><span class="o">&amp;</span><span class="n">lt</span><span class="p">;</span><span class="n">message_request</span><span class="o">*</span> <span class="o">&amp;</span><span class="n">gt</span><span class="p">;(</span><span class="n">req</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">data</span><span class="p">);</span>
</span></span><span class="line"><span class="cl">  <span class="n">WiiMote</span> <span class="o">*</span> <span class="n">self</span> <span class="o">=</span> <span class="n">r</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">wiimote</span><span class="p">;</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="n">HandleScope</span> <span class="n">scope</span><span class="p">;</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="c1">// Create JavaScript objects with the message_request
</span></span></span><span class="line"><span class="cl">  <span class="p">...</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl">  <span class="c1">// Emit this event to a JavaScript callback.
</span></span></span><span class="line"><span class="cl">  <span class="k">this</span><span class="o">-&amp;</span><span class="n">gt</span><span class="p">;</span><span class="n">Emit</span><span class="p">(</span><span class="n">event</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="n">argv</span><span class="p">);</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span></code></pre></div><p>Using a combination of eio_custom and eio_nop you should be able to interface with any external library of service. You just have to make sure you always know what thread you are on, and what methods you are allowed to use in that context.</p>
<p>Finally, writing correct thread-safe code is hard. From the various nodejs extensions I have come across I regularlly find memory management, or threading issues with them. So I suggest you rigorously use <a href="http://valgrind.org/">valgrind</a> while developing, and simplify your designs so that most of the heavily lifting is done by nodejs itself.</p>
</description>
    </item>
    
  </channel>
</rss>
