How to encrypt an ODROID-C1’s Ubuntu root filesystem with DM-crypt LUKS

The starting point is a running ORDOID-C1 with the Ubuntu minimal image. Make sure the Ubuntu installation has been dist-upgraded and to use the latest linux-image-c1 kernel image available (3.10.72-78 as of this writing). The ODROID-C1 has to be running the lastest kernel available, check with uname -r. Some of the early Ubuntu minimal images may suffer from a dist-upgrade problem, see here how to fix it. I’m using an 8 GB eMMC card but if you change the /dev ids throughout the installation process, it may work with an SD-card too.

root@c1:/# apt-get -y install lvm2 cryptsetup parted nano rsync

Since we can’t convert a running root partition, we’re going to add a 3rd partition which will be our encrypted root filesystem. Check with parted -l where the 2nd partition ends because we’re going to add the new partition right there.

root@c1:~# parted -l
Model: MMC 008G92 (sd/mmc)
Disk /dev/mmcblk0: 7818MB
Sector size (logical/physical): 512B/512B
Partition Table: msdos

Number Start End Size Type File system Flags
1 1049kB 135MB 134MB primary fat16 lba
2 135MB 4295MB 4160MB primary ext4

In this case, the 2nd partition ends at 4295MB, which will be the starting value for the new partition.

root@c1:~# parted
(parted) mkpart primary ext4
Start? 4295MB
END? 100%
q

Now we’re going to tag the new partition for LVM:
root@c1:~# fdisk /dev/mmcblk0
Command (m for help): t
Partition number (1-4): 3
Hex code (type L to list codes): 8e

Command (m for help): w

The next step is to setup LVM and to encrypt our new root partition. I’m going to name the physical volume (PV) lvm, the volume group vg and the logical root volume root.

root@c1:~# cryptsetup -c aes-xts-plain -y -s 512 luksFormat /dev/mmcblk0p3
root@c1:~# cryptsetup luksOpen /dev/mmcblk0p3 lvm
root@c1:~# pvcreate /dev/mapper/lvm
root@c1:~# vgcreate vg /dev/mapper/lvm
root@c1:~# lvcreate -l 100%FREE -n root vg
root@c1:~# mkfs.ext4 /dev/mapper/vg-root

Let’s try to mount the new, encrypted root volume:

root@c1:~# mount /dev/mapper/vg-root /mnt

Copy the existing root volume to the new, enrypted root volume:

root@c1:~# rsync -av --exclude=/media --exclude=/mnt --exclude=/proc --exclude=/dev --exclude=/sys / /mnt

These are the commands to chroot our new root volume from the old root partition. You can always use them to gain access to the encrypted root volume from the old root partition.

mkdir -p /mnt/dev
mkdir -p /mnt/mnt
mkdir -p /mnt/proc
mkdir -p /mnt/sys
mkdir -p /mnt/media
cryptsetup luksOpen /dev/mmcblk0p3 lvm
mount /dev/mapper/vg-root /mnt
mount -o rbind /dev /mnt/dev
mount -t proc proc /mnt/proc
mount -t sysfs sys /mnt/sys
mount -t vfat /dev/mmcblk0p1 /mnt/media
chroot /mnt

The following actions take place in the chrooted environment on the new, encrypted root LV. Make sure you don’t modify the existing root partition!

Register the encrypted volume in /etc/crypttab:

echo lvm UUID=$(cryptsetup luksUUID /dev/mmcblk0p3) none luks|tee /etc/crypttab

Add a line in /etc/fstab for the root volume:

/dev/mapper/vg-root / ext4 errors=remount-ro 0 1

Being chrooted to the encrypted volume, we can now regenerate the initrd.img using

root@c1:~# update-initramfs -u -k $(uname -r)

Since support for dm-crypt has already been built into the kernel of the minimal image, we don’t have to add any crypto-modules to /etc/initramfs-tools/modules/. initramfs also does a pretty good job (thanks to the MODULES=most setting) determining what to add for lvm and dm-crypt support. Just to make sure, let’s have a look what has been placed into the new initrd.img:

root@c1:~# lsinitramfs /boot/initrd.img-$(uname -r) | grep crypt
sbin/cryptsetup
conf/conf.d/cryptroot
scripts/local-top/cryptopensc
scripts/local-top/cryptroot
scripts/local-bottom/cryptopensc
lib/libcryptsetup.so.4
lib/modules/3.10.72-78/kernel/arch/arm/crypto
lib/modules/3.10.72-78/kernel/arch/arm/crypto/aes-arm.ko
lib/modules/3.10.72-78/kernel/crypto
lib/modules/3.10.72-78/kernel/crypto/rmd160.ko
lib/modules/3.10.72-78/kernel/crypto/seed.ko
lib/modules/3.10.72-78/kernel/crypto/michael_mic.ko
lib/modules/3.10.72-78/kernel/crypto/rmd320.ko
lib/modules/3.10.72-78/kernel/crypto/cast6_generic.ko
lib/modules/3.10.72-78/kernel/crypto/rmd128.ko
lib/modules/3.10.72-78/kernel/crypto/rmd256.ko
lib/modules/3.10.72-78/kernel/crypto/lzo.ko
lib/modules/3.10.72-78/kernel/crypto/blowfish_generic.ko
lib/modules/3.10.72-78/kernel/crypto/khazad.ko
lib/modules/3.10.72-78/kernel/crypto/serpent_generic.ko
lib/modules/3.10.72-78/kernel/crypto/fcrypt.ko
lib/modules/3.10.72-78/kernel/crypto/camellia_generic.ko
lib/modules/3.10.72-78/kernel/crypto/twofish_generic.ko
lib/modules/3.10.72-78/kernel/crypto/async_tx
lib/modules/3.10.72-78/kernel/crypto/async_tx/async_tx.ko
lib/modules/3.10.72-78/kernel/crypto/async_tx/async_pq.ko
lib/modules/3.10.72-78/kernel/crypto/async_tx/async_raid6_recov.ko
lib/modules/3.10.72-78/kernel/crypto/async_tx/async_xor.ko
lib/modules/3.10.72-78/kernel/crypto/async_tx/async_memcpy.ko
lib/modules/3.10.72-78/kernel/crypto/cast5_generic.ko
lib/modules/3.10.72-78/kernel/crypto/tea.ko
lib/modules/3.10.72-78/kernel/crypto/xts.ko
lib/modules/3.10.72-78/kernel/crypto/xor.ko
lib/modules/3.10.72-78/kernel/crypto/ansi_cprng.ko
lib/modules/3.10.72-78/kernel/crypto/wp512.ko
lib/modules/3.10.72-78/kernel/crypto/cast_common.ko
lib/modules/3.10.72-78/kernel/crypto/tgr192.ko
lib/modules/3.10.72-78/kernel/crypto/zlib.ko
lib/modules/3.10.72-78/kernel/crypto/lrw.ko
lib/modules/3.10.72-78/kernel/crypto/anubis.ko
lib/modules/3.10.72-78/kernel/crypto/blowfish_common.ko
lib/modules/3.10.72-78/kernel/crypto/sha512_generic.ko
lib/modules/3.10.72-78/kernel/crypto/twofish_common.ko
lib/modules/3.10.72-78/kernel/crypto/salsa20_generic.ko
lib/modules/3.10.72-78/kernel/crypto/gf128mul.ko
lib/cryptsetup
lib/cryptsetup/askpass
lib/arm-linux-gnueabihf/libgcrypt.so.11

Looking good, the scripts/local-top/cryptroot script is now part of initrd.img. It will be called during the first phase of the Linux boot and ask for the root volume passphrase once initramfs is executed.

To update the uInitrd file in the FAT32 boot partition we first have to recreate the image using the new initrd.img containing lvm and crypto support:

root@c1:~# mkimage -A arm -O linux -T ramdisk -C none -a 0 -e 0 -n "uInitrd $(uname -r)" -d /boot/initrd.img-$(uname -r) /tmp/uInitrd-$(uname -r)

If everything went well, copy the uInitrd to /boot and /media:

root@c1:~# cp /tmp/uInitrd-$(uname -r) /boot
root@c1:~# cp /tmp/uInitrd-$(uname -r) /media/uInitrd

