With Ubuntu 19.10 Desktop there is finally (experimental) ZFS setup option or option to install ZFS manually. However, getting Ubuntu Server installed on ZFS is still full of manual steps. Steps here follow my desktop guide closely and assume you want UEFI setup.
Entering root prompt from within Ubuntu Server installation is not hard if you know where to look. Just find Enter Shell behind Help menu item (Shift+Tab comes in handy).
The very first step should be setting up few variables - disk, pool, host name, and user name. This way we can use them going forward and avoid accidental mistakes. Just make sure to replace these values with ones appropriate for your system.
To start the fun we need debootstrap and zfsutils-linux package. Unlike desktop installation, ZFS pacakage is not installed by default.
aptinstall--yesdebootstrap zfsutils-linux
General idea of my disk setup is to maximize amount of space available for pool with the minimum of supporting partitions. If you are planning to have multiple kernels, increasing boot partition size might be a good idea. Major change as compared to my previous guide is partition numbering. While having partition layout different than partition order had its advantages, a lot of partition editing tools would simply “correct” the partition order to match layout and thus cause issues down the road.
Assuming UEFI boot, two additional partitions are needed. One for EFI and one for booting. Unlike what you get with the official guide, here I don’t have ZFS pool for boot partition but a plain old ext4. I find potential fixup works better that way and there is a better boot compatibility. If you are thinking about mirroring, making it bigger and ZFS might be a good idea. For a single disk, ext4 will do.
Bootstrapping Ubuntu on the newly created pool is next. As we’re dealing with server you can consider using --variant=minbase rather than the full Debian system. I personally don’t see much value in that as other packages get installed as dependencies anyhow. In any case, this will take a while.
Let’s not forget to setup locale and time zone. If you opted for minbase you can either skip this step or manually install locales and tzdata packages.
If there are multiple encrypted drives or partitions, keyscript really comes in handy to open them all with the same password. As it doesn’t have negative consequences, I just add it even for a single disk setup.
Now we get grub started and update our boot environment. Due to Ubuntu 19.10 having some kernel version kerfuffle, we need to manually create initramfs image. As before, boot cryptsetup discovery errors during mkinitramfs and update-initramfs as OK.
Since we’re dealing with computer that will most probably be used without screen, it makes sense to install OpenSSH Server.
aptinstall--yes openssh-server
I also prefer to allow remote root login. Yes, you can create a sudo user and have root unreachable but that’s just swapping one security issue for another. Root user secured with key is plenty safe.
If you’re willing to deal with passwords, you can allow them too by changing both PasswordAuthentication and PermitRootLogin parameter. I personally don’t do this.
While you can go wild with firewall rules, I like to keep them simple to start with. All outgoing traffic is allowed while incoming traffic is limited to new SSH connections and responses to the already established ones.
sudoaptinstall--yesman iptables iptables-persistent
forIPTABLES_CMDin"iptables""ip6tables";do$IPTABLES_CMD-F$IPTABLES_CMD-X$IPTABLES_CMD-Z$IPTABLES_CMD-P INPUT DROP
$IPTABLES_CMD-P FORWARD DROP
$IPTABLES_CMD-P OUTPUT ACCEPT
$IPTABLES_CMD-A INPUT -i lo -j ACCEPT
$IPTABLES_CMD-A INPUT -m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPT
$IPTABLES_CMD-A INPUT -p tcp --dport22-j ACCEPT
done
iptables -A INPUT -p icmp -j ACCEPT
ip6tables -A INPUT -p ipv6-icmp -j ACCEPT
netfilter-persistent save
As install is ready, we can exit our chroot environment.
If you need to run Mikrotik’s WinBox under Ubuntu, solution is wine and 64-bit WinBox download. It works, as far as I can tell, flawlessly. However, I found dropping to command line every time I want to run it, a bit annoying.
Adding WinBox to activities is a two step process. The first step being creation of winbox.desktop file. In its simplest form it can look something like this
There is a newer version of this guide for Ubuntu 20.04.
With Ubuntu 19.10 there is finally (experimental) ZFS setup option. And frankly, you should use it instead of the manual installation procedure. However, manual installation does offer it’s advantages - especially when it comes to pool layout and naming. If manual installation is needed, there is great Root on ZFS installation guide that’s part of ZFS-on-Linux project but its final ZFS layout is a bit too complicated for my taste. Here is my somewhat simplified version of the same intended for a singe disk installations.
After booting into Ubuntu desktop installation we want to get a root prompt. All further commands are going to need root credentials anyhow.
sudo-i
The very first step should be setting up a few variables - disk, pool, host name, and user name. This way we can use them going forward and avoid accidental mistakes. Just make sure to replace these values with ones appropriate for your system.
To start the fun we need debootstrap package. With 19.10 ZFS is available in main repository so we don’t need to add universe as in the previous Ubuntu versions.
aptinstall--yesdebootstrap
General idea of my disk setup is to maximize amount of space available for pool with the minimum of supporting partitions. If you are planning to have multiple kernels, increasing boot partition size might be a good idea. Major change as compared to my previous guide is partition numbering. While having partition layout different than partition order had its advantages, a lot of partition editing tools would simply “correct” the partition order to match layout and thus cause issues down the road.
Assuming UEFI boot, two additional partitions are needed. One for EFI and one for booting. Unlike what you get with the official guide, here I don’t have ZFS pool for boot partition but a plain old ext4. I find potential fixup works better that way and there is a better boot compatibility. If you are thinking about mirroring, making it bigger and ZFS might be a good idea. For a single disk, ext4 will do.
Since we’re dealing with encrypted data, we should auto mount it via crypttab. If there are multiple encrypted drives or partitions, keyscript really comes in handy to open them all with the same password. As it doesn’t have negative consequences, I just add it even for a single disk setup.
Now we get grub started and update our boot environment. Due to Ubuntu 19.10 having some kernel version kerfuffle, we need to manually create initramfs image. As before, boot cryptsetup discovery errors during mkinitramfs and update-initramfs as OK.
If your default id_rsa key is different than the one you use for GitHub, it’s still possible to use simple git push regardless. Trick is in adding mapping to identity file in ~/.ssh/config:
Host github.com
User git
IdentityFile ^^~/.ssh/id_rsa_github^^
IdentitiesOnly yes
This will ensure all communication with github.com uses id_rsa_github key.
Considering how verbose make output is, it’s really easy to miss warnings or errors. What we need is a bit of color. However, make being such an old program, doesn’t support any ANSI coloring. However, since both errors and warnings have standardized formats, it’s relativelly easy to use grep to color them.
This will color all lines following the Makefile:number: format in default color. Extending this for catching errors is similar as there is just an extra match of “.Stop”:
And yes, the order of greps is important as we first want to capture errors. Matched lines are to be colored red (01;31) and prefixed with ANSI escape sequence thus preventing the second grep matching. Lines matching the second grep will get similar treatment, just in yellow (01;33).
Instead of remembering this, we can create a new amake function that will do the coloring:
One of many details available in Windows but not in Ubuntu is automatic backlight change when system switches from AC to battery. And it’s not just a dumb change to predefined value either. Every switch from AC to battery and vice versa restores the last value system had. Ubuntu on the other hand just keeps the backlight as is resulting in me manually adjusting it every time. Lookup on Internet for applications providing this functionality gave me no warm fuzzy feeling so I decided to roll my own. I mean, how hard can it be.
Well, actually annoyingly hard if you want to support every interface out there. As I wanted to support only my Dell XPS 15, I had quite a bit easier work.
The main part of the story is in two files: /sys/class/power_supply/AC/online and /sys/class/backlight/intel_backlight/brightness. All what’s needed was actually a small script handling tracking and restoring brightness values every once in a while. This is roughly what I ended with:
#!/bin/bashSTORED_AC=`cat /var/cache/.backlight.ac`STORED_BAT=`cat /var/cache/.backlight.bat`
while(true);doBRIGHTNESS=`cat /sys/class/backlight/intel_backlight/brightness`IS_AC=`cat /sys/class/power_supply/AC/online`if[["$IS_AC"!="$LAST_AC"]];thenif[["$IS_AC"!="0"]];thenif[["$STORED_AC"!=""]];thenecho-e"Restoring AC backlight to $STORED_AC"echo$STORED_AC>$FILE_BRIGHTNESSfielseif[["$STORED_BAT"!=""]];thenecho-e"Restoring battery backlight to $STORED_BAT"echo$STORED_BAT>$FILE_BRIGHTNESSfifiLAST_AC=$IS_ACelseif[["$IS_AC"!="0"]];thenif[["$STORED_AC"!="$BRIGHTNESS"]];thenecho$BRIGHTNESS> /var/cache/.backlight.ac
STORED_AC=$BRIGHTNESSfielseif[["$STORED_BAT"!="$BRIGHTNESS"]];thenecho$BRIGHTNESS> /var/cache/.backlight.bat
STORED_BAT=$BRIGHTNESSfififisleep0.5done
As you can see, the script is just checking in loop if there was an AC status change. If computer was plugged or unplugged, it simply restores the last saved value for that power state. If power status remained the same, it will track any brightness change so it’s possible to restore it later. Really simple and really working.
And yes, the script above contains no error handling. If you want to see the real stuff, it’s available on GitHub. Even better, it’s available as a Debian package if you want to install it.
Moving from Windows to Ubuntu, there is one shortcut I surely miss - Ctrl+Shift+Escape. On Ubuntu this does absolutely nothing.
Fortunately one can always add a custom shortcut to System Monitor:
gsettings set org.gnome.settings-daemon.plugins.media-keys custom-keybindings \"['/org/gnome/settings-daemon/plugins/media-keys/custom-keybindings/custom0/']"GSCHEMA=org.gnome.settings-daemon.plugins.media-keys.custom-keybinding
GPATH=/org/gnome/settings-daemon/plugins/media-keys/custom-keybindings/custom0/
gsettings set$GSCHEMA:$GPATH name "System Monitor"
gsettings set$GSCHEMA:$GPATHcommand"gnome-system-monitor"
gsettings set$GSCHEMA:$GPATH binding "<Primary><Shift>Escape"
However, this is not quite “it”. The major issue is that, if System Monitor is already open, it will remain in background. As this is Linux, of course there is a command line solution for this.
First we need to install wmctrl package
sudoaptinstall wmctrl
Then we can setup a script to run System Monitor and activate it’s window. Since application itself is single instance, this does exactly what we need:
Upon getting Linux Mint installed, I went ahead with installing VPN by Private Internet Access. Went through the same motions as usually albeit now with slightly different result - it wouldn’t connect.
Looking at logs ($HOME/.pia_manager/log/openvpn.log) just gave cryptic errors:
SIOCSIFADDR: Operation not permitted
: ERROR while getting interface flags: No such device
SIOCSIFDSTADDR: Operation not permitted
Quick search on internet brought me to Linux Mint forum where exactly the same problem was described. And familiarity didn’t stop there; author had one other similarity - encrypted home folder. Sounded like a perfect fit so I killed PIA client and went with slightly modified procedure:
However, this didn’t help. Still the same issue in my log files. So I decided to go with atomic option. First I killed PIA client (again) and removed PIA completely together with all my modifications:
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.
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.
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:
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).