配置
设备#
PC Master Race
- OS: Kubuntu 26.04 LTS
- CPU: AMD Ryzen 5 3600
- GPU: AMD Radeon RX 6800 16 GB
- RAM: 32 GB (4×8 GB GeIL Super Luce DDR4 3200 MHz)
- NVMe: 1 TB (2×512 GB Adata XPG Spectrix S40G)
- 主板: ASUS TUF Gaming X570-PRO (Wi-Fi)
- 鼠标: Logitech G305
- 键盘: HyperX Alloy Origins Core,配 Razer Pink PBT 键帽
- 耳机: Audio-Technica ATH-M50x 配 FiiO BTA10,以及 Sony Inzone H9
Raspberry Pi 4 Model B
Apple MacBook Air M1 2020
Samsung Galaxy S22 Ultra
基础安装#
Kubuntu 26.04 用 UEFI 模式安装:
- Btrfs
- Swap file
- 启用 LUKS
布局:子卷 /@、/@home 和 /@swap,swap file 在 /swap/swapfile,磁盘用 LUKS 加密。
BIOS#
- 加载优化默认值
- 用 DOCP/XMP 把内存设到 3200 MHz
- 启用 Above 4G Decoding
- 启用 Resizable BAR
- 启用 SVM Mode / AMD-V
- 启用 Secure Boot
- 禁用 CSM
- 调风扇曲线,尽量安静
Linux#
GRUB#
sudo nvim /etc/default/grub
把 preempt=full pcie_aspm=off 加到 GRUB_CMDLINE_LINUX_DEFAULT,别删掉原本就有的。
LUKS 示例:
GRUB_CMDLINE_LINUX_DEFAULT="cryptdevice=UUID=blablabla:luks-blablabla root=/dev/mapper/luks-blablabla splash preempt=full pcie_aspm=off"
sudo update-grub
preempt=full- 降低调度延迟。pcie_aspm=off- 修 Intel AX200 WiFi 卡在 D3cold 的问题。- 不用
quiet,因为我想开机时看到更多信息。 cryptdevice=...和root=...每台机器都不一样。
LUKS performance#
sudo dmsetup table
sudo cryptsetup --perf-no_read_workqueue --perf-no_write_workqueue --allow-discards --persistent refresh luks-blablabla
no_read_workqueue/no_write_workqueue- NVMe 上延迟更低。allow-discards- 在 SSD 上启用 TRIM。
Btrfs mounts#
Kubuntu 已经创建好子卷和 swap file。/tmp 已经由 systemd 放在 tmpfs。我只改 mount options:
sudo nvim /etc/fstab
在 / 和 /home 上,如果有 autodefrag 就删掉,再加 compress=zstd:
/dev/mapper/luks-blablabla / btrfs subvol=/@,defaults,noatime,compress=zstd 0 0
/dev/mapper/luks-blablabla /home btrfs subvol=/@home,defaults,noatime,compress=zstd 0 0
noatime- 少写点。compress=zstd- 透明压缩。
sysctl#
sudo tee /etc/sysctl.d/99-performance.conf > /dev/null << 'EOF'
kernel.nmi_watchdog = 0
kernel.watchdog = 0
net.ipv4.tcp_fastopen = 3
vm.dirty_ratio = 10
vm.dirty_background_ratio = 5
EOF && \
sudo tee /etc/sysctl.d/99-vm-zram.conf > /dev/null << 'EOF'
vm.swappiness = 150
vm.vfs_cache_pressure = 50
vm.page-cluster = 0
vm.watermark_scale_factor = 100
vm.compaction_proactiveness = 50
EOF && \
sudo sysctl --system
zram#
sudo apt install systemd-zram-generator && \
sudo tee /etc/systemd/zram-generator.conf > /dev/null << 'EOF'
[zram0]
zram-size = ram / 2
compression-algorithm = zstd
swap-priority = 100
EOF && \
sudo systemctl daemon-reload && sudo systemctl start dev-zram0.swap
Btrfs swap file#
sudo swapoff /swap/swapfile && \
sudo rm -f /swap/swapfile && \
sudo btrfs filesystem mkswapfile --size 4G /swap/swapfile && \
sudo swapon /swap/swapfile
磁盘 swap 留作 zram 满了之后的 fallback。
OOM#
sudo apt install systemd-oomd && \
sudo systemctl enable --now systemd-oomd.service
CPU#
powerprofilesctl set performance
amd-pstate active+ governorperformance+ EPPperformancetransparent_hugepage=madvise已经是默认值。- NVMe scheduler
none对 NVMe 来说通常已经是默认值。
Intel AX200 WiFi#
sudo tee /etc/modprobe.d/iwlwifi-fix.conf > /dev/null << 'EOF'
options iwlwifi power_save=0
options iwlmvm power_scheme=1
EOF
sudo tee /etc/NetworkManager/conf.d/99-disable-wifi-powersave.conf > /dev/null << 'EOF'
[connection]
wifi.powersave=2
EOF && sudo systemctl restart NetworkManager
KWin AMDGPU#
仅 KDE。只有开机黑屏时才需要。
sudo mkdir -p /etc/systemd/system/sddm.service.d && \
sudo tee /etc/systemd/system/sddm.service.d/restart-limits.conf > /dev/null << 'EOF'
[Unit]
StartLimitIntervalSec=30
StartLimitBurst=5
[Service]
ExecStartPre=/usr/bin/sleep 3
Restart=on-failure
RestartSec=2
EOF && \
sudo systemctl daemon-reload
NetworkManager#
sudo systemctl disable --now NetworkManager-wait-online.service
sudo tee /etc/NetworkManager/conf.d/99-mac-address-policy.conf > /dev/null << 'EOF'
[device]
wifi.scan-rand-mac-address=yes
[connection]
wifi.cloned-mac-address=stable
ethernet.cloned-mac-address=preserve
EOF && sudo systemctl restart NetworkManager
Bluetooth restart#
sudo rfkill unblock all
sudo systemctl restart bluetooth
sudo modprobe -r btusb
sudo modprobe btusb
软件包#
apt#
sudo apt install \
7zip adb atuin audacity bleachbit ble.sh build-essential buildah clang \
bat ca-certificates criu curl ddcui ddcutil easyeffects \
fastboot ffmpeg flatpak fzf gamemode gammastep gh ghostty git \
gnupg golang-go gwenview handbrake hashcat hugo isoimagewriter kcalc \
kde-config-flatpak lazygit libvirt-daemon-system \
mpv neovim nmap okular openrgb \
plasma-discover-backend-flatpak pipx podman podman-docker python3 \
python3-dev python3-full python3-venv \
qemu-system-x86 ssh sshpass ripgrep starship thefuck timeshift tmux \
torbrowser-launcher tree ufw unrar unzip virt-manager vlc wget \
wireshark yt-dlp zoxide
用户权限#
sudo usermod -aG kvm,libvirt,wireshark "$USER"
注销重新登录。
ROCm#
sudo apt install rocm rocm-podman-support && \
sudo usermod -aG render,video "$USER"
注销重新登录。
APT security auto-updates#
sudo apt install unattended-upgrades && \
sudo tee /etc/apt/apt.conf.d/20auto-upgrades > /dev/null << 'EOF'
APT::Periodic::Update-Package-Lists "1";
APT::Periodic::Download-Upgradeable-Packages "1";
APT::Periodic::AutocleanInterval "7";
APT::Periodic::Unattended-Upgrade "1";
EOF
Ubuntu Pro#
在 https://ubuntu.com/pro/dashboard 获取令牌。
sudo pro attach <你的令牌>
pro status
外部仓库#
Brave#
sudo curl -fsSLo /usr/share/keyrings/brave-browser-archive-keyring.gpg \
https://brave-browser-apt-release.s3.brave.com/brave-browser-archive-keyring.gpg && \
sudo curl -fsSLo /etc/apt/sources.list.d/brave-browser-release.sources \
https://brave-browser-apt-release.s3.brave.com/brave-browser.sources && \
sudo apt update && sudo apt install brave-browser
Firefox#
sudo apt remove firefox
snap list firefox >/dev/null 2>&1 && sudo snap remove firefox
snap list thunderbird >/dev/null 2>&1 && sudo snap remove thunderbird
sudo install -d -m 0755 /etc/apt/keyrings && \
wget https://packages.mozilla.org/apt/repo-signing-key.gpg -O- \
| sudo tee /etc/apt/keyrings/packages.mozilla.org.asc > /dev/null && \
cat <<EOF | sudo tee /etc/apt/sources.list.d/mozilla.sources
Types: deb
URIs: https://packages.mozilla.org/apt
Suites: mozilla
Components: main
Signed-By: /etc/apt/keyrings/packages.mozilla.org.asc
EOF && \
cat <<EOF | sudo tee /etc/apt/preferences.d/mozilla
Package: *
Pin: origin packages.mozilla.org
Pin-Priority: 1000
EOF && \
sudo apt update && sudo apt install firefox
Tailscale#
sudo mkdir -p --mode=0755 /usr/share/keyrings && \
curl -fsSL https://pkgs.tailscale.com/stable/ubuntu/resolute.noarmor.gpg \
| sudo tee /usr/share/keyrings/tailscale-archive-keyring.gpg > /dev/null && \
curl -fsSL https://pkgs.tailscale.com/stable/ubuntu/resolute.tailscale-keyring.list \
| sudo tee /etc/apt/sources.list.d/tailscale.list && \
sudo apt update && sudo apt install tailscale && sudo tailscale up
Antigravity#
sudo mkdir -p /etc/apt/keyrings && \
curl -fsSL https://us-central1-apt.pkg.dev/doc/repo-signing-key.gpg | \
sudo gpg --dearmor --yes -o /etc/apt/keyrings/antigravity-repo-key.gpg && \
echo "deb [signed-by=/etc/apt/keyrings/antigravity-repo-key.gpg] https://us-central1-apt.pkg.dev/projects/antigravity-auto-updater-dev/ antigravity-debian main" | \
sudo tee /etc/apt/sources.list.d/antigravity.list > /dev/null && \
sudo apt update && sudo apt install antigravity
包管理器和运行时#
Homebrew#
/bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)" && \
eval "$(/home/linuxbrew/.linuxbrew/bin/brew shellenv)" && \
brew install fnm topgrade uv
Topgrade auto-update#
mkdir -p ~/.config
cat > ~/.config/topgrade.toml << 'EOF'
[misc]
assume_yes = true
cleanup = true
no_retry = true
notify_end = "on_failure"
disable = ["system", "snap"]
EOF
mkdir -p ~/.config/systemd/user
cat > ~/.config/systemd/user/topgrade.service << 'EOF'
[Unit]
Description=Update user-level packages with Topgrade
[Service]
Type=oneshot
Environment=PATH=%h/.local/bin:%h/.bun/bin:%h/.cargo/bin:/home/linuxbrew/.linuxbrew/bin:/home/linuxbrew/.linuxbrew/sbin:/usr/local/bin:/usr/bin:/bin
ExecStart=/home/linuxbrew/.linuxbrew/bin/topgrade
EOF
cat > ~/.config/systemd/user/topgrade.timer << 'EOF'
[Unit]
Description=Run Topgrade automatically
[Timer]
OnCalendar=daily
Persistent=true
RandomizedDelaySec=1h
[Install]
WantedBy=timers.target
EOF
systemctl --user daemon-reload && systemctl --user enable --now topgrade.timer
npm global#
eval "$(fnm env --use-on-cd --shell bash)" && \
fnm install --lts --use && \
fnm default "$(fnm current)" && \
npm install -g @google/gemini-cli @openai/codex opencode-ai
脚本安装#
# Bun
curl -fsSL https://bun.sh/install | bash
# Rust / Cargo
curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh
应用#
Nerd Fonts#
brew install --cask font-hack-nerd-font font-ubuntu-mono-nerd-font && fc-cache -fv
Flatpak#
flatpak remote-add --if-not-exists flathub \
https://flathub.org/repo/flathub.flatpakrepo
flatpak install flathub \
com.github.tchx84.Flatseal \
com.github.PintaProject.Pinta \
com.obsproject.Studio \
com.obsproject.Studio.Plugin.OBSVkCapture//stable \
com.spotify.Client \
com.stremio.Stremio \
com.usebottles.bottles \
com.vysp3r.ProtonPlus \
dev.vencord.Vesktop \
io.github.flattool.Warehouse \
io.github.hedge_dev.hedgemodmanager \
io.podman_desktop.PodmanDesktop \
it.mijorus.gearlever \
net.lutris.Lutris \
net.retrodeck.retrodeck \
org.freedesktop.Platform.VulkanLayer.OBSVkCapture//25.08 \
org.gimp.GIMP \
org.kde.kdenlive \
org.kde.krita \
org.kde.yakuake \
org.libreoffice.LibreOffice \
org.localsend.localsend_app \
org.qbittorrent.qBittorrent \
org.signal.Signal \
org.telegram.desktop
Steam#
wget -O /tmp/steam.deb https://cdn.fastly.steamstatic.com/client/installer/steam.deb && \
sudo apt install /tmp/steam.deb && rm /tmp/steam.deb
Google Chrome#
wget "https://dl.google.com/linux/direct/google-chrome-stable_current_amd64.deb" -O /tmp/chrome.deb && \
sudo apt install /tmp/chrome.deb && rm /tmp/chrome.deb
Android Studio#
url=$(curl -s "https://developer.android.com/studio" | grep -o 'https://[^"]*linux[^"]*\.tar\.gz' | head -1) && \
wget -O /tmp/android-studio.tar.gz "$url" && \
tar -xzf /tmp/android-studio.tar.gz -C /tmp && \
sudo rm -rf /opt/android-studio && \
sudo mv /tmp/android-studio /opt/android-studio && \
mkdir -p ~/.local/bin && \
ln -sf /opt/android-studio/bin/studio ~/.local/bin/studio && \
rm /tmp/android-studio.tar.gz
第一次运行:
~/.local/bin/studio
等 ~/.local/bin 加到 PATH 之后:
studio
然后,在 Android Studio 里:
Tools > Create Desktop Entry
Setup Wizard 会把 SDK 下载到 ~/Android/Sdk。
Visual Studio Code#
wget -O /tmp/code.deb "https://code.visualstudio.com/sha/download?build=stable&os=linux-deb-x64" && \
sudo apt install /tmp/code.deb && rm /tmp/code.deb
Zed#
curl -f https://zed.dev/install.sh | sh
Trezor Suite#
把 Trezor Suite 下载成 AppImage,用 Gear Lever 管理。
Timeshift#
sudo timeshift-gtk
配置:
- 类型:Btrfs
- 位置:和系统同一个 Btrfs 磁盘
- 调度:每日 + 启动时
- 保留:3 个每日、3 个启动、2 个每周
/home: 不包含用户数据
Shell和终端#
Ghostty#
mkdir -p ~/.config/ghostty && \
tee ~/.config/ghostty/config.ghostty > /dev/null << 'EOF'
background-opacity = "0.9"
font-family = "UbuntuMono Nerd Font"
font-size = "14"
theme = "Dark Pastel"
window-height = "32"
window-width = "100"
EOF
bashrc#
编辑 ~/.bashrc:
nvim ~/.bashrc
加到最上面:
# ble.sh - load first, attach last
[[ $- == *i* && -f /usr/share/blesh/ble.sh ]] && source -- /usr/share/blesh/ble.sh --attach=none
覆盖默认值:
HISTCONTROL=ignoreboth:erasedups
HISTSIZE=100000
HISTFILESIZE=100000
shopt -s globstar
添加 alias:
alias cat='batcat --paging=never'
alias egrep='grep -E --color=auto'
alias fgrep='grep -F --color=auto'
删掉 PS1 那段代码(chroot、彩色提示符、xterm 标题),starship 已经接管了。
正常配置:
# path helper
path_prepend() {
[[ -d "$1" ]] || return
case ":$PATH:" in
*":$1:"*) ;;
*) export PATH="$1:$PATH" ;;
esac
}
# local bin
path_prepend "$HOME/.local/bin"
# android sdk
export ANDROID_HOME="$HOME/Android/Sdk"
export ANDROID_SDK_ROOT="$ANDROID_HOME"
path_prepend "$ANDROID_HOME/cmdline-tools/latest/bin"
path_prepend "$ANDROID_HOME/emulator"
path_prepend "$ANDROID_HOME/platform-tools"
# bun
export BUN_INSTALL="$HOME/.bun"
path_prepend "$BUN_INSTALL/bin"
# homebrew
if [[ -x /home/linuxbrew/.linuxbrew/bin/brew ]]; then
export HOMEBREW_PREFIX="/home/linuxbrew/.linuxbrew"
export HOMEBREW_CELLAR="$HOMEBREW_PREFIX/Cellar"
export HOMEBREW_REPOSITORY="$HOMEBREW_PREFIX/Homebrew"
path_prepend "$HOMEBREW_PREFIX/bin"
path_prepend "$HOMEBREW_PREFIX/sbin"
[[ -z "${MANPATH-}" ]] || export MANPATH=":${MANPATH#:}"
export INFOPATH="$HOMEBREW_PREFIX/share/info:${INFOPATH:-}"
fi
# fnm
command -v fnm >/dev/null && eval "$(fnm env --use-on-cd --shell bash)"
# rust/cargo
[[ -f "$HOME/.cargo/env" ]] && . "$HOME/.cargo/env"
# starship
command -v starship >/dev/null && eval "$(starship init bash)"
# thefuck - lazy load
fuck() { unset -f fuck; eval "$(thefuck --alias)"; fuck "$@"; }
# fzf
command -v fzf >/dev/null && eval "$(fzf --bash)"
# zoxide
command -v zoxide >/dev/null && eval "$(zoxide init --cmd cd bash)"
# atuin
if command -v atuin >/dev/null; then
if [[ ${BLE_VERSION-} ]]; then
eval "$(atuin init bash --disable-up-arrow)"
ble-bind -x 'C-r' '__atuin_history'
else
eval "$(atuin init bash)"
fi
fi
加到最后:
# ble.sh attach
[[ ! ${BLE_VERSION-} ]] || ble-attach
服务和网络#
Podman socket#
systemctl --user enable --now podman.socket
OpenCode server#
mkdir -p ~/.local/bin ~/.config/systemd/user
cat > ~/.local/bin/opencode-serve << 'EOF'
#!/usr/bin/env bash
set -euo pipefail
export PATH="$HOME/.local/bin:$HOME/.bun/bin:$HOME/.cargo/bin:/home/linuxbrew/.linuxbrew/bin:/home/linuxbrew/.linuxbrew/sbin:/usr/local/bin:/usr/bin:/bin"
[[ -x /home/linuxbrew/.linuxbrew/bin/brew ]] && eval "$(/home/linuxbrew/.linuxbrew/bin/brew shellenv)"
command -v fnm >/dev/null && eval "$(fnm env --use-on-cd --shell bash)"
exec opencode serve --mdns
EOF
chmod +x ~/.local/bin/opencode-serve
cat > ~/.config/systemd/user/opencode-serve.service << 'EOF'
[Unit]
Description=OpenCode serve
[Service]
Type=simple
Environment=PATH=%h/.local/bin:%h/.bun/bin:%h/.cargo/bin:/home/linuxbrew/.linuxbrew/bin:/home/linuxbrew/.linuxbrew/sbin:/usr/local/bin:/usr/bin:/bin
ExecStart=%h/.local/bin/opencode-serve
Restart=always
RestartSec=3
[Install]
WantedBy=default.target
EOF
systemctl --user daemon-reload && systemctl --user enable --now opencode-serve.service
SSH#
sudo systemctl enable --now ssh
UFW#
sudo ufw default deny incoming && \
sudo ufw default allow outgoing && \
sudo ufw allow OpenSSH && \
sudo ufw allow kdeconnect && \
sudo ufw enable
游戏#
Eden#
从 Eden(Nintendo Switch 模拟器)下载 AppImage,用 Gear Lever 管理。选 amd64 PGO 版本性能最好。
Sonic Unleashed Recompiled#
从 Unleashed Recompiled 下载 Flatpak 安装。需要 Sonic Unleashed Xbox 360 游戏文件(US 或 EU),title update,DLC 可选(强烈推荐,包含高质量光照)。
wget -O /tmp/UnleashedRecomp-Flatpak.zip \
https://github.com/hedge-dev/UnleashedRecomp/releases/latest/download/UnleashedRecomp-Flatpak.zip && \
unzip -o /tmp/UnleashedRecomp-Flatpak.zip -d /tmp/UnleashedRecomp && \
flatpak install /tmp/UnleashedRecomp/*.flatpak && \
rm -rf /tmp/UnleashedRecomp /tmp/UnleashedRecomp-Flatpak.zip
Steam#
- 启用 Steam Play
- 每个游戏设置启动选项:
gamemoderun %command%
- 用 ProtonPlus 安装 Proton-CachyOS 或 Proton-GE
Half-Life / Portal / Counter-Strike#
-vulkan -novid -fullscreen
Sonic Adventure#
用 Adventure Mods 给 Linux 上的 Sonic Adventure DX 和 Sonic Adventure 2 配置 mod。自动检测 Steam 安装,安装 mod manager、mod、依赖、预设和基础配置。
从 GitHub Releases 下载 AppImage,用 Gear Lever 安装。
GTA IV#
从 Steam 安装 Grand Theft Auto IV: The Complete Edition。
安装 FusionFix:下载 GTAIV.EFLC.FusionFix.zip,解压到游戏根目录(.exe 所在的位置)。
Steam 启动选项:
WINEDLLOVERRIDES="dinput8=n,b" %command%
Git#
git config --global user.name "astrovm"
git config --global user.email "[email protected]"
git config --global init.defaultBranch main
git config --global pull.rebase true
git config --global rebase.autoStash true
git config --global core.autocrlf input
git config --global core.pager batcat
git config --global fetch.prune true
git config --global rerere.enabled true
ssh-keygen -t ed25519 -C "[email protected]"
eval "$(ssh-agent -s)" && \
ssh-add ~/.ssh/id_ed25519 && \
cat ~/.ssh/id_ed25519.pub
把公钥贴到 https://github.com/settings/ssh。