Author Archives: hpeyerl

Radon in our basement

By   November 27, 2016

Some folks at work were talking about their radon detectors the other day. Since I’m a sucker for gathering data, I was curious and did some reading. I’m usually not one for crackpot science and ‘radon’ just sounds like it would fit right in.

The first link I get when I type “radon” into Google is the Health Canada website and the second is Wikipedia.  Ok, maybe this isn’t so crackpot after all.

In short, radon is a colorless odorless gas.  Why is it that everything that wants to kill us is either colorless and odorless or furry and brown?   Radon is produced as a result of the decay of uranium which is in soil, rock and water. Normally it seeps out of the ground and dissipates in the air where it does us no real harm with a half-life of only 3.8 days (unlike furry brown things which don’t dissipate and have much longer half-lives).  It can cause problems when it seeps out of the ground and is trapped, say, under the concrete slab in your basement looking for a way in.  Once inside the living space of your home, when radon is inhaled, it breaks down further and emits an alpha particle, which I’ve read can strike a lung cell and cause cell death or worse, damage.  If a cell is damaged in a particular way, it can cause cancer.  As I am not a “nukular scientist” I won’t go into any more detail at the risk of confirming that I am a fool to those readers who already suspect it.    Statistically, however, the data is clear:  16% of lung cancers in Canada are caused by radon, as compared with 83% caused by smoking (Health Canada).

If the radon is under the floor of your basement, how does it get into the house? Unfortunately, it’s a very sneaky gas.  It can seep right through concrete but usually prefers to enter through cracks or the seams between your basement walls and floor; or any openings like those left for plumbing cleanouts.  As many of you know,  we spent about five years renovating our Bergen home which included sealing it from top to bottom and adding a heat exchanger to keep the air fresh while reducing the amount of lost energy.  Normally when it’s cold outside and your furnace comes on to heat your cold toes, that warm air rises and looks to escape through your ceiling (stack effect)…  Even the wind blowing on one side of your home can create a lower pressure area on the other side of your home pulling valuable warm air from inside the house.   All of that escaping air creates a slight negative pressure in your home and must be replaced by air from elsewhere.  Since most of our homes are relatively well sealed, that makeup air has to come from somewhere so it gets pulled from the under slab in your basement through the cracks and openings I mentioned above.

At first I thought I would measure the radon in our home.  We have a heat recovery ventilator and  I figured that since the air is being exchanged quite frequently, it would not be an issue.  So I bought an electronic radon detector for about $250 and put it in the basement.  There are a few different varieties of detectors.  The less expensive ones are the type you put in your basement for three to six months and then mail away to a lab where they are analyzed and the results mailed back to you.  These can be had for approximately $20 but I wanted something a little more interactive so I went with the electronic version that can give a very approximate number within 24 hours and more accurate data as time goes on.

In Canada, radon is measured using “becquerels per cubic meter”.  The World Health Organization recommends a national guideline of 100 bq/m3.  Health Canada has set our guideline at 200 bq/m3.

Within 24 hours, the first reading that came back from our detector was 446 bq/m3.  Since this is a very rough number as a first reading, I decided to give it a week to get something closer to accurate.  Well, seven days later, the reading was substantially higher:  1031 bq/m3.


More than five times what Health Canada recommends as the upper limit, and more than ten times what the World Health Organization recommends.

I decided then that it was time to do something.  My goal was to get our readings below 100 bq/m3.  I read up on mitigation methods and it looked promising.  The best way to mitigate the problem is before the house is built but obviously that’s not an option for us, so I had to look at a retrofit solution.   It turns out the way this is done is by installing a fan outside the home (or in the attic) to suck air through a hole in the concrete slab and blow it up and away from the home.  The theory is that the gravel underneath your basement floor is fairly porous, so even creating a negative pressure zone in one corner will eventually suck the radon from all over the slab.   Normally a radon contractor will be happy to come into your home and install such a thing for $3000 or so.  In our case, a plumber already left a convenient hole in our floor exposing the gravel at the bottom through which  we were mining for radon.


