因为手贱给路由器装了一个 Hyprland 桌面环境然后自己弄不干净就打算刷系统,这次尝试一下著名的 FreeBSD,由于不需要桌面环境所以配置起来还是很简单的。本来应该是这样的,然而在发布这篇文章时我已经使用接近半年的 FreeBSD 了。

好处:系统稳如老狗,硬路由瘫了这个都不瘫

安装过程和其他系统也没什么太大区别,只不过这次使用 ZFS 文件系统。由于是路由器也只有一块硬盘所以就不做 RAID 了。

软件包方面相较于我之前使用过的 Linux 发行版最大的区别就是多了一个 ports,它提供了定制化的编译安装方式,可以开启预编译包没有开启的某些功能等。

由于还是拿来当路由用,所以最重要的 DHCP C/S 要在第一时间配置好,这样就可以用 ssh 连接继续配置了。

刷机流程

直接从官网下载 14.1RELEASE 版本的镜像文件,然后掏出我二十块买来的 500G 硬盘用命令直接刷入

sudo dd if=FreeBSD-14.1-RELEASE-amd64-dvd1.iso of=/dev/sda bs=1M conv=sync

在一路点点点之后先别急着重启,找到 /etc/ssh/sshd_config 这个文件并允许 root SSH 方便后续操作。

vi /etc/ssh/sshd_config
- #PermitRootLogin no
+ PermitRootLogin yes

或者创建一个普通用户并添加到 wheel 组,这一步在安装系统时可以直接一起做掉。

接下来算是安装完成了,这里再额外装点平时和待会要用到的东西。

pkg install sudo fastfetch neovim zsh btop git isc-dhcp44-server radvd tcpdump portsnap

DHCP Client

首先怼上网线,查看网卡名称,这里是我配好后的。因为我是 Intel 的 I-226 网卡所以是这种命名方式。

# ifconfig
igc0: flags=1008843<UP,BROADCAST,RUNNING,SIMPLEX,MULTICAST,LOWER_UP> metric 0 mtu 1500
    options=4e427bb<RXCSUM,TXCSUM,VLAN_MTU,VLAN_HWTAGGING,JUMBO_MTU,VLAN_HWCSUM,TSO4,TSO6,LRO,WOL_MAGIC,VLAN_HWTSO,RXCSUM_IPV6,TXCSUM_IPV6,HWSTATS,MEXTPG>
    ether e4:3a:6e:5f:65:a9
    inet 192.168.1.7 netmask 0xffffff00 broadcast 192.168.1.255
    inet6 fe80::e63a:6eff:fe5f:65a9%igc0 prefixlen 64 scopeid 0x1
    inet6 2409:8a38:9e24:6d40:e63a:6eff:fe5f:65a9 prefixlen 64 autoconf pltime 3273 vltime 3273
    media: Ethernet autoselect (1000baseT <full-duplex>)
    status: active
    nd6 options=23<PERFORMNUD,ACCEPT_RTADV,AUTO_LINKLOCAL>
igc1: flags=8802<BROADCAST,SIMPLEX,MULTICAST> metric 0 mtu 1500
    options=4e427bb<RXCSUM,TXCSUM,VLAN_MTU,VLAN_HWTAGGING,JUMBO_MTU,VLAN_HWCSUM,TSO4,TSO6,LRO,WOL_MAGIC,VLAN_HWTSO,RXCSUM_IPV6,TXCSUM_IPV6,HWSTATS,MEXTPG>
    ether e4:3a:6e:5f:65:aa
    media: Ethernet autoselect
    status: no carrier
    nd6 options=29<PERFORMNUD,IFDISABLED,AUTO_LINKLOCAL>
