Usar memoria de vídeo sobrante como SWAP en Linux

Electrónica relacionada con ordenadores de todo tipo, desde retro a modernos.
Avatar de Usuario
Naguissa
Administrador del Sitio
Mensajes: 486
Registrado: 04 Jul 2016, 11:17
Agradecido: 103 veces
Agradecimiento recibido: 134 veces

Usar memoria de vídeo sobrante como SWAP en Linux

Mensaje sin leer por Naguissa »

Tras mi NAS basado en una Orange Pi, que fué destruído tras caer una pieza metálica (disipador) por toda la placa, usé un antiguo AMD Athlon 64x2 para montar el NAS. Era ideal, pues tiene 2 canales doble IDE PATA y 4 canales SATA.

Pues bien, en ese PC hay 2Gb de RAM, algo escasos, y una gráfica nVidia GeForce 210 con 512Mb de vídeo, conectada por PCI-e.

Dándole vueltas al asunto, con tan poca RAM y tanta vRAM sin usar, ¿podría aprovechar esa vRAM? La respuesta, en Linux, es "evidentemente sí".

Así llegué a la tecnología MTD de Linux, y su posibilidad para crear un dispositivo de bloques con ella. Y en ese dispositivo crear una unidad Swap con máxima prioridad.

Se trata de crear un dispositivo de bloques en la memoria de vídeo sobrante de la tarjeta. Luego podemos usarlo como deseemos, en mi caso, como unidad swap.


1. Detectar el PCI ID de la tarjeta

Usamos el comando lspci para ver todos nuestros dispositivos PCI. En el listado buscamos la tarjeta que queremos usar y copiamos su ID:

Código: Seleccionar todo

root@NAS:/home/nas# lspci
00:00.0 Host bridge: Advanced Micro Devices, Inc. [AMD/ATI] RX780/RX790 Host Bridge
00:02.0 PCI bridge: Advanced Micro Devices, Inc. [AMD/ATI] RX780/RD790 PCI to PCI bridge (external gfx0 port A)
00:0a.0 PCI bridge: Advanced Micro Devices, Inc. [AMD/ATI] RD790 PCI to PCI bridge (PCI express gpp port F)
00:11.0 SATA controller: Advanced Micro Devices, Inc. [AMD/ATI] SB7x0/SB8x0/SB9x0 SATA Controller [AHCI mode]
00:12.0 USB controller: Advanced Micro Devices, Inc. [AMD/ATI] SB7x0/SB8x0/SB9x0 USB OHCI0 Controller
00:12.1 USB controller: Advanced Micro Devices, Inc. [AMD/ATI] SB7x0 USB OHCI1 Controller
00:12.2 USB controller: Advanced Micro Devices, Inc. [AMD/ATI] SB7x0/SB8x0/SB9x0 USB EHCI Controller
00:13.0 USB controller: Advanced Micro Devices, Inc. [AMD/ATI] SB7x0/SB8x0/SB9x0 USB OHCI0 Controller
00:13.1 USB controller: Advanced Micro Devices, Inc. [AMD/ATI] SB7x0 USB OHCI1 Controller
00:13.2 USB controller: Advanced Micro Devices, Inc. [AMD/ATI] SB7x0/SB8x0/SB9x0 USB EHCI Controller
00:14.0 SMBus: Advanced Micro Devices, Inc. [AMD/ATI] SBx00 SMBus Controller (rev 3c)
00:14.1 IDE interface: Advanced Micro Devices, Inc. [AMD/ATI] SB7x0/SB8x0/SB9x0 IDE Controller
00:14.2 Audio device: Advanced Micro Devices, Inc. [AMD/ATI] SBx00 Azalia (Intel HDA)
00:14.3 ISA bridge: Advanced Micro Devices, Inc. [AMD/ATI] SB7x0/SB8x0/SB9x0 LPC host controller
00:14.4 PCI bridge: Advanced Micro Devices, Inc. [AMD/ATI] SBx00 PCI to PCI Bridge
00:14.5 USB controller: Advanced Micro Devices, Inc. [AMD/ATI] SB7x0/SB8x0/SB9x0 USB OHCI2 Controller
00:18.0 Host bridge: Advanced Micro Devices, Inc. [AMD] K8 [Athlon64/Opteron] HyperTransport Technology Configuration
00:18.1 Host bridge: Advanced Micro Devices, Inc. [AMD] K8 [Athlon64/Opteron] Address Map
00:18.2 Host bridge: Advanced Micro Devices, Inc. [AMD] K8 [Athlon64/Opteron] DRAM Controller
00:18.3 Host bridge: Advanced Micro Devices, Inc. [AMD] K8 [Athlon64/Opteron] Miscellaneous Control
01:00.0 VGA compatible controller: NVIDIA Corporation GT218 [GeForce 210] (rev a2)
01:00.1 Audio device: NVIDIA Corporation High Definition Audio Controller (rev a1)
02:00.0 Ethernet controller: Realtek Semiconductor Co., Ltd. RTL8111/8168/8411 PCI Express Gigabit Ethernet Controller (rev 03)



2. Tomamos nota de los bloques de memoria

Volvemos a usar lspci, con las opciones -v y -s y el PCI ID de la tarjeta de video para extraer los detalles de los bloques de VRAM accesibles. Aquí seguramente haya varios bloques y no aparezca toda la VRAM, es normal y desgraciadamente solo tendremos acceso a los que aparezcan. Nos interesan los bloques grandes marcados como "prefetchable".

Código: Seleccionar todo