Edit /media/boot.ini (make a backup copy first) and replace the root UUID and add cryptdevice in the setenv booargs line:

# Boot Arguments
setenv bootargs "root=/dev/mapper/vg-root cryptdevice=/dev/mmcblk0p3:lvm ...and so on

Important: leave the rest of the setenv bootargs line intact!

That’s it.

root@c1:~# shutdown -r now

initramfs should now aks for the passphrase to decrypt the root volume during boot. Make sure to have a keyboard nearby ;-)

Free multi-domain SSL certificates from WoSign and HAProxy OCSP stapling

Since everyone now can get free 2-year multi-domain certificates from WoSign, I grabbed one for one of my web sites. However, WoSign’s OCSP server is located in China which may, depending on your and your server’s location, increase latency once the web browser is verifying the certificate’s revocation status. In my case from Europe:

PING ocsp6.wosign.com (111.206.66.61) 56(84) bytes of data.
64 bytes from 111.206.66.61: icmp_seq=1 ttl=53 time=428 ms
64 bytes from 111.206.66.61: icmp_seq=2 ttl=53 time=347 ms
64 bytes from 111.206.66.61: icmp_seq=3 ttl=53 time=312 ms
64 bytes from 111.206.66.61: icmp_seq=4 ttl=53 time=328 ms
64 bytes from 111.206.66.61: icmp_seq=5 ttl=53 time=313 ms

OCSP stapling comes in handy to reduce the latency for the revocation status check, again, depending on your clients and your server’s location.

Here’s the all-in-one shell script in /etc/cron.daily I’m using…

  1. to create the domain’s OCSP file for HAProxy
  2. to inject the latest OCSP data into a running HAProxy instance using its stats socket
#!/bin/sh
ROOT_CERT_FILE=/etc/ssl/private/wosign-root-bundle.crt
SERVER_CERT_FILE=/etc/haproxy/certs.d/domain.crt
HAPROXY_SOCKET=/var/run/haproxy.socket
OCSP_URL=`/usr/bin/openssl x509 -in $SERVER_CERT_FILE -text | grep -i ocsp | cut -d":" -f2-2,3`
OCSP_FILE=${SERVER_CERT_FILE}.ocsp

/usr/bin/openssl ocsp -noverify -issuer $ROOT_CERT_FILE -cert $SERVER_CERT_FILE -url "$OCSP_URL" -respout $OCSP_FILE -header Host `echo "$OCSP_URL" | cut -d"/" -f3`
echo "set ssl ocsp-response $(/usr/bin/base64 -w 10000 $OCSP_FILE)" | socat stdio $HAPROXY_SOCKET

To check if OCSP stapling works:

openssl s_client -connect mydomain.xyz:443 -tls1 -tlsextdebug -status

or for SNI-only configurations:

openssl s_client -connect mydomain.xyz:443 -servername mydomain.xyz -tls1 -tlsextdebug -status

If it works, there should be an OCSP section in the response like this:

OCSP response:
======================================
OCSP Response Data:
    OCSP Response Status: successful (0x0)
    Response Type: Basic OCSP Response
    Version: 1 (0x0)
    Responder Id: C = CN, O = WoSign CA Limited, CN = WoSign Free SSL OCSP Responder(G2)
    Produced At: Mar  8 14:01:14 2015 GMT
    .
    .
    .

A few notes:

  1. HAProxy’s stats socket needs to be enabled
  2. wosign-root-bundle.crt was taken from the Apache bundle in the certificate .zip file I received from WoSign
  3. /etc/haproxy/certs.d/domain.crt contains the private key and the certificate bundle from the “for Other Server” directory, however you could remove the last certificate since it’s the root CA cert.
  4. Requires HAProxy >= 1.5
  5. If socat is missing: apt-get install socat in Debian/Ubuntu
  6. Always aim for an A or A+ grade: SSL Server Test

How to set up a transparent VPN Internet gateway tunnel using OpenVPN

