Linux, Unix, and whatever they call that world these days

Better Vi Coloring

On my default Ubuntu server installation vi is very colorful. However, most of colors are so dark that I cannot really see what’s written against dark window background. This is fortunately mitigated by setting background into “dark mode”.

set background=dark

Second issue I faced was inability to copy/paste from other applications without the whole text being indented like crazy. Of course, there is setting for that too.

filetype indent off

With these two settings, my vi was usable again.

Syncing Time Zone via IPMI

After using UTC time zone exclusively on my servers for a while, I decided to give local time a try for the next 6 months or so. In addition to “normal” shenanigans time zones bring, I got another interesting one - my IPMI servers required me to manually tell them whether daylight saving is in effect or not. What that meant is that, even with time zone set correctly, every daylight saving time change my server’s BMC will be 1 hour off.

As all my servers were Supermicro (M11SDV-4CT-LN4F and A1SRi-2558F) I decided to use Supermicro’s powerful IPMI to programmatically deal with that issue.

My thoughts were going in the following direction. As long as I keep script on my main server that will update time zone information (if needed) twice a day (at 02:00 and 03:00), it should be enough to keep me happy. As retrieving time zone information via IPMI is not something that’s standardized, I contacted Supermicro’s support to get the details. While they didn’t really provide those details, they did point me toward their SMCIPMITool utility.

Unfortunately this didn’t fully solve it for me as it didn’t support FreeBSD. However, it did have debug mode (in SMCIPMITool.properties set debug_level=1) and this really helped.

./SMCIPMITool ^^192.168.1.1^^ ^^admin^^ ^^password^^ ipmi oem x10cfg ntp timezone
 …
 [ YOU -> BMC : ^^30 68 01 00 00^^ ]
 [ YOU <- BMC : 00 01 2D 30 37 30 30 01 ]

With these response bytes it was easy enough to construct ipmitool raw bytes:

ipmitool -I lanplus -H ^^192.168.1.1^^ -U ^^admin^^ -P ^^password^^ raw ^^0x30 0x68 0x01 0x00 0x00^^
 01 2d 30 30 30 30 00

The first byte tells us if NTP is enabled or not, next 5 bytes tells time zone in ASCII (+0000), while the last byte says if daylight saving is on or not.

Using the same principle, it’s easy enough to update IPMI:

ipmitool -I lanplus -H ^^192.168.1.1^^ -U ^^admin^^ -P ^^password^^ raw 0x30 0x68 0x01 0x
 01 0x00 ^^0x01 0x2d 0x30 0x37 0x30 0x30 0x00^^

Trying to script this change is a bit tricky. There isn’t really easy and fireproof method of determining if daylight savings is active. However, I decided to ignore that field and just set offset every time as that’s really easy to determine (date +%z).

The final script was looking something like this:

#!/bin/bash

IP="^^192.168.1.1^^"
USER="^^admin^^"
PASSWORD="^^password^^"

CURR_STATE=`ipmitool -I lanplus -H $IP -U $USER -P $PASSWORD raw 0x30 0x68 0x01 0x00 0x00 | xargs | tr ' ' '\n' | awk '{printf " 0x" $1}' | xargs`
NEXT_STATE="0x01 `date +%z | hexdump -C | head -1 | cut -d' ' -f3-7 | tr ' ' '\n' | awk '{printf " 0x" $1}'| xargs` 0x00"

if [[ "$CURR_STATE" != "$NEXT_STATE" ]]; then
    ipmitool -I lanplus -H $IP -U $USER -P $PASSWORD raw 0x30 0x68 0x01 0x01 0x00 $NEXT_STATE 2>/dev/null
fi

Muting Sound Every Time Ubuntu Starts

Ubuntu 19.04 doesn’t remember audio settings between reboots. This means that after every reboot I need to mute sound again and again. Since making it remember volume between reboots is hard, I went for the next best thing - mute it on reboot to start with.

Command is easy:

amixer set Master mute

To perform it on every startup, we can use @reboot crontab directive. However, be careful which crontab you’re editing as this statement is applicable only for root. It will simply be ignored for any other account’s crontab.

Keeping that in mind, this is what sorted it out for me

sudo crontab -e
@reboot /usr/bin/amixer set Master mute

Now my laptop starts muted and any unmuting is left to my discretion.

Redirect Only Errors to StdOut

The most usual thing I want with redirect is just throwing errors to null:

command >/dev/null

Alternatively, one can throw everything to null:

command >/dev/null 2>1

However, what if you want only error being shown and proper output ignored? Well, there is a redirect for that too:

$ command 2>1 >/dev/null

Using iSCSI from Ubuntu 19.04

Samba has taken over most of my sharing but I still occasionally need iSCSI. Connecting to it from Ubuntu is straight enough. First step is of course installing necessary package:

sudo apt-get install open-iscsi

Next step is simply connecting to iSCSI and discovering the drive name within dmesg output:

sudo iscsiadm -m discovery -t sendtargets -p ^^192.168.1.1^^
 192.168.1.1:3260,1 iqn.2007-09.jp.ne.peach.istgt:somedisk0

sudo iscsiadm --mode node --targetname iqn.2007-09.jp.ne.peach.istgt:^^somedisk0^^ \
    --portal ^^192.168.1.1^^:3260 --login

sudo dmesg | grep "Attached SCSI disk" | tail -1
 [ 3203.813577] sd 2:0:0:0: [^^sda^^] Attached SCSI disk

Lastly, just use the normal mounting to access the disk:

sudo mkdir /mnt/scsi
sudo mount /dev/sda2 /mnt/iscsi

Installing MPLAB X IDE 5.25 on 64-bit Ubuntu 19.04