root@NAS:/home/nas# lspci -v -s 01:00.0
01:00.0 VGA compatible controller: NVIDIA Corporation GT218 [GeForce 210] (rev a2) (prog-if 00 [VGA controller])
Subsystem: ASUSTeK Computer Inc. GT218 [GeForce 210]
Flags: bus master, fast devsel, latency 0, IRQ 18, NUMA node 0
Memory at fb000000 (32-bit, non-prefetchable) [size=16M]
Memory at c0000000 (64-bit, prefetchable) [size=256M]
Memory at de000000 (64-bit, prefetchable) [size=32M]
I/O ports at ef00 [size=128]
Expansion ROM at 000c0000 [virtual] [disabled] [size=128K]
Capabilities: [60] Power Management version 3
Capabilities: [68] MSI: Enable- Count=1/1 Maskable- 64bit+
Capabilities: [78] Express Endpoint, MSI 00
Capabilities: [b4] Vendor Specific Information: Len=14 <?>
Capabilities: [100] Virtual Channel
Capabilities: [128] Power Budgeting <?>
Capabilities: [600] Vendor Specific Information: ID=0001 Rev=1 Len=024 <?>
Kernel driver in use: nvidia
Kernel modules: nvidia
En este caso voy a usar el bloque:

Código: Seleccionar todo

Memory at c0000000 (64-bit, prefetchable) [size=256M]
También hay que dejar unos Mbytes libres para el funcionamiento de la tarjeta; en mi caso voy dejar 32Mbytes, pero es posible que con unos 4Mbytes baste para el modo texto.


3. Configuramos el módulo phram

Usa los valores del punto anterior para configurar el módulo phram según tus necesidades.

Block Addres: es la dirección inicial del bloque de VRAM de la tarjeta. En el caso anterior es c0000000
Block size, in Mbytes: El tamaño del bloque en MBytes. En el caso anterior es 256
Reserved size, in Mbytes: Hay que dejar unos Mbytes para la memoria de vídeo, aunque sea para el modo texto. Como he dicho, dejaré 32Mbytes.

En la siguiente calculadora podéis extraer los valores para configurar el módulo. Los valores los guardaremos en un archivo nuevo que llamaremos /etc/modprobe.d/vram-swap.conf





Nos dará algo como:

Código: Seleccionar todo

options phram phram=swap,0xc2000000,224Mi

Si queréis añadir mas de un bloque podéis hacerlo repitiendo la calculadora y añadiendo el nuevo bloque detrás cambiando su nombre. Por ejemplo:

Código: Seleccionar todo

options phram phram=swap,0xc2000000,224Mi phram=swapB,0xff000000,64Mi

4. Configuramos las X

Especialmente importante si usamos las X, creamos el archivo /etc/X11/xorg.conf.d/vramswap.conf y añadimos la limitación de VRAM a la que hemos reservado en el punto anterior, en mi ejemplo, 32Mb:

Código: Seleccionar todo

Section "Device"
    Driver "nvidia" # or whichever other driver you use
    VideoRam 32768
EndSection


5. Probamos que todo funcione correctamente

Ahora cargaremos los módulos manualmente para probar que todo funcione correctamente:

Código: Seleccionar todo

root@NAS:/home/nas# modprobe phram
root@NAS:/home/nas# modprobe mtdblock
root@NAS:/home/nas# mkswap /dev/mtdblock0
root@NAS:/home/nas# swapon /dev/mtdblock0 -p 10
(usa el mkswap y el swapon con otros dispositivos mtdblock si has creado mas de uno).



Ahora lo ideal sería estresar el sistema o usarlo a fondo durante un rato, para comprobar que sea estable.

Si hay inestabilidad podemos aumentar el margen de memoria reservada del punto 3.


6. Configuramos todo para el arranque del sistema

Editamos el archivo /etc/modules-load.d/vramswap.conf y añadimos los módulos para que se carguen automáticamente al arrancar el sistema:

Código: Seleccionar todo

phram
mtdblock

Luego creamos el servicio systemd para que inicie todo automáticamente:

Editamos el archivo /usr/lib/systemd/system/vramswap.service

Código: Seleccionar todo

[Unit]
Description=Swap on Video RAM

[Service]
Type=oneshot
ExecStart=/usr/sbin/mkswap /dev/mtdblock0
ExecStart=/usr/sbin/swapon /dev/mtdblock0 -p 10
ExecStop=/usr/sbin/swapoff /dev/mtdblock0
RemainAfterExit=yes

[Install]
WantedBy=multi-user.target
Aquí hemos de añadir todos los bloques que hemos creado, como por ejemplo:

Código: Seleccionar todo

[Unit]
Description=Swap on Video RAM

[Service]
Type=oneshot
ExecStart=/usr/sbin/mkswap /dev/mtdblock0
ExecStart=/usr/sbin/swapon /dev/mtdblock0 -p 10
ExecStart=/usr/sbin/mkswap /dev/mtdblock1
ExecStart=/usr/sbin/swapon /dev/mtdblock1 -p 10
ExecStop=/usr/sbin/swapoff /dev/mtdblock0
ExecStop=/usr/sbin/swapoff /dev/mtdblock1
RemainAfterExit=yes

[Install]
WantedBy=multi-user.target

Y lo activamos en el arranque:

Código: Seleccionar todo

root@NAS:/home/nas# systemctl enable vramswap



Con ésto tendremos todo el sistema configurado para usar esa memoria de video sobrante como SWAP con cada reinicio.






Fuente: https://wiki.archlinux.org/title/Swap_on_video_RAM

Tags:
  • Similar Topics
    Respuestas
    Vistas
    Último mensaje