I created a transparent VPN Internet gateway tunnel (sorry, couldn’t come up with a better name for it) using OpenVPN and my new Odroid-C1 Linux mini computer. However, this will work with any Linux PC (including the Raspberry Pi). The beauty of a transparent VPN gateway is that a device in the LAN doesn’t have to know anything about the VPN. I don’t have to remember to turn on the VPN nor does it drain the battery on mobile devices to encrypt and decrypt the packets. The VPN is just “there”. On the other hand, mostly for performance reasons, I don’t want to encrypt all traffic leaving my home LAN, that’s why I didn’t set up the VPN in the existing router. vpn-gatewayI wanted to be able to choose, on a per-device basis, which devices will route their traffic unencrypted to my ISP and which devices will get their traffic encrypted and forwarded to the remote VPN server using a second gateway in my LAN. And all this without additional subnets in my LAN, VLANs or additional WiFi or Ethernet-adapters. This may not look like the brightest idea to everyone but it works for me and I wanted to document it to save time if I have to set it up again. This is not a step-by-step tutorial but should provide enough pointers to get started.

Continue reading

Could not load host key: /etc/ssh/ssh_host_ed25519_key

Sep 29 19:19:41 wopr sshd[11801]: error: Could not load host key: /etc/ssh/ssh_host_ed25519_key

If you’re getting this error message in the log file, you most likely have the ed25519 HostKey enabled in your sshd_config file but for some reason, no host key was generated for it.

Since openssh-6.4 you can run the ssh-keygen command to generate any missing host keys:

$ ssh-keygen -A
ssh-keygen: generating new host keys: ED25519

strongSwan 5 based IPSec VPN, Ubuntu 14.04 LTS and PSK/XAUTH

I prefer strongSwan over Openswan because it’s still in active development, easier to setup and doesn’t require a L2TP daemon. I prefer a simple IKEv1 setup using PSK and XAUTH over certificates. If you plan to share your VPN server with your friends it’s also a lot easier to setup for them without certificates. I haven’t tried the VPN configuration below with non-Apple clients but it works well with iOS and OS X clients. Make sure to use the Cisco IPSec VPN profile, not the L2TP over IPSec profile you need for Openswan. While strongSwan works well with KVM and Xen containers, it probably won’t work with non-virtualised containers like OpenVZ or LXC. Continue reading

How to auto backup a Gmail account to a QNAP NAS

It’s pretty straightforward to (incrementally) backup all emails in a Gmail account to a QNAP NAS. There’s a QNAP NAS solution using Getmail but it comes with some limitations. I prefer to use Gmail-Backup. It doesn’t need any configuration files and it doesn’t have a 100 messages per session limit. It stores all mails in the .eml format, which not only works on Windows PCs but is compatible with Apple Mail as well. You can even restore deleted emails using Gmail-Backup from the NAS back to a Gmail account.

Here’s how I installed Gmail-Backup on my QNAP TS-439 PRO II+. This tutorial should work with all Intel-based QNAP TS-* models but obviously I only have the 439 to test with. I’m looking forward for your feedback if it works on your QNAP NAS model as well. Please make sure you enabled IMAP in your Gmail account settings. Gmail-Backup works for “Gmail for your domain” (it’s part of “Google Apps” now) accounts as well.

The tutorial is divided into three parts. The first part shows how to install the Optware QPKG on the NAS. This package installer is needed in order to (easily) install Python on the NAS. The 2nd part deals with the installation of Gmail-Backup and the third shows how to automate the backup using cron. It probably is helpful to have some command line skills. Continue reading

Backup a Linux server with IMAP to Gmail

When I compiled the how-to about using Duply to backup a Linux server to a FTP account I mentioned the possibility to backup all data to an IMAP account. So, all we need for our encrypted backup is a reliable IMAP account provider with a few GB of email space. In this post I’m using Gmail which provides up to 7 GB for emails for free, but instead of saving emails Duply will store encrypted backup files on that Gmail account. Continue reading

How-to: FTP-Backup a Linux server with Duply

My Linux root server’s hosting price plan includes a 50 GB backup storage option. The backup server can only be reached using FTP, unsecured. Even though the backup server is only visible from within my server provider’s local network, I still don’t want to expose all my server settings, accounts and databases in clear text to a man in the middle. Or, I don’t want an untrustworthy subject with access to the backup server’s file system to be able to read my backup. Also, I don’t want to send my entire site to the backup storage every day as this would eat up my 50 GB within days.

