NUC8-FNOS

FNOS(飞牛nas)

fnOS官网:https://www.fnnas.com/

系统和用户

启用SSH:系统设置 ——> SSH ——> 点击开启即可

fnOS 基于 Debian 发行版的 Linux 内核构建,继承了 Debian 的软件包管理(APT)和系统

bash
cat /etc/os-release   # 显示系统名称、版本号(如 NAME="Debian GNU/Linux")

uname -a              # 显示内核版本(如 6.12.18-trim)

每个 fnOS 应用层账号映射到 Linux 的普通用户(如 fnuser),权限受 sudo 限制,避免直接系统操作

启用 Root 账户(谨慎操作):

bash
# 为 Root账户 设置密码
sudo passwd root  # 输入两次新密码

# 解锁 Root 账户
sudo passwd -u root 

# 允许 SSH 登录(可选), 编辑 /etc/ssh/sshd_config
sudo vim /etc/ssh/sshd_config 
# 修改如下内容
PermitRootLogin yes  

# 修改后重启 SSH 服务
sudo systemctl restart ssh

修改完成后就可以使用终端工具通过 root 账户登录了


fnOS 通过管理页面创建的数据存储空间在位于根目录下(以vol开头):

bash
ls /vol*

例如管理页面的存储空间1对应的就是 vol1, 其数据位于 /vol1/1000/ 目录下


雷电网桥

