<?xml version="1.0" encoding="utf-8"?>
<feed xmlns="http://www.w3.org/2005/Atom">

  <title><![CDATA[Roads Less Taken]]></title>
  <link href="http://goran.krampe.se/atom.xml" rel="self"/>
  <link href="http://goran.krampe.se/"/>
  <updated>2013-01-25T00:49:33+01:00</updated>
  <id>http://goran.krampe.se/</id>
  <author>
    <name><![CDATA[Göran Krampe]]></name>
    
  </author>
  <generator uri="http://octopress.org/">Octopress</generator>

  
  <entry>
    <title type="html"><![CDATA[Going virtual from CLI]]></title>
    <link href="http://goran.krampe.se/2013/01/21/going-virtual-from-cli/"/>
    <updated>2013-01-21T15:22:00+01:00</updated>
    <id>http://goran.krampe.se/2013/01/21/going-virtual-from-cli</id>
    <content type="html"><![CDATA[<p>Recently when I automated a development process I looked deeper at managing virtual environments and ended up using two really nice tools complementing <a href="http://www.virtualbox.org">VirtualBox</a> in a slick way - <a href="http://www.vagrantup.com">Vagrant</a> and <a href="https://github.com/jedi4ever/veewee">Veewee</a>. A lot of us use VirtualBox of course, but getting a new Ubuntu box up is still a bit of blablablabla&#8230; What if it could be done <em>all from the command line and easily automated</em>?</p>

<!--more-->


<p></p>

<p>Instead of talking, let me show you how you can get a Ubuntu 12.10 box (as an example) up and running. Note that this should work on <strong>Ubuntu 12.10 (Quantal)</strong> and probably 12.04 too:</p>

<figure class='code'><figcaption><span>Installing the tools</span></figcaption><div class="highlight"><table><tr><td class="gutter"><pre class="line-numbers"><span class='line-number'>1</span>
<span class='line-number'>2</span>
<span class='line-number'>3</span>
<span class='line-number'>4</span>
<span class='line-number'>5</span>
<span class='line-number'>6</span>
<span class='line-number'>7</span>
<span class='line-number'>8</span>
<span class='line-number'>9</span>
<span class='line-number'>10</span>
<span class='line-number'>11</span>
</pre></td><td class='code'><pre><code class='bash'><span class='line'><span class="c"># Base needed to get going, hope I didn&#39;t miss anything important</span>
</span><span class='line'>sudo apt-get install squashfs-tools genisoimage libxml2-dev zlib1g-dev libxslt1-dev ruby1.9.3
</span><span class='line'>
</span><span class='line'><span class="c"># New VirtualBox 4.2.0 (the one in Ubuntu proper is 4.1.x), it seems linux-headers are needed.</span>
</span><span class='line'>wget -q http://download.virtualbox.org/virtualbox/debian/oracle_vbox.asc -O- | sudo apt-key add -
</span><span class='line'>sudo sh -c <span class="s1">&#39;echo &quot;deb http://download.virtualbox.org/virtualbox/debian quantal contrib&quot; &gt;&gt; /etc/apt/sources.list&#39;</span>
</span><span class='line'>sudo apt-get update <span class="o">&amp;&amp;</span> sudo apt-get install linux-headers-generic virtualbox-4.2
</span><span class='line'>
</span><span class='line'><span class="c"># Vagrant and Veewee from gems, used to build Ororo basebox and appliance</span>
</span><span class='line'>sudo gem1.9.3 install vagrant
</span><span class='line'>sudo gem1.9.3 install veewee
</span></code></pre></td></tr></table></div></figure>


<p>As you can see I am installing VirtualBox 4.2.0, but 4.1.x probably works fine too. Ok, now that we have VirtualBox, Vagrant and Veewee we can get cracking. Veewee is a tool that adds some sub commands to Vagrant and automates the creation the VirtualBox instance from a vanilla OS ISO file that Vagrant then can control. Vagrant can then be used to bring such a box up, down and ssh into it and install lots of more software on it etc.</p>

<p>Let&#8217;s pretend we are running a 64 bit Ubuntu on our machine but suddenly we want to compile some 32 bit libraries and the simplest way to do it is to just get a 32 bit virtual Ubuntu:</p>

<figure class='code'><figcaption><span>Create an empty Ubuntu 12.10 32 bit basebox that we can reuse</span></figcaption><div class="highlight"><table><tr><td class="gutter"><pre class="line-numbers"><span class='line-number'>1</span>
<span class='line-number'>2</span>
<span class='line-number'>3</span>
<span class='line-number'>4</span>
<span class='line-number'>5</span>
<span class='line-number'>6</span>
<span class='line-number'>7</span>
</pre></td><td class='code'><pre><code class='bash'><span class='line'>mkdir quantal32
</span><span class='line'><span class="nb">cd </span>quantal32
</span><span class='line'>vagrant basebox define quantal32 ubuntu-12.10-server-i386
</span><span class='line'>vagrant basebox build quantal32
</span><span class='line'>vagrant basebox validate quantal32
</span><span class='line'>vagrant basebox <span class="nb">export </span>quantal32
</span><span class='line'>vagrant box add quantal32 quantal32.box
</span></code></pre></td></tr></table></div></figure>


<p>The steps:</p>

<ol>
<li>Pick a template. Veewee offers lots of templates we can use and you can list them using <code>veewee vbox templates</code> (just run <code>veewee</code> for more commands). We picked <strong>ubuntu-12.10-server-i386</strong>.</li>
<li>Build the box. You will see how VirtualBox pops up to life but everything is automated so don&#8217;t touch!</li>
<li>Validate the box. This makes Veewee run a bunch of quick tests to check that the few things Veewee installed are all OK. The stuff installed can easily be inspected if you take a look in the sub dir definitions etc, it all has to do with making Vagrant happy for further provisioning etc.</li>
<li>Export the box as a single file called <strong>quantal32.box</strong> that we could share if we wanted to.</li>
<li>Add this exported box as a known basebox in Vagrant. This last step makes this basebox available to clone using Vagrant.</li>
</ol>


<p>Okidoki, so now we have progressed from a downloaded ISO file of vanilla unmodified Ubuntu to a preconfigured VirtualBox. Of course, if you think the above is too much work :) then you can find <a href="http://www.vagrantbox.es">prebuilt baseboxes here</a>. Let&#8217;s now create one of these puppies to use:</p>

<figure class='code'><figcaption><span>Create an empty Ubuntu 12.10 32 bit basebox that we can reuse</span></figcaption><div class="highlight"><table><tr><td class="gutter"><pre class="line-numbers"><span class='line-number'>1</span>
<span class='line-number'>2</span>
<span class='line-number'>3</span>
<span class='line-number'>4</span>
<span class='line-number'>5</span>
</pre></td><td class='code'><pre><code class='bash'><span class='line'>mkdir mynewbox
</span><span class='line'><span class="nb">cd </span>mynewbox
</span><span class='line'>vagrant init quantal32
</span><span class='line'>vagrant up
</span><span class='line'>vagrant ssh
</span></code></pre></td></tr></table></div></figure>


<p>The steps:</p>

<ol>
<li>When we init vagrant in our empty directory Vagrant will create a file called Vagrantfile in there. This file is actually a ruby script and you can edit it to customize your box. Since we gave a basebox name as the argument this file will include an entry <code>config.vm.box = "quantal32"</code>. The file could even include a URL to this basebox so if you had published the basebox somewhere you could actually send this Vagrantfile to some other developer (or commit to SCM).</li>
<li>The up command simply brings the box up and running! Tada!</li>
<li>And then we can ssh into it easily. For more details see the homepage of Vagrant.</li>
</ol>


<p>And when we are fed up with the box - just take it down with <code>vagrant suspend</code> (or halt) or nuke it with <code>vagrant destroy</code>. Just run <code>vagrant</code> for a list of commands.</p>

<p>So now whenever you need a clean 32 bit Ubuntu for some testing or such - create a directory, run init and up, and there you are. :)</p>

