3D Printed Safety Interlock for Model Rocketry

I have a four position launch controller and stand for launching model rockets, which I have written about here.  It’s been a few years since I’ve had an opportunity to use it, but it looks like I might get to have some launches again this year.  I’m hoping, anyway.  So I pulled it off the shelf to check it out.

The controller was designed to use a variety of UPS batteries, that is, sealed lead-acid units with quick-disconnect terminals.  I’ve been pulling those batteries out of UPS units in a used condition, which means they don’t have a great shelf life; as a consequence, I’ve been obliged to take spares with me to every launch.  When I saw this model by fdavies on Thingiverse, I had an idea… why not upgrade the controller to use 20V Max batteries from Black & Decker?  Of course, I remodeled fdavies’ design so I could print it the other way around and not need supports, and also to fit my project better.

I printed out the parts and made and installed the electrical connectors, cutting strips from the cheap case metal of old computers (mild steel, perfect for my purposes, and I have a nibbler tool and snips to cut it with) and using JB Weld to complete that part.  This last week I finally got around to installing it in the launch controller, and after changing the protective resistors to 1K Ohm units due to the increase in voltage I was ready to test it.

But, no joy.  It would show good continuity but would not fire the igniter.  It took me quite a bit of poking around with my meter to figure out that the safety interlock key wasn’t making consistent contact.

Here’s my solution:

The metal bits are the original safety key contacts; the key itself is cut from an old antenna wire guide I had lying around.  The key contacts are, as you can see, held by a single screw each; screwed into the original controller (as shown in the upper left of the picture below) they had worked pretty well, for a while.  Due to wear, they had begun moving around, twisting on the screw and making intermittent contact.

I made new leaves (blades? dunno) for the controller with a second screw to stabilize them, but I didn’t like that solution either as it was tricky to bend them just right so they would be close enough for the roughly 4mm diameter key to make contact, but far enough apart not to touch without it.  So then I designed a barrier setup as shown in the first picture (the red part).  Side walls to prevent twisting, and a slotted 3mm thick barrier between the blades to prevent them from touching.

That was cool and all, but then I got fancy and designed the faceplate shown in the first picture.  It involves a filament change in the middle of printing, which I had never done before, but I followed the directions and it sort of worked.

Sort of, because my Ender 5 Plus has a Micro Swiss Direct Drive Extruder installed; the 300mm unload and reload distances had never been changed, but 80 or 85mm is more correct.  The 300mm unload wasn’t an actual problem, just annoying; the 300mm load, on the other hand, chewed on the filament and pushed out a big blob from the nozzle.  I cleared it away (with the head in flight, so to speak) as much as I could but I got a blob right on the first letter of the message.  The faceplate on the left in the first pic is the result after I cleaned as much of the blob away with a knife after printing.

So I figured out how to do the M603 command to change the distances, choosing 80mm after measuring around 71 mm of manual retraction to clear the filament; for some reason it seems I need more like 85mm but 80 worked for my purposes this one time.  I also manually edited the gcode for the faceplate, after reslicing it and using the preview mode of Ultimaker Cura to show me the printing order.  The gcode file has comments where each phase of printing begins, and I noticed that the layer began with an outside perimeter followed by an inside perimeter.  Watching the preview I saw that the outside was the first two words, and then the inside was center of the keyhole.  So I moved the M600 reload command to just before that inside perimeter, figuring that if there was a blob I could just drill it out.

Anyway, the faceplate on the right is the unmodified result of those steps.  I think a thicker font would look better but this will do.

Now to put it all together…

DiskPart “Attribute Volume” Object Not Found

The title isn’t very pretty, but it gets the point across.  I had a weirdly partitioned computer come in to my shop, and I needed to make corrections.  The last issue I confronted was that the Recovery partition had a drive letter… it shouldn’t.  The user shouldn’t see it at all, normally.  But when I tried

attribute volume set nodefaultdriveletter

