{ "meta": { "title": "Dispositivos e aceleração ProxMenux", "description": "Como o OCI Manager Apps passa GPU, NVIDIA, Coral, USB, FUSE e outros dispositivos para um recipiente OCI como recursos Proxmox VE nativos validados." }, "header": { "title": "Dispositivos e aceleração", "description": "GPU, NVIDIA, Coral, USB, FUSE e dispositivos de bloco tornam-se os recursos de Proxmox VE nativos validados do recipiente.", "section": "OCI manager Apps" }, "sections": [ { "id": "principle", "title": "O dispositivo de que a aplicação necessita, não a máquina inteira", "blocks": [ { "p": "Um dispositivo solicitado pelo arquivo Compose ou pelo perfil da aplicação torna-se uma entrada de devN ou uma montagem LXC. Pedir um GPU, um dispositivo USB ou um Coral não torna o recipiente privilegiado." }, { "flow": { "nodes": [ { "label": "Inventário da máquina", "detail": "/dev/dri/renderD128\nGID 993 · Intel" }, { "label": "ProxMenux", "detail": "fornecedor e\npermissões verificadas" }, { "label": "LXC", "detail": "mesmo dispositivo\nGID efetivo" } ] } } ] }, { "id": "origin", "title": "De onde vem o pedido do dispositivo", "blocks": [ { "table": { "headers": [ "Origem", "O que é lido", "O que o instalador faz" ], "rows": [ [ "Docker Compose", "Pedidos de devices, group_add, deploy.resources e NVIDIA", "Cada requisito torna-se um pedido de dispositivo mostrado para revisão" ], [ "Perfil do catálogo", "O suporte que o aplicativo realmente tem para GPU, Coral, OpenCL, USB ou FUSE", "Apenas são oferecidas as opções validadas para essa imagem" ], [ "Metadados e documentação da imagem", "VA-API, Selkies, LinuxServer mods ou o tempo de execução NVIDIA", "As variáveis documentadas e preparação são adicionadas" ], [ "Seleção do usuário", "Apenas CPU, Intel/AMD, OpenCL, NVIDIA ou um dispositivo opcional", "A seleção é armazenada no contrato de instância" ] ] } }, { "calloutWarning": { "title": "Os dispositivos detectados não são anexados automaticamente", "body": "O host é inventariado, mas apenas dispositivos declarados pelo arquivo Compose ou por um perfil compatível são oferecidos e anexados. Um GPU, dongle USB ou Coral presente no host não é exposto a cada LXC." } } ] }, { "id": "identify", "title": "Como o dispositivo da máquina é identificado", "intro": "Antes de o LXC ser modificado, o dispositivo é lido no host e corresponde ao perfil escolhido.", "blocks": [ { "table": { "headers": [ "Tipo", "Identidade", "Validação" ], "rows": [ [ "Intel/AMD DRM", "/dev/dri/renderD* e /sys/class/drm/NODE/device/vendor", "Um dispositivo de caracteres com o fornecedor 0x8086 (Intel) ou 0x1002 (AMD)" ], [ "AMD OpenCL", "O nó de renderização, mais /dev/kfd quando o perfil precisa dele", "Existência, tipo, fornecedor, permissões e compatibilidade declarada" ], [ "AMD ROCm", "O nó de renderização, /dev/kfd e a geração que o controlador de computação relata em /sys/class/kfd/kfd/topology/nodes/*/properties", "Uma GPU de uma geração suportada pela imagem ROCm da aplicação (as GPUs RDNA2 que indica e as mais recentes) é oferecida sem alterações. As outras GPUs dessas famílias, como as Radeon 680M e 780M, são oferecidas como experimentais e nunca são a opção proposta. O ROCm não as suporta oficialmente: a aplicação apresenta-as como a geração da sua família (HSA_OVERRIDE_GFX_VERSION) e o instalador pede confirmação antes de transferir a imagem maior. Uma GPU mais antiga, como a gráfica integrada de um Ryzen 5000U, não é oferecida e o Immich mantém o reconhecimento na CPU" ], [ "NVIDIA", "nvidia-smi e nvidia-container-cli", "GPU, UUID, PCI bus, versão driver, Toolkit, /dev/nvidia* nós, binários e bibliotecas" ], [ "Coral PCIe/M.2", "/dev/apex_N e sua ligação em /sys/dev/char/MAJOR:MINOR", "Nó de caracteres, major/menor, proprietário, GID e permissões" ], [ "USB e serial", "/dev/ttyUSB*, /dev/ttyACM* ou /dev/bus/usb/BBB/DDD", "Nó de caracteres; para USB também fornecedor, produto e série quando sysfs publica-los" ], [ "KVM, TUN, FUSE, vídeo e SCSI genérico", "/dev/kvm, /dev/net/tun, /dev/fuse, /dev/videoN ou /dev/sgN", "Caminho suportado, tipo de nó e permissões efetivas" ], [ "Unidade óptica", "/dev/srN", "Um dispositivo de bloco" ] ] } } ] }, { "id": "install", "title": "O que acontece durante a instalação", "blocks": [ { "steps": { "items": [ { "title": "O modelo oferece seus perfis", "body": "Por exemplo, CPU apenas, Intel/AMD VA-API, AMD OpenCL, Intel OpenCL ou NVIDIA. As opções pertencem à imagem, não a um menu comum." }, { "title": "Um perfil é escolhido", "body": "Ele define os nós do dispositivo, ambiente, mods ou tempo de execução que a aplicação precisa." }, { "title": "É proposto um caminho", "body": "Para DRM, /dev/dri/renderD128, que pode ser alterado em um host com vários nós de renderização. Para USB ou serial, o nó específico é selecionado." }, { "title": "Validação", "body": "Existência, tipo, fornecedor permitido, permissões e GID são verificados. Um desencontro impede a operação." }, { "title": "O contrato está escrito", "body": "Caminho, modo, GID, acesso de escrita e perfil são gravados para atualizações e recriações." }, { "title": "Anexar e testar", "body": "pct set adiciona a entrada devN e o acesso é então verificado dentro do LXC. As imagens LinuxServer também são verificadas como usuário abc." } ] } } ] }, { "id": "config", "title": "Como aparece na configuração LXC", "intro": "Valores ilustrativos: dev0 e dev1 são as atribuições de slots livres Proxmox VE, e renderD128, apex_0 e o GID dependem do hardware do nó.", "blocks": [ { "codeGrid": { "items": [ { "title": "Intel/AMD VA-API", "code": "dev0: path=/dev/dri/renderD128,mode=0660,gid=993,deny-write=0" }, { "title": "Coral PCIe/M.2", "code": "dev0: path=/dev/apex_0,mode=0660,gid=GID,deny-write=0" }, { "title": "Um dispositivo USB específico", "code": "dev0: path=/dev/bus/usb/003/004,mode=0660,gid=GID,deny-write=0" }, { "title": "AMD OpenCL", "code": "dev0: path=/dev/dri/renderD128,mode=0660,gid=GID,deny-write=0\ndev1: path=/dev/kfd,mode=0660,gid=GID,deny-write=0" } ] } }, { "p": "O GID é lido com stat no host e escrito na entrada devN; os grupos render e video não são assumidos como tendo um número fixo. O dispositivo mantém o mesmo caminho /dev dentro do LXC, onde os próprios mecanismos da aplicação procuram por ele." } ] }, { "id": "profiles", "title": "Perfis que uma imagem pode oferecer", "blocks": [ { "table": { "headers": [ "Perfil", "Configuração resultante", "Oferecido quando" ], "rows": [ [ "Intel/AMD VA-API", "Nó de renderização /dev/dri", "O aplicativo suporta aceleração de vídeo" ], [ "OpenCL", "Nó de renderização, /dev/kfd quando necessário e o mod oficial", "A imagem ou perfil documenta- a" ], [ "NVIDIA", "Dispositivos de driver e bibliotecas da máquina", "O host tem um driver funcionando e o NVIDIA Container Toolkit" ], [ "Coral", "/dev/apex_0 ou o barramento USB", "O perfil declara suporte ao Coral (Frigate)" ], [ "USB, série, FUSE", "Um único dispositivo, uma árvore validada ou uma funcionalidade LXC", "O contrato pede-o." ] ] } } ] }, { "id": "nvidia", "title": "NVIDIA", "blocks": [ { "calloutWarning": { "title": "Requisito do nó: NVIDIA Container Toolkit", "body": "Um driver funcional em Proxmox VE não é suficiente para dar um NVIDIA GPU a uma imagem OCI. O OCI Manager Apps usa nvidia-container-cli, do NVIDIA Container Toolkit, para identificar os dispositivos e obter os binários e bibliotecas que correspondem ao driver carregado." } }, { "p": "O ProxMenux NVIDIA instalador instala o NVIDIA Container Toolkit do repositório oficial NVIDIA juntamente com o driver. Ele verifica seus quatro pacotes, valida o nvidia-container-cli e registra o resultado na registro de alterações do Audit & Report." }, { "p": "Estes dois comandos na máquina mostram se o driver e o Toolkit estão disponíveis:" }, { "shell": { "code": "nvidia-smi -L\nnvidia-container-cli --version" } }, { "p": "Em uma máquina onde o driver foi instalado por outros meios, o Toolkit é instalado a partir do repositório estável oficial:" }, { "shell": { "code": "apt-get update\napt-get install -y --no-install-recommends ca-certificates curl gnupg2\n\ncurl -fsSL https://nvidia.github.io/libnvidia-container/gpgkey \\\n | gpg --dearmor -o /usr/share/keyrings/nvidia-container-toolkit-keyring.gpg\n\ncurl -s -L https://nvidia.github.io/libnvidia-container/stable/deb/nvidia-container-toolkit.list \\\n | sed 's#deb https://#deb [signed-by=/usr/share/keyrings/nvidia-container-toolkit-keyring.gpg] https://#g' \\\n > /etc/apt/sources.list.d/nvidia-container-toolkit.list\n\napt-get update\napt-get install -y nvidia-container-toolkit libnvidia-container-tools" } }, { "p": "O inventário que o OCI manager Apps usa é a saída de:" }, { "shell": { "code": "nvidia-container-cli list --device all --libraries --binaries --firmwares --ipcs" } }, { "calloutInfo": { "title": "A configuração do tempo de execução do Docker não está envolvida", "body": "Os contêineres são LXC nativos e não usam daemon Docker, portanto nvidia-ctk runtime configure --runtime=docker não faz parte do processo: o ProxMenux consulta nvidia-container-cli diretamente e configura os dispositivos e montagens LXC. Os comandos e as plataformas suportadas são mantidos no guia de instalação do NVIDIA Container Toolkit." } }, { "cards": { "items": [ { "icon": "cpu", "title": "Inventário do driver", "body": "nvidia-container-cli lista os nós do dispositivo, binários, firmware e bibliotecas do driver instalado." }, { "icon": "refresh", "title": "Nenhuma versão fixa", "body": "O modelo não nomeia arquivos de bibliotecas. O perfil é gerado a partir da máquina atual." }, { "icon": "shield", "title": "Montagens somente de leitura", "body": "As bibliotecas host são montadas somente para leitura em vez de serem copiadas para o recipiente." }, { "icon": "hardDrive", "title": "Alterações do driver", "body": "Após uma mudança de driver, o inventário é gerado novamente antes do início dos LXCs afetados." } ] } }, { "code": { "title": "Resultado NVIDIA (simplificado)", "code": "devN: path=/dev/nvidia0,...\ndevN: path=/dev/nvidiactl,...\ndevN: path=/dev/nvidia-uvm,...\nlxc.mount.entry: HOST_LIBRARY CONTAINER_LIBRARY none ro,bind,create=file 0 0" } }, { "p": "Passar apenas /dev/nvidia0 não é suficiente. Os componentes de espaço de usuário do driver carregado são montados somente de leitura, e nvidia-smi então é executado dentro do LXC para comparar GPU, UUID, PCI bus e versão com o inventário host." } ] }, { "id": "usb", "title": "Coral USB, serial e USB", "blocks": [ { "calloutWarning": { "title": "Numeração USB pode mudar", "body": "Um caminho como o /dev/bus/usb/003/004 pode mudar quando o dispositivo é reconectado ou a máquina reinicia. O perfil registra fornecedor, produto e série quando estão disponíveis, mas um novo endereço de barramento não é remapeado automaticamente." } }, { "p": "Um periférico é dado pelo seu nó específico: /dev/ttyUSB0, /dev/ttyACM0, /dev/apex_0 ou /dev/bus/usb/BBB/DDD. Não é aceite passar todo o /dev. O Coral é oferecido apenas para aplicações cujo perfil o declara." } ] }, { "id": "trees", "title": "Árvores de dispositivos e recursos LXC", "blocks": [ { "table": { "headers": [ "Pedido", "Configuração resultante", "Escopo" ], "rows": [ [ "/dev/dvb, /dev/snd ou /dev/bus/usb", "Cada nó de caracteres da árvore recebe sua própria entrada devN com o modo host e GID", "Apenas a árvore solicitada, e não o resto do /dev" ], [ "/dev/fuse", "O nó e, quando o perfil precisa dele, o recurso fuse=1", "O FUSE sozinho não publica montagens para outros LXCs" ], [ "/dev/net/tun", "Uma entrada devN no mesmo caminho dentro do LXC", "A configuração VPN ou rede permanece na aplicação" ], [ "/dev/kvm", "Uma entrada devN validada", "Oferecido apenas quando o contrato o solicitar" ] ] } } ] }, { "id": "security", "title": "Confirmações por nível de risco", "blocks": [ { "p": "Dispositivos específicos, privilégio opcional, privilégio exigido, relaxamento AppArmor ou seccomp e acesso ao espaço de nomes PID do hospedeiro são tratados como casos separados, não sob uma etiqueta genérica privilegiada. Cada opção com risco é explicada e confirmada durante a instalação." } ] } ] }