WireGuard on the CID

From Unofficial Tesla Tech
Revision as of 22:03, 31 May 2020 by Carl (talk | contribs)
Jump to navigation Jump to search

Introduction

WireGuard is a next generation VPN. It has a far smaller attack surface than IPSec or OpenVPN, and Linus Torvalds likes it so much he put it in the Linux kernel as a module.

However, after putting in mighty effort to port Wireguard over to the CID, I've failed. It turns out that wireguard-go has significant problems and can not successfully run on the Tegra3 ARMEL platform. I did manage to cross-compile the wg helper tool, but with no parent app it is useless. I looked in to compiling the WireGuard kernel module, but the problem is there is no Debian or Ubuntu OS, contemporary with My CID's OS, which is software floating point (ARMEL, aka ... it's all HFP.

So can't compile the WireGuard module and wireguard-go is busted. There comes a point where you have to toss it in. That said, I am not going to bother with OpenVPN because it's stupid. My plan now is to try and set everything up with reverse SSH tunnels.

Tesla CIDs run several different kernel versions so I didn't even bother to compile the WireGuard module. We'll be using the user-mode application which is slightly slower but is kernel-independent. There are several incantations of the user-mode application, and I chose the Go language rendering as it's the farthest along.

This will establish a highly-secure, meshed (establish link on-demand), and relatively easy encrypted tunnel to your LAN, phone, whatever, to and from the car. Some will prefer to just set up a reverse SSH tunnel, but my LAN is complex and WireGuard is preferable.

Download and Install

First, download my handy pre-compiled binary (sha512sum), which at the time of this writing is version wireguard-go-0.0.20200320. If you don't trust me, Ok be that way and compile it yourself.

Then scp it to the cid:/var/solar/assets . And on the CID:
# chown root:root /var/solar/assets/wireguard-go
# chmod 550 /var/solar/assets/wireguard-go

Now, WireGuard must have a helper exe called wg. You can get my binary over here. This is compiled for my firmware version 18.36.2 ("Xenial Xerus") and may not be compatible with your version of /lib/libc.so.6, especially if it's older. If that's the case you'll have to compile your own.

Configuration

You first must set up WireGuard's config directory -- Everything in Config only needs to be done once:
# mkdir /var/solar/assets/wireguard/ && cd /var/solar/assets/wireguard/

Now this next part we're going to do on your home server which is running wg, so we don't have to cross-compile wireguard-tools for the CID.

Create the tunnel interface config file. Don't worry, we won't disturb your existing configuration. On your home WireGuard server:
# cd /etc/wireguard
# (umask 077 && printf "[Interface]\nPrivateKey = " | sudo tee /etc/wireguard/wg-tesla0.conf > /dev/null)

Now create the private and public keys:
# wg genkey | sudo tee -a /etc/wireguard/wg-tesla0.conf | wg pubkey | sudo tee /etc/wireguard/tesla-publickey
# chmod -R 600 /etc/wireguard

And set up the config file, adding these lines:
# nano wg-tesla0.conf

[Interface]
Address = {teslaWGaddress}/32
ListenPort = {yourWGport}
PrivateKey = {leaveYourPrivateKeyAlone}
DNS = {yourWGpeerDNSserverWG_IP}  # unbound listens on all interfaces

[Peer]
# {yourHouse}
PublicKey = {yourHousesPublicKey}
AllowedIPs = 0.0.0.0/0
Endpoint = {yourHousesPublicIP}:{yourWGport}

Running

Now, WireGuard doesn't have the concept of server-client... it's all peer communication, aka meshed. The VPN is silent unless there is traffic to move in either direction, which is a big plus.

I've developed a script for this, which is part of my suite of scripts reworked from Lunar's fine initial work. The script is in /var/solar/assets/scriptEveryBoot/wireguard-go.sh and config file is /var/solar/wireguard-go.conf .


Science.jpg CAUTION - Science Content

~~ Cross-Compile wireguard-go Yourself ~~

It's not hard.

  • Install golang -- MUST be version 1.13 or higher. In my case I run CentOS 8 and the highest repo version is 1.12, so I had to go to pkgs.org to download CentOS 7 versions of golang-1.13.6. You also need golang-src.1.13.6 and golang-bin-1.13.6, so download and install. In my case:

# dnf install golang-src-1.13.6-1.el7.noarch.rpm golang-bin-1.13.6-1.el7.x86_64.rpm golang-1.13.6-1.el7.x86_64.rpm

  • Now the latest WireGuard code, we first go to the correct Posix location to compile stuff, then download:

# cd /usr/local/src
# git clone https://git.zx2c4.com/wireguard-go
# cd wireguard-go

  • Since you are probably working on an x86 machine and the MCU1 CID is an ARMv7L 32bit (MCUs 2 and 2.5 are 64bit) we have to advise Go on what architecture the executable will be running:

# export GOARCH=arm GOARM=7 GOOS=linux
... or for MCU2 & 2.5:
# export GOARCH=arm64 GOOS=linux .
(To get a list: # go tool dist list)

# make
go build -v -o "wireguard-go"
And *BZAP* just like that it's done.

  • Now scp your shiny new wireguard-go over to cid:/var/solar/assets and you've got it.


~~ Cross-Compile wg Yourself ~~

Now we'll compile wireguard-tools for the wg helper exe. Take my word for it, the cross-compile toolchain for RHEL, CentOS, and Fedora is busted for this operation, so I ended up installing Kubuntu in a KVM virtual machine to compile it.

The first question is, does our CID have software floating-point, or hardware (vector) floating point? This matters matters matters.
# readelf -A /proc/self/exe | grep Tag_ABI_VFP_args
#

Well, no response, so the Tegra3 is soft floating point, meaning we will cross-compile with gcc-arm-linux-gnueabi and gcc-arm-linux-gnueabi, not gcc-arm-linux-gnueabihf and binutils-arm-linux-gnueabihf (as for the RPi).

It's important that you do this cross-compile in an Ubuntu release which is the same or similar to that in your CID. So download that .iso, install it, and work in there.

Then in that VM:
# apt install git make gcc-arm-linux-gnueabi binutils-arm-linux-gnueabi
# cd /usr/local/src
# git clone https://github.com/WireGuard/wireguard-tools
# cd wireguard-tools/src
# make CC=arm-linux-gnueabi-gcc target.arch=armv7l

CC wg.o
CC config.o
CC curve25519.o
CC encoding.o
CC genkey.o
CC ipc.o
CC pubkey.o
CC set.o
CC setconf.o
CC show.o
CC showconf.o
CC terminal.o
LD wg

You don't know how pretty this was, after days of struggle...

Then scp wg over to your CID into /var/solar/assets/ and in /var/solar/scripts.conf, uncomment the wireguard-over-cell.sh script.