I was presented with an “Object Not Found” message.  I searched for a solution but could not find one; I was about to give up when I had an idea.

(Note that the drive in question was a Basic disk.  This likely doesn’t work the same way for Dynamic disks; I haven’t tried it so I can’t say for sure.)

First, I did:

select partition <x>

where <x> was the partition for the C: drive.  Then I did:

detail partition

I highlighted and copied the GUID after the Type: heading and pasted it into a notepad window.  I then selected the “problem” partition and did the same thing, so that now I knew both of the Type ID values.  Then, with the problem partition still selected I did:

set id=<drive-C-type>

Now I was able to fix the volume:

select volume <problem-partition>

attribute volume set nodefaultdriveletter

This time it worked.  Finally, I made sure the problem partition was still selected and did:

set id=<problem-partition-type>

to put the partition back to the correct type.

Rebooted just to make sure, and all was well.

Raspberry Pi Setup For Information Screens

I have a customer who needed several non-interactive displays for their business.  There are in fact many reasons you might want this; for example, menu displays in a restaurant are often done like this.  My customer needed these displays in public areas where there would be little room to hide a computer.  We wanted to display a (local, intranet) web page which would update itself nearly in real-time to follow some business statistics, but we could have been displaying pretty much anything.

My solution was to use the Raspberry Pi Zero W, a tiny single-board ARM computer with built-in wifi.  The system boots from a micro SD card, which you preload with a copy of what they now call Raspberry Pi OS.  Basically it’s a customized Debian installation.

Note that these instructions are relevant as of November 2020.  If it’s been a while since I wrote this, well, expect some changes.  Also note, this is my very easy way of setting up such a display; don’t expect it to be the most efficient or elegant solution, just one that works.

To begin, download the Raspberry Pi OS Lite image from the website here and copy it to an appropriate micro SD card (there are instructions on the site).  We’re using the “Lite” image so we can install just what we need.

Set up your Raspberry Pi for interactive use for the moment.  You probably won’t need a mouse but you will certainly need a keyboard.  Put in the card you prepared and power it up.  When it gets to the login prompt, the username is pi and the password is raspberry.

We are running without a GUI, so to connect to the Internet we need to connect to wifi using the raspi-config script:

$ sudo raspi-config

In the provided menu, go to Network Settings.  After selecting your country, you’ll be prompted for SSID and passphrase.  Note that if you are using a wired model of Raspberry Pi, you won’t have to do this step; however, you still need to be in raspi-config for the next part.

Next, go to Localisation Options and set up your country and time zone information.  You might not need this, but it only takes a moment so why not?

Now, and this is kind of important, go to the Advanced Settings and disable Screen Blanking.  In the same menu, choose the option to expand the partition so you have all the available space allocated.

With all of that done, exit the menu using the Finish option, and let it reboot, and log in again.

Now we should update the operating system, and install some packages we need for this project:

$ sudo apt update
$ sudo apt upgrade
$ sudo apt install chromium openbox lightdm

Chromium will be used to display whatever information we are wanting to show.  Installing OpenBox will automatically install a minimal X Windows environment; OpenBox has a simple mechanism for automatically starting programs and does not show any menus or widgets on the screen by default (as in olden days, you click on the root window to get a menu).  LightDM will permit us to arrange automatic login, so the system will go straight to our screen view.

After all of these installations are done, there are several things you need to do.  First, go back into raspi-config (as above) and choose System Options, Boot / Auto Login, then Desktop / CLI.  Choose the option for a graphical desktop with automatic login, then exit out as before.

DON’T reboot yet!  Now we need to set up the autostart situation for the default “pi” user account to autostart a Chromium session.  In the folder $HOME/.config/openbox edit (or create) a file named autostart and put in these lines:

#!/bin/bash
xset -dpms
xset s off
xset s noblank
/usr/bin/chromium --noerrdialogs --disable-infobars --kiosk https://my.website.com/

The first three lines are intended to prevent the screen from blanking.  Even though you turned it off in raspi-config, X may still want to blank the screen, and you don’t want that.