I knew that I could probably seal the hole and maybe reduce the radon levels a bit but I also suspect that it wouldn’t be significant enough given the various effects of air pressure during the heating months or windy months.  I like to think I’m a fairly handy guy (how did Red Green put it?  “If the women don’t find you handsome, at least let them find you handy!”), I decided the right thing to do was to follow the recommended mitigation method and install the fan.  The fan itself was $300 plus another $100 in PVC pipes and fittings.   The fan needs to be mounted outside of the living space.  You don’t want it inside the living space because the other side of the fan is pushing high concentrations of radon gas and a small leak will have you back to mining for radon again.   It took about 6 hours of work but I finally had the fan hooked up outside the house and powered it up for the first time.  I reset the detector and waited.

24 hours later, the first reading came in.  38 bq/m3.  I was cautiously optimistic.  A week later, it read 2 bq/m3.


Now the drawbacks.  The fan is fairly loud when it’s running; especially at the top of the 4″ PVC pipe that’s sticking up the side of the house.  It’s also fairly ugly.  While the fan is fairly energy efficient, it does consume 82 watts which is about $50/year in electricity.

Over the next year, I’m going to experiment by running the fan periodically.  I’ll start with a 50% duty cycle and adjust up or down depending on the readings.  Since the fan noise isn’t significant inside the house, I’ll start by running it primarily at night and less during the day.   Ideally, I would have one of the very expensive detectors that can hook to a computer so I can add some more intelligent automation behind the process as is my nature.  I suspect I’ll be able to get by with running the fan far less during the summer ‘window open’ months.   Only the data will tell me.

Now back to figuring out what piece of technology will let me address the furry brown things.



socat on OS X – TCDRAIN returns Invalid Argument.

By   June 26, 2016

When using socat, as installed by ‘brew install socat’ on OS X, you will likely get this error when trying to proxy a serial device to another host via TCP:

TCSADRAIN, 0x7fffffffe148):Invalid argument

This is because OS X uses the FreeBSD termios interface and the bug is explained here:

This is the patch you want to apply to ‘socat’:


Unfortunately, ‘brew install socat’ just gives you someone else’s precompiled binary and you want to retrieve the source so you can apply the above patch.


Do it like so:


cd `brew --cache`
brew unpack socat
cd socat-
curl > patch
patch < patch
make install


pfSense openvpn client to generic openvpn server in bridge mode

By   May 27, 2016

This should really go into the ‘memo to self’ category but I don’t have one.  Regardless…

I have an Ubuntu VM running OpenVPN in Bridge mode (tap).  I wanted to bridge my cottage network to my home network using pfSense out at the cottage. In the process of making this work, a fair amount of googling was involved so I decided to aggregate all of the information in one place in case I ever needed to reproduce it.  Friend Kurt was running up against some of the same issues.


First, make sure your OpenVPN server is working and that you have the following client specific files available (filenames will likely vary):

  • site.ovpn
  • ca.crt
  • ta.key
  • client.crt
  • client.key

On the server, I had to make some minor changes to make everything work:

If you can ping client->server but the connection hangs when you try to edit a file or view a web-page

mssfix 142
fragment 1200

If on the client, you see “OpenVPN Bad LZO decompression header byte:”? I had to comment out “comp-lzo” on the server… This seems bogus but it made it work. Need to investigate this later.

The client says “Authenticate/Decrypt packet error: cipher final failed”, the issue is the cipher being used. The default on the server was “BF-CBC” but the pfSense default was “AES-128-CBC”. Change the pfSense to “BF-CBC” and you’re good to go.