This is where Duply (formerly known as FTPlicity) comes in handy. Duply claims to make your incremental encrypted backups on non-trusted spaces a child’s play. It manages backup job settings in profiles and allows to batch execute commands. It supports symmetric and asymmetric encryption using GPG.

Duply is not limited to FTP, you can also send your backups to a IMAP, WebDAV or ssh destination (and even more!). I haven’t tried the IMAP method but in theory you could send your encrypted backup to a free Google mail account as long as you don’t exceed the 7 GB provided by Gmail. However, in this sample, I’m using a FTP scenario with asymmetric encryption.

Continue reading

How to enable WPA2 in the Netopia 7347-84 VDSL router

For “compatibility reasons” Swisscom decided to not let you choose the more secure WPA2-PSK wireless encryption mode over the now insecure WPA-TKIP mode in the Netopia 7347 VDSL router. Swisscom customer service says that there are still many customers with old wifi hardware and that’s why only WPA-TKIP is selectable and WPA2 (which uses the more secure AES algorithm) has been disabled in the router’s web interface even though the router is capable of using WPA2!
WTF?! Come on…forcing clients to use insecure wireless settings just to get rid of a few support phone calls? Continue reading

How to prevent referer spam

Even though referer spam isn’t something new to black hat SEOs, WordPress blogs seem to get hit pretty hard with referrer spam these days.

Every time somebody clicks a link on a website, the browser sends the originating URL (the URL of the web page that hosts the link) to the target web server. This referer information can be parsed with web server log statistic software to show the webmaster where the web site’s visitors originated from. Continue reading

SSO between BEA WebLogic Server and SAP Enterprise Portal (Web Dynpro) using Web services

You’re looking for a way to consume Web services in SAP NetWeaver 2004s (and SAP Composition Environment aka NetWeaver 7.1) from BEA WebLogic Server 8.1 (and newer versions) using Single Sign On (SSO)?

You may have figured out already that SAML is not an option here because the SAP side is just a SAML consumer and not a provider (as of today). The only way left is to use the proprietary SAP Logon Tickets. Proprietary authentication mechanisms always require some extra work. In this blog article I’ll fill you in on what you need to SSO-connect those two J2EE platforms. Continue reading

Banning “problem countries” from your Linux server

It’s not a secret that these days most server hacking attempts originate from chinese IP addresses. A lot of attempts originate from other countries like South Korea and Indonesia as well. It seems that in those countries (cyber-)law-enforcement and technological advancement don’t correlate. I agree that a server has to be able to sustain non-flooding attacks just by using a proper and secure server configuration. But what if almost all traffic from those countries are automated vulnerability scans? Continue reading

SSO with SAP Logon Tickets and Java

To validate/verify a SAP Logon Ticket in a non-SAP Java environment you have to call into native libraries. Fortunately there’s some Java sample code provided in the SAPSSOEXT library archive.

Go to service.sap.com (you need a valid user and download permissions) -> Download -> Support Packages and Patches -> Entry by Application Group -> Additional Components, follow the SAPSECULIB and SAPSSOEXT links and download the library versions for your operating system. You’ll also need SAPCAR to extract those .SAR files. Both libraries – sapsecu.dll and sapssoext.dll – are needed to validate a SAP Logon Ticket. Continue reading

Setting up a Linux UT3 game server

While the installation of the Linux binary for the Unreal Tournament 3 Server is dead simple, some very brave game server administrators apparently chose to run the server with root permissions because there’s no useful server start script. This usually is an exceptionally bad idea for everything that opens ports on an Internet server.

Here’s a very simple start script that starts the UT3 server with a different account which you have to create using the groupadd/useradd command. In my case I’m using user game in group game. The script will sudo to this less powerful account and then start a botless deathmatch UT3 server. The server will continue to run after you close your shell. Well, at least until the server crashes, which it does frequently. In its current form the script has to be put into the ut3-dedicated/Binaries directory. Continue reading