The third line starts a Chromium session, with no navigation or informational bars, no error dialogs, and in “kiosk mode.”  These options should present a totally blank, frameless window in which your chosen web page will appear.  Of course, you must change the URL given to whatever page you have chosen to display.

Don’t forget to mark the file readable and executable:

$ chmod a+rx .config/openbox/autostart

Now, reboot.  With any luck, everything will Just Work…

BUT IT DIDN’T

The only problem I’ve encountered with this procedure is that the chromium package doesn’t work right on some Raspberry Pi units, and no, I don’t know why.  I get “Illegal Operation” as an error output on those systems.  The best option I’ve found is to substitute the chromium-chromedriver package:

$ sudo apt install chromium-chromedriver

Note that apt will uninstall the chromium package when you do this; also, you have to change your command path from /usr/bin/chromium to /usr/bin/chromium-browser in the autostart file.  So far this has worked reliably for me when the error occurs.  Possibly I should update the instructions above and just run this package by default, but as of right now I have Raspberry Pi units working both ways.

BONUS ROUND

You can install OpenSSH for remote access.  If you do this, first CHANGE THE PASSWORD from the default!

$ passwd
$ sudo apt install openssh

If you are setting up the Raspberry Pi on one network, but intend to deploy it to another, the handy wifi setup tool Comitup may be helpful.  Installing it is easy:

$ sudo apt install comitup

Using it is pretty simple too; I don’t think I can improve on the original author’s docs here: https://davesteele.github.io/comitup

Setting Up Mirrored Boot Hard Drives in Windows 10

This is a thing I have to do from time to time, and up to now I’ve been depending on two different sets of instructions (because one was not correct for Windows 10, and the other isn’t complete). So I’ve finally written my own instructions, and here they are.

Disclaimer

This is a somewhat advanced procedure.  Try it at your own risk.  I will not be responsible if this kills your computer, eats your family pictures for seven generations, or causes the heat death of the universe… or any other bad thing, big or small.  This is the procedure I used yesterday, and as far as I know it’s good, but follow it at your own risk.

Introduction

First, it’s important that the partition structure of the boot drive be “normal,” that is, the way Windows 10 would create it. The instructions below won’t work right if the partitions are in a different order. Unfortunately, many system builders (including my distributor) use a non-standard partition layout.

So for me, at least, the first thing to do is to erase the hard drives with zeros (I use a Linux boot flash drive for this) and then reinstall Windows 10 on the primary drive. This task will not be described here, as it’s a very basic procedure.

Assuming we are starting with the first hard drive having a more or less default Windows installation (on a GUID formatted drive), and the second being entirely blank, here’s how we do it:

Duplicate the Recovery Partition:

Open an administrative command prompt window, then run the diskpart command. We need the information about the Recovery Partition, so execute these commands:

1
2
3
select disk 0
select partition 1
detail partition

You should get something like this:

1
2
3
4
5
6
Partition 1
Type    : de94bba4-06d1-4d40-a16a-bfd50179d6ac
Hidden  : No
Required: Yes
Attrib  : 0X8000000000000001
Offset in Bytes: 1048576

Volume ### Ltr Label Fs Type Size Status Info
———- — ———– —– ———- ——- ——— ——–
* Volume 4 Recovery NTFS Partition 529 MB Healthy Hidden

Take careful note of the Type ID (i.e. Type, above) as well as its size.

Now make sure the second drive is GPT and completely empty, then create a new Recovery Partition there:

1
2
3
4
5
6
7
8
9
select disk 1
clean
convert gpt
select partition 1
delete partition override
create partition primary size=529 (or whatever size is given in the details)
format fs=ntfs quick label=Recovery
select partition 1
set id=de94bba4-06d1-4d40-a16a-bfd50179d6ac (or whatever Type ID was given in the details)

We’ll need drive letters assigned to both the original and the duplicate recovery partitions:

1
2
3
4
5
6
7
select disk 0
select partition 1
assign letter=q
select disk 1
select partition 1
assign letter=r
exit

That last command will take you out of diskpart. Now we need to use robocopy to make a duplicate of the original recovery partition:

1
robocopy.exe q:\ r:\ * /e /copyall /dcopy:t /xd "System Volume Information"

Duplicate the EFI System Partition:

Next, we need to duplicate the EFI System Partition. Back into diskpart:

1
2
select disk 0
list partition

You’ll get something like this:

1
2
3
4
5
6
Partition ###  Type              Size     Offset
-------------  ----------------  -------  -------
Partition 1    Recovery           529 MB  1024 KB
Partition 2    System              99 MB   530 MB
Partition 3    Reserved            16 MB   629 MB
Partition 4    Primary            930 GB   645 MB

Note the sizes of the System and Reserved partitions, and recreate them on the second drive:

1
2
3
4
5
select disk 1
create partition efi size=99 (or whatever the partition list indicates)
format fs=fat32 quick
assign letter=t
create partition msr size=16 (or whatever the partition list indicates)

We need the primary disk System partition to have a drive letter:

1
2
3
4
select disk 0
select partition 2
assign letter=s
exit

Now we’re out of diskpart again, off to robocopy:

1
robocopy.exe s:\ t:\ * /e /copyall /dcopy:t /xf BCD.* /xd "System Volume Information"

Mirror the Operating System Partition:

Most instructions say to close the Admin CMD window at this point, but you can honestly just ignore it; you’ll need it again later, so close it or leave it
open, does not matter.

You need to launch diskmgmt.msc now, or just go to Computer Management and select the Disk Manager section. Right-click on the primary disk and choose Convert to Dynamic Disk, then do the same for the secondary disk. Finally, right-click on the C: volume and choose Add Mirror to choose a drive for the mirror. Select Disk 1 and click the Add Mirror button.

This is the boring part. You need to wait for the mirroring to complete before moving on to duplicating the BCD boot instructions (in the next part, below).

Prepare the BCD Boot Entries

The procedures done so far have created a proper mirror of the boot drive, and a boot menu item has been added to allow you to boot from the secondary plex (drive). However, if the primary drive fails, booting from the secondary drive may fail as well. It is possible to use a boot CD and repair the boot on the secondary drive, and this is always an option, but duplicating the BCD boot information on the secondary drive should remove any need for this.

If the Admin command prompt has been closed, you’ll need to reopen it; if the system has booted, you’ll need to reassign the drive letters for the EFI partitions. To do this, run diskpart and enter the following commands:

1
2
3
4
5
6
7
select disk 0
select partition 2
assign letter=s
select disk 1
select partition 2
assign letter=t
exit

Now you’re back at the command prompt. Type the following commands:

1
2
3
s:
cd EFI\Microsoft\Boot
bcdedit /enum

That last command should give you something like this (warning, long):

1
2
3
4
5
6
7
8
9
10
11
12
13
14
Windows Boot Manager
--------------------
identifier              {bootmgr}
device                  partition=S:
path                    \EFI\MICROSOFT\BOOT\BOOTMGFW.EFI
description             Windows Boot Manager
locale                  en-US
inherit                 {globalsettings}
default                 {current}
resumeobject            {6fb37501-3d6b-11ea-914e-85f8d8cf8c72}
displayorder            {current}
{6fb37506-3d6b-11ea-914e-85f8d8cf8c72}
toolsdisplayorder       {memdiag}
timeout                 30

Windows Boot Loader
——————-
identifier {current}
device partition=C:
path \Windows\system32\winload.efi
description Windows 10
locale en-US
inherit {bootloadersettings}
recoverysequence {6fb37503-3d6b-11ea-914e-85f8d8cf8c72}
displaymessageoverride Recovery
recoveryenabled Yes
isolatedcontext Yes
allowedinmemorysettings 0x15000075
osdevice partition=C:
systemroot \Windows
resumeobject {6fb37501-3d6b-11ea-914e-85f8d8cf8c72}
nx OptIn
bootmenupolicy Standard