igc2: flags=8802<BROADCAST,SIMPLEX,MULTICAST> metric 0 mtu 1500
    options=4e427bb<RXCSUM,TXCSUM,VLAN_MTU,VLAN_HWTAGGING,JUMBO_MTU,VLAN_HWCSUM,TSO4,TSO6,LRO,WOL_MAGIC,VLAN_HWTSO,RXCSUM_IPV6,TXCSUM_IPV6,HWSTATS,MEXTPG>
    ether e4:3a:6e:5f:65:ab
    media: Ethernet autoselect
    status: no carrier
    nd6 options=29<PERFORMNUD,IFDISABLED,AUTO_LINKLOCAL>
igc3: flags=8802<BROADCAST,SIMPLEX,MULTICAST> metric 0 mtu 1500
    options=4e427bb<RXCSUM,TXCSUM,VLAN_MTU,VLAN_HWTAGGING,JUMBO_MTU,VLAN_HWCSUM,TSO4,TSO6,LRO,WOL_MAGIC,VLAN_HWTSO,RXCSUM_IPV6,TXCSUM_IPV6,HWSTATS,MEXTPG>
    ether e4:3a:6e:5f:65:ac
    media: Ethernet autoselect
    status: no carrier
    nd6 options=29<PERFORMNUD,IFDISABLED,AUTO_LINKLOCAL>
lo0: flags=1008049<UP,LOOPBACK,RUNNING,MULTICAST,LOWER_UP> metric 0 mtu 16384
    options=680003<RXCSUM,TXCSUM,LINKSTATE,RXCSUM_IPV6,TXCSUM_IPV6>
    inet 127.0.0.1 netmask 0xff000000
    inet6 ::1 prefixlen 128
    inet6 fe80::1%lo0 prefixlen 64 scopeid 0x5
    groups: lo
    nd6 options=21<PERFORMNUD,AUTO_LINKLOCAL>

我插上网线后一开始只有协商速率并没有 IP 需要在指定网口打开 DHCP 才能正常使用。

然后到 /etc/rc.conf 添加一行配置并重启服务(更推荐使用 sysrc 来编辑配置,类似于 visudo 有语法检查可以避免拼写错误等)。

sysrc ifconfig_igc0="DHCP"
service netif restart

有网络之后就可以从我的服务器下载公钥方便 ssh 了,因为 root 默认情况下是禁止密码连接的,不想改配置直接使用密钥就行了。

pkg install wget curl
mkdir ~/.ssh && chmod 700 ~/.ssh
wget https://example.com/path/to/file -O ~/.ssh/authorized_keys

不建议在性能弱的设备编译安装任何软件,特别是静态编译

然后需要打开 pf 内核模块才能有网, 这里拿 GPT 糊了一个。

/etc/pf.conf

# NAT for IPv4 traffic from LAN (bridge0) to WAN (igc0)
nat on igc0 from 10.0.0.0/16 to any -> (igc0)

# LAN rules (IPv4 & IPv6)
# Allow all traffic within the LAN (bridge0)
pass quick on bridge0 from any to any

# WAN rules (Outbound IPv4 & IPv6 traffic)
# Allow all outbound traffic from LAN to WAN
pass out on igc0 from any to any

# WAN rules (Inbound IPv6 traffic)
# Allow inbound IPv6 traffic (if necessary for external access)
pass in on igc0 inet6 from any to any

# ICMPv6 rules (for proper IPv6 network functions)
# Allow ICMPv6 (neighbor discovery, router advertisements, etc.)
pass inet6 proto icmp6 all

pass in on bridge0 inet6 from any to any
pass in on igc0 inet6 proto icmp6 from any to any
pass in on bridge0 inet6 proto icmp6 from any to any

Proxy

软路由的重要组成部分, 虽然软件对这个系统支持不是很好, 但是还是得装一个. 由于需要开机自启动功能, 所以需要涉及到手动添加 daemon 不过和 Linux systemctl 也差不太多.

这里我打算整合一个懒人包方便以后接着用, 主要是替换更新的 mmdb 文件, 再把所有核心丢到一个目录通过软链接来实现不同平台一起用, 这样只需要改链接就好了. 代价就是特别大, 一堆核心和更精细的数据库每个都超过 10Mb 了.