While I love seeing companies provide Linux version of their software, it still annoys me when they do it as lazily as possible. For example Microchip not only doesn’t provide repository for their software, making you download and install every version separately, but they also don’t provide up-to-date instructions. Their section describing Ubuntu 14.04 and above simply doesn’t work.

To install MPLAB X on newer Ubuntu one must first explicitly add architecture:

sudo dpkg --add-architecture i386
sudo apt-get update
sudo apt install libc6:i386 libx11-6:i386 libxext6:i386 libstdc++6:i386 libexpat1:i386

Only once those are up you can proceed installing MPLAB IDE X itself:

tar -xvf MPLABX-v*-linux-installer.tar
chmod +x MPLABX-v*-linux-installer.sh
sudo ./MPLABX-v*-linux-installer.sh

Of course, installing compiler follows (XC8 in this case):

chmod u+x xc8-v*-full-install-linux-installer.run
sudo ./xc8-v*-full-install-linux-installer.run

And now MPLAB X IDE is installed.


PS: I won’t even go into the need for 32-bit compatibility libraries in 2019…

ZFS Pool for Virtual Machines

Running VirtualBox on ZFS pool intended for general use is not exactly the smoothest experience. Due to it’s disk access pattern, what works for all your data will not work for virtual machine disk access. Yes, you can play with record size and adding SLOG device but you can also go slightly different route. Add disk specifically for VirtualBox.

My testing has found that simple SSD with the following settings does wonders:

zpool create -o autoexpand=on -m /VirtualBox \
    -O compression=off -O recordsize=4K -O atime=off \
    -O utf8only=on -O normalization=formD -O casesensitivity=sensitive \
    VirtualBox /dev/diskid/^^DISK.eli^^

First of all, you don’t want compression. Not because data is not compressible but because compression can lead you to believe you have more space than you actually do. Even when you use fixed disk, you can run out of disk space just because some uncompressible data got written within VM. Due to copy-on-write architecture, you can still get into the trouble but exposure is greatly limited.

Ideally record size should match your expected load. In case of VirtualBox that’s 512 bytes. However, tracking 512 byte records takes so much metadata that 4K records are actually both more space efficient and perform better. Depending on your exact hardware you might find that going to 8K or even higher might hit the sweet spot. Testing is the only way to know for sure but 4K is a reasonable starting point.

All other options are just plumbing - of course you want UTF-8 and no access time tracking.

Now you can run VirtualBox without complicating your main data pool.


PS: This assumes that you have disks enumerated by diskid and fully encrypted.

PPS: I usually just spin up temporary virtual machines for testing and thus I don’t care much about them long term. If you plan to kick something up long-term, do consider mirrored ZFS.

Dual Boot Clock Shenanigans

Probably the most annoying thing when dual booting Windows and Linux is the clock. For the various reasons, Windows keeps BIOS clock in local time-zone while Linux prefers it as UTC. While this is not a problem in Reykjavík, it surely is everywhere else.

There are ways to make Windows run in UTC but they either don’t work with the latest Windows 10 or they require time synchronization to be turned off. As I value precise time, a solution on Linux side was needed.

Fortunately, Linux does offer setting for just this case. Just run the following command:

sudo timedatectl set-local-rtc 1 --adjust-system-clock

This will tell Linux to keep local clock in RTC. While this is not necessarily fully supported, I found it’s actually the only setting that reliably works when dual booting Windows 10.

PS: You might need a reboot or two before this takes effect.

Avoiding Select Audio Device Prompt on Dell XPS 15 under Ubuntu

Illustration

As a headphone user I find nothing more annoying than computer asking me every single freaking time what exactly did I plug in. While Windows drivers for Dell XPS 15 audio do allow you to select default, one is not so lucky under Linux.

However, Linux being configurable to a fault does offer a workaround.

You can append the following options to the end of /etc/modprobe.d/alsa-base.conf, followed by a reboot:

options snd-hda-intel model=headset-mic

This will lie a bit to sound driver and stop the darn questions.


PS: You can also use this one liner:

echo "options snd-hda-intel model=headset-mic" | sudo tee -a /etc/modprobe.d/alsa-base.conf

Installing DropBox on ZFS

While I already wrote about expanding DropBox’s Ext4 volume on ZFS, I never actually wrote how to create one in the first place. I guess it’s time to fix that injustice.

First you need to create a volume of sufficient size. While you can just make it as big as your Dropbox allowance is, I would advise going with at least double of that. Not only this helps if you are doing ZFS snapshots (remember it’s copy-on-write) but it also helps if you are moving files around as Dropbox fully releases space only once the new files are created.

Whatever you decide, you need to create a volume and format it:

sudo zfs create -V 12G ^^pool^^/dropbox
sudo mkfs.ext4 /dev/zvol/^^pool^^/dropbox

Once volume is created, mounting the newly created volume within our user directory is in order:

mkdir /home/^^user^^/Dropbox
sudo mount /dev/zvol/^^pool^^/dropbox /home/^^user^^/Dropbox
sudo chown -R ^^user^^:^^user^^ Dropbox

Of course, to retain it between reboots one should add it to fstab:

echo "/dev/zvol/^^pool^^/dropbox /home/^^user^^/Dropbox ext4 defaults,_netdev 0 0" | sudo tee -a /etc/fstab

Do note the _netdev part as it ensures dropbox volume is mounted way after ZFS has already done so. Without it you might have a race condition and volume mounting might prevent subpools to be mounted under the same path.

Finally you can install Dropbox as you usually would. While it will complain about directory already being present, you can simply cancel directory selection and it will start syncing regardless.

Congratulations, your Dropbox is now on ZFS.