RFID Reader v2 Starts

2018-06-07 23:14 - Making

The first working prototype of the next version of my RFID reader project.

I've used Arduinos for some time now, for electronics projects. They're very easy to get started with, but a little bit limited. As I called out in the VFD clock project I did a few years ago, STM32 is a nice next step up. Pictured is a Maple Mini clone I still had from that project, easily available for around $5. Even better is the (as it's colloquially known) "Blue Pill board with almost the same functionality at around $2, and it's close cousin the "Black Pill". More speed and RAM and Flash, more peripherals. More exciting!

I designed a multi-headed RFID reader project, on top of an Arduino core. After some delays it's finally seen real usage, and revealed several opportunities for improvement. Mostly around the hardware, but if I'm going to redesign, I want to take the opportunity to revisit the software as well.

On my clock project, I found the SDK very detail-heavy and hard to work with. ST Microelectronics, which makes the STM32 chips, also makes a package called STM32CubeMX, a code generator that makes the SDK easier to consume. But it wants to output projects that specifically work with a small handful of professional (read: $$$) IDE packages. I recently discovered that Atollic TrueSTUDIO, which is in that list, is available for free download! I've spent a fair deal of free time, in small chunks, recently getting these all set up and working, and especially understood.

The plan is to take advantage of FreeRTOS, which the Cube tool can include with just a click, to handle scheduling and some other things to make this next version both faster and more stable. For now at least, I've got a proof of concept, working end-to-end, able to read cards and developed with a capable IDE with breakpoints and value inspection built right in.

Custom Game Case, from Unused Koozie

2018-05-29 17:12 - Making

The pair of source Koozies, with the Game Boy Micro on top. Top sewn up, bottom cut open, sides sewn. Flipped right side out. Tucked in. Flap closed.

Several months ago I got a pair of Koozies, which have sat unused since then. More recently I've pulled out my Game Boy Micro, which has no protective case, unlike most of my portable devices. I realized that the Koozie was the right sort of material, soft and padded, and almost exactly the right size. So I cut one side of the bottom off, sewed closed the top, and sewed the sides in closer, to be the right size. After flipping it right side out and confirming a good fit, I trimmed what was the bottom of the Koozie down, to be a flap which I can tuck in to cover the open side. It worked out quite nicely!

There was a fire, a couple buildings down from mine

2018-05-28 17:49 - General

There was a fire, a couple buildings down from mine, and I had quite the view of it. I actually smelled something first as I was sitting down to work on something, flipping the switch that enabled (among other things including the light I want) my soldering iron, but it was still in sleep mode of course. Not much later, I noticed this out the window:

That's the back side of this building. Seems pretty serious, enough to have broken through the roof. I'm totally fine, but things are a bit smelly.

Here's a story about it from the Post, which says over 100 fire fighters responded, two of which ended up with minor injuries.

My phone only lets me shoot 10 minutes of video at a time, so I had to (spend 20 minutes shooting, then) re-encode to stitch two clips together. But you get to see the blaze at (what seems) its worst through to being put out by New York's Bravest.

The wi-so-serial works!

2018-03-24 21:33 - Making

The first working wi-so-serial, installed.

For months, stalled by a partially broken computer, I've been working on this project. I have a server at home (and another for remote backups, at a relative's house). And I've got full disk encryption which needs a password to unlock, at boot. Which means if it ever reboots I have to physically be there to get it going again. I'd like to be able to administer my servers remotely.

I've looked into commercial IP KVM devices, but they cost hundreds of dollars. Since I'm working with Linux here, in theory all I need is a serial terminal. So I've designed a serial-to-WiFi bridge. The picture above is the first one that I've ever had working, installed. The ribbon cable hooks up to the internal serial port header, the green terminal plugs into an unused USB port header for power. Then there's snaking trails of several other pairs of wires: one each hooking to the case and to the motherboard for the power LED, the power button, and the reset button.

Most newer motherboards power their USB ports all the time, even while the computer is off, this one included. So I can remotely power up or down, restart, and then control the computer. In theory. I've just gotten far enough to test all this, and discover performance issues. I've got all the computer-side setup to manage, yet. But after working on this since August, it's great to have it finally proven to really be workable.

Small Tools: Bisect

2018-02-23 11:59 - Programming

Git provides a great bisect tool. When something has been broken, it will automatically help you find out how and why, by bisecting (splitting into halves) the source control history, incrementally narrowing down on changes. I've sometimes got situations where I'd like to do a similar operation on something else that's not git history, but is instead numbered. A while ago I threw together a python script to help me do this:

#!/usr/bin/env python

def main(argv):
  if len(argv) != 3:
    print "Usage: bisect.py <good> <bad>"
  good = int(argv[1])
  bad = int(argv[2])

  while True:
    if bad == good + 1:
      print "First bad:", bad

    totry = ((bad - good) / 2) + good
    inp = raw_input('At %s [g/b]: ' % totry)

    if 'g' == inp:
      good = totry
    elif 'b' == inp:
      bad = totry
      print "I don't understand."

if __name__ == '__main__':
  import sys

Save this in your path, mark it executable, and run it with two arguments: the (smaller) number which was good and the (larger) number that is now bad. It will find the midpoint, you test that number and tell it good or bad and it repeats until you've tested immediate neighbors, indicating the first number which was bad: the one that introduced the problem.

Hokkaido Milk Bread

2018-02-20 14:31 - Making

I recentely learned about the tangzhong bread making method. I pickeda recipe and decided to try it.

The dough is formed. Dough has risen, is divided and rolled and set in (the wrong) pan. Baked!

So I made the dough first of course. Then, I didn't know where my Mom kept her bread loaf pans so I used a Bundt pan instead. And I don't know where the pastry brush is, so I didn't do the egg wash. But it still came out quite nice. Very dense, and certainly tasty. Worth trying again with a few more details "right".

Detailed Arcade Switch Testing

2017-12-30 18:55 - Gaming

As mentioned, I converted my button tapper machine to also test the buttons being tapped. Since that I revamped it to get slightly more accurate readings, and now I have interesting data to report. Beware the wall of text, but delight in the pretty graphs in the middle.


See the linked post for a description of the raw data format. For each switch type, it's 250 events each pressing the button down, tracking the state of the switch over time, releasing the button and tracking again. All real physical switches will bounce as their contacts strike each other and spring back, only eventually settling to really be closed (or open). Each particular (model of) switch will bounce more or less, based on how it's built. With the raw data in hand, for each switch and event (press or release), I measured a virtual point at every microsecond, counting for each of the 250 tests, was the switch opened (0) or closed (1) at that point. Then take the average closed-ness, at every microsecond, for each switch and event.

So in the graphs below, a line at the bottom (0) means the switch was always open at that microsecond, and at the top (1) it was always closed. Anything in between means it was sometimes open, sometimes closed, at that microsecond. Across 250 tries, this averages out to a nice visual representation of how quickly, on average, the switch closes or opens, and how it acts while doing so.

The Switches

Force (gf)
OmronD3V-01-1C221C2225$1.39I've recommended these, before doing such deep research.
ZF Electronics (Cherry)D449-R1AAD44976$4.20The ZF Electronics corporation bought Cherry in 2008.
E-SwitchLS ???LS100?$1.72?This one will take its own section to discuss, see below.
HoneywellV7-1D10D8V71D150$3.65Most players feel this is too stiff.
ZippyVM05B-00D0VM520$0.85These are not "Zippyy" brand like the joysticks.

In alphabetical order, by nickname. Nickname is the short form I'll use to refer to each of these switches, going forward. With the nickname, you can look above to see exactly what I mean, but hopefully otherwise avoid bias ("I'm a fan of brand X!"). Activation force is the "gram force" required to activate an idle switch. Cost is the price each, to buy quantity ten.

The LS switches were mixed in my pile of spares, where I save even bad/removed ones (sometimes the next bad one is worse, and you've got no good spares, and you don't want to wait for shipping for a replacement!). Most are visibly used, stained (drinks/spills?), which shows easily on their white plastic body. Comparing limited known properties, I'm guessing this is a LS0851500F100C1A but I could be wrong there. I left question marks in the table, because I have to guess at the various values as well. As best I can tell, actuator 00 is the bare pin (definitely matching this switch), and that comes with a minimum 100gf activation.

Also worth mentioning is that the VM5 switches were described by everyone I can remember as being unsuitable for play, immediately upon installation while brand new. We'll see why shortly.

Button Presses

1C22 1C23 D449 LS V71D V73A V75F VM5 (Hover above links to isolate their graph.)