Windows Boot Loader
——————-
identifier {6fb37506-3d6b-11ea-914e-85f8d8cf8c72}
device partition=C:
path \Windows\system32\winload.efi
description Windows 10 – secondary plex
locale en-US
inherit {bootloadersettings}
recoverysequence {6fb37503-3d6b-11ea-914e-85f8d8cf8c72}
displaymessageoverride Recovery
recoveryenabled Yes
isolatedcontext Yes
allowedinmemorysettings 0x15000075
osdevice partition=C:
systemroot \Windows
resumeobject {6fb37501-3d6b-11ea-914e-85f8d8cf8c72}
nx OptIn
bootmenupolicy Standard

The boot loader entry entitled “Windows 10 – secondary plex” was added when the C: drive was mirrored. Now we clone the working Windows Boot Manager:

1
bcdedit /copy {bootmgr} /d "Windows Boot Manager Cloned"

You’ll get a reply like this:

1
The entry was successfully copied to {6fb37507-3d6b-11ea-914e-85f8d8cf8c72}.

The GUID at the end will vary, of course. Use it in the following command:

1
bcdedit /set {GUID} device partition=t:

Now we need to export the BCD store to copy it to the T: drive:

1
bcdedit /export T:\EFI\Microsoft\Boot\BCD

This should complete the operation. Rebooting the system to remove any excess drive letter assignments is recommended.

Added “getrows” Feature for additionalbands

I added a new feature, getrows, for use with additionalbands. Just declare a band like this:

1
2
3
Band([
    # ... elements ...
], getrows = rowfunction)

where rowfunction (or whatever you’ve decided to call it) is defined like this:

1
2
3
4
def rowfunction(row):
    return [
        # ... row objects, i.e. dicts or lists ...
    ]

If getrows is supplied, it will be called each time the Band is generated, receiving the current data source row as its only parameter.  The row function must return a sequence of row-like objects, i.e. dicts or lists; the Band will then be generated once for each of these rows, instead of being generated with the parent data source row.  This allows a kind of light-weight subreporting.  Because these are additionalbands, they are not attached to the parent band and can flow from page to page automatically.

Pythonic Windows Printing

Way back when, circa 2006 or so, I was writing an application for a customer in Python.  It needed to be able to print, as many applications do, and so I thought “how hard could it be?”

Well, it took a lot of head-scratching and code-diving before I understood how to do it right.  It was such a pain that I decided to write an article about how to print from Python on Windows; eventually I added my own module, MSWinPrint.py, to make it easier.

Time has moved on and the site where I originally shared this is kinda creaky and may be about to be canned.  So here is the original article, with basically no changes.

The module MSWinPrint.py can be downloaded from my Github page, or you can get it via PyPI.

So without further ado, here’s the original article:

Note: The following instructions are supplied without warranty. If you use them, you are accepting responsiblity for anything that might go wrong. Also note that the instructions below have been tested on Python 2.4 on Windows XP only (usingpywin32 build 205 and later).

So you want to produce some output? On the surface it sounds pretty simple:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
# create a dc (Device Context) object (actually a PyCDC)
dc = win32ui.CreateDC()

# convert the dc into a "printer dc"

# leave out the printername to get the default printer
# automatically
dc.CreatePrinterDC(printername)

# you need to set the map mode mainly so you know how
# to scale your output.  I do everything in points, so
# setting the map mode as "twips" works for me.
dc.SetMapMode(win32con.MM_TWIPS) # 1440 per inch

# here's that scaling I mentioned:
scale_factor = 20 # i.e. 20 twips to the point

# start the document.  the description variable is a string
# which will appear in the print queue to identify the job.
dc.StartDoc(description)

# to draw anything (other than text) you need a pen.
# the variables are pen style, pen width and pen color.
pen = win32ui.CreatePen(0, int(scale_factor), 0L)

