diff options
-rw-r--r-- | blog/route.md | 239 |
1 files changed, 239 insertions, 0 deletions
diff --git a/blog/route.md b/blog/route.md new file mode 100644 index 0000000..3f6d0cb --- /dev/null +++ b/blog/route.md @@ -0,0 +1,239 @@ ++++ +rss = "How to set up an Ubuntu system as a router" +date = Date(2024, 8, 3) +tags = ["fun", "recipe", "net"] ++++ + +# GNU as a Router, the Canonical Way + +A while ago I noticed that my ISP leases IPv4 addresses out indefinitely. +It was everything I'd ever wanted and I gotta seize it to truly _self_-host. +As an experiment, I started on something cheaper, like a single-board compooter. +In 2024, support for general-purpose RISC-V chips began to ripen, so naturally +due to FOMO, I bought a board with JH-7110. Boy, was that a mistake! +While the bootloaders' support had been well [upstreamed], +certain essential features like PCIe (for NVMe) has yet to reached +a mainline Linux release, even worse so on the BSDs. I ended up flashing +the _only_ distribution with official support [at the time][goatse], Ubuntu. + +Funny enough, after over a decade of daily driving GNU, twas the first time +I installed Ubuntu on a machine of my own. At the time of writing, +the reason for the was more apparent than ever: Canonical had been +forcing Snap[^snap] down the users' throat, even on the _server_ edition. +Thankfully Snap was still managed by APT and twas easy enough to remove +prevent it from coming back. Another annoyance was the lack of manual pages +in the minimized installation _and_ that the official way to enable them +is through a script that also install other bloats SMFH (the script +is quite short and the actually necessary commands can be trivially found, +I'd rather they're documented instead). + +That being said, not everything Ubuntu includes due to NIH is bad. +Unity (not the game engine that's proprietary like Snap server) +was loved by many; and this article is basically an appreciation post +for some others: [Netplan] and [ufw]. Before diving in, +lemme finish the story to give you the full context of this setup. +The SBC is the VisionFive 2 which is blessed with plenty of IO: + +* 8 GB of memory +* 4 USB 3.0 type-A ports +* 2 RJ45 ports (1 Gb and 100/10 Mb) +* 1 M.2 slot (I used this as an excuse to buy a larger SSD + and put the old 256 GB one here) +* 1 eMMC slot[^mmc] (eMMC are cheap, got one also with 256 GB) +* 1 TF slot +* 40 pin GP(and predefined-purpose)IO +* Other stuff for interfacing with humen like HDMI, audio jack, etc. + +Initially, my plan for the SBC was to host services unlisted +on the [loang network]. Official services were not considered +because my home network has no IPv6 and sometimes I'll like +to have most of the bandwidth for meself. Shortly afterwards, +I also purchased a somewhat beefy desktop compooter with even more I/O, +especially a bunch of SATA, which are a lot more attractive +than connecting hard di\*ks via USB. On the other hand, the SBC barely +consume any electricity, well under 10 W with the NVMe drive, a Wi-Fi dongle +and a fan connected. Since it cost virtually nothing to keep it up 24/7, +I decided to hand it the following two tasks: + +* Reverse proxying services running on more powerful machines + in the local network. +* Acting as a virtual router between nodes I manage. + This is particularly useful for tunneling to my work network + and accessing the servers, allowing me to work remotely with low latency. + +Setting up the VPN with Wireguard was relatively easy, so I assumed swapping +the SBC for the home router couldn't be too hard. Once again, I [chose poorly], +this little project'd costed me so many sleepless nights so I figured +I should note down what I learned here in case it can save someone else +from the same pain. **Do not take inspiration from this!** + +\toc + +## Connecting to the Internet + +My landlord handles the contract with the ISP so I don't know the details +of the subscription, but there's certainly no IPv6 nor any static IPv4 address. +Bandwidth to datacenters in the region is approximately 100 Mb/s +and the wall socket connects to a Cat 5e cable. I know about the latter +because whatever dumb ass did the last maintenance wired that to another +short one dangling from the wall socket[^futa], and after getting stabbed +in the eyes for months I finally to open it up and made the socket +a proper socket. + +It would not make the slightest of a difference but I connect +the SBC's 1 Gb port (identified in Ubuntu as end0) to the Internet +and the slower one (end1) to my desktop on the local network. +Thankfully no [special setup][router freedom] was needed +and here is the entire Netplan configuration to connect to the outside world: + +```yaml +network: + ethernets: + end0: + dhcp4: true + renderer: networkd + version: 2 +``` + +## Local Networking + +For simplicity's sake, I decided to use the same subnet for both Ethernet +and Wi-Fi under a bridge br0, where addressing and routing is configured: + +```yaml +network: + bridges: + br0: + addresses: + - 192.168.147.254/25 + interfaces: + - end1 + routes: + - from: 192.168.147.128/25 + on-link: true + to: 0.0.0.0/0 + type: nat + via: 192.168.147.254 + ethernets: + end1: + dhcp4: false +``` + +As Netplan doesn't configure any DHCP server, +that's done separately by udhcpd from busybox: + +```plaintext +interface br0 +start 192.168.147.128 +end 192.168.147.253 +max_leases 126 +option subnet 255.255.255.128 +option router 192.168.147.254 +``` + +I couldn't seem to get a concrete information on the ports used by DHCP +so I open the firewall for UDP on both 67 and 68 (I swear +this isn't an engagement bait to test out the new mailing list): + +```plaintext +ufw allow in on br0 to any port 67 proto udp +ufw allow in on br0 to any port 68 proto udp +``` + +## Wireless Access Point + +Thanks to systemd, the Wi-Fi dongle is recognized as wlx600dd0g8b33f. +Yes, that abomination of a name includes the chip's full MAC address. +That being said, I'd like to stick to the basis of a systemd/Linux distro. +Even though Netplan doesn't support Wi-Fi hotspot with systemd-networkd +but NetworkManager, so the interface had thus to be declared as Ethernet: + +```yaml +network: + bridges: + br0: + interfaces: + - wlx600dd0g8b33f + ethernets: + wlx600dd0g8b33f: + dhcp4: false +``` + +Actual wireless connectivity is handled by hostapd: + +```ini +interface=wlx600dd0g8b33f +bridge=br0 + +ssid=YΦ +utf8_ssid=1 +country_code=KR +channel=6 +ieee80211d=1 +ieee80211h=1 +ieee80211n=1 +hw_mode=g +wmm_enabled=1 + +wpa=2 +wpa_pairwise=TKIP +wpa_passphrase=just enter random characters +``` + +## Name Resolution + +My ISP is [known to be evil][KT malware] so I'd rather rely on more reputable +resolvers like [OpenNIC] (plus free-of-charge domain names!). Most of their +[tier 2] are located on the other side of the globe (200 to 300 ms RTT), +so a local cache is almost required. SmartDNS seems to be the best fit +for this purpose, as it queries upstream servers simultaneously +and also check for the IP with the lowest RTT among the results. +Since I don't trust my ISP, connections to the upstream servers are encrypted: + +```plaintext +bind :53@br0 +server-tls 51.254.162.59 -host-name ns1-dot.iriseden.fr +server-tls 202.61.197.122 -host-name dns.furrydns.de +server-tls 80.152.203.134 -host-name dot.kekew.info +server-tls 178.201.248.159 -host-name dot.kekew.info +server-tls 178.201.248.160 -host-name dot.kekew.info +server-tls 95.216.99.249 -host-name dns.froth.zone +``` + +For the router itself, the nameserver is set in /etc/resolv.conf +and Netplan is told not to change it: + +```yaml +network: + ethernets: + end0: + dhcp4-use-dns: false +``` + +After ufw is configured to allow UDP traffic in port 53 on br0, +udhcpd is instructed to advertise this local DNS server: + +```plaintext +option dns 192.168.147.254 +``` + +I might consider blocking ads at the domain-name level someday, but for now +uBlock Origin is working well enough on my systems and I rarely have +people over, especially not for looking at _their_ electronic devices. + +[^snap]: Not [the good one][snap]. +[^mmc]: Innovation's gone full circle, _eMMC_ is short for _embedded MMC_. +[^futa]: Basically a futanari of the RJ45 world. + +[upstreamed]: https://rvspace.org/en/project/JH7110_Upstream_Plan +[goatse]: https://loa.loang.net/chung/D16T24MXDP3T.3BR1X04I90CGT@guix/t +[Netplan]: https://netplan.io +[ufw]: https://launchpad.net/ufw +[loang network]: https://loang.net +[chose poorly]: https://antifandom.com/how-i-met-your-mother/wiki/Knight_Vision +[snap]: http://snap.berkeley.edu +[router freedom]: https://docs.fsfe.org/en/teams/router-freedom-tech-wiki +[KT malware]: https://www.tomshardware.com/tech-industry/cyber-security/south-korean-telecom-company-attacks-torrent-users-with-malware-over-600000-people-report-missing-files-strange-folders-and-disabled-pcs +[OpenNIC]: https://opennic.org +[tier 2]: https://servers.opennic.org +[SmartDNS]: https://pymumu.github.io/smartdns/en |