<p>Of course, integrating these commands into Makefiles are quite simple too.</p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[HyperDex on Ubuntu 12.10 from source]]></title>
    <link href="http://goran.krampe.se/2013/01/16/hyperdex/"/>
    <updated>2013-01-16T23:48:00+01:00</updated>
    <id>http://goran.krampe.se/2013/01/16/hyperdex</id>
    <content type="html"><![CDATA[<p>So ok, I really like looking at new interesting NoSQL databases. Up until yesterday I felt <a href="http://basho.com">Riak</a> was the most interesting one (have also coauthored <a href="http://www.smalltalkhub.com/#!/~gokr/Phriak">Phriak</a> - a Riak binding for <a href="http://www.pharo-project.org">Pharo Smalltalk</a>) but after an evening of discussing choices of key/value backends for the <a href="http://goran.krampe.se/category/oak">Oak</a> project I decided to &#8220;google a bit&#8221; and stumbled upon <a href="http://hyperdex.org">HyperDex</a>.</p>

<!--more-->


<p></p>

<p>Without having had the pleasure to actually play with it yet - on paper - it sure looks like a killer NoSQL database. It seems to offer basically the same kind of robustness and horisontal <em>&#8220;just add another box&#8221;</em> kind of scalability that Riak offers including auto balancing etc. But at the same time it offers awesome raw speed <strong>beating both MongoDB (without cheating like Mongo does) and even Redis</strong>, although HyperDex is truly persistent. And to put sugar on top - it has atomic operations in Redis style and manages to somehow avoid the eventual consistency corner - not sure about the details around that.</p>

<p><strong>In summary - an extremely interesting NoSQL database.</strong></p>

<h2>Building from source</h2>

<p>The instructions on how to build HyperDex from source were a tad incomplete. So I offer the following procedure that seemed to work for me in a relatively clean Ubuntu 12.10.</p>

<p>First we need a bunch of tools <strong>(updated 2013-01-17 with some corrections from Robert Escriva)</strong>:</p>

<figure class='code'><figcaption><span></span></figcaption><div class="highlight"><table><tr><td class="gutter"><pre class="line-numbers"><span class='line-number'>1</span>
</pre></td><td class='code'><pre><code class='bash'><span class='line'>sudo apt-get install git autoconf automake autoconf-archive libtool python-dev python-pyparsing cython libpopt-dev libcityhash-dev g++ libgoogle-glog-dev libleveldb-dev bison gperf flex python-sphinx
</span></code></pre></td></tr></table></div></figure>


<p>Then we need a bunch of git clones:</p>

<figure class='code'><figcaption><span></span></figcaption><div class="highlight"><table><tr><td class="gutter"><pre class="line-numbers"><span class='line-number'>1</span>
<span class='line-number'>2</span>
<span class='line-number'>3</span>
<span class='line-number'>4</span>
<span class='line-number'>5</span>
</pre></td><td class='code'><pre><code class='bash'><span class='line'>git clone git://git.hyperdex.org/po6.git
</span><span class='line'>git clone git://git.hyperdex.org/e.git
</span><span class='line'>git clone git://git.hyperdex.org/busybee.git
</span><span class='line'>git clone git://git.hyperdex.org/replicant.git
</span><span class='line'>git clone git://git.hyperdex.org/HyperDex.git
</span></code></pre></td></tr></table></div></figure>


<p>Then, in the order listed above, do the following in the first four:</p>

<figure class='code'><figcaption><span></span></figcaption><div class="highlight"><table><tr><td class="gutter"><pre class="line-numbers"><span class='line-number'>1</span>
</pre></td><td class='code'><pre><code class='bash'><span class='line'>autoreconf -i; ./configure; make <span class="o">&amp;&amp;</span> sudo make install
</span></code></pre></td></tr></table></div></figure>


<p>&#8230;and perhaps something like this in HyperDex:</p>

<figure class='code'><figcaption><span></span></figcaption><div class="highlight"><table><tr><td class="gutter"><pre class="line-numbers"><span class='line-number'>1</span>
</pre></td><td class='code'><pre><code class='bash'><span class='line'>autoreconf -i; ./configure --enable-python-bindings; make <span class="o">&amp;&amp;</span> sudo make install
</span></code></pre></td></tr></table></div></figure>


<p>If all is well you should be able to find the <code>hyperdex</code> command in your path and if <code>hyperdex daemon --help</code> provides helpful output then all is probably fine. For more details take a look in <strong>HyperDex/doc/02.installation.rst</strong>.</p>

<p>Happy hacking!</p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[New SSD for my Lenovo X220]]></title>
    <link href="http://goran.krampe.se/2013/01/10/new-ssd-for-my-x220/"/>
    <updated>2013-01-10T09:32:00+01:00</updated>
    <id>http://goran.krampe.se/2013/01/10/new-ssd-for-my-x220</id>
    <content type="html"><![CDATA[<p>After the <a href="http://goran.krampe.se/2013/01/02/ssd-nightmare">conundrum with my Intel 320 SSD</a> I did some googling and decided to invest a fair chunk of money in a really good SSD - the <a href="http://www.anandtech.com/show/6328/samsung-ssd-840-pro-512gb-review">Samsung 840 Pro, 512GB</a>. The 840 Pro seems to be the king of the hill right now and it&#8217;s only 7mm thick which is what I need for my X220 (although people have shoved 9mm drives into it with a bit of force).</p>

<!--more-->


<p></p>

<p><img class="left" src="http://goran.krampe.se/pics/pic3.jpg" title="Not so big..." ></p>

<p>The actual replacement was trivial, one normal screw to remove the lid on the side, pull out the old disk, move the plastic rails over to the new disk (just pull off and slide onto the new drive), add a piece of tape as a pull handle (to make it easy to remove) and slide it in. If it doesn&#8217;t want to go in you need to flip the rails.</p>

<p>Reboot, go into BIOS and make sure AHCI is selected for SATA and off to happy land. I installed Ubuntu 12.10 from a USB stick and just let it do the automatic thing. This creates a swap partition on the SSD, but that is fine with me - I adjust the swappiness instead to make sure it is only used when really needed.</p>

<br clear="ALL">


<p>You can test performance to make sure all looks ok:</p>

<figure class='code'><figcaption><span></span></figcaption><div class="highlight"><table><tr><td class="gutter"><pre class="line-numbers"><span class='line-number'>1</span>
</pre></td><td class='code'><pre><code class='bash'><span class='line'>hdparm -tT /dev/sda
</span></code></pre></td></tr></table></div></figure>


<p>&#8230;or whatever /dev you have. I get around <strong>7000MB/sec for cached reads and 515 MB/sec for buffered reads</strong>.</p>

<p>In /etc/fstab I added the options &#8220;noatime,nodiratime,discard&#8221;. The &#8220;nodiratime&#8221; is not really necessary since it is implied by noatime. This makes Linux not update access time on files which in turn reduces write operations a lot which prolongs the life of the SSD and increases performance.</p>

<p>The &#8220;discard&#8221; option is to make sure we enable <a href="https://en.wikipedia.org/wiki/TRIM">TRIM</a> on the disk. I just followed <a href="http://techgage.com/article/enabling_and_testing_ssd_trim_support_under_linux">this article</a> (and this <a href="http://nedoboi.wordpress.com/2011/11/12/tiny-tips-ssd-linux-enable-trim-and-check-it-works">other</a>) describing it and how to test it works. Another good page on <a href="http://askubuntu.com/questions/18903/how-to-enable-trim">AskUbuntu</a>. Some <a href="http://serverfault.com/questions/307397/verify-trim-support-with-btrfs-on-ssd/401506#401506">people say</a> that the test in that article is not reliable, but still, if you <strong>do get zeroes</strong> then you can rest assured it works. :)</p>

<p>Next up is setting down swappiness, changing to a disk scheduler more suitable for an SSD and setting /tmp up using tmpfs in RAM. I will not repeat all this - instead I offer some links to <a href="http://tombuntu.com/index.php/2012/04/26/setting-up-ubuntu-on-an-ssd">good instructions at Tombuntu</a> or in the <a href="https://wiki.archlinux.org/index.php/Solid_State_Drives">ArchLinux wiki</a> or <a href="http://bernaerts.dyndns.org/linux/250-ubuntu-tweaks-ssd">this one going even deeper</a>.</p>

<p>Rergarding partition alignment - I read that it should be automatic so I didn&#8217;t bother looking into that.</p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[Moving to SmalltalkHub]]></title>
    <link href="http://goran.krampe.se/2013/01/07/moving-to-smalltalkhub/"/>
    <updated>2013-01-07T16:20:00+01:00</updated>
    <id>http://goran.krampe.se/2013/01/07/moving-to-smalltalkhub</id>
    <content type="html"><![CDATA[<p>As a long time Squeak/Pharo (Smalltalk) developer I have accumulated a set of packages that I have written or co-written and that have been published open source for others to use. Since quite a few years <a href="http://www.squeaksource.com">SqueakSource</a> has been the natural hosting place, but it has reached the end of the road and it&#8217;s <a href="http://news.squeak.org/2012/11/18/move-your-squeaksource-files/">high time to move on</a>.</p>

<!--more-->


<p>
Since then we have had <a href="http://www.squeaksource.com/ss2.html">SqueakSource2</a> (an improved SqueakSource but not deployed I think) and now <a href="http://ss3.gemstone.com">SqueakSource3</a> that runs in GemStone and hosted by GemStone. A lot of projects have migrated to SS3 and that is definitely <strong>not a bad choice</strong> and has been the suggested and only path forward for some time. Never mind it says <em>&#8220;public Alpha&#8221;</em> :)</p>

<p>Personally though I find <a href="http://www.smalltalkhub.com">SmalltalkHub</a> more attractive - but this is perhaps because I am involved in some of the <a href="http://www.amber-lang.net">technology</a> behind it and I know Nicolas quite well. Anyway, I am now moving (well, copying) all my projects there and the process to moving is simple and has been <a href="https://marianopeck.wordpress.com/2011/11/08/migrating-projects-to-squeaksource3/">described for SS3</a> over a year ago:</p>

<ul>
<li><p>Create a project on SH. And if you don&#8217;t have an account, create one.</p></li>
<li><p>Run a few snippets using Gofer to copy over all the code. Here is an example copying over all snapshots for DeltaStreams, PlusTools and System in the DeltaStreams project on SS to my new project on SH:</p></li>
</ul>


<figure class='code'><figcaption><span></span></figcaption><div class="highlight"><table><tr><td class="gutter"><pre class="line-numbers"><span class='line-number'>1</span>
<span class='line-number'>2</span>
<span class='line-number'>3</span>
<span class='line-number'>4</span>
<span class='line-number'>5</span>
<span class='line-number'>6</span>
<span class='line-number'>7</span>
<span class='line-number'>8</span>
<span class='line-number'>9</span>
<span class='line-number'>10</span>
<span class='line-number'>11</span>
<span class='line-number'>12</span>
<span class='line-number'>13</span>
</pre></td><td class='code'><pre><code class='smalltalk'><span class='line'><span class="nc">Gofer</span> <span class="nf">it</span>
</span><span class='line'>  <span class="nf">url:</span> <span class="s">&#39;http://www.squeaksource.com/DeltaStreams&#39;</span> <span class="nf">username:</span> <span class="s">&#39;gokr&#39;</span> <span class="nf">password:</span> <span class="s">&#39;secretpasswordonSS&#39;</span><span class="p">;</span>
</span><span class='line'>  <span class="nf">package:</span> <span class="s">&#39;DeltaStreams&#39;</span><span class="p">;</span>
</span><span class='line'>  <span class="nf">package:</span> <span class="s">&#39;PlusTools&#39;</span><span class="p">;</span>
</span><span class='line'>  <span class="nf">package:</span> <span class="s">&#39;System&#39;</span><span class="p">;</span>
</span><span class='line'>  <span class="nf">fetch</span>
</span><span class='line'>
</span><span class='line'><span class="nf">Gofer</span> <span class="nf">it</span>
</span><span class='line'>  <span class="nf">url:</span> <span class="s">&#39;http://smalltalkhub.com/mc/gokr/DeltaStreams/main&#39;</span> <span class="nf">username:</span> <span class="s">&#39;gokr&#39;</span> <span class="nf">password:</span> <span class="s">&#39;secretpasswordonSH&#39;</span><span class="p">;</span>
</span><span class='line'>  <span class="nf">package:</span> <span class="s">&#39;DeltaStreams&#39;</span><span class="p">;</span>
</span><span class='line'>  <span class="nf">package:</span> <span class="s">&#39;PlusTools&#39;</span><span class="p">;</span>
</span><span class='line'>  <span class="nf">package:</span> <span class="s">&#39;System&#39;</span><span class="p">;</span>
</span><span class='line'>  <span class="nf">push</span>
</span></code></pre></td></tr></table></div></figure>


<p>In the above code we need to list all packages that exists in this repository in order for Gofer to pick them all up. So you might want to look in the SS web UI (tab &#8220;Versions&#8221;) to make sure you didn&#8217;t miss any snapshots.</p>

<ul>
<li>Edit the package description on SS to reflect that SS is no longer the primary repository for this package:</li>
</ul>


<figure class='code'><figcaption><span></span></figcaption><div class="highlight"><table><tr><td class="gutter"><pre class="line-numbers"><span class='line-number'>1</span>
</pre></td><td class='code'><pre><code class='html'><span class='line'><span class="nt">&lt;b&gt;</span>NOTE: This project has been moved to <span class="nt">&lt;a</span> <span class="na">href=</span><span class="s">&quot;http://smalltalkhub.com/#!/~gokr/DeltaStreams&quot;</span><span class="nt">&gt;</span>http://smalltalkhub.com/#!/~gokr/DeltaStreams<span class="nt">&lt;/a&gt;&lt;/b&gt;</span>!!!
</span></code></pre></td></tr></table></div></figure>


<p>To make it extra clear I also include a line like below on SH to make sure people understand this is the right place now:</p>

<pre><code>**NOTE: As of 2013-01-06 this is the primary repository of DeltaStreams, there is also an old repository on www.squeaksource.com.**
</code></pre>

<ul>
<li>Finally, if you have other people than yourself with write access on SS, make sure you check and add them as contributors in SH, if they have accounts on SH. And make sure to drop them an email! :)</li>
</ul>


<p>And poh, a little bird just told me that <strong>SH is being upgraded by the end of the week</strong> with new functionality and bug fixes. Go Nicolas, go!</p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[Never an Intel SSD again]]></title>
    <link href="http://goran.krampe.se/2013/01/02/ssd-nightmare/"/>
    <updated>2013-01-02T01:44:00+01:00</updated>
    <id>http://goran.krampe.se/2013/01/02/ssd-nightmare</id>
    <content type="html"><![CDATA[<p>When I bought my Lenovo X220  - which I have been <strong>extremely pleased with</strong> to date - I chose an <strong>Intel 320 160Gb SSD</strong> disk with it, in retrospect a <strong>BAD MISTAKE</strong>. No idea why I didn&#8217;t find the warnings plastered all over the net at the time, and the problem was even acknowledged by Intel <a href="http://www.techpowerup.com/149064/Intel-Acknowledges-SSD-320-Series-8-MB-Bug-.html">as early as july 2011</a>. The disk has been working fine since april when I got it, until the last day of 2012&#8230;</p>

<!--more-->


<p></p>

<p>The laptop has experienced &#8220;freezes&#8221; from time to time - you know, when the only thing you can do is hold the ON button to shut it off hard. I have been suspecting bad memory, but every time I tested they seemed fine. Yesterday I ran memtest for 5 hours on them and no, no problem there. I would guess this has happened perhaps 15 times since I got the machine in april - so about 15 power cycles is all it took to make 2012 end with a BANG.</p>

<p>After this last freeze and power cycle the machine suddenly ended up at the grub prompt and couldn&#8217;t boot. <strong>Not a reassuring feeling</strong>. Playing around at the grub prompt the partitions seemed to look fairly fine though, I could see &#8220;most&#8221; of my files.</p>

<p>After getting myself a bootable USB rescue disk I managed to access the disk and copy my home catalog to an external disk - phew! My backup was at least a week old so thank you, thank you disk Gods for allowing me to do this. &#8230;then I did another reboot to try to figure things out <strong>and suddenly not even a grub prompt</strong>!</p>

<p>Ehrm, what? WHAT? I started scavenging the net and behold - this seems to be the well known so called &#8220;BAD_CONTEXT or BAD_CTX 8MB bug&#8221; that the Intel 320 based SSD drives are plagued with. So power cycling can apparently trigger this - and the disk for some odd reason (self protection?) decides to decapitate itself and set accessible cylinders down to 16 instead of 16384.</p>

<p>Funny thing here is that the last reboot was NOT a power cycle, but for some reason the <strong>SSD decided that &#8220;enough is enough&#8221; and chopped off its head in desperation</strong>.</p>

<!--more-->


<p>This is of course a legacy thing, SSDs don&#8217;t have cylinders of course, but the net effect is that the disk appears to be only 8MB large. It seems (googling conclusion) this happens whenever the SSD experiences <strong>ANY</strong> disastrous error, so not only this particular &#8220;bug&#8221;.</p>

<p>And in fact, I am not even sure my disk got the same bug, because after the BAD_CTX there is a number, and mine says &#8220;15&#8221;. The one people talk about, and that Intel claims to have fixed with a firmware update, is number &#8220;13&#8221;. But fact remains, my disk is not accessible and it was apparently trigged by a power cycle.</p>

<p>Since the disk uses encryption internally (I <em>think</em> this is one of the reasons) there is <strong>apparently no way for ordinary people to salvage any data</strong>. And I can&#8217;t even persuade the disk to even show me the rest of the disk. When the upper bound is set down like this the &#8220;hidden&#8221; area (most of the disk in this case) is called a <a href="https://en.wikipedia.org/wiki/Host_protected_area">Host Protected Area</a>. Using hdparm and other tools one is supposed to be able to set this &#8220;SET MAX ADDRESS&#8221; threshold back up and remove this &#8220;protected area&#8221;, but all my fiddling with this has utterly failed. I tried <a href="http://www.thomas-krenn.com/de/wiki/SSD_Over-Provisioning_mit_hdparm">hdparm</a> and <a href="http://www.ultimatebootcd.com/">HDAT2 using ultimatebootcd</a> but no, no go. It just gives me some error when I try.</p>

<p>And the rest of the net also says that the <strong>contents of the disk is lost</strong> but that <a href="http://communities.intel.com/message/145676#145676">you can reset the disk so that it at least &#8220;works&#8221; again</a>, but empty. And another post describing <a href="http://www.tested.com/forums/pc-and-mac/44240-huge-bug-in-intel-ssds-complete-recovery-information-here/">a different procedure</a>.</p>

<p>Now&#8230; there is some data salvage firm claiming they can save data from this problem (sorry, no link from me, but if you are in this situation you will find them) - and I think they have cooperated with Intel to be able to do this. I would guess Intel has provided some &#8220;super keys&#8221; to the encryption in that case? Who knows. I haven&#8217;t lost enough data to contact them though.</p>

<p>So&#8230; it seems the net is in fact quite enraged over Intel for all this - because this drive (and SSDs in general) is supposed to be very safe and actually has special features for preventing these exact things! How ironic.</p>

<p>Now, Intel is stone walling, they claim to have fixed the problem with the firmware update - but <strong>lots of people are reporting the same issue happening again, over and over, even with updated firmware&#8230; And no answers from Intel</strong>.</p>

<p>And you might ask, what about my firmware? Well, this is a Lenovo OEM (INTEL SSDSA2BW160G3L), so it has a Lenovo firmware number (4PC1LE04) but I did go through the Intel <a href="http://www.intel.com/support/go/ssdfirmware/index.htm">firmware update dance</a> (unetbooting from Linux onto USB stick works fine) and it tells me that my firmware IS UP TO DATE. No, it doesn&#8217;t tell me that I have some Lenovo firmware that it doesn&#8217;t know about - it says <strong>IT IS UP TO DATE</strong>. So I trust Intel on that one. Ha, silly me. So yes, chalk me up as one of those that had new firmware and got hit by the truck anyway.</p>

<p>IMHO hardware that has faults is generally not a big problem, it doesn&#8217;t generally cause lots of data loss if a graphics card or a motherboard burns up. But <strong>disks</strong> with bugs like this is more problematic. And we are not talking about &#8220;a few sectors lost&#8221; but <strong>the whole 100% shebang lost</strong>.</p>

<p>Backups? Sure. But you will generally still lose lots of valuable time when a thing like this happens, and I don&#8217;t think it is enough to just point the finger back at the customer like that. Sure shit happens, but here we are talking about <strong>known about and repeatedly happening after less than a year due to freaking bugs shit</strong> and not just <strong>weared down by 10 years of continuous spinning shit</strong>.</p>

<p>What makes it more than &#8220;a problem&#8221; is that Intel doesn&#8217;t respect its customers enough to:</p>

<ul>
<li>explain what is going on</li>
<li>explain what these different error numbers mean</li>
<li>explain why it truncates to 8MB</li>
<li>explain why people still have problems after the firmware update</li>
<li>explain what the firmware update claims to have fixed</li>
</ul>


<p>&#8230;and <strong>take responsibility</strong> when their product is obviously badly broken and not trustworthy - that is much more than &#8220;a problem&#8221;!</p>

<p>Boycotting Intel is not an easy thing, but one thing is for sure, <strong>I will NEVER buy an SSD from Intel again. NEVER. And if you google the net you will see lots of other people with the same conclusion.</strong></p>

<p>If Intel doesn&#8217;t care about their customers and their own goodwill - so be it. And if someone from Intel wants to comment on this blog post - feel free - but I truly doubt it since they don&#8217;t even comment <strong>in their own damn forum</strong> which is full of <a href="http://communities.intel.com/message/153620#153620">posts like this one</a>.</p>

<p>And if there are factual errors in this text and Intel somehow miraculously can explain all this crap - go ahead and contact me and I will HAPPILY edit the text and explain to the world what I completely misunderstood.</p>

<p>So&#8230; end of steam. Anyone that can recommend a good <strong>trustworthy</strong> SSD that fits in a Lenovo X220?</p>

<p>No idea what I will do with this old one, I sure don&#8217;t trust it anymore and getting another one on warranty wouldn&#8217;t make it different.</p>

<p><strong>UPDATE:</strong> As I write in my comment below I revived the SSD but it&#8217;s now just wasting space on my desk here. I instead bought a <a href="http://goran.krampe.se/2013/01/10/new-ssd-for-my-x220">Samsung 840 Pro, 512Gb</a> (here is <a href="http://thessdreview.com/our-reviews/samsung-840-pro-512gb-ssd-review-killer-performance-and-untouchable-iops/">one of all reviews</a>), yes, expensive but seems to be <strong>extremely fast</strong> (only 1-2 other SSDs are even close), uses <strong>very little power</strong> (no other SSD seems to be close) and above all - Samsung seems to have a better track record on robustness and how to deal with problems. Of course, I will know more in a year from now, and I am also investing some time into a full recovery solution like Mondo Rescue or similar. :)</p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[Oak]]></title>
    <link href="http://goran.krampe.se/2012/12/29/oak/"/>
    <updated>2012-12-29T15:05:00+01:00</updated>
    <id>http://goran.krampe.se/2012/12/29/oak</id>
    <content type="html"><![CDATA[<p>In a customer project right now I need to be able to work and evolve code fast, with a relatively complex model. And by <em>fast</em> I mean that I want to cut away as much as possible of the efforts related to persistence. Generally this is what OODBs excel at.</p>

<p>In the Squeak world we have <a href="http://www.gemstone.com/products/gemstone">GemStone</a> (commercial), <a href="http://wiki.squeak.org/squeak/3492">GOODS</a> and <a href="http://wiki.squeak.org/squeak/2665">Magma</a> as &#8220;full fledged&#8221; OODBs. Last century :) I worked with GemStone (both Gemstone/S and /J) and its a great product - but I want something lightweight and open source. And simple. And hackable. And new. :)</p>

<p>I also used Magma in the Gjallar project, and while I respect it highly - this time I want to try something with an &#8220;externally supported backend&#8221;. I also had a mixed performance experience, but this was &#8220;pre Cog&#8221; and Magma has also surely evolved lots since then, and I am not sure we did everything the way we should have either.</p>

<p>SandstoneDB could also be interesting to look more closely at, but since I have been working with <a href="http://www.nicolas-petton.fr">Nicolas Petton</a> on improving <a href="http://smalltalkhub.com/#!/~gokr/Phriak">Phriak</a> (Riak interface for Pharo) it was natural to take a look at one of his &#8220;under the radar&#8221; projects - <a href="http://www.smalltalkhub.com/#!/~NicolasPetton/Oak">Oak</a>, an &#8220;OODBish&#8221; solution on top of Riak. At this point I have been doing much more than looking, in fact I am hacking on it! And oh, yeah, of course there are <a href="http://wiki.squeak.org/squeak/512">lots more persistence options</a> available too.</p>

<!--more-->


<h2>What is Riak?</h2>

<p>To understand Oak one should probably learn a bit about <a href="http://basho.com">Riak</a> first. Riak is the <em>primary backend</em> for Oak, although one can use different backends quite easily. The core Oak functionality only needs a key/value store. As Oak evolves I however suspect that some features will be more tightly associated with specific functionality in Riak, like the use of indexing and map/reduce. Nicolas has experimented with using <a href="http://www.mongodb.org">MongoDB</a> and combining with <a href="http://www.memcached.org">memcached</a>, and I am intrigued to also test if Oak can run nicely on top of my Tokyo Tyrant binding. Bottom line is that while Oak is indeed <em>abstracted</em> on top of a key/value store - we are still focusing on Riak as the primary platform.</p>

<p>Riak is an <em>open source ultra scalable</em> key/value store modelled after the highly influential Dynamo database built and used internally at Amazon. The architecture of Riak sets it apart from most of its competitors - it is completely masterless. All nodes participate in a &#8220;hash ring&#8221; and key/value pairs are stored redundantly on multiple nodes in parallell. Automatically. If one box burns up, nothing happens because data is spread out and Riak will compensate the loss of a node by automatically rebalancing data.</p>

<p>If you want more requests/second (reads <em>or</em> writes) just add more boxes. On the fly. Anyway, this article is not about Riak, but having Riak at the bottom we have the ability to scale and best of all, <em>we can sleep calm at night</em>. There is a lot of advanced algorithms involved in Riak to make all this work, but from the outside it is a beautifully simple system.</p>

<p>The binding we use for Riak is called <a href="http://smalltalkhub.com/#!/~gokr/Phriak">Phriak</a> and it&#8217;s an HTTP binding (Riak also offers a Protocol Buffer API) written using Zinc. Phriak can be used all by itself and covers quite a lot of Riak features including secondary indexes and map reduce. Finally, Riak is &#8220;data agnostic&#8221; so we don&#8217;t need to store JSON if we do not want to.</p>

<h2>Installing Oak</h2>

<p>I am using Pharo 1.4 and there is a Metacello configuration available on <a href="http://www.smalltalkhub.com/#!/~NicolasPetton/Oak">SmalltalkHub</a> so load it:</p>

<figure class='code'><figcaption><span></span></figcaption><div class="highlight"><table><tr><td class="gutter"><pre class="line-numbers"><span class='line-number'>1</span>
<span class='line-number'>2</span>
<span class='line-number'>3</span>
<span class='line-number'>4</span>
<span class='line-number'>5</span>
</pre></td><td class='code'><pre><code class='smalltalk'><span class='line'><span class="nc">Gofer</span> <span class="nf">it</span>
</span><span class='line'>   <span class="nf">url:</span> <span class="s">&#39;http://www.smalltalkhub.com/mc/NicolasPetton/Oak/main&#39;</span><span class="p">;</span>
</span><span class='line'>   <span class="nf">package:</span> <span class="s">&#39;ConfigurationOfOak&#39;</span><span class="p">;</span>
</span><span class='line'>   <span class="nf">load</span><span class="p">.</span>
</span><span class='line'>(<span class="nc">Smalltalk</span> <span class="nf">at:</span> <span class="ss">#ConfigurationOfOak</span>) <span class="nf">project</span> <span class="nf">stableVersion</span> <span class="nf">load</span><span class="p">.</span>
</span></code></pre></td></tr></table></div></figure>


<p>Then you need Riak and there are <a href="http://docs.basho.com/riak/1.2.1/tutorials/installation/">detailed instructions available</a> and it is generally quite simple. Currently Oak does not use secondary indexing so at this point Riak should work fine, later when we start messing with secondary indexing you will need to <a href="http://docs.basho.com/riak/latest/tutorials/choosing-a-backend/LevelDB/#Installing-eLevelDB">switch to LevelDB</a> as the backend library, but that is just a simple config tweak.</p>

<p>Now, open up TestRunner, filter on &#8220;Oak&#8221;, select &#8220;Oak-Tests&#8221;, then click &#8220;Run Selected&#8221; - if all is fine you should have 40 green tests. OAOakSessionTest is running against your local Riak. OASessionMockTest is just running against a Dictionary in the image.</p>

<h2>How does Oak work?</h2>

<p>Oak is a layer on top of a key/value store creating a semi transparent OODB. By &#8220;semi transparent&#8221; I mean that it is slightly less &#8220;automagic&#8221; than a real OODB, but on the other hand there is much less code and logic that can go wrong and we get the luxury of leaning against a rock solid industry strenght backend. We are also gradually making it more and more transparent.</p>

<p>Oak has some fundamental mechanisms:</p>

<ul>
<li>Serialization of objects using Fuel, <strong>no mapping to JSON</strong>.</li>
<li>The concept of a transaction/&#8221;unit of work&#8221; which can be committed as a whole or aborted, <strong>no explicit write operations</strong>.</li>
<li>The concept of &#8220;persistence by reachability&#8221;, <strong>no explicit insert operations</strong> (but we still need explicit delete).</li>
<li>Proxies to do automatic &#8220;faulting&#8221; of more objects from disk, <strong>no explicit read operations</strong>.</li>
</ul>


<p>So Oak doesn&#8217;t convert to JSON, instead we store Fuel blobs. Fuel is fast, heavily tested and supports schema changes. When it comes to generic serialization I would guess it is the best we have. We simply give Fuel an object to serialize into a ByteArray and Fuel follows all references and makes a blob for us.</p>

<p>The Oak transaction keeps track of all changes during a &#8220;unit of work&#8221; and applies them at the end, or not at all. The transactions are not truly atomic, but at least we postpone all operations until at the end, so if one decides to abort half way through - nothing is written. If the actual writing of the changes would fail it would still be non atomic. The operations we collect are basically <em>delete</em>, <em>insert</em> and <em>update</em> of Oak objects. An Oak object is a partial object graph.</p>

<p>Partial? Well, let&#8217;s say we have a domain object Person. It might be arbitrarily complex but since it is a domain object it is designed to be self contained and not referencing UI stuff etc. We can save this single object in Oak like this:</p>

<figure class='code'><figcaption><span></span></figcaption><div class="highlight"><table><tr><td class="gutter"><pre class="line-numbers"><span class='line-number'>1</span>
<span class='line-number'>2</span>
<span class='line-number'>3</span>
<span class='line-number'>4</span>
<span class='line-number'>5</span>
<span class='line-number'>6</span>
<span class='line-number'>7</span>
<span class='line-number'>8</span>
<span class='line-number'>9</span>
<span class='line-number'>10</span>
<span class='line-number'>11</span>
</pre></td><td class='code'><pre><code class='smalltalk'><span class='line'><span class="c">&quot;Get a session object for localhost, port 8098 where Riak is running by default&quot;</span>
</span><span class='line'><span class="nv">session</span> <span class="o">:=</span> <span class="nc">OAOakSession</span> <span class="nf">newDefault</span><span class="p">.</span>
</span><span class='line'>
</span><span class='line'><span class="c">&quot;Create our domain object, no need to do this inside a transaction in fact&quot;</span>
</span><span class='line'><span class="nv">person</span> <span class="o">:=</span> <span class="nc">Person</span> <span class="nb">new</span> <span class="nf">name:</span> <span class="s">&#39;Goran&#39;</span><span class="p">;</span> <span class="nf">yourself</span><span class="p">.</span>
</span><span class='line'>
</span><span class='line'><span class="c">&quot;All modifications we do must be inside a transaction.</span>
</span><span class='line'><span class="c">#setRoot: is used to save the single top level object in Oak.&quot;</span>
</span><span class='line'><span class="nv">session</span> <span class="nf">commit:</span> [
</span><span class='line'>  <span class="nv">session</span> <span class="nf">setRoot:</span> <span class="nv">person</span>
</span><span class='line'>]
</span></code></pre></td></tr></table></div></figure>


<p>First of all, Oak doesn&#8217;t require anything special from the objects it saves. No need to inherit a base class or do any other kind of pre-processing.</p>

<p>One wouldn&#8217;t normally save a Person as the root. A more normal approach would be to save a Dictionary there, and then save other objects in it. Or set your domain top level object of your system as the root.</p>

<p>When objects are saved, Oak will use a &#8220;UUID new asString36&#8221; as the key. We call this key the &#8220;oid&#8221; (Object id) of the object. So in order to get an object back we would either need to know the oid or we get the object through some other object by <em>reachability</em>, typically starting at the root object. The root object is saved using a hard coded oid, so we can always find that one.</p>

<p>Now, let&#8217;s modify the person. Reuse the session you have, or create a new one. Let&#8217;s focus on the interesting bit:</p>

<figure class='code'><figcaption><span></span></figcaption><div class="highlight"><table><tr><td class="gutter"><pre class="line-numbers"><span class='line-number'>1</span>
<span class='line-number'>2</span>
<span class='line-number'>3</span>
<span class='line-number'>4</span>
<span class='line-number'>5</span>
</pre></td><td class='code'><pre><code class='smalltalk'><span class='line'><span class="nv">session</span> <span class="nf">commit:</span> [ <span class="o">|</span> <span class="nv">person</span> <span class="nf">|</span>
</span><span class='line'>  <span class="nv">person</span> <span class="o">:=</span> <span class="nv">session</span> <span class="nf">root</span><span class="p">.</span>
</span><span class='line'>  <span class="nv">person</span> <span class="nf">name:</span> <span class="s">&#39;Nicolas&#39;</span><span class="p">.</span>
</span><span class='line'>  <span class="nv">person</span> <span class="nf">oakSave</span>
</span><span class='line'>]
</span></code></pre></td></tr></table></div></figure>


<p>When we send #root to the session it will actually not read the Person, it will instead create a proxy object which has a single instance variable holding the oid, which in this case is the hard coded oid for the root object. So the temp variable &#8220;person&#8221; will hold the proxy. The magic happens when we send #name: to this proxy. It will trap the message, fetch the Person instance from Riak (as a Fuel ByteArray) and materialize it into a &#8220;real&#8221; Person instance. Then the proxy will forward the #name: message to this Person instance and return whatever it returns.</p>

<p>Most OODBs tend to use #become: to actually turn the proxy into the real object. Oak currently does not do this, instead Oak keeps forwarding. There are advantages and disadvantages of both approaches. If one uses &#8220;short&#8221; transactions - quickly find your way down to your object, modify and commit - then you will send few messages and the commit will be quick. In this scenario one might argue that the cost of #become: is higher than doing a few message forwards. Perhaps Oak will use #become: later, the obvious advantage is that it enables more fool proof handling of identity.</p>

<p>Then we send #oakSave to the proxy, and this will schedule an update operation which in turn will be executed after the commit block has run to the end. The #oakSave has two functions here. First it tells Oak that the object is dirty and needs to be written to disk. Secondly it tells Oak that this object should be a separate Oak object, serialized, read and written as a separate key/value pair in Riak with its own oid.</p>

<p>In fact, Oak also implements #oakInsert but there is no real need to use it, because one can always use #oakSave and it will itself decide to use insert if the object is a new object. Finally we have #oakDelete to actually delete an object. Oak has no garbage collection at this point so it is not enough to just &#8220;not reference&#8221; an object anymore. Well, nothing bad happens if you forget to send #oakDelete, but the key/value pair will still be in Riak consuming disk space.</p>

<p>Now&#8230; lately we have added autoSave so one do not need to use #oakSave at all! This mechanism does two things automatically:
- It will detect which objects have been changed during the commit block and will save them automatically. This costs a little bit of performance, but nothing dramatic.
- It will also detect insertions automatically, but this depends on the instance answering true when asked #isOakPersistentWannabe. If an object answers true it means that it wants to be a separate Oak object if it happens to be reachable from another persistent Oak object. If it answers false it will not be saved as a separate key/value pair, instead it will be contained within the serialization of the object referencing it.</p>

<p>So if we use autoSave we simply implement #isOakPersistentWannabe as &#8221;<sup>true&#8221;</sup> in those domain objects that we think should be serialized as separate key/value pairs. Neat!</p>

<h2>Next in Oak</h2>

<p>Next steps for Oak are probably:</p>

<ul>
<li>Polishing code by using it for real. :)</li>
<li>Adding custom Oak collection classes that behaves like &#8220;normal&#8221; collections but leverage things like secondary indexing and map/reduce.</li>
<li>Possibly adding some kind of automatic deletion.</li>
</ul>


<p>Custom collection classes one would like to have is of course large scale OrderedCollection and large scale Dictionary for starters.</p>

<p>When it comes to deletion there are some things we can do. First we could automatically handle the special case of a single owner. If an object &#8220;promise&#8221; us that it is only referenced by ONE other Oak object, typically an owner, then we can automatically delete it when that owner &#8220;drops&#8221; it. For hierarchical models this would work, but of course it depends on the developer being sure these objects are only referenced from one and one object only. Since it wouldn&#8217;t solve the general case it might not be worth implementing it at all, not sure.</p>

<p>This turned into a rather long article, I hope that I have managed to tickle your interest and that you take Oak out for a spin and perhaps help out in making it better.</p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[Moved from Wordpress to Octopress]]></title>
    <link href="http://goran.krampe.se/2012/12/27/moved-from-wordpress-to-octopress/"/>
    <updated>2012-12-27T14:43:00+01:00</updated>
    <id>http://goran.krampe.se/2012/12/27/moved-from-wordpress-to-octopress</id>
    <content type="html"><![CDATA[<p>So… I kinda got tired of Wordpress. A bit too much for me, I want something more lightweight that “just works”. I also stumbled over some blog that had just moved over to Octopress and made it sound like “da shit” for coders. So be it! And so far so good.</p>

<p>In short I did an XML export from inside Wordpress admin, created an account on Disqus, added the disqus plugin for Wordpress, exported over all comments, then “git cloned” Octopress onto my laptop, used exitwp (from github) to migrate my XML file from Wordpress, used rsync deploy over to my server and adjusted config in Octopress to use disqus (and thus pick up all old comments).</p>

<p>Yeah, that’s about it. :)</p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[Literal arrays vs JSON vs STON vs Tirade]]></title>
    <link href="http://goran.krampe.se/2012/05/08/literal-arrays-vs-json-vs-ston-vs-tirade/"/>
    <updated>2012-05-08T02:11:22+02:00</updated>
    <id>http://goran.krampe.se/2012/05/08/literal-arrays-vs-json-vs-ston-vs-tirade</id>
    <content type="html"><![CDATA[<p>Recently there were a range of threads on the pharo-dev mailinglist discussing the textual format to use for Smalltalk source code metadata. The discussion veered off from the specific use case but basically four different formats were discussed and compared, of which one I am the author. And oh, sorry for the formatting of this article - I need to change theme on this blog for better readability.</p>

<!--more-->


<h1>JSON</h1>

<p>The first format is <a href="http://json.org">JSON</a>, Javascript Object Notation. JSON is a simple language neutral (despite its name) readable format that is very small to implement. It is a restricted variant of the native JavaScript literal syntax for objects (dictionaries) and arrays. Basically it excels in simplicity but lacks a bit in features, but people tend to ignore those shortcomings due to its widespread adoption. I will not go into describing it, <a href="http://json.org">json.org</a> does a very good job and there are TONS of JSON implementations around.</p>

<h1>STON</h1>

<p>Sven Van Caekenberghe recently created a variation on JSON he calls <a href="https://github.com/svenvc/ston/blob/master/ston-paper.md">STON</a>, Smalltalk Object Notation. STON is basically JSON plus the following:</p>

<ul>
<li><p><strong>Object references</strong>, the concept of being able to refer to other previously described arrays/objects in the STON file. This is done by number using the @-sign like &#8220;@2&#8221; refers to the second array/object in the file.</p></li>
<li><p><strong>Class prefixing</strong>, the idea of annotating arrays and objects (JSON terminology) so that one can instantiate a reasonable class when reading.</p></li>
<li><p><strong>Symbols</strong>, simply adding support for a primitive data type for Smalltalk symbols, although I do note - a limited form of Symbols not allowing the same range of characters in them as Squeak/Pharo does.</p></li>
</ul>


<p>Then there are a few subtle differences from JSON, like using $&#8217; instead of $&#8221; as string delimiter and nil instead of null, but not much else that I can see. Numbers seem to be exactly the same as in JSON, and escape codes inside strings are also the same, obviously by design.</p>

<p>First I admit that I have not played with STON, my comparison is purely in theory. STON has the same basic positive notes that JSON has, it is small, simple and well defined. <strong>But are the differences worth it?</strong></p>

<p>JSON is everywhere and there are already tons of parsers for it, probably in every Smalltalk on earth, and of course all other languages too. STON on the other hand is Smalltalk only, and as of this writing probably Pharo only, although I admit it must be simple to port.</p>

<p>It boils down to if the additions are worth it and I don&#8217;t think they are. Embedding class names, if needed, could be done in JSON, although slightly inelegantly of course, but one approach would be to wrap each &#8220;typed&#8221; object/array in an object like this:</p>

<pre><code>ByteArray [1, 2, 3] ==&gt; {"type": "ByteArray", "data": [1, 2, 3]}
</code></pre>

<p>I agree, clunky, but on the other hand I tend to think that the parsing end needs to know the semantics and construction of the JSON anyway - JSON is too &#8220;simplistic&#8221; to be used as a true generic serialization mechanism and trying to turn it into such a beast by adding types and references, like STON does, is IMHO not that useful.</p>

<p>STON looks neat, but in practice<strong> I don&#8217;t think the benefits outweigh the ubiquity and availability of JSON</strong>. Had it been even <strong>more</strong> different it might have been another story. But if we don&#8217;t think we will use type annotations and circular references - then why not simply use JSON?</p>

<h2>Literal Smalltalk arrays</h2>

<p>The simplest notation of all in the lineup is the literal array syntax in Smalltalk. The example below covers all its capabilities AFAIK (in Pharo/Squeak), please tell me if I missed anything:</p>

<pre><code>#(4711 3.4 16r3F 'string' #symbol #'another-symbol' (nested array) #(one more) true false nil $x #[12 32])
</code></pre>

<p>So we have space separated elements and arrays that can nest, with or without #-prefix inside the array. Primitive literals are numbers (full numeric Smalltalk parser, not as limited as JSON/STON), strings (no escape codes, single quotes needs to be doubled), symbols (can handle more characters than STON symbols), character literals, byte array literals and true/false/nil.</p>

<p>Literal arrays are quite nice but they lack the concept of &#8220;associations&#8221; and thus no simple readable way to represent a Dictionary. <strong>And that is a BIG negative</strong>. Funny enough, if we added support for literal dictionaries to Smalltalk then literal arrays would match JSON, with a few extras on the side!</p>

<p>Amber has recently added support for dynamic literal HashedCollections using this syntax:</p>

<pre><code>#{'hey'-&gt;12 . aString-&gt;'123123'}
</code></pre>

<p>It is simply a dynamic {} array (was introduced originally in Squeak I believe) but with the assumption that the expressions all evaluate to Associations that are limited to a string as key. This is because it will be turned into a HashedCollection which is the Amber counter part of a JavaScript object, and JavaScript objects are limited to having strings as keys (Sidenote: Amber also has a generic Dictionary without that limitation).</p>

<p>Without a syntax for dictionaries, literal arrays, although nifty and syntactically quite compact, are still limited in expression. And of course, while Smalltalk literals are fairly simple to parse, other languages do not typically know how to do it - and when it comes to numbers, the Smalltalk full range of syntax is perhaps a bit of an overkill if we aim at cross language portability. Having literal syntax for Characters is also clearly of less value, ByteArrays on the other hand are obviously useful.</p>

<h2>Sidestory: Adding literal Dictionaries to Smalltalk?</h2>

<p>Smalltalk only evolves in micro steps every other 10 years, but with the current onslaught of Pharo perhaps there is an opportunity to actually take a few more such steps.</p>

<p>We will see below that Tirade has added support for &#8220;->&#8221; as a literal syntax instead of being a message send and as I mentioned above Amber has added a special syntax for dynamic Dictionaries, and that was actually done in order to more easily match JavaScript object syntax when interacting with JavaScript.</p>

<p>So perhaps the Smalltalk/Pharo community could decide to add literal Dictionaries to Smalltalk using the Amber &#8220;#{&#8221; syntax? In such a syntax the separators between Associations can probably not be spaces, it gets confusing to read:</p>

<pre><code>#{ key -&gt; value key2 -&gt; value2 }
</code></pre>

<p>A separator is clearly needed and since we use periods generally for that in Smalltalk it&#8217;s a good choice. Syntactically it could lead people to think it&#8217;s a dynamic Dictionary, but let&#8217;s continue the thought experiment. How would it look? As is customary for #() we can ommit the # inside the array:</p>

<pre><code>#(123 'hey' {key -&gt; value. key2 -&gt; value} 456)
</code></pre>

<p>It looks fairly nice. However I do admit that we probably should take a long hard look at all our syntaxes and try to bring some harmony to them. Currently, due to legacy, we have literal and dynamic Arrays using #() and {}. A bit unfortunate since we then use both $( and ${ as delimiters for Arrays and make it harder to find good characters for Dictionaries.</p>

<p>It would be nice to have a symmetric syntax. Ideally the leading # could indicate &#8220;literalness&#8221; - and perhaps we could use another character to indicate dynamic evaluation? Again, just a thought:</p>

<ul>
<li><h1>() - literal Array</h1></li>
<li><p>§() - dynamic Array, expressions separated by periods.</p></li>
<li><h1>{} - literal Dictionary, literals separated by periods, support for associations as literals.</h1></li>
<li><p>§{} - dynamic Dictionary, expressions separated by periods, associations created as usual using sends.</p></li>
</ul>


<p>Yeah, right, how would we ever be able to reach concensus on a leading dynamic character? :) Also, I do think it is wise to syntactically indicate literal vs dynamic, heuristics only lead to developer traps. Better to clearly indicate intention.</p>

<h1>Tirade</h1>

<p><a href="http://www.squeaksource.com/Tirade.html">Tirade</a> is a format I created for Deltas (ChangeSets improved) and I have written <a href="http://goran.krampe.se/2009/03/16/tirade-a-file-format-for-smalltalkers/">four</a> articles <a href="http://goran.krampe.se/2009/03/20/tirade-part-2/">about</a> <a href="http://goran.krampe.se/2009/04/20/tirade-first-trivial-use/">it</a> <a href="http://goran.krampe.se/2011/04/15/tirade-supporting-embedded-text/">earlier</a>. Now, if I would at this point subjectively rank the formats along a few axis it could look like this:</p>

<ul>
<li><p><strong>Interoperability</strong></p>

<ul>
<li><p>JSON: 100% (all languages has it)</p></li>
<li><p>STON: 70% (one could probably tweak a JSON parser in any language to work)</p></li>
<li><p>Litarrays: 30% (could get higher score if we limit them, a parser would still have to be written)</p></li>
<li><p>Tirade: 20% (same problem as with literal arrays, but even more advanced to parse)</p></li>
</ul>
</li>
<li><p><strong>Capability</strong></p>

<ul>
<li><p>Tirade: 100% (has the most features and options, by some margin)</p></li>
<li><p>STON: 60% (second best, still not much better than JSON)</p></li>
<li><p>JSON: 50%</p></li>
<li><p>Litarrays: 40% (severely limited by lack of assocations but has a some features to compensate)</p></li>
</ul>
</li>
<li><p><strong>Grokkability</strong></p>

<ul>
<li><p>JSON: 100% (well documented, we all know it and so does the rest of the world)</p></li>
<li><p>STON: 90% (rides on JSON)</p></li>
<li><p>Litarrays: 80% (not hard but has quite a few quirks)</p></li>
<li><p>Tirade: 70% (more or less as hard as literal arrays, but with a few more concepts added)</p></li>
</ul>
</li>
</ul>


<p>Conclusions from the above? Before looking at Tirade I think we can safely say that <strong>JSON is a strong choice</strong>. STON is IMHO in limbo, I can&#8217;t see picking it instead of any of the others in a given situation, sorry. Literal arrays could easily become the obvious &#8220;JSON for Smalltalk&#8221; if it had associations/literal dictioneris, it sucks for interoperability though.</p>

<p>Tirade on the other hand <strong>has associations</strong> (on two levels one could even claim) so it can be viewed as &#8220;JSON++ for Smalltalk&#8221;. But with more features comes a slightly higher learning curve and a penalty in interoperability. We now have set the scene for the last section about Tirade.</p>

<h1>Tirade</h1>

<p>Obviously I am partial, since I created Tirade. But let me try to contrast Tirade to all the others. Note that Tirade was never meant to be interoperable with other languages, it was however designed to be interoperable between different Smalltalk implementations, or at least all Squeak derivatives.</p>

<h2>A stream of messages</h2>

<p>First of all, Tirade is slightly different than the others. They describe a single structure. A valid Tirade &#8220;document&#8221; on the other hand, is a series of &#8220;records&#8221; terminated by periods. Each such &#8220;record&#8221; looks like a Smalltalk message (but without a receiver on the left side), either a unary or a keyword message, like this:</p>

<pre><code>unaryMessage.
key: 'Hello' word: 'world' message: 4711.
</code></pre>

<p>This high level view as a &#8220;stream of messages&#8221; gives us several nice properties:</p>

<ul>
<li><p>The selector of the Tirade message is a kind of record &#8220;type&#8221;. It normally maps to a method on the receiving end that handles this record. That method then knows what to do with the arguments, and thus we don&#8217;t need to hard code class names into Tirade, like STON does. <strong>NOTE: This is not a security problem.</strong> There is nothing forcing the parsing end to just blindly perform these messages. In fact, there is nothing forcing the parsing end to be specific at all, it could just be a generic Tirade parser.</p></li>
<li><p>If we look at a keyword message we realize that it is very similar to a JSON object, it is basically a &#8220;naked dictionary&#8221; where each key word is&#8230; right, a key! :) So for simple data we need perhaps not make it more complicated than this.</p></li>
<li><p>It makes it very easy to extend a Tirade format by simply adding new message selectors that the receiving end can ignore if it wants to.</p></li>
<li><p>Since Tirade is a flow of messages instead of a single, potentially quite large, structure like the other three formats, we can naturally stream it and handle each message one by one.</p></li>
<li><p>And since we have this flow we can also use &#8220;control messages&#8221; that can instruct the receiving end on how to receive the messages coming next in the flow. One could even use Tirade over a bidirectional link (a SocketStream for example) and do handshaking and client server communication with it.</p></li>
<li><p>Finally, in between Tirade messages one can add Smalltalk style comments which are simply skipped by the parser. JSON and STON has no concept of comments.</p></li>
</ul>


<h2>Smalltalk literals</h2>

<p>The next level of Tirade is what kind of arguments we are allowed to put in between the keywords. Basically its most kinds of Smalltalk literals with some additional constructs. I would also like to point out that this part is not encarved in stone, I am still contemplating the best mix of literal support here. But the main point is that <strong>we only allow literals - no expressions</strong>, so there is no generic &#8220;eval&#8221; going on here.</p>

<p>Notable differences again compared to JSON/STON on the atomic level are just like with literal arrays:</p>

<ul>
<li><p>Strings are Smalltalk strings, no escape codes except for double single quote for single quote.</p></li>
<li><p>Numbers are Smalltalk literal numbers, in fact we rely on the number parser of Pharo/Squeak. This gives us a rich notation for numbers, at the expense of possible portability issues with other Smalltalks.</p></li>
</ul>


<p><strong>NOTE:</strong> Tirade doesn&#8217;t currently implement Character literals nor ByteArrays, both can of course be added.</p>

<p>Let&#8217;s continue with the added features for literals.</p>

<h3>Literal feature: Verbatim strings</h3>

<p>A problem with JSON for dealing with readability is that JSON strings can&#8217;t have newlines in them! So if you want to store source code in JSON it will end up as a single very long line.</p>

<p>Smalltalk strings like in Tirade can have newlines in them, but they suffer from double quoting of single quotes and the problem that the single quotes surrounding the string needs to be first on the first line and last on the last line, which makes it less readable.</p>

<p>This is why I came up with verbatim strings in Tirade, specifically for being able to contain unmodified source code in a readable way with no escapes whatsoever. I am not sure if this is the best approach, perhaps here-docs would be a simpler approach, but currently a verbatim string looks like this:</p>

<pre><code>some: 1 message: 'hey' withVerbatimStringForCode: [
 This is untouched, perfectly unescaped source code, ANY character combinations will work!
 Tirade will split the input on each CR (byte = 13) and then prepend each line with a TAB character.
 This means that the parser can detect the end by looking for the first line starting with "]",
 that must be the end of the verbatim string since all other lines start with TAB.
 Copy paste will work but you will need to care for the TAB indentation, but most editors
 can do that easily. Also, right before and after the string there is a newline added to improve readability.
].
</code></pre>

<h3>Literal feature: Associations</h3>

<p>Since we really want to be able to do dictionaries I first added literal support for Associations. This means &#8220;->&#8221; is a literal syntax for creating an Association, it doesn&#8217;t need to be in a Dictionary, you can use them wherever you like and the key and value can be ANY literal construct allowed by Tirade, even an Assocation!</p>

<p>Note though that we do not have parenthesis in Tirade (no expressions at all) and the current Tirade parser is a recursive descent bottom up parser so the code below will produce an Assocation with key #key and value an Association 123->&#8217;123&#8217;. In Smalltalk where #-> is a message this is instead executed from left to right creating a different result.</p>

<pre><code>cool: #key-&gt;123-&gt;'123'.
</code></pre>

<p>This also means that Tirade can have associations inside literal arrays, which is not syntactically possible in Squeak/Pharo:</p>

<pre><code>cool: #(12-&gt;'123').
</code></pre>

<p>Finally, since Amber lately added #{} syntax for Dictionaries I think it could be a worthwhile addition to Tirade also.</p>

<h3>Literal feature: Dynamic arrays as literal</h3>

<p>Tirade supports {} style arrays, but doesn&#8217;t allow expressions so they are very much like normal arrays except they do not remove #-prefixes from nested arrays/symbols and they look more natural to Squeakers since Squeak allows Association literals inside them:</p>

<pre><code>cool: {12-&gt;'123. 'banana'-&gt;true}.
</code></pre>

<p>Is it worth supporting both kinds of arrays? It depends, either Tirade defines a literal subset that is as small as possible, or Tirade tries to cover all literals of Pharo. I was leaning towards a subset but perhaps a super set is more attractive to people.</p>

<h1>Ending thoughts</h1>

<p>I hope this article explained a few things and made at least Tirade a bit clearer. There are several things not fully settled in Tirade and if anyone wants to dig in and tweak it, feel free to email me.</p>

<p>regards, Göran</p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[Going Lenovo...]]></title>
    <link href="http://goran.krampe.se/2012/04/14/going-lenovo/"/>
    <updated>2012-04-14T03:02:06+02:00</updated>
    <id>http://goran.krampe.se/2012/04/14/going-lenovo</id>
    <content type="html"><![CDATA[<p>When I started my own company about a year ago I ended up buying an <a href="http://www.notebookreview.com/default.asp?newsID=5866&amp;review=asus+g73+g73jw">ASUS G73JW</a> gaming laptop - I took a deliberate decision to focus on raw power for decent money and totally ignoring portability. Generally it has served me well, although it does tend to make a lot of fan noise, at least under Ubuntu. It might work smoother in Windows, but I seldom boot into Windows.</p>

<p>Needless to say though it is a <strong>real ton of bricks</strong> (8.8 lbs = 4 kg) and including the truly fat power supply it simply weared my back down during 2011. I have been carrying this beast in a backpack every day - and my body eventually said &#8220;enough dammit!&#8221;. :)</p>

<!--more-->


<p></p>

<h2>Ultrabook?</h2>

<p>So I decided to upgrade to some hot new hardware weighing <strong>below 2 kg</strong> and naturally I started looking at the current crop of <a href="http://en.wikipedia.org/wiki/Ultrabook">ultrabooks</a>. And no, Macbook Air is not for me, sorry. After reading lots of reviews my perception is that all of the current Ultrabooks have one problem or another. This may be because of this being the first generation of Ultrabooks in combination with manufacturers pushing the envelope technologically:</p>

<ul>
<li><p>Keyboards tend to be troublesome given the limitations on thickness making the keys too shallow, the Zenbook for example suffers from bad reviews pointing out the fact that you really need to hit the keys in the middle for them to register.</p></li>
<li><p>Touchpads are also an area lacking, probably because most of them are now moving to so called &#8220;clickpads&#8221; with integrated buttons.</p></li>
<li><p>Screens tend to be less than stellar.</p></li>
<li><p>There have also been reports on issues with wifi having bad reception.</p></li>
<li><p>Then of course, a general lack of ports, but that is to be expected in this form factor.</p></li>
</ul>


<p>I was still leaning towards the <a href="http://www.lenovo.com/products/us/laptop/ideapad/u-series/u300s/">Lenovo u300s</a>. It seems to be a truly awesome machine with no apparent weakness although they say the screen is not something to write home about. But I simply can not find where to buy one! Reading up on this Lenovo I came across a lot of people proposing the <a href="http://www.lenovo.com/products/us/laptop/thinkpad/x-series/x220/">X220</a> as a better choice. Eventually I started to <a href="http://en.wikipedia.org/wiki/ThinkPad_X_Series#X220">read up</a> more on the rest of the Lenovo line, especially the X220 and <a href="http://www.notebookreview.com/default.asp?newsID=6125&amp;review=lenovo+thinkpad+x1">X1</a>.</p>

<h2>Lenovo X220!</h2>

<p>After some serious soul searching I decided that I really need an X220 instead of a <a href="http://zenbook.asus.com">shiny ultrabook toy</a>, and today when I was home sick I ordered one from <a href="http://www.dustin.se/">Dustin</a> with home delivery - 2 hours after placing the order a car drove up to the house and delivered it - <strong>sweet</strong>!</p>

<p>So what about the newer X1 then? Well, what did it for me was the weight and size difference combined with the fact that I really wanted the IPS display. I have read some more comparisons afterwards and feel I made the right decision, although the keyboard on the X1 does get rave reviews even compared to X220. This means it must be insanely great since the keyboard is one of the true highlights of the X220.</p>

<p>After just a few hours with the X220 I am certain I made the right choice. This machine is&#8230; well, if Ultrabooks are flashy slim Ferraris and Porsches this machine would be&#8230; a mini Humvee. It is <strong>function focus all the way</strong>. Here is a list of key arguments for the X220:</p>

<ul>
<li><p><strong>Superb real keyboard</strong> which is a true joy to type on. This is important and a key differentiator for Lenovo in general. It also has the Trackpoint (the little red mouse stick thing), quite nice if you learn to use it - which I am trying right now.</p></li>
<li><p><strong>Full voltage CPUs with top of the line being a Core i7-2640</strong> giving even more power than the low voltage variations found in Ultrabooks.</p></li>
<li><p><strong>8 Gb</strong> <strong>RAM</strong> (two replaceable slots). Many ultrabooks only give you 4 Gb max and non replaceable. For a small additional price I got an extra 4Gb memory module that was trivial to install. In fact, there are people who have managed to install two 8Gb modules giving a <strong>maximum of 16Gb</strong>!</p></li>
<li><p>1366 x 768 <strong>matte IPS panel</strong>, same technology as in the Ipad they say. Awesome display and a rarity among laptops. And matte damnit! This is alone a very strong argument for the X220. I mean, this screen rocks! Of course, higher resolution would have been nice but it&#8217;s fine.</p></li>
<li><p><strong>Tons of ports</strong> and ways to extend and replace parts (battery, memory, hard drive etc)</p></li>
<li><p><strong>1.3-1.6 kg</strong> depending on choice of battery, clearly in Ultrabook class.</p></li>
<li><p><strong>Insane battery life</strong> with several battery options! The protruding 9-cell battery I got is meant to give up to 15 hours! There are 4 different battery sizes, just pick and choose. I am going to get an additional 4 or 6-cell variant which doesn&#8217;t protrude, when I want to be &#8220;slick&#8221; :)</p></li>
</ul>


<p>So it has most Ultrabook properties (real power, lightweight, small form factor, good battery life) although not as slim. But in all other respects it is a true work horse for professionals. And for me weight is what counts, not thickness.</p>

<p>I guess it boils down a bit to what kind of person you are. I wanted a really good and lightweight laptop that I can work on, but I also wanted <strong>something different</strong>, as the title of this blog says - I travel the road less taken. <strong>And X220 is a true utilitarian beast sending a &#8220;100% no nonsense&#8221; message.</strong><strong>
</strong></p>

<h2>Performance</h2>

<p>Getting acquainted with the machine I decided to run some benchmarks in Windows 7. I downloaded the CrystalDiskMark and while not as good numbers as the best drive in UX31E it still got decent numbers:</p>

<pre><code>           Sequential Read :   259.164 MB/s
          Sequential Write :   170.058 MB/s
         Random Read 512KB :   172.326 MB/s
        Random Write 512KB :   169.432 MB/s
    Random Read 4KB (QD=1) :    17.175 MB/s [  4193.1 IOPS]
   Random Write 4KB (QD=1) :    31.436 MB/s [  7674.9 IOPS]
   Random Read 4KB (QD=32) :   140.489 MB/s [ 34299.1 IOPS]
  Random Write 4KB (QD=32) :    95.920 MB/s [ 23418.1 IOPS]
</code></pre>

<p>But this is of course an attribute of the Intel SSD drive more than the actual notebook. I also downloaded and ran the free PCMark 7 in which it scored <strong>4004</strong>. This is better than the fastest Ultrabook (UX31E which got 3653) but I had hoped for even better, perhaps I missed cranking up the speed correctly.</p>

<p>To top things off, here is a list of more funky details:</p>

<ul>
<li><p>A small downward directed LED lamp (Thinklight) right beside the web cam that illuminates the keyboard. Hehe, kinda low tech compared to backlit keyboards, but it works. I guess it is hard to make a traditional &#8220;non chiclet&#8221; keyboard backlit.</p></li>
<li><p>A 720p HD web cam. Oh. :)</p></li>
<li><p>A fingerprint biometric reader! So now I log on W7 by swiping my index finger, funky.</p></li>
<li><p>54 mm Express Card slot. No idea what to use it for yet!</p></li>
<li><p>One combined mSATA/PCIe internal slot. In my machine it holds a UMTS 3G card. I just slid in my SIM card and it hooked up nicely!</p></li>
<li><p>The second half PCIe port. No idea what to use that for either.</p></li>
<li><p>Option to buy an additional mSATA SSD drive (currently available up to about 128Gb) giving even more disk space. Unfortunately this would mean ripping out the UMTS card.</p></li>
<li><p>The navpoint (red mouse stick) has three buttons below and if you hold the middle button you get scrolling for the navpoint - really nice! Or perhaps obvious, but I like it.</p></li>
</ul>


<h2>Negative stuff so far</h2>

<p>Well, these are nitpickings, but still, these are things that have annoyed me a bit:</p>

<ul>
<li><p>Although I really like the little red nubbin, it does get in the way when I type &#8220;b&#8221; sometimes, my right hand index finger &#8220;stumbles&#8221; over it. Might be simply an issue of getting used to the keyboard.</p></li>
<li><p>The palm rests are very small on this machine due to its size. For my right hand it is not an issue because the red nubbin and touchpad is slightly off to the left so I tend to rest my right palm slightly more to the middle. But my left wrist ends up squarely on the left side corner of the laptop. And while the front edge is sloped downwards to make it comfortable, the sides are not sloped at all.</p></li>
<li><p>The Ctrl and Fn keys seems swapped for my taste, the Ctrl should IMHO be in the corner. In the BIOS one can swap these (!) but then I would really like to change the writing on the keys too&#8230;</p></li>
</ul>


<p><strong>UPDATE:</strong> The nubbin doesn&#8217;t get in the way anymore, obviously a thing that one &#8220;learns&#8221; automatically. I haven&#8217;t thought about the palm rests since I wrote the article, so it was nitpicking. I haven&#8217;t swapped the Ctrl-Fn keys, simply learned the layout. Possibly will swap still though.</p>

<h2>Software included</h2>

<p>Normally I don&#8217;t care about installed software but Lenovo has actually included quite a few useful utilities for Windows 7. Power management, biometric finger print management, yaddayadda. This makes it harder to make the decision to wipe Windows.</p>

<h2>Here comes&#8230;. Ubuntu!</h2>

<p>First I tested running Ubuntu in a VirtualBox and while it works quite well it still seems to behave better on the real hardware. This is probably due to the graphics capabilities in VirtualBox. Anyway, one of the main reasons for going with a Thinkpad is also of course the fact that they tend to work really, really well with Linux. And the X220 <a href="https://help.ubuntu.com/community/X220">is not an exception</a>. I have been running Linux as primary OS for almost 6 years now so I really want to continue doing that, but I am being cautious and will go for a dual boot setup for now.</p>

<p>These are the basic steps I performed:</p>

<ul>
<li><p>Produce the so called &#8220;Factory Recovery&#8221; disks. This takes the recovery partition that Lenovo has put on the SSD and slaps it onto external media so that you can wipe that partition and reclaim about 16Gb of disk space. It&#8217;s also nice to have, if something goes bonkers.</p></li>
<li><p>Shrink the Windows 7 partition thus leaving unpartitioned space for Ubuntu.</p></li>
<li><p>Prepare a USB stick with Ubuntu.</p></li>
<li><p>Install Ubuntu from the USB stick producing a dual boot setup.</p></li>
</ul>


<p>Funny enough it was the first step that turned out a bit tricky, the rest was a piece of cake.</p>

<h2>Producing Factory Recovery media</h2>

<p>One would think that since everyone should do this it would be trivial to do. If I would design this procedure I would make it possible to produce iso-files that can just be saved onto an USB hard drive, but no no&#8230; :)</p>

<ul>
<li><p>Prepare a USB drive <a href="http://support.lenovo.com/en_US/detail.page?LegacyDocID=MIGR-74246">according to this document</a>. It must be either at least 350Mb (only for booting) or about 9Gb (both bootable and recovery data).</p></li>
<li><p>If you picked a small USB like I did, when you run the utility from Lenovo - only select &#8220;boot&#8221; when you get the dialog with two check boxes. It will then wipe the drive and make it bootable, but not put recovery data onto it. Then you can fire up the utility once more and use an USB hard drive for the other checkbox (recovery data), it does not need to be empty because it will not wipe it, it will just create a directory called &#8220;factoryrecovery&#8221; and put all data into it.</p></li>
<li><p>If you picked a large USB stick (or hard drive) then you can select both checkboxes and get it all in one place in one go.</p></li>
</ul>


<p><strong>NOTE:</strong> You should try booting from it to see that it actually boots. To do that you will need to enter the BIOS setup (F1 or F12 on boot) and move the USB flash drive higher up in the boot order list. Of course, when this is all done one could produce an iso from that bootable USB stick and store it away somewhere to free up a perfectly good USB stick :)</p>

<p>Then finally you can let the tool &#8220;reclaim&#8221; the partition, it will nuke the paritition and then enlarge the Windows 7 partition with that space, but we will shrink it in the next step.</p>

<h2>Shrink Windows</h2>

<p>This is easy in 2012, Windows can do it for you. Just open control panel, type in &#8220;partition&#8221; and open the tool that it finds. Select the Windows 7 partition and use &#8220;shrink&#8221; in the popup menu. Then you get to a dialog in which you can specify how much you want to shrink it.</p>

<h2>Prepare a USB with Ubuntu</h2>

<p>There are many ways to install Linux and in the older days the traditional way was to burn a CD and boot from it into the installation procedure. These days I guess the most common procedure is to do the same, but with a USB stick. In retrospect the <a href="http://www.ubuntu.com/download/ubuntu/windows-installer">Wubi</a> installer might have been even easier, but I wanted to install the beta 2 of Ubuntu &#8220;Precise Pangolin&#8221; and didn&#8217;t think Wubi was up to date with that, but it seems you can download any iso you want on the side for it.</p>

<p>Anyway, I downloaded <a href="http://unetbootin.sourceforge.net/">Unetbootin</a> and the <a href="http://releases.ubuntu.com/precise/ubuntu-12.04-beta2-desktop-amd64.iso">Pangolin beta 2 iso</a> and then &#8220;burned&#8221; it with Unetbootin to a USB stick. Done.</p>

<h2>Install Ubuntu</h2>

<p>Well, what can I say? Just boot from the stick and go with the flow. The installer is trivially easy, it will detect the existing Windows 7 and even offers to import bookmarks and stuff from your Windows user! A dual boot setup is produced without questions asked even, it was simple as that.</p>

<h2>Conclusion</h2>

<p>I love this machine! And the only thing not working perfectly smooth in Ubuntu is the 3G, it fails to unlock when I give the PIN code, not sure why. Also, one will need to do <a href="http://www.williambrownstreet.net/blog/?p=387">some tweaking</a> to get less battery drain in Linux, but I think the forums indicate that it is possible to get similar results as in Windows.</p>

<p>So take my advice - if you are looking at the Ultrabooks, do take a long look at the X220 before making your decision. :)</p>

<p><strong>UPDATE:</strong> The 3G card actually works perfectly, the failure to unlock was just a glitch. Also, now there is X230 which seems to be an upgraded X220 but with the new backlit chiclet-keyboard instead. Good move Lenovo, although I honestly don&#8217;t know if I would pick it in favor of the &#8220;real old-fashioned&#8221; keyboard of X220.</p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[Current Smalltalk obsessions...]]></title>
    <link href="http://goran.krampe.se/2012/02/07/current-smalltalk-obsessions/"/>
    <updated>2012-02-07T01:15:10+01:00</updated>
    <id>http://goran.krampe.se/2012/02/07/current-smalltalk-obsessions</id>
    <content type="html"><![CDATA[<p>These days I am, as usual, torn between several interesting technical projects.</p>

<h1>Amber</h1>

<p>The new <a href="http://www.world.st">Smalltalk</a> called <a href="http://www.amber-lang.net">Amber</a> (by Nicolas Petton) that compiles to javascript is pretty awesome and there are tons of interesting things one can do with it. My contributions so far include the beginning of a package model, a faster simpler chunk format exporter/importer, a command line compiler, a Makefile system so that Amber can be built fully from the command line and a bunch of <a href="https://github.com/NicolasPetton/amber/tree/master/examples">examples</a> running on top of <a href="http://nodejs.org">Nodejs</a> and <a href="http://developer.palm.com">webOS</a>, and a few other odds and ends.</p>

<!--more-->


<p></p>

<p>I would like to port <a href="http://wiki.squeak.org/squeak/DeltaStreams">Deltas</a> to Amber in order to create a powerful toolset for managing code changes. Using local storage it would among other things enable undo and change logging to prevent accidental code loss. It could also easily form the basis for a &#8220;commit tool&#8221;, similar functionality that git stash offers etc.</p>

<p>Another thing I would like to build is a dead simple public shared package repository. And play with <a href="http://socket.io">Socket.IO</a>, or just fool around with the compiler trying to add optimizations like various type inferencing, optimizing self and super sends etc :). So much fun stuff to do!</p>

<h1>STOMP and Apollo</h1>

<p>For a personal &#8220;secret project X&#8221; I need scalability so it is being designed with lots of daemons each taking care of a specific task. I want to be able to implement these daemons primarily in either Nodejs (in plain js or using Amber) or <a href="http://www.pharo-project.org">Pharo Smalltalk</a>, but also in any other language that fits.</p>

<p>This requires some kind of messaging infrastructure to tie them together. So&#8230; after looking hard and long and reading a lot about messaging, job scheduling, <a href="http://www.amqp.org">AMQP</a>, <a href="http://www.zeromq.org">0MQ</a>, <a href="http://stomp.github.com">STOMP</a>, <a href="http://kr.github.com/beanstalkd/">Beanstalkd</a>, <a href="http://www.rabbitmq.com">RabbitMQ</a>, <a href="http://activemq.apache.org/apollo/">ActiveMQ Apollo</a> (and tons of other things) I decided to try to use the new ActiveMQ Apollo together with <a href="http://stomp.github.com/stomp-specification-1.1.html">STOMP 1.1</a> (which should also be supported by the STOMP plugin for RabbitMQ etc).</p>

<p>The new Apollo implementation is written in Scala using <a href="http://hawtdispatch.fusesource.org/">HawtDispatch</a> so the architecture seems modern and the JVM of course has very good performance these days. So, while I generally am very tired of Java and its eco system, this actually seems like a solid product and has already shown <a href="http://hiramchirino.com/blog/2011/12/stomp-messaging-benchmarks-activemq-vs-apollo-vs-hornetq-vs-rabbitmq/">very impressive numbers in benchmarks</a>.</p>

<p>So a sound asynchronous architecture with good performance is nice but the other thing I like with ActiveMQ is their focus on STOMP. Since I intend to use Pharo as one major component I need to be able to hook it into the messaging backbone. And sure, Tony Garnock Jones - one of the main developer behind RabbitMQ - actually has an AMQP client library written for Squeak 3.9, so I could probably us AMQP, but I somehow foresee a &#8220;world of hurt&#8221; in the complexity given that AMQP is a magnitude more complex than STOMP.</p>

<p>I have already <a href="http://www.squeaksource.com/StompProtocol.html">implemented STOMP 1.0 for Pharo</a>, actually tried it with RabbitMQ at the time, so I am now upgrading that library to work with 1.1 of the specification.</p>

<h1>Riak</h1>

<p>The other important piece of the puzzle for true &#8220;Internet scalability&#8221; is of course the choice of persistence. I am a long time fan of the new NoSQL databases and having played with a few of them, implemented a C# binding for CouchDB, hacked some bindings in Squeak for both CouchDB and Tokyo Tyrant&#8230; I now have decided to focus on <a href="http://wiki.basho.com/Riak.html">Riak</a>. Riak is IMHO the most interesting NoSQL database out there right now, at least for worry free ultra scaling. Sure, it may not be the fastest on a single box - but if you are really serious about scaling - one box is totally uninteresting. :)</p>

<p>Runar Jordahl had already started a Riak binding in Pharo, I took it and changed quite a lot of it - not really because it was &#8220;bad&#8221; or anything, I just have a different style of coding I guess. So I decided to fork because I didn&#8217;t feel comfortable - thus <a href="http://www.squeaksource.com/Phriak.html">Phriak was born</a>. Now Nicolas Petton is getting hard into Riak too and has pushed Phriak forward <strong>quite a LOT</strong> in the last few days, much further than I had time to do. It now has a clean command style protocol implementation, an object model similar to the one in Ripple (Ruby Riak client) and initial working code for both secondary indexing, link walking and map/reduce! Quite impressive stuff.</p>

<p>Nicolas is also experimenting with writing an &#8220;OODB-ish&#8221; database using <a href="http://rmod.lille.inria.fr/web/pier/software/Fuel">Fuel</a> called <a href="http://www.squeaksource.com/Oak.html">Oak</a> and after I managed to get him hooked on Riak he has been moving that codebase over onto Phriak. The initial experience we have with Phriak and Oak is extremely promising and who knows where this will lead.</p>

<p>Happy coding, Göran</p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[ESUG day 4]]></title>
    <link href="http://goran.krampe.se/2011/08/25/esug-day-4/"/>
    <updated>2011-08-25T18:50:52+02:00</updated>
    <id>http://goran.krampe.se/2011/08/25/esug-day-4</id>
    <content type="html"><![CDATA[<p>This day started with some stress, Nicolas and I whipped up the last details of our co-presentation on <a href="Http://jtalk-project.org">Jtalk</a> (Nicolas decided to skip <a href="Http://www.iliadproject.org">Iliad</a>) - and my Eris demo suddenly got b0rken. But I managed to fix it and our presentation was <strong>very well</strong> received - it was great fun!</p>

<p>Nicolas managed to do quite a few &#8220;on the fly&#8221; demonstrations of various Jtalk snippets etc, and running <a href="Http://nicolas-petton.fr/presentations/esug2011">the slides</a> in Jtalk was of course a killer thing. I explained how jtalkc is being run on top of Node.js and quickly proceeded into showing the <a href="Http://github.com/gokr/jtalk/tree/master/nodejs/trivialserver">TrivialServer</a> demo in Node.is - when Apache benchmark showed <strong>1800 requests/second</strong> there was a spontaneous applause. :)</p>

<p>Now we can relax and talk to all people about Jtalk - and now in fact the web panel starts with Nicolas on the panel. Unfortunately the panel discussion didn&#8217;t play out that well, it needs some entertainment and also at least one or two that disagree :)</p>

<p>Later tonight and tomorrow we will probably keep on hacking Jtalk like mad. So much fun stuff to play with! We intend to &#8220;finish&#8221; the first stab at so called &#8220;speculative inviting&#8221; that we started earlier this week, and try to do some profiling on it to verify the gains. Using the Compiler is actually a good candidate for a reasonable benchmark.</p>

<p>The evening ended with the usual pubs and hacking and chatting about cool things people are doing.</p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[ESUG day 3]]></title>
    <link href="http://goran.krampe.se/2011/08/24/esug-day-3/"/>
    <updated>2011-08-24T12:07:30+02:00</updated>
    <id>http://goran.krampe.se/2011/08/24/esug-day-3</id>
    <content type="html"><![CDATA[<p>Suddenly it is Wednesday and we are already on day three at <a href="Http://www.esug.org">ESUG</a> - a superb software developer conference focused on <a href="http://www.world.st">Smalltalk</a>. Time flies. Yesterday I mainly hacked together with Nicolas Petton on <a href="Http://www.jtalk-project.org">Jtalk</a>, really fun, unfortunately I missed a few interesting presentations, like Fuel and Bifrost etc.</p>

<p>This day starts with Stéphane presenting &#8220;Humane assessment&#8221;. Mmm, got distracted by my Touchpad, but Stéphane is showing some cool visualizations right now, clearly useful for large systems and organisations that need understand their own &#8220;huge legacy software&#8221;. Hehe, the browsers shows visual queues on &#8220;bad designs&#8221; like marking methods as &#8220;BrainMethod&#8221; or marking a class as &#8220;God Class&#8221; - that is indeed very slick!</p>

<p>All in all it looks like a very useful tool - I should probably try it out on some codebase. In fact, this tool is a really good &#8220;added value&#8221; tool that can be offered to customers when helping them. I have at least one client that really could make some good use of a tool like this.</p>

<p>Next up before coffee is Arden Thomas from <a href="Http://www.cincomsmalltalk.com">Cincom</a> (hehe, that was funny, the Touchpad wanted to correct &#8220;Cincom&#8221; to &#8220;Condom&#8221;&#8230;) presenting what is new in their products / ObjectStudio and VisualWorks. These are really mature and amazing Smalltalk tools, but of course they also costs money, money, money. But VisualWorks is accessible in a non commercial full version, which is quite nice if it fits your needs. Cincom is also quite active in a bunch of open source Smalltalk projects like for example GLORP (think &#8220;Hibernate&#8221; for all you non-Smalltalkers) and <a href="Http://www.seaside.st">Seaside</a> (the most outstanding web framework in the world).</p>

<p>After running around flaunting the Touchpad :) - I came slightly late to Igor Stasenko&#8217;s presentation on <a href="http://code.google.com/p/nativeboost/">NativeBoost</a>. I have worked with Igor and he has this refreshing &#8220;fearlessness&#8221; so diving into assembler is not a problem for him. So NativeBoost is an extension to the Squeak VM (and the new Cog VM) that enables dynamic machine code generation - and execution - directly from Smalltalk using just Smalltalk. So it includes a DSL for writing assembler (a port of <a href="http://code.google.com/p/asmjit/">AsmJit</a>) and mechanisms to access memory etc etc. The machine code needs to be relocation agnostic since it is actually stored directly in a Smalltalk object (the method) and will be moving around due to the garbage collector moving things around. Another interesting issue is that if the machine code calls into the VM in order to create a Smalltalk object, it will need to be aware of the fact that this can trigger GCs and move things around - but this is just the same for building VM plugins. Of course, Igor&#8217;s stuff is very impressive and you can make very fast code using it.</p>

<p>The day then ended with the social event and announcing the winners of the awards and a nice dinner followed up with some beer and endless &#8220;Why doesn&#8217;t everyone use Smalltalk?&#8221; discussions - as is customary.</p>

<p>Over and out, Goran &#8220;typing this in on my Touchpad using the bluetooth keyboard&#8221;</p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[Touchpad finally in my hands, first day]]></title>
    <link href="http://goran.krampe.se/2011/08/24/touchpad-finally-in-my-hands-first-day/"/>
    <updated>2011-08-24T01:42:35+02:00</updated>
    <id>http://goran.krampe.se/2011/08/24/touchpad-finally-in-my-hands-first-day</id>
    <content type="html"><![CDATA[<p>Sooo&#8230;. I actually managed to order a HP Touchpad 32Gb here in Edinburgh to be picked up at Comet within 48 hours. I ordered when it was still a whopping 429£, but when I went to pick it up I got it at the UK <strong>discount price of 115</strong>, and I will get the VAT back too.</p>

<p>The first hours were frustrating because I was in the ESUG conference and we only had a WiFi with a so called &#8220;captive portal&#8221; with a login form - and the first time you power up a Touchpad it wants to hook up to a Palm Profile, and does not want to do that using a WiFi with a captive portal.</p>

<p>The Montague pub to the rescue later that evening, an open wifi. I am currently writing this post using the Bluetooth keyboard (so nice) while the TP is snugly positioned on the Touchstone inductive charger. Both these are great accessories. I have also managed to do Skype with my wife, really easy and worked well, hook up the calendar to Google with perfect sync, and in fact it synched over all my contacts etc from my Palm Profile for my Palm Pre 2 - just works!</p>

<p>I have done the OTA 3.0.2 update (in the pub while eating) and I have installed a bunch of apps, like the one I am typing in know - for WordPress. I have also activated the included 50Gb free cloud space included from box.net - brilliant.</p>

<p>Email app is running fine, Facebook app is very good, tons of other little nifty things - I am a happy camper! Is it just as &#8220;smooth as silk&#8221; as the iPad? No, but it excels in other areas like true multitasking, a real Linux beneath (bonus for me as a developer), synergy, full flash, 50Gb cloudspace for life included, really good virtual keyboard (multiple sizes even) etc etc. Sure, slightly thicker and slightly heavier - but&#8230;. BUT&#8230;. It cost me around 85£ with 32Gb RAM. That argument is a killer.</p>

<p>Day after tomorrow I will be demonstrating apps written in <a href="Http://jtalk-project.org">Jtalk</a> running on it - yiha!</p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[ESUG 2011 in Edinburgh]]></title>
    <link href="http://goran.krampe.se/2011/08/11/esug-2011-in-edinburgh/"/>
    <updated>2011-08-11T13:59:57+02:00</updated>
    <id>http://goran.krampe.se/2011/08/11/esug-2011-in-edinburgh</id>
    <content type="html"><![CDATA[<p>Each year I try to attend at least one developer conference. Earlier OOPSLA was a given but it lost its appeal quite a few years back and now it is not even called OOPSLA anymore. As a die hard <a href="http://www.world.st">Smalltalker</a> I instead attended the <a href="http://www.esug.org/wiki/pier/Conferences">ESUG conference</a> in Brest 2009 and it was easily the most rewarding conference I ever have attended! Missed last year in Barcelona but this year I am going to <a href="http://www.esug.org/wiki/pier/Conferences/2011">Edinburgh</a> for a week of Smalltalking.</p>

<p>I am not presenting anything but I hope I will get my <a href="http://www.hpwebos.com/us/products/pads/touchpad/index.html">HP Touchpad</a> from Amazon before it starts so that I can demonstrate a <a href="http://www.hpwebos.com">WebOS</a> app running on it written in <a href="http://www.jtalk-project.org">Jtalk</a>.</p>

<p>If you are going too, see you there!</p>

<p><a href="http://www.esug.org/wiki/pier/Conferences/2011"><img src="http://goran.krampe.se/files/2011/08/Esug2011_logo_small.png" alt="" /></a></p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[WebOS 3.0 is coming - with Enyo!]]></title>
    <link href="http://goran.krampe.se/2011/07/09/webos-3-0-is-coming-with-enyo/"/>
    <updated>2011-07-09T03:27:37+02:00</updated>
    <id>http://goran.krampe.se/2011/07/09/webos-3-0-is-coming-with-enyo</id>
    <content type="html"><![CDATA[<p>A few weeks ago I joined the Early Access program that HP/Palm has been offering for a while and I have been toying with the new <a href="http://developer.palm.com">WebOS 3.0</a> (SDK with emulator) that appeared in public on the 1st of july when the <a href="http://www.hpwebos.com/us/products/pads/touchpad/index.html">HP Touchpads</a> hit the stores in the US. Since a week I also have a <a href="http://www.hpwebos.com/us/products/phones/pre2/index.html">Palm Pre 2</a> phone running WebOS 2.1, hopefully to be upgraded later to 3.0.</p>

<p>What can I say, <strong>I am totally hooked!</strong> The SDK for WebOS 3.0 looks really nice and the Palm Pre 2 is <a href="http://www.trustedreviews.com/Palm-Pre-2-Review_Mobile-Phone_review">the best phone</a> I have ever used, if I disregard the poor battery life.</p>

<p>No, I have never owned an iPhone but my previous phone was the Samsung Galaxy, and that is a really good phone! :) Now, of course, getting the <a href="http://www.hp.com/pre3">Pre 3</a> would be even better.</p>

<h2>Screenshots</h2>

<h2>[nggallery id=2]</h2>

<h2>WebOS</h2>

<p>Having used the phone for a week or two some things stand out:</p>

<ul>
<li><p>The gesture and cards system for multitasking is a real joy to use. Hard to describe, should be experienced.</p></li>
<li><p>Notifications are <a href="http://www.bgr.com/2011/06/08/apples-ios-5-notifications-are-great-but-webos-is-still-better/">really nicely done</a>, non intrusive and slick.</p></li>
<li><p>The &#8220;just type&#8221; mechanism is awesome, typing in a name or a website or whatever - and WebOS will suggest and list &#8220;everything&#8221;. And even better, WebOS discovers new &#8220;search engines&#8221; when I surf and offer to include them in quick list for searching! Simple and so smart.</p></li>
<li><p>Synergy - the system merging all contact information together is amazingly good, much better than on my Android phone. It merges and syncs info from my LinkedIn, Facebook and Google accounts (and many other sources) brilliantly.</p></li>
<li><p>Messaging is uniform, I can SMS or Gtalk or whatever in the same threaded view for a given contact. Yay!</p></li>
</ul>


<p>And there is lots more of these little things, adding up to a very smooth user experience.</p>

<h2>Application frameworks</h2>

<p>One of the primary new things in WebOS 3.0 (vs 2.x) is <a href="http://www.infoq.com/news/2011/07/webOS-3-Enyo">Enyo</a> - the new application framework in Javascript that is replacing Mojo, the older framework. Enyo looks like a really well designed object oriented UI toolkit. It focuses on using code and not HTML to produce the user interface and the API looks nice, well documented with examples and quite complete!</p>

<p>Applications for WebOS 3.0 come basically in three flavors - Enyo/Javascript, OpenGL/SDL/C/C++, or hybrid.</p>

<ul>
<li><p>An Enyo app is &#8220;just&#8221; Javascript running in V8 + Webkit and will be the framework that the majority of the applications will use. Given the push in Javascript land these days I would say it is a very interesting platform.</p></li>
<li><p>More demanding graphical apps, especially games, can be written in the C/C++ tool chain and use the OpenGL ES and <a href="http://en.wikipedia.org/wiki/Simple_DirectMedia_Layer">SDL</a> APIs. This seems to be a very friendly platform for game development.</p></li>
<li><p>Hybrid apps are Enyo apps (or Mojo) that can embed native components written in the C/C++ tool chain and allow them to render parts of the screen and also communicate with them. This is clearly an interesting option for many demanding apps.</p></li>
</ul>


<h2>An open eco system</h2>

<p>Although WebOS is not open source it seems in many ways more &#8220;open&#8221; than the competition:</p>

<ul>
<li><p>It is trivial to get &#8220;root&#8221; on the devices. Just type in &#8221;<a href="http://en.wikipedia.org/wiki/Konami_Code">upupdowndownleftrightleftrightbastart</a>&#8221; and click the icon that appears!</p></li>
<li><p>HP/Palm seems to realize that the <a href="http://www.webos-internals.org/wiki/Main_Page">homebrew community</a> is very important and this community is <a href="http://www.preware.org">exceptionally strong</a>.</p></li>
<li><p>Using the <a href="http://www.preware.org">Preware</a> homebrew app catalog and installing themes, patches, applications and more is just as easy and smooth as the <a href="http://www.hpwebos.com/us/products/software/mobile-applications.html">regular app catalog</a> (no, you can&#8217;t browse it on the web, only on a device)!</p></li>
<li><p>The OS is a real Linux at the base! In fact, the ipk package format for apps is the deb format.</p></li>
<li><p>The base technologies used are major open source projects like Webkit, V8, SDL, GStreamer etc etc.</p></li>
<li><p>HP is offering a multitude of distribution channels including a &#8220;web distribution&#8221; channel where you can market your own app outside of the regular app catalog - but people can still just click on a URL and buy/install the application! That is very nice.</p></li>
</ul>


<p>&#8230;and there are many more aspects to this &#8220;openness&#8221;, but I think HP realize that they need to play this part of the game quite a bit better than the competition in order to be able to catch up.</p>

<h2>High hopes</h2>

<p>I think HP has a diamond here in WebOS and if they play their cards right they should be able to find their piece of the market share. And that share just needs to be &#8220;descent&#8221; in order to be fruitful. But in order for that to happen I am hoping that:</p>

<ul>
<li><p>The products (Touchpad, Pre 3, Veer) really hit the stores all over the world ASAP.</p></li>
<li><p>The 3G/4G versions of the Touchpad will show up soon. Just wifi is not enough.</p></li>
<li><p>The next generation of products keep up with the competition in hardware specs.</p></li>
<li><p>The major apps people want and need start appearing.</p></li>
</ul>


<p>The first three are primarily up to HP. The fourth is hopefully not a problem since the eco system is so appealing to developers. And I think HP is trying to make sure some crucial apps are not missing - for example, I think HP made sure the Facebook app is there - and it is indeed a really good app!</p>

<p>Next up? Well of course, using Smalltalk to build Enyo applications&#8230; :)</p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[Konsten att måla ett drev, del 2]]></title>
    <link href="http://goran.krampe.se/2011/05/17/konsten-att-mala-ett-drev-del-2/"/>
    <updated>2011-05-17T15:27:34+02:00</updated>
    <id>http://goran.krampe.se/2011/05/17/konsten-att-mala-ett-drev-del-2</id>
    <content type="html"><![CDATA[<p>Dags för andra delen i artikelserien om att måla ett drev. <a href="http://goran.krampe.se/2011/05/01/konsten-att-mala-ett-drev-del-1/">Första delen</a> avhandlade mest teori om målningsprocessen. Nu är det dags för avmontering av drevet från skölden samt applicering av färgstripper.</p>

<h2>Demontering</h2>

<p>Dags att börja meka. Min ambition är att komma åt det mesta av drevets delar utan att gå så långt som att plocka isär det i alla sina beståndsdelar. Köpte Selocs manual - <strong>&#8220;Volvo Penta Stern Drives 1992-2002 Repair Manual&#8221;</strong> - från <a href="http://www.drev.se">www.drev.se</a> (finns en från Clymer också, vet ej vilken som är bäst) och följer instruktionen för att plocka av drevet.</p>

<p>Det första man noterar är att den lyftögla som man ska använda i oljestickans hål för att enkelt kunna hänga upp drevet inte går att köpa hos <a href="http://www.bjornhammarvarvet.se">min Volvo Penta dealer</a>. De berättar att de tillverkat egna sådana öglor! Ok, det ska alltså vara en lyftögla med tumgänga, 1/2&#8221;. Kollar med en rad järnaffärer och handlar till slut hos Stockholms expertbutik - <a href="http://www.sifvert-skruv.se">Sifvert</a>. Där plockar jag med lite hjälp ihop en lös ögla + en stoppskruv och landar på 150:-. På vägen hem trillar jag in på Jula och tror knappt mina ögon <strong>när de faktiskt har en enda sorts lyftögla - precis en sådan jag vill ha! För 29:-, ok.</strong></p>

<p>[nggtags id=1 template=caption2 gallery=tag1]</p>

<p>Med öglan iskruvad och en provisorisk stång monterad över båtens akter kan jag skrida till verket med avmonteringen av drevet vilket visar sig vara en relativt enkel operation. Kåpan har jag ju tagit av tidigare, tre enkla muttrar så att man kommer åt växelmekanismen. (Grattis Finland, ni tog precis VM-guldet!) Momenten i översikt:</p>

<ol>
<li><p>Plocka loss trimstängerna från drevet.</p></li>
<li><p>Plocka loss växelvajern från växelmekanismen.</p></li>
<li><p>Plocka loss de sex låsmuttrarna som håller drevet och dra ut drevet från skölden.</p></li>
</ol>


<p>Vad gäller trimstängerna så varnade varvet för att låsringarna kan gå sönder när man knackar av/på dem, och de kostar 50:- styck! Mina höll dock, men jag var försiktig. Därefter fick jag tålmodigt knacka axeln rakt igenom drevet ut till andra sidan, använde ett armeringsjärn för att kunna knacka vidare när den försvann in i hålet. Seloc säger att man ska använda gummiklubba, men hade ingen sådan :)</p>

<p>[nggtags id=1 template=caption2 gallery=tag2]</p>

<p>Växelvajern var också lätt att plocka bort - tricket här är nog att <strong>dokumentera väl</strong> hur den var monterad. Jag räknade varven som låskuben var påskruvad på vajern, och tog lite foton! När man lossat vajern är det dags att lossa dess infästning på baksidan. När skruven är lös kan man dra ut låsblecket åt sidan så att vajern går att dra ut. På bilden ser man att blecket är utdraget cirka 1 cm och man ser också skåran i växelvajerns plasthölje som blecket var instucket i.</p>

<p>[nggtags id=1 template=caption2 gallery=tag3]</p>

<p>Dags att göra den stora manövern. Lossar de sex muttrarna och när jag försöker få loss den sjätte börjar tappen att snurra! Blir lite stressad eftersom jag inte förstår hur jag nu ska göra - men det visar sig att det bara är att skruva vidare, hela skruven kommer ut istället, puh! När alla sex är borta tar jag tag i drevet och rycker ut det sakta men säkert, ta emot drevaxeln bara så att den inte trillar ner och får sig en smäll. När drevet väl hänger kan jag känna efter hur tungt det är och visst, tungt är det men jag orkar lyfta det så inte så svårt att hantera ensam.</p>

<p>[nggtags id=1 template=caption2 gallery=tag4]</p>

<p>Värt att notera är de nästan helt bortrostade fästena för plastskydden på sidorna om drevet, samt saltavlagringarna väl synliga i huset. Där är det också en del korrosion faktiskt, ska se ifall man kan kromatera lite där. Det viktigaste - knuten - ser dock väldigt bra ut :)</p>

<p>[nggtags id=1 template=caption2 gallery=tag5]</p>

<p>För att senare kunna rengöra och måla delarna av drevet som sitter kvar på båten vill jag i alla fall få bort det yttre &#8220;huset&#8221; för att komma åt bättre. Läste om en annan kille i USA som <a href="http://www.boated.com/forum/topic.asp?TOPIC_ID=146008">plockat isär sitt drev och plastblästrat det</a> - men jag orkar nog inte gå lika långt som han gick för att ta loss &#8220;gimbal ring&#8221; osv, det verkar krävas en del specialverktyg också.</p>

<p>Börjar med att lossa bälgarna, den övre är enkel att &#8220;trycka in&#8221;. Med hjälp av en stor skruvmejsel bänder man enkelt den över halskanten. Den under avgasbälgen är svårare - här behöver man verkligen en sk &#8220;inre ringtång&#8221; för att ta tag och få loss den inre metallringen som säkrar bälgen runt halsen. Åter ett inköp på Jula. Manualen tipsar om att vara försiktig för den kan sprätta iväg ordentligt ifall man tappar ringen.</p>

<p>[nggtags id=1 template=caption2 gallery=tag6]</p>

<p>Därefter ska vi skruva loss de två feta &#8220;bultarna&#8221; på sidorna, eh&#8230; ok. Seloc säger att jag ska använda en <em><strong>1/2&#8221; hex drive with a ratchet</strong></em>. Ehum, ok? Efter lite förvirring kring metriska insexnycklar (som tyvärr nästan passar) inser jag att det jag måste ha är alltså en <strong>halvtums insexhylsa</strong>, dvs insexnyckel för montering på hylsnyckeldragare. Problemet är att de flesta vanliga L-formade insexnyckelsatser i tum, inklusive den jag redan har, stannar precis på storleken innan, dvs 3/8&#8221;. Jula verkade inte ha något och inte heller en Claes Ohlson jag sprang förbi. Till slut hittar jag en lös insexhylsa hos <a href="http://www.tools.se/taby/">TOOLS i Täby</a> - tack, tack! Men mer om det i nästa artikel, nu går vi vidare med att försöka strippa drevet&#8230;</p>

<p>[nggtags id=1 template=caption2 gallery=tag7]</p>

<h2>FedEx levererar</h2>

<p>Som jag nämnde i förra artikeln beställde jag fyra spännande kemikalier från <a href="http://www.chemical-supermarket.com">www.chemical-supermarket.com</a>:</p>

<ol>
<li><p><a href="http://www.chemical-supermarket.com/EFS-2500-Paint-Stripper-p639.html">EFS 2500</a>, färgstripper.</p></li>
<li><p><a href="http://www.chemical-supermarket.com/Metalprep-79-p370.html">Metalprep 79</a>, metallpreparationsvätska.</p></li>
<li><p><a href="http://www.chemical-supermarket.com/Henkel-Alodine-T-5900-RTU-Conversion-Coating-p601.html">T5900 TCP</a>, kromateringsvätska.</p></li>
<li><p><a href="http://www.chemical-supermarket.com/Stratocoat-Green-Epoxy-Primer-p318.html">Stratocoat Green Epoxy primer</a>, superprimer.</p></li>
</ol>


<p>[nggtags id=1 template=caption2 gallery=tag8]</p>

<p>Allt levererades prydligt inslaget och nu har det blivit dags att se ifall strippern är <a href="http://www.m-tc.com/efs2500_home.htm">så otrolig som den verkar</a>! Jag börjar med att använda Henkels Degreaser som jag köpt på Seasea, enklast att hälla över i en vanlig sprayflaska, spraya och torka av med en gammal T-shirt som trasa (luddar ej).</p>

<p>Därefter tar jag och häller upp strippern i en liten mugg och penslar på med en vanlig pensel. Använder gummihandskar men denna vätska känns inte alls &#8220;farlig&#8221; att hantera, som tapetklister egentligen. Tyvärr är temperaturen relativt låg, kanske 17 grader som mest på dagen. Helst ska det vara 25-29 grader varmt, men det ska fungera i låga temperaturer men då kan det ta flera dagar tills det är helt klart. Penslar hela drevet överallt där jag kommer åt, har vid detta laget bestämt mig för att göra &#8220;rent hus&#8221;.</p>

<p>Slår därefter in hela drevet i en sopsäck eftersom det är risk för regn. Efter några timmar ser man hur färgen &#8220;bubblar upp&#8221;, både delar av lacken och självklart också resterna av den hårda Triluxen som bubblar upp bara inom någon timme, den färgen är ju inte alls lika hård som själva lacken.</p>

<p>[nggtags id=1 template=caption2 gallery=tag9]</p>

<p>Blir otroligt spännande att se ifall det blir så rent som det ser ut på hemsidan! Ifall allt går enligt plan ska jag kunna blåsa av flagorna med högtryckstvätten eller skrubba bort med en grov tvättsvamp.</p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[Konsten att måla ett drev, del 1]]></title>
    <link href="http://goran.krampe.se/2011/05/02/konsten-att-mala-ett-drev-del-1/"/>
    <updated>2011-05-02T01:40:39+02:00</updated>
    <id>http://goran.krampe.se/2011/05/02/konsten-att-mala-ett-drev-del-1</id>
    <content type="html"><![CDATA[<p>Vi som kör inombordare i våra båtar har typiskt drev från Volvo Penta eller Mercruiser. Dreven är av aluminium, eller typiskt någon sorts aluminiumlegering och att måla aluminium är en tekniskt sett mycket intressant process och de flesta som gjort detta kan säkert vittna om att det inte funkar så bra, färgen lossnar helt enkelt efter ett tag. Det verkar gått så långt att många helt enkelt inte ens bryr sig om att försöka bygga upp en korrekt målning utan istället slänger på lite primer och antifouling direkt på aluminiumet och får göra om samma visa efter nåt år!</p>

<p>Ifall du frågar ditt lokala båtvarv, din färgaffär, din billackeringsfirma eller kanske din marinbutik så tror du att de borde veta hur man gör detta på bästa sätt, eller hur? Men det är inte alls troligt! I alla fall inte enligt mina erfarenheter när jag gjorde just detta.</p>

<p>Mitt drev - ett Volvo Penta DP-SM drev från 1998-99 - hade råkat ut för en hel del ytkorrosion, antagligen under föregående ägares sista säsong med landström på bryggan (ajajaj). Det märktes dock inte eftersom hela drevet var målat i svart Trilux-färg (vilket i sig känns lite knepigt - visst, koppartiocyanat, men ändå&#8230;), men när jag började skrapa så slutade det med att jag fick slipa ner drevet till aluminium på kanske 30% av ytan! Ja, båda anoderna var ordentligt slut, på bara en säsong.</p>

<p><strong>OBS!</strong> Slipa bara med aluminiumoxid-papper, icke metalliska saker eller sand. Absolut inte stålborste (om den inte är av rostfritt stål) eller stålull, dessa släpper ifrån sig stål in i aluminiumytan och det kommer sedan att rosta som attans. Jag använde tyvärr en stålborste på borrmaskin (osäker på vad den är av, men knappast rostfri) och har försökt slipa ytterligare för att bli av med det, osäker på om det lyckas.</p>

<p>Nörd som jag är så ville jag veta hur Volvo Penta anser att man bör lacka upp ett drev från grunden och lyckades till slut få tag på verkstadshandboken på nätet för detta drev. Värt att notera i detta sammanhang är att boken för min motor från 1998 (V8 5.7GS) har gamla instruktioner och den lite nyare handboken för 5.7Gi etc har uppdaterade instruktioner för målning av DP-S/SX-drev!</p>

<p><em>Jag utgår ifrån att Volvo Penta insåg att de behövde justera råden eftersom DP-S/SX-dreven är gjutna i en kisel-aluminiumlegerin. Har ej bekräftat detta med Volvo Penta, men en annan teori kan ju vara att de ändrade tillverkningsprocessen av SX/DP-S efter några år, men det verkar osannolikt. Tacksam ifall någon kan bringa klarhet i detta.</em></p>

<p>Hur som helst, följande text återfinns i verkstadshandboken (tror inte Volvo Penta blir arga ifall jag återger den här):</p>

<blockquote><ol>
<li>Remove all marine growth.</li>
</ol>
</blockquote>

<ol>
<li><p>Remove all loose paint and corrosion by sanding or sandblasting.
If sandblasting, use an aluminum oxide blasting media with a particulate
size of 0.008-0.028 in. (0.2-0.7 mm).</p></li>
<li><p>Remove all trace of grease and wash with hot water and detergent.
Roughen all painted surfaces with medium 3M ScotchbriteTM
pad. Rinse thoroughly with water.</p></li>
<li><p>Treat any bare aluminum with chromate conversion coating. Clean
the entire area with an acid cleaner that does not contain fluoride,
such as DuPont 5717. Scrub the surface with 3M ScotchbriteTM
pad until it is completely “wetted” with no beads of water.</p></li>
</ol>


<p>Note! Fluoride in a cleaner causes a “smut” (dark discoloration
on silicon-alloy aluminum castings), and paint will not
stick to “smut”. If this happens, sand the surface and start
over using a different acid cleaner.</p>

<p>Note! Do not use steel wool. Small pieces of steel wool become
embedded in the aluminum and will cause severe corrosion.</p>

<ol>
<li><p>Rinse thoroughly with water. The area must appear “wetted” or the
surface is not clean, and paint will not adhere.</p></li>
<li><p>While the surface is still wet from rinsing, treat all bare aluminum
with DuPont 226S chromate conversion solution. Brush the chromate
solution as required for 2 to 5 minutes to prevent it from drying
on the surface. Rinse the surface thoroughly with water and
allow to air dry. Follow the label instructions exactly.</p></li>
</ol>


<p>–If the chromate is allowed to dry anywhere on the bare aluminum
surface, chromic acid salts will form which will prevent
paint adhesion and promote corrosion. Sand the surface to
bare metal.
–It is best to let the part air dry, but if you must wipe the surface
to speed up drying, use lint free wipes not treated with
anything that may contaminate the surface. Do not scrub the
surface, wipe very lightly.
–Do not blow dry with shop air unless it is completely free of
dirt, oil, and water.
–Do not heat the part above 150°F, before painting.
–Do not touch the treated surface with bare bands before
painting.
–The part should be primed soon after it dries, or at least
within 24 hours.</p>

<ol>
<li><p>Where the prime coat is thin or where the surface is unpainted,
prime with Volvo Penta Primer or PPG Super Koropon epoxy
primer. Do not apply primer over hard finish coat. Primer solvents
must be allowed time to evaporate and the primer must harden
before applying the finish coat. Allow 8 to 12 hours drying time.</p></li>
<li><p>Apply finish coat. The parts catalogs list numbers for finishing
products.</p></li>
</ol>


<p>Ok&#8230; här visar det sig gömmas ett helt kunskapsområde att gräva i som de flesta inte har en aning om vad det är. Pröva med att fråga ditt varv om de vet vad <a href="http://en.wikipedia.org/wiki/Chromate_conversion_coating">kromatering</a> eller <a href="http://en.wikipedia.org/wiki/Passivation">passivering</a> av aluminium är, eller om de hört talas om Alodine!</p>

<p>Medlen som nämns, DuPont 5717 samt DuPont 226S är en metallpreparationsvätska resp. en kromateringsvätska. Dessa ämnen finns i olika tappningar från olika leverantörer, exempelvis motsvarande DX533 samt DX503 från <a href="http://www.ppg.com/">PPG</a> eller olika varianter kallade Alodine från Henkel. Preparationsvätskan kallas ofta för Alumiprep 33 (dock ej den vi ska använda till ett DP-S/SX-drev, läs vidare) och kromateringsvätskan kallas generellt för Alodine, det är visserligen ett produktnamn men har blivit näst intill synonymt med &#8220;kromateringsvätska för aluminium&#8221;.</p>

<p>NOT: &#8220;State of the art&#8221; idag är tydligen elektrokeramisk behandling kallad <a href="http://henkelec2.com/marine.htm">Alodine EC2</a></p>

<p>Preparationsvätskan är i grunden baserad på forsforsyra som helt enkelt djuprengör ytan från oxidering, korrosion och annat jox. Kromateringsvätskan genomför en kromatering (även kallat mer generellt för <a href="http://en.wikipedia.org/wiki/Passivation">passivering</a>) av aluminiumets yta, dvs det är ett extremt tunnt lager som kemiskt binds mycket starkt med det yttersta skiktet av aluminiumet. Detta skikt förhindrar korrosion och ger en mycket bättre yta att måla vidare på. Detta är otroligt viktigt för resten av målningsprocessen ifall vi vill ha en lackering som håller lika bra som Volvo Pentas originallack dsv mer än några få säsonger - <strong>kort sagt, kromateringen sitter benhårt på aluminium och primern sitter benhårt på kromateringen i sin tur!</strong> Volvo Penta har (läste jag någonstans) under 30 år använt denna kromatering i deras lackprocess.</p>

<p>Alodine har traditionellt varit baserat på <a href="http://en.wikipedia.org/wiki/Hexavalent_chromium">sexvärt krom</a>, giftigt som satan! Kommer du ihåg <a href="http://sv.wikipedia.org/wiki/Erin_Brockovich_(film">Erin Brockovich</a>)? Japp, sexvärt Krom. Kallas &#8220;hexavalent&#8221; på engelska. Jag utgår ifrån att Volvo använt Alodine baserat på sexvärt krom. Ifall man googlar på nyckelord som passivering av aluminium, kromatering osv så hittar man svenska industriföretag som sysslar med detta.</p>

<p>Jag hittade också <a href="http://www.boatered.com/forum/topic.asp?TOPIC_ID=97217">denna mycket bra beskrivning</a> av en person som använt ovanstående process själv för att måla drev, med goda resultat.</p>

<p>Men hur ska vi göra som privatpersoner? För det första hittar jag inga affärer i Sverige som saluför dessa ämnen, rätta mig ifall jag har fel. För det andra vill i alla fall inte jag ta i sexvärt krom med en 5 meter lång tång ens, det är cancerogent och man måste ha avancerad skyddsutrustning osv. Inget för hobby-Pelle hemma på gården alltså! Men under senare år har det alltså dykt upp en rad olika alternativa vätskor/processer som exempelvis ChromitAL TCP, Surtec 609 Zetacoat osv. Flera av dessa baseras på trevärt krom som inte alls är giftigt!</p>

<p>På nätet finns det <a href="http://www.aircraftspruce.com">en affär som de flesta jänkare refererar till</a>, och där finns alla dessa ämnen - men de levererar inte internationellt&#8230; Efter att ha pratat med tonvis med folk så hade jag vid det här laget bestämt mig för att hoppa över kromateringen och köra på den varianten som de flesta rekommenderar:</p>

<ol>
<li><p>Slipa ner, undvik stål och sand. Jag försöker behålla originallackskiktet där det går. Har ingen bläster som såklart är det bästa utan använder skrapa + aluoxidpapper + borrmaskin med slipstift eller icke stålborste.</p></li>
<li><p>Använd avfettning, typ Henkel Degreaser, finns i båtshoppen. Tar bort fetter och oljor osv.</p></li>
<li><p>Högtryckstvätta som en idiot. Möjligen slabba på slutet med avjoniserat vatten för att bli av med salter i kranvattnet.</p></li>
<li><p>Måla med en 2-komponents epoxy primer enligt instruktion. Jag valde att köpa Henkels standardprimer från båtshoppen. Första lagret ska målas förtunnat, sedan 3-4 lager till.</p></li>
<li><p>Dags för Volvos originalfärg på sprayburk. DP-S har metallic.</p></li>
<li><p>Metallic behöver klarlack, Volvos återigen på sprayburk.</p></li>
</ol>


<p>Värt att notera med ovanstående är:</p>

<ul>
<li><p>Vi använder inte självetsande primer. För det första är det enligt flera &#8220;old school&#8221;. För det andra tycks epoxy primern har svårt att fästa på sådan primer och de flesta avråder från det. För det tredje har International slutat att sälja sin Etching Primer och rekommenderar istället att göra som Henkels epoxy primer beskriver - förtunnat lager och därefter en rad lager till, direkt på aluminiumet. De anser att det blir bättre än etsande primer tydligen, enligt en kille på färgaffären.</p></li>
<li><p>Degreasern klarar inte av att få bort oxidationen och jag är osäker på hur effektiv den är mot kiseln som ju finns inne i aluminiumet. Detta tillsammans med att vi inte fått stopp på aluminiumets korrosionsförmåga och att primern har svårt att fästa på aluminiumet är de stora svagheterna. Inte undra på att alla som sysslar med detta säger att, &#8220;Tja, du får vara beredd på att måla om efter några säsonger&#8230;&#8221;. Färgen fäster helt enkelt inte tillräckligt bra och oxidationen kommer tillbaka.</p></li>
</ul>


<p>Det gnagde i mig att det borde gå att få tag på de där två vätskorna ändå. Det var då jag till slut hittade <a href="http://www.chemical-supermarket.com">www.chemical-supermarket.com</a> - aha! De har både giftiga varianter och moderna sorter fria från sexvärt krom. <strong>Game on!</strong></p>

<p>Jag satsar på Chromital TCP från Henkel dvs <a href="http://www.chemical-supermarket.com/Henkel-Alodine-T-5900-RTU-Conversion-Coating-p601.html">T5900-TCP</a> samt <a href="http://www.chemical-supermarket.com/Metalprep-79-p370.html">Metal Prep 79</a> som preparationsvätska istället för Alumiprep. Detta eftersom jag hittat på nätet att Metal Prep 79 rekommenderas av Henkel för kisel-aluminiumlegeringar eftersom den ej innehåller fluor, också noterat i Volvos instruktion. Alumiprep 33 avråder Henkel ifrån. T5900-TCP (TCP står för Trivalent Chromium Process) har också erhållit militärt godkännande i USA och visar näst intill lika bra egenskaper som referensprodukten Alodine 1200S (sexvärt krom) samt är inte alls lika giftig och läskig att använda. De helt kromfria varianterna visar inte riktigt lika bra resultat som TCP-varianterna.</p>

<p>När jag ändå bestämt mig för att köpa saker från chemical-supermarket så slog jag också till på <a href="http://www.chemical-supermarket.com/Stratocoat-Green-Epoxy-Primer-p318.html">deras Epoxy Primer</a> som verkar vara riktigt vass, också godkänd för militärt bruk, samt deras stripper <a href="http://www.chemical-supermarket.com/EFS-2500-Paint-Stripper-p639.html">EFS 2500</a> för färgborttagning, uppenbarligen något i hästväg. Ska bli intressant att se ifall strippern kan ta resten av färgen på drevet utan slipning!</p>

<p>Alla fyra produkter landar totalt på 174 dollar, men FedEx-frakten går lös på 253 dollar! Vi landar således på <strong>427 dollar dvs cirka 2700:-</strong>, inte billigt direkt.</p>

<p>Nu ser vår reviderade process ut såhär:</p>

<ol>
<li><p>Pröva EFS-2500 Paint Stripper. Ifall den funkar extremt bra så gör jag drevet 100% rent. Annars försöker jag behålla originallacken där det går. Har ingen bläster som såklart är det bästa utan använder skrapa + sandpapper + borrmaskin med slipstift eller icke stålborste.</p></li>
<li><p>Använd avfettning, typ Henkel Degreaser, finns i båtshoppen. Tar bort fetter och oljor osv.</p></li>
<li><p>Högtryckstvätta.</p></li>
<li><p>Använd Metal Prep 79 enligt instruktion. Penslas på några minuter och sköljs av, skall ej torka på ytan. Vattnet skall sluta bilda droppar. Gummihandskar, förkläde och skyddsglasögon samt god ventilation är viktigt!</p></li>
<li><p>Högtryckstvätta samt skölja med avjoniserat vatten för att bli av med salter i kranvattnet.</p></li>
<li><p>Använd T5900-TCP enligt instruktion. Penslas på några minuter och sköljs av. Gummihandskar, förkläde och skyddsglasögon samt god ventilation är viktigt!</p></li>
<li><p>Måla med Stratocoat Green epoxy primer enligt instruktion. Antagligen 2-3 lager.</p></li>
<li><p>Dags för Volvos originalfärg på sprayburk. DP-S har metallic så det blir klarlack på det också.</p></li>
<li><p>Klarlack, Volvos återigen.</p></li>
</ol>


<p>Vi är därmed uppe i cirka 6 lager, vilket ju är barnsligt jämfört med Volvos 19 i deras process! :) Steg 8 och 9 skulle kunna vara mer avancerade men jag kör gärna Volvo originalprylar på den nivån.</p>

<p>Detta är sålunda planen, i nästa artikel tänker jag visa steg för steg med bilder och detaljerade instruktioner samt tidsåtgång.</p>

<p>Ifall jag har faktafel, kommentera så justerar jag gärna. Ifall någon har mer kunskaper i ämnet, kommentera så lägger jag gärna till. Ifall någon firma erbjuder tjänster för kromatering av drev - maila så kan jag lägga in länkar till er.</p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[Tirade, supporting embedded text]]></title>
    <link href="http://goran.krampe.se/2011/04/15/tirade-supporting-embedded-text/"/>
    <updated>2011-04-15T03:22:58+02:00</updated>
    <id>http://goran.krampe.se/2011/04/15/tirade-supporting-embedded-text</id>
    <content type="html"><![CDATA[<p>Two years ago I ended up creating <a href="http://goran.krampe.se/2009/03/16/tirade-a-file-format-for-smalltalkers/">Tirade</a> - a new &#8220;file format&#8221; for Smalltalkers. Or rather, a way to serialize stuff into a sequence of Smalltalk messages with literals as arguments. I have written a <a href="http://goran.krampe.se/category/tirade">few blog articles about Tirade</a> so I will not go into details in this one.</p>

<p>One thing that has been disturbing with Tirade is that I wanted it to be the main format for serializing Deltas, the new implementation of &#8220;21st Century ChangeSets&#8221;. This means I want Tirade to handle Smalltalk source code in the best possible way. Ideally I would want the Tirade file to be editable in a text editor if I wanted, and not being broken by that.</p>

<p>So, what properties do we want:</p>

<ol>
<li><p><strong>No escaping of special characters.</strong> In regular Tirade strings (just like in Smalltalk) need to escape the single quote as doubled single quote, and that would suck for Smalltalk code of course.</p></li>
<li><p><strong>No length encoding.</strong> One way to avoid escaping is to store the length of the data before the actual data - like a <a href="http://cr.yp.to/proto/netstrings.txt">Netstring</a> for example. This prohibits easy editing in a text editor though, since that would change the length.</p></li>
<li><p><strong>A reasonable syntax.</strong> Tirade so far has been a subset of Smalltalk (disregarding lack of receiver to the left), but I think we might have to break that a bit here.</p></li>
</ol>


<p>After pondering this for a while I have come up with this solution which feels kinda nice, but <strong>if someone has an even better idea I am all ears</strong>. This is how it could look embedding a method source in Tirade:</p>

<pre><code>class: #MyClass selector: #at:put: source: [
    at: pos put: arg
    "Put something here"

    ^array at: pos put: arg
].
</code></pre>

<p>So what gives here?  We are reusing the syntax for Smalltalk blocks without arguments. Simply [&#8230;content&#8230;]. The content will be delivered as a String and the guarantee is that it will be received exactly as sent. There is a trick here - this is what Tirade will do:</p>

<ol>
<li><p>Write the starter $[ and then a CR</p></li>
<li><p>Before each line in the string (a line being all characters up to and including the next CR or up to end) we insert a TAB. This means that the String begins on the line after the opening $[ and all lines will be prefixed with a TAB.</p></li>
<li><p>Then, regardless if the last line ended with a CR or not - we add a CR before the closing $]. This makes sure the closing $] ends up on its own line.</p></li>
</ol>


<p>The above trick gives us the ability to detect the end of the string because if a line starts with something else than a TAB then we have reached the end. Thus we do not have to escape the $] inside the string and we still don&#8217;t need to do length encoding. <strong>We DO however need to make sure all lines begin with a TAB, but if you are editing a Tirade file you should just learn that fact. :)</strong></p>

<p>I am not sure if the above is a good solution, but it is ONE solution and I can&#8217;t come up with a better one, unless we would use a really &#8220;odd&#8221; marker at the end in order to not have to escape it, but that feels &#8220;dirty&#8221; to me.</p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[Preaching Smalltalk inside a nuclear reactor]]></title>
    <link href="http://goran.krampe.se/2011/04/08/preaching-smalltalk-inside-a-nuclear-reactor/"/>
    <updated>2011-04-08T14:07:35+02:00</updated>
    <id>http://goran.krampe.se/2011/04/08/preaching-smalltalk-inside-a-nuclear-reactor</id>
    <content type="html"><![CDATA[<p>&#8230;is what I did yesterday. It was the <a href="http://sites.google.com/site/stockholmgtug">Stockholm GTUG</a> group having a loose and laid back meetup in a rather special venue - R1, <a href="http://sv.wikipedia.org/wiki/R1_(reaktor">Sweden&#8217;s first nuclear reactor</a>)! 27 meters below ground, kinda&#8230; funky.</p>

<p>Anyway, I tried doing an ultra compact version of several of my other presentations around <a href="http://www.world.st">Smalltalk</a> and <a href="http://www.seaside.st">Seaside</a> - didn&#8217;t really go 100% since I both had some technical issues (keyboard problems and projector issues too) and ended up taking more time than was planned. Hopefully noone got upset about that.</p>

<p>In about 60 minutes I taught the <strong>whole language in 5 slides</strong> (the language is very small from a semantic and grammatic view), a bit of the amazing history behind Smalltalk, some of the traditional tools in a classic Smalltalk environment - and finally, a quick whipup of a Todolist app in Seaside, <strong>including support for the back button!</strong> I used <a href="http://www.squeak.org">Squeak</a> and <a href="http://www.pharo-project.org">Pharo</a> and I hope I get to do a similar presentation some other time - then I will polish it and try to keep the &#8220;blitz&#8221; tempo. Shock and awe. :)</p>

<p>I think the audience appreciated it (always hard to tell), would have been nice to show more of course - I could easily spend a whole day teaching Smalltalk and various mind blowing aspects around the environment, the language, cool libraries and techniques - and of course Seaside.</p>

<p>Then I spent some time chatting with my friend <a href="http://divineprogrammer.blogspot.com">Mikael Kindborg</a> (also a Smalltalker at heart) and a couple of his colleagues from <a href="http://www.mosync.com">Mosync</a> who were actually sponsoring the event with beer, wine and sandwiches. It was a nice evening and it&#8217;s always fun to show Smalltalk to people who have never seen it.</p>
]]></content>
  </entry>
  
  <entry>
    <title type="html"><![CDATA[Node.js vs Nginx/Squeak, part 1]]></title>
    <link href="http://goran.krampe.se/2011/03/14/node-js-vs-nginxsqueak-part-1/"/>
    <updated>2011-03-14T17:55:58+01:00</updated>
    <id>http://goran.krampe.se/2011/03/14/node-js-vs-nginxsqueak-part-1</id>
    <content type="html"><![CDATA[<p>Hmmm, after seeing the <a href="http://nodejs.org">Node.js</a> presentation at <a href="http://swdc-central.com/dyncon2011/index.html">Dyncon 2011</a> I couldn&#8217;t help installing Nginx and Blackfoot (SimpleCGI) in a Squeak 4.2 image running on the Cog VM to make some performance tests! In fact I started doing that during the presentation. :)</p>

<p>My first run on Nginx/Squeak looked quite unimpressive. Well, one client doing 1300 req/s to a small helloworld was decent although Node.js handled approximately 2x that. With Nginx we have a two tier solution so a factor of 2 is not really surprising in this trivial case. Top showed similar load, both solutions only seem to consume 8-9% of my CPU power on this box, but the Nginx/Squeak solution of course spreads load between them with approximately 1/3 or 1/4 on nginx.</p>

<p>But jacking up concurrent clients really destroys Nginx/Squeak! How come? I was surprised because my memory of this when I wrote Blackfoot was that it was handling that fairly ok. Trying 50 concurrent clients with Node.js pushes it up to almost <strong>8000 req/s</strong>! Quite impressive and it still only uses about 9% of my CPU power. Blackfoot ends up serving less than 1/10nth of that. Now, thinking and looking more closely it is quite obvious - SCGI opens <strong>a new connection for each request&#8230; ouch</strong>. Why on earth did they design SCGI like that? So basically Nginx will hammer Squeak just like we hammer Nginx I guess, and Squeak doesn&#8217;t deal with that too nicely.</p>

<p>A small experiment with firing up 3-5 Squeak backends and letting Nginx load balance over them (really simple to do) shows that we can get around this somewhat and scare Blackfoot into serving over <strong>3000 req/s</strong> and still not going over 30% CPU. Not that shabby, but still not in the same league as Node.js, but now we know why - we need a solution that holds the connection open between Nginx and the backend.</p>

<p>At this point I wanted to try three things:</p>

<ol>
<li><p>What numbers can Nginx on its own produce, just returning a small HelloWorld file?</p></li>
<li><p>What numbers can plain KomHttpServer running on Cog produce?</p></li>
<li><p>And finally, how does Nginx/AJP/Squeak behave? AJP does keep the connection open I think.</p></li>
</ol>


<p>Let&#8217;s guess first - plain Nginx should beat Node.js, Kom with Cog is probably not much faster than regular Squeak VM since the issues I believe are in the Socket plugin (and we saw that it didn&#8217;t like getting hammered by Nginx), and finally I am hoping AJP puts Squeak at say half Node.js even with 50 concurrent clients, that would be 4000 req/s and I would be darn happy. And of course, with a load balancer on top even more, but that can be done with Node.js also of course.
So more on that next time&#8230;</p>
]]></content>
  </entry>
  
</feed>
