nbd-vram - Linux'ta NVIDIA GPU VRAM'ini swap alanı olarak kullanan araç
(github.com/c0dejedi)- nbd-vram, Linux'ta NVIDIA GPU'nun boşta duran VRAM'ini yüksek öncelikli swap alanı olarak kullanmayı sağlayan küçük bir daemon'dur
- Lehimli bellek nedeniyle yükseltmenin zor olduğu ve görüntü çıkışını dahili AMD/ATI GPU'nun üstlendiği hibrit grafik dizüstü bilgisayarlarda, boştaki NVIDIA VRAM'ini bellek baskısını hafifletmek için kullanır
- Test ortamı AMD/ATI + RTX 3070 Laptop, 16GB RAM, 8GB VRAM, NVIDIA driver 580.159.03, kernel 6.17 ve Pop!_OS'tur; 7GB VRAM swap olarak ayrılarak zram ve SSD swap ile birlikte yaklaşık 46GB adreslenebilir bellek oluşturulmuştur
- Çalışma sırası şu şekildedir: önce RAM dolar, ardından VRAM PCIe üzerinden taşan sayfaları emer, sonra zram bunları CPU üzerinde sıkıştırır ve en sonunda SSD kullanılır
- Daemon, CUDA driver API ile VRAM ayırır, Unix socket üzerinde NBD(Network Block Device) protokolüyle bir blok aygıtı sunar ve çekirdeğin yerleşik
nbdsürücüsü bunu/dev/nbdXolarak açığa çıkararak normal bir swap aygıtı gibi kullanılmasını sağlar - Veri yolu kernel swap subsystem →
/dev/nbdX→ nbd kernel driver → Unix socket → nbd-vram daemon →cuMemcpyHtoD/DtoH→ GPU VRAM şeklindedir - Ayrı bir kernel modülü ya da NVIDIA kernel sembolleri gerektirmediği için, kernel ve driver güncellemelerinden sonra yeniden derleme olmadan kullanılmaya devam edilebilir
- NVIDIA P2P API yaklaşımında consumer GeForce GPU'larda
nvidia_p2p_get_pages_persistentEINVALdöndürür; BAR1 doğrudanioremap_wcyaklaşımı da yaklaşık 16MiB'lik ekran framebuffer bölgesi dışını okurken 0 döndürdüğü için başarısız olur - CUDA kopyalama yolu olan
cuMemcpyHtoDvecuMemcpyDtoH, özel izin gerektirmeden CUDA GPU'larda çalıştığından, NBD erişimi P2P ve BAR1 kısıtlarını aşar - Gereksinimler: CUDA destekli bir NVIDIA GPU,
libcuda.so.1içeren NVIDIA driver, Linux kernel 3.0+ içindeki nbd modülü,nbd-client,gccvemake; CUDA toolkit gerekli değildir - Kurulumdan sonra
vram-swap-nbdsystemd servisi açılışta otomatik çalışır; kullanılacak azami VRAM miktarı ve swap önceliği/etc/systemd/system/vram-swap-nbd.serviceiçindekiVRAM_SETUP_SIZE_MBveVRAM_SWAP_PRIORITYile ayarlanır - Daemon önce istenen VRAM boyutunu dener, GPU belleği yetersizse bunu 512MiB adımlarla azaltarak ayırır; bu yüzden
VRAM_SETUP_SIZE_MBzorunlu bir boyut değil, üst sınır olarak işlev görür - Güç farkındalıklı yönetim etkinleştirildiğinde, AC güç kesildiğinde veya pil belirli eşiklerin altına düştüğünde servis otomatik olarak durur; güç geri geldiğinde yeniden başlar ve elle verilen
systemctl stopkomutunu geçersiz kılmaz - RTX 3070 Laptop kıyaslamasında sıralı throughput ve sürekli rastgele I/O'da NVMe daha hızlıdır; ancak 4K okuma için 1 request/sec gecikmesinde VRAM ortalama 335us ile NVMe'nin 9.05ms değerinden 27 kat daha hızlıdır
- MIT lisansı ile sunulur; depo ayrıca smoke test için
test-nbd.sh, tüm bölüm doğrulaması içintest-fill.shve throughput, IOPS, gecikme ölçümü için benchmark betikleri sağlar
1 yorum
Hacker News görüşleri
CUDA üzerinden dosya depolama ya da mount gibi ele alınırsa ek yük yüksek olur; BAR kullanılırsa aktarım hızı veya IOPS belirgin şekilde iyileşebilir gibi görünüyor
Bunun yükseltme yolu olmayan lehimli belleğe sahip dizüstüler için olduğu açıklaması, “pahalı RAM’den neden daha da pahalı RAM’e swap yapılıyor?” şeklindeki ilk soruya cevap oluyor
Kullanım alanı dar görünüyor ama SSD’ye swap atılan durumlarda boşta duran 8GB VRAM’i kullanmak, ihtiyaç anında iyi bir fikir
Örneğin oyun oynamak için GPU aldıysanız, oyun oynamadığınız zaman masaüstü görüntüleme için 16GB VRAM gerekmiyordur; o halde başka amaçla kullanılabilir gibi geliyor
Yalnız bunun için oyun başlatıldığında sistemin swap olarak kullanılan VRAM’i serbest bırakabilmesi gerekir; pratikte bunun mümkün olup olmadığını merak ediyorum
80’lerin ortasından 90’ların ortasına kadar Birleşik Krallık’ta yaygın olan Amstrad PCW’de en fazla 512kB RAM kullanılabiliyordu ve bunun kayda değer bir bölümü RAM disk yapılabiliyordu
Turbo Pascal ile derleme yaparken de ciddi hız kazandırıyordu :-)
Fikir güzel ama burada ciddi biçimde yanlış giden bir şey var gibi
RTX 3070 Laptop’ta sıralı aktarımın yaklaşık 1.3 GB/s olduğu söyleniyor; oysa bu RTX 3070 çipi PCIe 4.0 x16 ile 64GB/s vermeli, 8GB GDDR6’nın kendisi de 448GB/s
NVMe sürücüye swap yapmak muhtemelen iki kat daha hızlı olurdu ama gecikme daha yüksek olurdu
Benchmark da ZRAM ile çalıştırılmış; ZRAM swap’e yazmadan önce sayfaları sıkıştırır. Bunun performans ek yükünün tam olarak ne kadar olduğunu bilmiyorum ama oldukça büyük olma ihtimali var
Öncelikle userspace programı, yavaşlığıyla bilinen nbd sürücüsüne bağlı ve GPU’ya aktarmadan önce userspace bounce buffer da kullanıyor. Kernel bir sayfayı swap’lemek istediğinde önce onu userspace’e açık bir buffer’a kopyalamalı, sonra userspace programı yeniden uyanıp CUDA işlemlerini başlatarak sayfayı aygıt belleğine kopyalamalı
nbd ayrıca yüksek kuyruk derinliğini veya bitişik erişim birleştirmeyi de iyi desteklemiyor. Kernel birleştirme olmadan çok sayıda 4K sayfa swap’i gönderirse, sadece 4 GB/s işlemek bile saniyede en az bir milyon kernel/userspace bağlam değişimi gerektirir. 64 GB/s’den hiç söz etmiyorum. Bu yalnızca NBD tarafı; NVIDIA sürücüsünün karmaşıklığını buna dahil etmiyorum
PCIe çok veri taşıyabilir ama toplam bant genişliğine yaklaşmak için uzun sayfa listeleri olan bir DMA motoru kullanmak gerekir. PCIe üzerinde her 4K sayfa için aktarım kurarsanız veri yolunu tam doyuramazsınız
NVMe’ye swap yolu çok iyi optimize edilmiştir. Swapper sayfa listesini doğrudan NVMe sürücüsüne verebilir ve denetleyici bunu RAM’den doğrudan DMA ile alır; CPU tarafında ne kopyalama ne de bağlam değişimi olur
ublk sürücüsüne taşınırsa userspace bounce buffer’dan kaçınılabilir ve birden fazla yazma kuyruğuyla CUDA kopyaları paralel ayarlanabilir; böylece iyileştirme şansı olabilir
RAM ya da VRAM ise kullanımla yıpranmaz
Geliştirme makinemde 32GB RAM ve yapay zeka modeli çalıştırmadığım zamanların çoğunda boşta duran 32GB VRAM var; bu yüzden fikir o kadar da kötü değil
Geri basıncın nasıl ele alındığını merak ediyorum. VRAM swap alanı olarak kullanılırken VRAM tahsis talebi gelirse ne oluyor?
X11’de buffer’lar önceden ayrıldığı için durum o kadar kötü değil ama Wayland’de tahsis çok daha dinamik; VRAM yetmezse tüm masaüstü kolayca çökebilir
Hyprland+llama-server+KVM ile bilgisayarlar arasında geçiş yaparken VRAM serbest bırakılamadığı için buna benzer çökmeleri birkaç kez yaşadım
Kullanıcı seviyesinde bir swap aygıtı oluşturmak, eskiden beri klasik çözülemez problemlerden biri sayılırdı
Demon bir sayfayı swap-in yapmak isterken, o sayfayı swap-in etmek için önce demonun kendi sayfasını swap-in etmek gerekiyorsa ne olacak?
En azından mikrokernellerin neden asla çalışmayacağına dair tartışmalarda bunun benzeri şeyler söylenirdi. Buradaki çözümün ne olduğunu pek bilmiyorum
Linux kernel’i de kendi metin sayfalarının swap-out edilmesini engelliyor; yani çözüm zaten var ve bunun mikrokernel tasarımlarına da uygulanmaması için bir neden göremiyorum
Demonun tüm belleğini sabitlerseniz bu sorun önemsiz hale gelir
Eskiden Linux’un MTD/phram sürücüsüyle buna benzer bir şey yaptığımı hatırlıyorum: https://wiki.archlinux.org/title/Swap_on_video_RAM
Ama bugün hâlâ ne kadar ilgili olduğunu bilmiyorum; çünkü DRM ile nasıl etkileştiğini ve VRAM’in bir kısmını ayırma işinin nasıl yapıldığını bilmiyorum. xorg.conf ile sınırlama öneren yaklaşım bugün oldukça demode olabilir
O sayfada OpenCL üzerinde uygulanmış bir FUSE dosya sistemi de var: https://github.com/Overv/vramfs
Bu taraf daha uyumlu olabilir
Eski günleri hatırlattı
Windows’ta da yıllar önce benzer bir şey görmüştüm
NVIDIA kartların VRAM’i ile RAM sürücüsü oluşturmayı sağlayan deneysel bir kavram kanıtı sürücüydü; sıralı erişim beklendiği gibi hızlıydı ama rastgele erişimde hâlâ ciddi iyileştirme alanı vardı
GpuRamDrive, GPU RAM ile desteklenen sanal bir sürücü oluşturuyor: https://github.com/prsyahmi/GpuRamDrive
AMD destekli fork: https://github.com/brzz/GpuRamDrive/
Benzeri ama OpenCL API kullandığı için AMD’de de çalışıyor
Yalnız AMD sürücülerinde epey hata var; dolayısıyla “çalışıyor”un tanımını yapmak lazım: https://libguestfs.org/nbdkit-vram-plugin.1.html
32GB RAM’li bir Apple Silicon Mac’te 20GB hâlâ kullanılmamış/“free” görünürken neden swap dosyası kullanıldığını, hatta oluşturulduğunu anlamıyorum
Linux’taki
swapoff -agibi basit bir komutla swap dosyasını tamamen devre dışı bırakmak neden mümkün değil?Amaç özellikle SSD ömrünü azaltmak değilse bu biraz anlamsız görünüyor
GUI’de swap dosyasını kapatmaya yönelik bir sistem ayarı olsa iyi olurdu; Apple da mevcut sistem ayarları/düzen “aşamalarını” artık bıraksa fena olmaz. Onca yıllık tercih panellerine kıyasla hâlâ kelime salatası gibi hissettiriyor
#Apple #Feedback #swapfile
“Kullanılabilir bellek” kavramı da ideal olarak “başka amaçlar için hızla geri kazanılabilecek bellek” anlamına daha yakındır
Bazı anlarda anonim belleği ana bellekte tutmak yerine, önbelleğe alınmış dosya içeriğinin o alanı kullanması daha mantıklı olabilir