# SelectObject is used to apply a pen or font to a dc.
dc.SelectObject(pen)

# how about a font?  Lucida Console 10 point.
# I'm unsure how to tell if this failed.
font = win32ui.CreateFont({
    "name": "Lucida Console",
    "height": int(scale_factor * 10),
    "weight": 400,
})

# again with the SelectObject call.
dc.SelectObject(font)

# okay, now let's print something.
# TextOut takes x, y, and text values.
# the map mode determines whether y increases in an
# upward or downward direction; in MM_TWIPS mode, it
# advances up, so negative numbers are required to
# go down the page.  If anyone knows why this is a
# "good idea" please email me; as far as I'm concerned
# it's garbage.
dc.TextOut(scale_factor * 72,
    -1 * scale_factor * 72,
    "Testing...")

# for completeness, I'll draw a line.
# from x = 1", y = 1"
dc.MoveTo((scale_factor * 72, scale_factor * -72))
# to x = 6", y = 3"
dc.LineTo((scale_factor * 6 * 72, scale_factor * 3 * -72))

# must not forget to tell Windows we're done.
dc.EndDoc()

So far, so good. Doing it this way gives you decent output, but you can’t change the paper size or orientation (or a bunch of other things).

It turns out that both win32ui and win32gui have a CreateDC function, but they are NOT equivalent. win32ui.CreateDC gives you a PyCDC object (wrapping an hDC and various methods for manipulating it), but win32gui.CreateDC gives you an integer hDC value. BUT… win32ui.CreateDC doesn’t allow you full access to configure the hDC (or if it does, I couldn’t figure out how to use it). So you can’t make those changes you’d like to make if you get the DC the way I did above.

SO… here’s another version. This is just the beginning of the text above; the whole procedure involves opening the printer, configuring it, getting an integer hDC for the configured printer, and making a PyCDC out of it:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
# if you just want to use the default printer, you need
# to retrieve its name.
printer = win32print.GetDefaultPrinter()

# open the printer.
hprinter = win32print.OpenPrinter(printer)

# retrieve default settings.  this code does not work on
# win95/98, as GetPrinter does not accept two
devmode = win32print.GetPrinter(hprinter, 2)["pDevMode"]

# change paper size and orientation
# constants are available here:
# http://msdn.microsoft.com/library/default.asp?
#      url=/library/en-us/intl/nls_Paper_Sizes.asp
# number 10 envelope is 20
devmode.PaperSize = 20
# 1 = portrait, 2 = landscape
devmode.Orientation = 2

# create dc using new settings.
# first get the integer hDC value.
# note that we need the name.
hdc = win32gui.CreateDC("WINSPOOL", printer, devmode)
# next create a PyCDC from the hDC.
dc = win32ui.CreateDCFromHandle(hdc)

# now you can set the map mode, etc. and actually print.

Hopefully this helps someone else.

Windows Update “Awaiting Restart” Fix

So say you have a Windows Update that isn’t finishing.  In the Windows Update Settings screen, beneath the update it says “Status: Awaiting Restart,” but you restart, and when you look it still says that.  Here’s the fix, collected from several different answers I found online:

First, you need an elevated command prompt.  Click start and type CMD in the search, but don’t press Enter; instead, right-click on the Command Prompt item that search should have found and choose Run as Administrator.  Say Yes to the prompt about making changes to your system… that’s exactly what we’re doing here.

Now you have a command window.  Enter the following commands one after another:

SC config wuauserv start= auto
SC config bits start= auto
SC config cryptsvc start= auto
SC config trustedinstaller start= auto

Now, restart your computer.  During the restart you should see the update actually running.

 

Dystechia

I read an article (several, actually) some time back which indicated that, in effect, some people can learn to program and others really can’t.  That article has since been retracted, with indications by the original author that the research was flawed; but the odd thing is, it did mirror my personal experiences in the field.

For the record, the original article is a PDF entitled “The Camel has Two Humps” and you can find a copy here.  There is an article covering the retraction here.