Jail

参考 Running FreeBSD jails with containerd 1.5 用 containerd 和 runj 作为运行时,至少贴合了之前在 Linux 那边的一些经验。

最后安装一点自己的常用软件并配置,美滋滋!

chsh -s /usr/local/bin/zsh <username>

总共修改的文件:

  • /etc/rc.conf

    hostname="J4125_8G"
    # WAN
    ifconfig_igc0="DHCP"
    ifconfig_igc0_ipv6="inet6 accept_rtadv"
    ipv6_activate_all_interfaces="YES"
    rtsold_enable="YES"
    radvd_enable="YES"
    # LAN
    kld_list="if_epair"
    
    pf_enable="YES"
    
    gateway_enable="YES"
    ipv6_gateway_enable="YES"
    
    dhcpd_enable="YES"
    
    cloned_interfaces="bridge0"
    
    dhcpd_ifaces="bridge0"
    
    ifconfig_bridge0="inet 10.0.0.1 netmask 255.255.0.0 addm igc1 addm igc2 addm igc3 up"
    ifconfig_igc1="up"
    ifconfig_igc2="up"
    ifconfig_igc3="up"
    
    sshd_enable="YES"
    powerd_enable="YES"
    moused_nondefault_enable="NO"
    # Set dumpdev to "AUTO" to enable crash dumps, "NO" to disable
    dumpdev="AUTO"
    zfs_enable="YES"
    ntpd_enable="YES"
    local_unbound_enable="NO"
    clash_enable="YES"
  • /etc/ssh/sshd_config
  • /etc/sysctl.conf
  • /etc/pf.conf
  • /usr/local/etc/dhcpd.conf
  • /usr/local/etc/prometheus.yml
  • /usr/local/etc/ezjail.conf
subnet 10.0.0.0 netmask 255.255.0.0 {
    range 10.0.0.1 10.0.0.254;
    option routers 10.0.0.1;
    option broadcast-address 10.0.255.254;
    option domain-name "kazusa.cc";
    option domain-name-servers 10.0.0.1, 192.168.1.1;
    option subnet-mask 255.255.0.0;
}
  • /usr/local/etc/radvd.conf(未生效)

    interface bridge0 {
      AdvSendAdvert on;
      prefix 2409:8a38:9e24:6d40::/64 {
          AdvOnLink on;
          AdvAutonomous on;
      AdvValidLifetime 3600;
      AdvPreferredLifetime 1800;
      };
    };

其他服务

也没什么特殊需求,装一个魔法猫咪和普罗米修斯就行了

pkg install go prometheus node_exporter

然后出于安全考虑让 Grafana(十月份刚爆大漏洞) 在 Jail 里运行,于是还要先安装 ezjail

pkg install ezjail
ezjail-admin install -h http://ftp.freebsd.org
ezjail-admin create grafana 'bridge0|10.0.0.10'
ezjail-admin start grafana

# 进入 Jail 环境进行后续操作, 类似于 docker 进容器
ezjail-admin console grafana
pkg update
pkg install grafana
sysrc grafana_enable="YES"
service grafana start

经常用 docker 的应该就发现了, 这里没有对 jail 实例进行精简化, 导致会产生超过 800M 的文件, 因为实例太少我就懒得处理了(

jail 足够轻量化以至于都没有守护进程, 所以不要奇怪为什么没有在运行

在我的 Arch Linux 上安装客户端

yay -S prometheus-node-exporter

是不是心智负担很小?

美中不足的是我的 LAN 网络的 SLAAC 还没配好,这就导致我电脑还需要连接上游的 WiFi 来获取到 IPv6 地址,这还会导致我的 DNS 一直跳需要指定代理才能获得一个稳定的网络。

更新: IPv6 消失了,不知道是跑了太多流量还是批量回收的,不过这下就不用去折腾网络了

冷知识:这篇博客三月份创建的,然而十月份才发布, 虽然还没写完但我自己都看不下去了