The general procedure for making this work in pfSense is the following:

    • Go to System->Cert. Manager and add your server’s “ca.crt” to Certificate Authorities. Give it a descriptive name.
    • Then go to System->Cert. Manager->certificates and add your client.crt and client.key.  Give it a descriptive name as well.   Ensure you do this after you’ve added ca.crt so that when you add this certificate, it will reference the above ca.crt.
    • Go to VPN->OpenVPN->Client and click ‘Add’
        • Select Peer-to-Peer under ‘Server mode’
        • Select ‘tap’ under ‘Device Mode’
        • Select ‘WAN’ under ‘Interface’
        • Set your server host/address to your VPN server address.
        • Set the port accordingly.
        • Set description to something you’ll recognize.
        • Under TLS Authetication, set ‘Enable authentication of TLS packets’.  It will drop down a text box into which you can paste the contents of ‘ta.key’.
        • Set ‘Peer Certificate Authority’ to the one you added above.
        • Set ‘Client Certificate’ to the one you added above.
        • Set encryption algorithm to whatever your VPN server is using (BF-CBC in my case)
        • Under ‘Custom Options’, I had:

      mssfix 142
      fragment 1200

The final note I’d like to add is one about IP addresses. When you set your ‘server-bridge’ parameter on the server’s VPN config, you assign a pool of IP addresses that are not in your dhcp server’s range. By default, the IP addresses assigned are specific to the client certificate. So if you find your clients are all getting the same IP address, it is because they each need a unique client certificate. You can override this behavior using the ‘duplicate-cn’ directive in your server’s config file. It’s generally not a good idea though so you should just create unique client certificates.

Zoro Canada – a company that doesn’t “get” e-commerce…

By   March 19, 2016

To me, a company that “gets” e-commerce is one that sends you an order confirmation, and then provides a decent interface to track your order.  Your order is fulfilled quickly, as in the same or next day.  The package is shipped the next day at the latest (barring an item that needs to be manufactured first, and that should be stated clearly before accepting the order)… Also, shipping cost is reasonable.  Handling should be part of the price. is such a company.  Recently, and on two separate occasions, I placed an order after 6PM.  I received a FedEx tracking number within 2 hours.  The package was at my door 14 hours later (North Dakota to Calgary, Canada)  Shipping was $8.00.    Simply amazing.   You’d never buy parts from Digikey for a mass produced item, but for the home DIYer, it’s an awesome service.


Contrast ZoroCanada against Digikey.   I placed an order on March 8th.  By March 12th, the status on their useless web interface said “Pending Fulfillment”.  When I called, I was told the package was being shipped from their warehouse to their fulfillment center via UPS at which point it would be given to DHL and I would receive it within 48 hours.   By March 14th, I received a DHL tracking number.  However, the tracking number was essentially that a Waybill had been created but the package had not actually been picked up because, presumably, ZoroCanada hadn’t actually called DHL.  March 16th, the DHL tracking number indicated movement.  Unfortunately, what happened next was quite surprising.   March 18th, I receive a Canada Post tracking number. DHL handed off the parcel to Canada Post at the border and as of March 19th, Canada Post tells me the parcel will be delivered on March 22nd.  Shipping cost was $55.00.  Now I understand why shipping was so expensive.  They had to pay 3 separate carriers!   The contents of this package were needed by me before today.

Don’t order from ZoroCanada


iterm2 arrow keys not working in cursor application mode

By   February 3, 2016

(TL;DR at the bottom)

This is one of those things that irritated me for ages.  I generally don’t use arrow/home/end keys for anything except when I run (rarely) certain applications like ‘make menuconfig’ where I’m forced to navigate using arrow keys.

For the longest time, the arrow keys didn’t work on iterm2 in certain applications.  After digging in, I discovered the problem.

Ages ago, I started using OS-X, but sucked so I installed iterm.  Then iterm2 came out and I upgraded.  Sometime thereafter I discovered the arrow keys didn’t work.  This morning, I decided enough was enough and I got to the bottom of it.  One of the answers on this question posted a handy little script to test whether the keys work in cursor application mode:


sh -c "$(cat <<\EOF
noecho_appmode() {
  stty -echo
  printf '\033[?1h'
modes="$(stty -g)"
restore_echo_and_appmode() {
  stty "$modes"
  printf '\033[?1l'
printf '\nType <Up> <Down> <Right> <Left> <Control-D> <Control-D>\n'
printf '(no output until after the first <Control-D>, please type "blindly")\n\t'
noecho_appmode             ; trap 'restore_echo_and_appmode' 0
cat -v
restore_echo_and_appmode   ; trap ''                         0
printf '\nExpected:\n\t'
printf 'kcu%c1\n' u d f b | /usr/bin/tput -S | cat -v
printf '\n\n'

This told me that iterm2 wasn’t working correctly. But it obviously works for many other people.



When I upgraded from iterm to iterm2, my settings survived and Preferences->Profiles->Keys (NOT Preferences->Keys) contained overrides for the arrow keys and home/end.  Once I loaded a Preset for “xterm default”, exited iterm2 and restarted it, arrow keys worked fine.



Delightful find!

By   January 21, 2016

Friend Mike sent along this Hackaday link on reverse engineering of some cheap chinese digital radio.  Since I dabble in digital radios at work it was of particular interest.  That article led me to downloading an issue of PoCk||GTFO which I had never encountered before.  A publication dedicated to reverse engineering or a glimpse into what the infinite monkeys are up to.  The writing is curiously delightful, most especially in the article on hacking a digital pregnancy test, e.g,

You can either look up the battery type to confirm it’s 3V, or just read the CE-mark label on the outside of the DPT that lists the part number, lot data, confirmation that this test is made by SPD GmbH out of Geneva, Switzerland (made in China), and that the test runs on 3V DC. Safety first, kids.

I spent my ‘hack time’ this morning reading this. [Aside: Usually I don’t allow myself the pleasure of ‘reading the internets’ in the mornings since I am smartest at 5AM and then become progressively more stupid as the day goes on.  By 21:30, I’m a drooling sack of meat barely capable of walking up the stairs to bed.   So I want to use my smart time for haxx0ring before I have to put it all down and head to work.]

Some christmas leds

By   December 1, 2015

Working on a sort of secret-santa gift for members of my truck club, I decided to do something with the WS2812B RGB LED’s. There’s a metric buttload of blog articles about these so I thought I would try to add something.

From what I can see, people are spending a lot of time dealing with timing. Nodemcu can do it but not if WIFI is enabled; or at least reliably anyway.. Since I’d had some success with the hardware SPI on the ESP8266 talking to a thermocouple amplifier, I thought I would try to get the SPI hardware to do my bitbanging for me. Turns out it’s actually quite trivial and ‘just worked’. Thanks to Joost Damad for the pattern which saved me the effort of figuring it out myself. Isn’t the internet amazing? Whenever you get a bright idea, turns out someone’s already done it.

First initialize the hardware SPI interface per David Ogilvy’s blog:

        if (initialized || sysCfg.board_id != BOARD_ID_PHROB_WS2812B)
                return true;
        spi_init_gpio(SPI_DEV, SPI_CLK_USE_DIV);
        spi_tx_byte_order(SPI_DEV, SPI_BYTE_ORDER_HIGH_TO_LOW);
        spi_rx_byte_order(SPI_DEV, SPI_BYTE_ORDER_HIGH_TO_LOW);
        initialized = 1;
        pcfg.stringlen = 16;
        pcfg.ms_delay = 500;
        os_timer_setfn(&PatternTimer, PatternTimerHandler, NULL);
        return true;

Then simply load the bit in question into the SPI data register:


        int xtemp;
        xtemp = spi_transaction(1, 8, 0x80, 0, 0, 0, 0, 0, 0);

        int xtemp;
        xtemp = spi_transaction(1, 8, 0xe0, 0, 0, 0, 0, 0, 0);

and that’s it. To send an RGB sequence for a single LED:

static inline void
ws2812b_send_color(uint8_t c)
        uint8_t bit=0x80;
        while(bit) {
                if (c&bit)

ws2812b_send_rgb(uint8_t r, uint8_t g, uint8_t b)

I haven’t really put any effort into optimizing this. I suppose it might be possible to pre-generate a pattern and blow the whole thing out the SPI but I wasn’t in the mood. What I’ve got works fairly well.

Here it is in action

Code is available here

How to reboot a DLink router from a script

By   November 7, 2015

I have a Dlink DIR-615 that periodically drops its connection to the outside world. It appears to coincide with my wireless provider going down but the DLink never recovers. I don’t know why; but whatever.

I was going to use a relay Phrob to just power cycle it but figured I’d explore doing a soft reboot since that appears to bring the connection back up. Because the HTTP foo is not strong within me, I searched and found this article which gave me the basic steps required to login to a DLink and reboot it. It didn’t work and I didn’t need to append a “A” to the password; but after some futzing and looking at the POST headers in Google Chrome, I eventually reached this script that I put in cron:

# Check whether we can see google's DNS, if not, login to the router and reboot it.

ping() {
        echo Pinging;
        ping -q -c 1 -n >/dev/null && exit 0

login() {
        curl -o - -X POST -d "html_response_page=login.asp&login_name=YWRtaW4A&login_pass=$ADMIN_PASS&graph_id=5190c&&log_pass=$ADMIN_PASS&graph_code=&login=Login" http://$ADDR/login.cgi | grep index.asp

reboot() {
        echo "Rebooting ... " ;
        curl -X POST -d  "html_response_page=reboot.asp" http://$ADDR/reboot.cgi

ping || (login && reboot)

In order to encode your $ADMIN_PASS, you need to:

$ echo -n MYPASSWORD | base64

The ADMIN_PASS=”Zm9vCg==” above is what you’d get if your admin password was “foo”.

This works on my DIR-615, Hardware Version E3 and Firmware Version 5.10. Hope it helps someone.

MQTT Config

By   October 13, 2015

MQTT Config

So as I work to integrate MQTT into my automation environment, I find myself wishing for some sort of device discovery mechanism. Possibly also a device configuration mechanism.

Here’s the problem as I see it.

If I know the topic of a device, I can subscribe to it and I can even get its last data. I can also subscribe to all topics or a subset of topics. But then I have to wait for a device to publish something in order to discover it.

Unfortunately, I can’t ask Mosquitto what devices it knows about.

There are many use-cases where this just isn’t sufficient:

  • A device that isn’t publishing when you reboot.
  • A device that is turned off and only publishes when it gets turned on (like a device that uses a tilt sensor to power itself on).
  • A device that doesn’t publish at all (a subscribe only device like a Relay).

It would also be nice to be able to re-configure some attributes of a device though I can see how this could be abused in an InternetOfThings scenario.

So I believe I’m going to define a ‘discovery’ record and experiment with that. I’m thinking something like this:




This tells me that is a sensor named “Kitchen” that publishes a temperature as an int in degrees celsius… There’s also a control named “Garage” that publishes a “Relay” state but it also has an output that it subscribes to called “Relay”… They both provide/take a boolean. There’s also a control named “Garage” that subscribes to “RelayToggle” that will conceivably cycle a relay on/off or off/on for some number of seconds.

I’ll experiment with that and see if I can make it useful… It will allow me to maintain an inventory of devices that are available… I will have to come up with some sort of expiry mechanism of course and if an attribute changes, I’ll need to override the old config with the new one presumably.

ESP8266 ESP-12 Deep Sleep

By   October 2, 2015

To address the issue of my temperature reading too high on boards with temperature/humidity sensors, I opted to deploy the ESP system_deep_sleep(us) call to put the board to sleep after publishing the temperature via MQTT.

Current draw when the board boots is 145mA until it connects to the AP, then it seems to go down to about 77mA and then when it goes to sleep, it draws about 55-60uA…

Presently I have it configured to wake up, bind to my AP, after it gets an IP, publishes the temperature/humidity and go to sleep for 30 seconds.

Here is the board:

Here’s a thermal video demonstrating this. At 00:04 and 00:35, you can see the LDO heat up when it wakes up from it’s nap:

Video was taken using a Therm-App android thermal imaging camera borrowed from Angus.