I worked for a while in a programming shop with two other competent programmers and one who had somehow fooled both the school where he got his degree and the boss who hired him.  He just did not really understand how a computer program worked… I tried, I really did, to get through to him, but without much in the way of luck.  I wonder now if the things the test described in the original article is testing for (understanding program flow, for instance) are things I should have been trying to teach him… things that seemed so obvious to me that I doubt I ever talked about them.

But that’s not what I’m discussing today.  I want to talk a little bit about a different level of understanding.  I’ve been selling and servicing computers (with a little programming tossed in) since 1993, and I’ve noticed something.

If I hand a customer a flash drive and tell them the name of a folder on the drive which contains a file, many (something more than half, but I don’t have a more accurate count than that) will just look at me blankly.  These people, many of whom are otherwise quite smart (doctors, for instance, and lawyers, and other professionals) just do not understand file systems.  I’m a member of a camera club, and at our meetings we all bring pictures on flash drive to share; new members often say, “I’d love to bring in pictures, but I don’t know how to get them off of my memory cards” (or sometimes, “I’ve got pictures on my computer but I can’t get them onto a flash drive to bring”).

I frequently have to write down detailed instructions, a recipe of sorts, for how to move files around or to locate files or whatever when dealing with this population of users.  Often, my instructions, written at what I consider the most basic level, are still over their heads; I will find myself explaining steps that, in my mind, are very basic operations.  It’s like telling someone to open a door, only to find that they don’t know they have to turn the doorknob… and then discovering that the next time they encounter a door, they don’t remember how to do it.

Again, these are smart people, for the most part.  People you would never think would have a problem, until you try to help them do things with a computer.

Then there’s the other population, to whom I can give that flash drive and have them smile and say “No problem.”

Here’s the thing… I’ve never, and I mean ever, seen any of the people in the first group master file systems.  They write down their recipes and tape them to their monitors, or stick them in their center desk drawers, or under their keyboards, and that’s how they get by.  They just never really understand.  But the people in the second group, when I tell them what I’ve observed, frown and say, “What’s so hard about it?”  Those who understand file systems seem to have never had a problem with it.

So you have a group that never masters it, and a second group that never had a problem with it, and to be honest I’ve never met a person who straddled that line in any way.  Oh, the “got it” group members don’t necessarily know everything, but when I find a “got it” I know I can teach that person the bits he or she does not know (for instance, navigating network drives).  When I find a “don’t got it” I often despair of helping them at all.

Now take a trip with me, back in time a few thousand years.  Some smart cookie has invented writing, probably to keep track of business transactions if the modern world is any indication.  The first scribes learn to read and write, and to them it’s the best thing ever; but few have the need and opportunity to learn this new skill.

If you had dyslexia, but were not destined to be a scribe, how would you know?  Answer: you wouldn’t.  Dyslexia as a disorder could not exist without writing… it took the invention of writing for the disorder to “appear.”  When most people don’t read or write, dyslexia isn’t a thing.  But time and civilization moves on, and a few hundred years ago things began to change.  More people needed to read and write (and do mathematics, but without writing the business effects of math are somewhat limited), and with more need for literacy, those with a problem learning the skill would suddenly stand out.  It took us a few years to give a name to the problem, but it’s been with us for a long time I’m sure.

Now we have a new field of endeavor, a new technology which is important (some might say critical) to business and to our modern civilization.  This “disorder” of not being able (for whatever reason) to understand file systems could not have existed without computers.  I titled this post “dystechia,” constructing the word in a similar fashion to dyslexia, but I have to say I don’t care for the word.  Does not roll nicely off of the tongue.  But whatever it’s called, I believe this is the next such “disorder” to be identified.

