如果你的筆電記憶體是焊死在主機板上、無法升級,但顯示卡上還閒置著 8GB VRAM,這個開源專案可以讓你把 GPU 的 VRAM 當成 Linux 的 swap 空間來用。專案作者 Sean Lobjoit(c0dejedi)把這個工具命名為 nbd-vram,整套機制靠 CUDA 驅動 API 與 Linux 內建的 NBD(Network Block Device)協定串起來,不需要寫 kernel module,也不需要 NVIDIA 私有 kernel 符號。
實測環境:RTX 3070 筆電版(GA104M、實體 16GB 記憶體、VRAM 8GB)、驅動 580.159.03、kernel 6.17、Pop!_OS。配置 7GB VRAM 當 swap,加上原本的 zram 與 SSD swap,整體可定址記憶體達到約 46GB,是原本 RAM 量的三倍。溢位順序設計成:先把 RAM 填滿 → VRAM 透過 PCIe 快速吸收溢位 → zram 用 CPU 壓縮剩下的資料 → SSD swap 只在所有空間都耗盡時才動用。
運作原理
整個架構由一個小型 daemon 組成。它先用 CUDA 驅動 API 從 VRAM 分配一塊空間,再用 NBD 協定透過 Unix socket 把它掛出成區塊裝置。Linux 內建的 nbd 驅動會自動連上 socket、產出 /dev/nbdX,從此它就是一個普通的 swap 裝置。
資料路徑很直觀:kernel swap 子系統 → /dev/nbdX → nbd kernel 驅動 → Unix socket → nbd-vram daemon → cuMemcpyHtoD / cuMemcpyDtoH → GPU VRAM。
這種設計的優點是:不需要寫 kernel module、不依賴 NVIDIA kernel 符號,因此即使 kernel 與驅動更新,daemon 也不用重編。
為什麼不走 NVIDIA P2P API?
直覺的做法是用 nvidia_p2p_get_pages_persistent 把 VRAM page pin 在 BAR1,再用 ioremap_wc 讓 CPU 直接存取。但所有走這條路的現有專案都撞到同一面牆:NVIDIA 驅動在消費級 GeForce 卡上會回傳 EINVAL,無論是 persistent 還是非 persistent 變體、哪種 flag 組合都一樣。這個限制寫在 RM(Resource Manager)層,只對 Quadro 與資料中心 SKU 開放,跟驅動版本無關。
另一個變通方法是跳過 P2P API、直接 ioremap_wc BAR1 實體位址,但這條路也不通。GPU 內部 page table 只映射大約 16 MiB 的 BAR1(剛好等於顯示 framebuffer),其他位址讀回來都是 0。表面上 mkswap 會成功,但 swapon 會失敗,因為 swap header 根本不在那裡。
nbd-vram 走 NBD 這條路就完全繞過這些限制:cuMemcpyHtoD 與 cuMemcpyDtoH 在任何 CUDA GPU 上都能用、不需要任何特殊權限。
系統需求
- 支援 CUDA 的 NVIDIA GPU(任何消費級 RTX/GTX 卡都行)
- 內含
libcuda.so.1的 NVIDIA 驅動(不需要完整 CUDA toolkit) - Linux kernel 3.0 以上(內建 nbd 模組,大部分發行版都有)
nbd-client套件gcc、make
安裝步驟
git clone https://github.com/c0dejedi/nbd-vram
cd nbd-vram
sudo ./install.sh
sudo systemctl start vram-swap-nbd
驗證 VRAM swap 是否掛載成功:
swapon --show
# NAME TYPE SIZE USED PRIO
# /dev/nbd0 partition 7G 0B 1500
安裝時 service 預設是 enabled,每次開機都會自動啟動。
設定參數
編輯 /etc/systemd/system/vram-swap-nbd.service:
Environment=VRAM_SETUP_SIZE_MB=7168 # 要分配多少 VRAM
Environment=VRAM_SWAP_PRIORITY=1500 # swap 優先權(數字越高越先用)
daemon 會先嘗試設定的大小,如果 GPU 被顯示占用太多就以 512 MiB 為單位往下退讓,所以 VRAM_SETUP_SIZE_MB 是上限而不是硬性需求,會盡量抓滿能用的空間。
改完之後執行:
sudo systemctl daemon-reload && sudo systemctl restart vram-swap-nbd
電源管理
安裝程式第一次安裝時會詢問是否啟用電源感知管理。啟用後,service 會在拔掉 AC 電源(或電量低於門檻)時自動停止,接上電源後自動重啟。手動 systemctl stop 永遠會被尊重、不會被覆蓋。
安裝後要改設定,編輯 /etc/nbd-vram.conf,新設定會在下次輪詢(60 秒內)生效,或者下次插拔 AC 電源時立即生效。
冒煙測試(不安裝也能跑)
sudo bash test-nbd.sh
會依序配置 VRAM、連上 NBD 裝置、做 1 MiB 寫入/讀回檢查、啟用 swap,最後印出拆卸步驟。如果當前有測試實例在跑,install.sh 會自動處理拆卸。
冒煙測試通過後要對整個 partition 做壓力測試:
sudo bash test-fill.sh
會把整個 VRAM partition 寫滿 0、抽樣讀回驗證,結束時自動還原 swap。
效能數據
在 RTX 3070 筆電版上用 test-fill.sh 實測(7 GiB 循序寫入、4M block):
- 循序吞吐量:約 1.3 GB/s
- 延遲比 NVMe 還低,因為資料路徑是 PCIe 到 GPU,而不是走儲存裝置
如果你的筆電已經有 zram,建議把 VRAM swap 設成較高優先權,這樣溢位會先被 VRAM 吸收,最後才落到 SSD。
解除安裝
sudo bash uninstall.sh
授權
MIT - Sean Lobjoit(c0dejedi)
Reddit 熱門留言 (4)