Nuc8有一个雷电3接口,连接到支持雷电3/4,以及USB4的设备可以组建雷电网桥,实现高速传输。以连接到Windows11为例:

  • 分别配置好Nuc(10.10.10.1)和windows设备(10.10.10.2)的IP和子网掩码(255.255.0.0
  • 设置Linux巨型帧,以 debian 为例:ip link set dev thunderbolt0 mtu 9000 该命令为临时设置,永久设置如下:
    bash
    # 找到您的连接名称(Connection Name)
    nmcli connection show  # Wired connection 2
    
    # 修改MTU设置
    nmcli connection modify "Wired connection 2" 802-3-ethernet.mtu 16000
    • 重新激活连接以应用更改
    bash
    nmcli connection down "Wired connection 2"
    nmcli connection up "Wired connection 2"
    • 测试巨型帧是否生效
    bash
    ping 10.10.10.2 -M do -s 8972  # linux ping windows
    
    ping 10.10.10.1 -f -l 8972     # windows ping linux

NetworkManager

要了解Debian系统的网络管理工具—NetworkManager,先要明白它的两个核心概念:设备(Device)和连接(Connection)

  • 设备 (Device): 指的是您系统中的物理或虚拟网络硬件。例如,您的有线网卡 (eno1)、无线网卡 (wlan0),雷电网桥 (thunderbolt0)。设备是客观存在的硬件。

  • 连接 (Connection): 指的是一套网络配置方案,或者说是一个“配置文件”。它定义了如何使用一个设备去连接网络,包含了IP地址、子网掩码、网关、DNS、MTU等所有设置。一个设备可以有多套连接配置方案,但同一时间只能激活一套。


常用命令:nmcli (NetworkManager Command-Line Interface)

nmcli是您在终端中与NetworkManager交互的主要工具,功能极其强大。

1. 查看状态

  • 查看所有网络设备及其状态:

    bash
    nmcli device status
    # 或者简写
    nmcli d

    这会列出所有物理/虚拟设备,以及它们当前是否被NetworkManager管理和连接状态。

  • 查看所有“连接”配置及其关联的设备:

    bash
    nmcli connection show
    # 或者简写
    nmcli c

2. 管理连接

  • 激活(启动)一个连接:

    bash
    sudo nmcli connection up "<连接名称>"

    例如:sudo nmcli connection up "Wired connection 1"

  • 停用(关闭)一个连接:

    bash
    sudo nmcli connection down "<连接名称>"
  • 修改一个连接的配置(永久生效):

    bash
    sudo nmcli connection modify "<连接名称>" <属性> <值>
    • 示例1:设置静态IP地址
      bash
      sudo nmcli connection modify "Wired connection 1" ipv4.method manual ipv4.addresses "192.168.1.100/24" ipv4.gateway "192.168.1.1"
    • 示例2:设置DNS服务器
      bash
      sudo nmcli connection modify "Wired connection 1" ipv4.dns "8.8.8.8 8.8.4.4"
    • 示例3:改回DHCP自动获取
      bash
      sudo nmcli connection modify "Wired connection 1" ipv4.method auto
  • 添加一个新的连接配置:

    bash
    sudo nmcli connection add type ethernet con-name "My Office LAN" ifname eno1

    这条命令会为eno1设备创建一个名为My Office LAN的新连接配置(默认为DHCP)。

  • 删除一个连接配置:

    bash
    sudo nmcli connection delete "<连接名称>"

3. 管理网络开关

  • 关闭所有由NetworkManager管理网络:

    bash
    sudo nmcli networking off
  • 开启所有由NetworkManager管理网络:

    bash
    sudo nmcli networking on

配置文件详解

nmcli的所有操作最终都会体现在配置文件中。这些文件是纯文本,也可以直接手动编辑。

  • 配置文件位置: /etc/NetworkManager/system-connections/ 目录下

  • 文件命名: 每个连接配置都对应一个文件,文件名就是连接的名称,后缀为.nmconnection。例如 Wired connection 2对应的文件就是/etc/NetworkManager/system-connections/Wired connection 2.nmconnection

  • 文件结构(INI格式): 文件采用简单的INI格式,分为不同的配置段(Section)。

    一个典型的静态IP配置文件示例 (My Static IP.nmconnection):

    ini
    [connection]
    id=My Static IP
    uuid=a1b2c3d4-e5f6-7890-1234-fedcba987654
    type=ethernet
    interface-name=eno1
    permissions=
    
    [ethernet]
    mac-address-blacklist=
    mtu=9000
    
    [ipv4]
    address1=192.168.1.100/24,192.168.1.1
    dns=8.8.8.8;8.8.4.4;
    method=manual
    
    [ipv6]
    addr-gen-mode=default
    method=auto
    
    [proxy]

    关键配置段解释:

    • [connection]: 定义了连接的基本信息,如名称(id)、UUID、类型(type)和绑定的设备名(interface-name)。
    • [ethernet]: 存放以太网相关的设置,例如mtu
    • [ipv4]: 存放IPv4相关的设置,method定义了是manual(手动)还是auto(DHCP),address1包含了IP、子网掩码和网关,dns则是DNS服务器。
    • [ipv6]: 同理,存放IPv6的设置。

NetworkManager通过nmcli提供了一个强大而一致的命令行接口来管理网络。它的核心是围绕“设备”和“连接”这两个概念。所有的配置更改都是永久性的,因为它们最终都会被写入到/etc/NetworkManager/system-connections/目录下的配置文件中。


Docker

通过管理页面设置数据存储位置后就可以直接使用docker了。通过docker info可以看到:

bash
# ...
Docker Root Dir: /vol1/docker
# ...

类似的信息,该信息表示docker的主要目录就是 存储空间1

bash
root@Nuc8:~# ls /vol1/docker
buildkit  containers  engine-id  image  network  overlay2  plugins  runtimes  
swarm  tmp  volumes

Docker Root Dir下,每个子目录负责存储不同类型的数据:

  • buildkit/:如果使用BuildKit来构建镜像,那么相关数据将存储在这里。
  • containers/:存储有关容器的信息。每个容器会有一个对应的子目录,里面包含了该容器的配置文件等。
  • image/:这里存放了与镜像相关的数据,包括层数据等。
  • volumes/:用于存储由Docker管理的数据卷。数据卷是用来在容器之间共享数据的一种机制。
  • network/:包含有关Docker网络的信息。
  • plugins/:存储Docker插件的相关数据。
  • tmp/:临时文件的存放位置。
  • trust/:涉及内容信任功能的相关数据,如果启用了的话。

Docker Root Dir指的是Docker在主机上存储其所有数据的根目录。这个目录是Docker守护进程存储镜像、容器、卷、网络配置以及其他相关数据的地方。默认情况下,这个目录位于/var/lib/docker,fnOS中通常在首次使用时通过管理页面设置


使用fnOS中的docker安装Redis:

bash
docker pull redis  # 下载镜像

mkdir -p /vol1/docker/data/redis/data

# 下载配置文件
wget http://download.redis.io/redis-stable/redis.conf \
    -O /vol1/docker/data/redis/redis.conf.backup


# 去除掉配置文件中的大量注释
grep -vE '^[[:space:]]*#|^[[:space:]]*$' \
    /vol1/docker/data/redis/redis.conf.backup \
    | sudo tee /vol1/docker/data/redis/redis.conf > /dev/null

修改配置文件: vim /vol1/docker/data/redis/redis.conf

bash
# 绑定到所有网络接口, 或者注释掉该行即可
bind 0.0.0.0
protected-mode no

# 设置数据目录
dir /data

创建实例并启动redis:

bash
docker run -p 6379:6379 --name redis --restart=always \
-v /vol1/docker/data/redis/redis.conf:/etc/redis/redis.conf \
-v /vol1/docker/data/redis/data:/data:rw \
-d redis \
redis-server /etc/redis/redis.conf

PostgreSQL

飞牛NAS(fnOS)内置了PostgreSQL(PG)数据库,主要用于支持其应用服务的数据存储与管理

下面把玩一下这个数据库吧,看看有哪些内容:

  1. 启用远程访问
    编辑配置文件:

    bash
    vim /etc/postgresql/15/main/postgresql.conf

    修改参数:

    ini
    listen_addresses = '*'          # 允许所有IP连接
    port = 5432                     # 默认端口
  2. 配置访问权限
    编辑 /etc/postgresql/15/main/pg_hba.conf,末尾添加:

    ini
    host    all             all             0.0.0.0/0               md5
  3. 重启服务生效

    bash
    systemctl restart postgresql
  4. 连接信息

    参数
    主机 主机的局域网IP
    端口 5432
    用户名 postgres
    密码 需通过命令行重置(见下方)
    bash
    # 1. 切换到 postgres 系统账户
    sudo -i -u postgres
    
    # 2. 进入 PostgreSQL 交互终端
    psql
    
    # 重置 postgres 密码
    ALTER USER postgres PASSWORD '123456';

    接下来就可以通过工具远程连接到数据了


fnOS内置的数据库有自己的使命,如果需要使用PG,考虑单独安装一个:

bash
docker pull pgvector/pgvector:pg16

docker run -d --name postgres16 --restart=always \
  -p 5433:5432 \
  -v /docker_data/postgre/pg16/data:/var/lib/postgresql/data \
  -e POSTGRES_PASSWORD=123456 \
  pgvector/pgvector:pg16

jellyfin

下载镜像:

bash
docker pull jellyfin/jellyfin

获取显卡用户组ID:

bash
root@Nuc8:~# ls -l /dev/dri
total 0
drwxr-xr-x 2 root root         80 Jul 26 12:08 by-path
crw-rw---- 1 root video  226,   0 Jul 26 12:08 card0
crw-rw---- 1 root render 226, 128 Jul 26 12:08 renderD128

root@Nuc8:~# getent group render
render:x:105:

这里是 105


安装(注意需要配置前面获取到的用户组ID):

bash
docker run -d \
--name jellyfin \
--user 1000:1000 \
-p 8096:8096 \
-p 8920:8920 \
-v /vol1/docker/data/jellyfin/config:/config \
-v /vol1/docker/data/jellyfin/cache:/cache \
-v /vol2/1000/media:/media \
--device /dev/dri:/dev/dri \
--group-add 105 \
--restart unless-stopped \
jellyfin/jellyfin:latest

安装ImmortalWrt

fnOS可以利用虚拟机功能安装ImmortalWrt,准备工作:

  • 先安装虚拟机:在fnOS的管理页面通过 应用中心 搜索安装 虚拟机
  • 下载 ImmortalWrt, iso文件和img文件(img一般是压缩文件.IMG.GZ,需要先解压),注意选择EFI版本,并将这两个文件上传到fnOS的存储空间中

创建虚拟机

  1. 管理页面打开之前安装好的虚拟机应用,点击虚拟机 —> 右上角新建虚拟机 —> 输入虚拟机名称,OS选择Linux,版本只有一个选择即可
  2. 选择之前上传的ISO文件 —> 主板类型:Q35, 主板固件:UEFI,GPU类型:vga, 选中开机自启动,其他默认即可
  3. 选择存储空间,设置硬盘大小(一般2~5G即可)
  4. 点击添加网卡(需要先在fnOS的系统设置->网络设置中,右上角开启OVS
  5. 硬件直通忽略即可,后续默认即可完成虚拟机的创建。然后就可以启动虚拟机了

开机后,通过VNC访问,先将 IP 地址设置为自己局域网的IP,方便进入管理页面和上传文件

bash
vi /etc/config/network

拷贝固件到硬盘

先通过fnOS的shell将 img 文件上传到 ImmortalWrt 的虚拟机中(/root目录下):

bash
scp -O /vol1/1000/Temp/immortalwrt-23.05.4-x86-64-generic-squashfs-combined-efi.img [email protected]:/root/

注意 img 文件的Linux文件路径可通过 fnOS 的管理页面获取: 文件管理 —> 找到文件后右击,点击详细信息 —> 点击复制原始路径

进入ImmortalWrt的shell,将 img 文件拷贝到硬盘中:

bash
dd if=immortalwrt-23.05.4-x86-64-generic-squashfs-combined-efi.img of=/dev/sda bs=4M

注意 /dev/sda 需要根据实际情况修改,可以通过 fdisk -l 查看硬盘信息


至此已经完成了固件的安装,现在需要关机 poweroff 后,在fnOS的管理页面中,将虚拟机的ISO文件去掉,然后再次启动虚拟机即可。

最后参照前面设置好IP地址,网关和DNS可通过管理页面指定(网关和DNS均指向主路由),同时关闭 lan 口的dhcp (旁路由设置)


常用插件安装

  • theme-argon
  • diskman
  • openclash

网卡硬件单元挂起

Linux终端中突然出现 e1000e 0000:00:1f.6 eno1: Detected Hardware Unit Hang 相关的日志信息,机器断网无法访问,只能重启恢复

尝试方法一:

bash
vim /etc/network/interfaces

# 示例 /etc/network/interfaces 文件配置
auto eno1
iface eno1 inet dhcp
    # 添加此行以禁用有问题的卸载功能,防止 e1000e 硬件挂起
    post-up /sbin/ethtool -K eno1 tso off gso off gro off

# 如果使用的是静态 IP,配置可能如下:
# auto eno1
# iface eno1 inet static
#     address 192.168.1.100
#     netmask 255.255.255.0
#     gateway 192.168.1.1
#     post-up /sbin/ethtool -K eno1 tso off gso off gro off

网络卸载(TSO, GSO, GRO)

  • TSO — TCP 分段卸载 (TCP Segmentation Offload, TSO): 当应用程序需要发送一个大的数据块时(例如,一个 64KB 的数据块),CPU 无需将其分割成符合以太网最大传输单元(MTU,通常为 1500 字节)的多个小数据包。相反,CPU 可以将整个大数据块直接交给网卡,由网卡硬件来完成分段工作。
  • GSO 通用分段卸载 (Generic Segmentation Offload, GSO): GSO 是 TSO 在内核协议栈中的软件实现版本。它在数据包离开内核、进入驱动程序之前进行分段,如果网卡硬件不支持 TSO,GSO 也能起到优化作用。
  • GRO 通用接收卸载 (Generic Receive Offload, GRO): GRO 是 GSO 的反向操作。它在接收端将多个相关的小数据包聚合成一个大的数据包,再递交给上层协议栈处理,从而减少了进入内核的中断次数和处理开销 。  

但是fnOS的默认网络管理工具为NetworkManager ,不适合该方式

bash
ls /etc/NetworkManager/system-connections/

systemctl status NetworkManager

可以创建一个 systemd 服务来禁用硬件卸载功能:

bash
vim /etc/systemd/system/disable-offloading.service

将以下内容复制并粘贴到文件中:

ini
[Unit]
Description=Disable TSO, GSO, GRO for e1000e NIC stability
After=network.target

[Service]
Type=oneshot
ExecStart=/sbin/ethtool -K eno1 tso off gso off gro off
RemainAfterExit=yes

[Install]
WantedBy=multi-user.target

保存文件并退出编辑器,然后启用该服务:

bash
systemctl daemon-reload
systemctl enable disable-offloading.service
systemctl start disable-offloading.service