There's eight switches on the graph. To my eye there's an obvious cluster of four near the left (don't miss the yellow one), three in the middle, and one outlier off to the right. A theoretically ideal switch would be a vertical line straight up at microsecond zero, but we're in the real world. My testing machine takes time to charge up the solenoid, time for it to move, and time for it to overcome the force of three springs (one built into the solenoid, one in the button housing, and then the one in the switch itself). That's the twelve-ish millisecond delay before any of the lines on the graph start to climb. And then real world randomness means that each trial happens at a slightly different time. That and the randomness of the bounces determines the slope of the line. Being closer to that theoretical straight-up line towards the left of the graph indicates a "better" switch. So how close does each one get?

The most critical thing is really the moment where the switch is done bouncing and is always closed. So I'll go in the order that I see them touch the top of the graph. First is the dark blue line (the V73A) which fully activates (here, this means time from the earliest to the latest reading across all 250 samples -- worst case) within 4.5ms of the first moment that it starts. Next is the yellow line (the V71D) with a nearly identical slope, and right behind it is the green line (the 1C23) which takes about 5.5ms. The light blue line (D449) finishes out this group at 6ms.

For all practical purposes, these buttons are identical. We'll have to look at some minimally processed data to tell them apart. Three of these bounce only two or three times typically (seven or eight worst case), only the V73A is bouncier. They all typically finish bouncing in well under two (or one!) millisecond, and the worst case (individual sample) is still under three milliseconds. They're all fine buttons, with the V73A being slightly towards the bottom of this pack.

So for the group in the middle: Purple (1C22) is the first of these three, taking 7.5ms. Red (V75F) is next with orange (LS) both taking 7 to 9 ms. A second glance at the data shows however that these three bounce many more times, with worse average and maximum single sample times bouncing.

Finally there's the outlier which forced me to zoom the graph way out: the VM5. Excepting the worn-out LS, it's a full two or three milliseconds slower to start the process of switching. But it has a timing spread from there of another 35ms, with lots of bounces and a 24ms worst-single-sample time to settle. This one is completely unacceptable. A simple "wait 20ms and then see what state the button is in" approach (which is exactly the sort of thing a simple debounce system might do!) will accidentally read the not-pressed bouncing state sometimes! This lines up perfectly with the real play experience with these switches: they're just not reliable enough.

So can we use data to explain where these lines fell on the graph? I think so! The first "good" group of four have activation forces of 50, 150, 49, and 76. The other four have activation forces of 25, 15, 100 (worn out), and 20. Again excepting that one worn out model, it's clear that the higher weight springs produce a more reliable button.

Button Releases

1C22 1C23 D449 LS V71D V73A V75F VM5 (Hover above links to isolate their graph.)

Releasing a switch is much easier than pressing it. So all switches tested have significantly fewer bounces on the release, and activate more quickly. There's not really much more to say here. This isn't an important criteria.

Subjective Experience

I installed all these switches into the local arcade cabinet and asked players to let me know what they thought of all of them. They all played okay, so there was only one consistent bit of feedback: despite one player who loved it, everyone else commented negatively about the 150gf V71D. So despite a heavier spring producing better looking data, we know that we can go too far.


The one thing to say for certain is that the model of replacement switch matters! Any name brand should do fine, and 50-100gf activation seems to be the sweet spot. Optimize for cost within that range. I'm interested in trying the LS in a non-worn-out state!

Custom Garbage Bag Holder

2017-12-25 20:24 - Making

The bag holder, "in place" except lifted up a bit for demo purposes.

Just in time* for Xmas, I put together this custom garbage bag holder for my Mom. Following availability at local grocery stores she's switched to plastic bags, and been awkwardly using them on this built in garbage bin, where they're too small to fit properly. Here's a mostly plywood contraption to fit over the existing bin, but with pegs to hold the bags' handles plus some cove molding to help keep the bag open and in place. It's about the same depth but narrower than the bin beneath it to be the right size for standard plastic shopping bags. A cutout in the lower layer of plywood fits around the lip of the bin, while the top layer holds all the bits mentioned above. It's all made from found materials already around the house, which is the perfect kind of gift for my Mom. No new/extra stuff!

* I definitely had an idea to do this over the Thanksgiving visit. And earlier in this visit. And forgot, despite a coded (to not give away the surprise) note to myself. Then I thought of it again, and realized what the note meant, and built this up over (mostly) a long afternoon on Xmas Eve.

Cleared: Samus Returns

2017-12-11 12:23 - Gaming

My clear screen for "Samus Returns".

I started this game over Thanksgiving week, and just (this weekend) finally finished it. Some boss fights were a bit frustrating, but overall I found it to be a great and enjoyable 2D Metroid game.