It appears to me that it’s a issue with abstraction.  The “don’t got it’s” seem unable to form a mental model of how the file system works.  They can’t see a file in their mind as a thing, nor imagine folders within folders containing those objects.  But this is speculation… don’t take this as fact.  All I can say for sure is what I’ve seen… people, smart, educated people, struggling to comprehend something that was obvious to me the very first time I read it.  People I depend on in some cases (my own family doctor, now retired, was in this group).

Dystechia:  It’s the disorder of a new generation.

RemixOS: Honeymoon is over, Annulment granted

I tried, I really did, but I just can’t live with RemixOS.

At first, I was swayed by the beauty of it.  It’s so clean and neat and functional, and access to the Play Store means so many apps are available already.

But.  Try to set up printing.  Or certain other services.

Even when they work, you either (a) pay for them, or (b) look at ads.  Whereas, as a user of Ubuntu (or any other Linux distro, really) you get the same things for free with no ads.

The honeymoon is over, it seems.

The only thing I’ve found that it’s good for is a set-top box; the streaming apps for various video/TV services are really pretty nice, and having RemixOS on a computer connected to a TV set can be a good way to enjoy them.  But that’s it, the only use case that makes sense to me.

RemixOS Survival Guide, Part 1

RemixOS is a beautiful thing.  Android on a PC, simple and fast and pretty, and all those apps!

But while it’s a nice place to visit, it still takes a bit of work to live there.  So I’m going to document, here on my blog, the things I’ve done to make my “toy” computer someplace I could actually do business.

I’m going to start this in the middle, with something I learned later that it pays to know in the beginning.  Install the 32 bit version!  Even if you have a 64-bit-capable computer, your life will be easier (at least right now) in 32 bit land.  Apps that provide native Intel libraries often do not supply 64 bit versions… apps like PrintHand or Print Hammermill.

Let’s start with installing RemixOS on your computer.  If you, like me, want RemixOS to be the only OS on the computer, then start by either making a bootable USB flash drive containing your preferred edition (i.e. 32 bit, as I explained above) or burning the image to a DVD.  I had a problem with the computer I’m using for testing being unable to boot USB… turned out it won’t boot any USB flash drive.  So I did the burning option.

Rather than explain all of this myself, I’m going to chicken out and let someone else do it.  If you want to create a bootable USB drive on Windows, you want to start following the directions at this link.  When you get to step 5 and the menu appears (the GRUB boot menu, to be exact), press TAB to pause the boot and pick up the directions below.

If you are using a modern Linux distribution, install UNetbootin from your package manager and then run it.  Tell it you are putting an ISO on your flash drive, then point it at the one you downloaded.  Again, boot from it, and at the blue GRUB menu press TAB.

Okay, so, now you should be looking at the GRUB menu with a long string of garbage at the bottom.  That long string of garbage is the boot command string which tells Linux (the underlying kernel for Android) how to boot.  Without changing anything that is already there, add a space and then type in

INSTALL=1

at the end.  Press ENTER, and the RemixOS installation system will start up.

I’m assuming you want to use the entire hard drive for RemixOS.  If not, stop.  The instructions I’m about to give you will DESTROY the contents of your hard drive… if you have anything important on there, you need to back it up first.  No, I’m not going to explain how… Google for it.

If you are sure you are ready to erase that hard drive, well, here’s how you do it.  RemixOS will ask where you want to install it, and it will show you a list of the available partitions on all your hard drives.  You probably should start by choosing the option to change partitions, then choose your /dev/sda (the first hard drive).  When it asks if you want to use GPT, say no.  The next screen that comes up will be cfdisk, which will allow you to delete your partitions and create new ones.

After erasing your partitions, create a single partition for the entire hard drive, make it bootable, and then choose the Write option to save it.  Finally, choose Quit to move on.

RemixOS will ask about formatting the drive.  Choose ext3 or ext4 as the partition type (I’m not sure that it makes much difference which one you choose; ext4 is a bit better, technically).  You’ll be warned that you are going to erase the hard drive, but don’t kid yourself, you already did that in the last step.

The operating system will now install.  Walk away and let it work.

More later… look for Part 2, coming soon!