Desempenho estranho do NFS: 1 thread melhor que 8, 8 melhor que 2!

Desempenho estranho do NFS: 1 thread melhor que 8, 8 melhor que 2!

Estou tentando determinar a causa do baixo desempenho do NFS entre duas máquinas virtuais Xen (cliente e servidor) em execução no mesmo host. Especificamente, a velocidade com que posso ler sequencialmente um arquivo de 1 GB no cliente é muito menor do que seria esperado com base na velocidade medida da conexão de rede entre as duas VMs e na velocidade medida de leitura do arquivo diretamente no servidor. As VMs estão executando o Ubuntu 9.04 e o servidor está usando o pacote nfs-kernel-server.

De acordo com vários recursos de ajuste do NFS, alterar o número de threads nfsd (no meu caso, threads do kernel) pode afetar o desempenho. Normalmente, esse conselho é estruturado em termos de aumentar o número do padrão de 8 em servidores muito usados. O que encontro na minha configuração atual:

RPCNFSDCOUNT=8: (padrão): 13,5 a 30 segundos para armazenar um arquivo de 1 GB no cliente, portanto, 35 a 80 MB/s

RPCNFSDCOUNT=16: 18s para cat o arquivo 60MB/s

RPCNFSDCOUNT=1: 8-9 segundospara cat o arquivo (!!?!) 125MB/s

RPCNFSDCOUNT=2: 87s para cat o arquivo 12MB/s

Devo mencionar que o arquivo que estou exportando está em um SSD RevoDrive montado no servidor usando a passagem PCI do Xen; no servidor posso capturar o arquivo em menos de segundos (> 250 MB/s). Estou descartando caches no cliente antes de cada teste.

Eu realmente não quero deixar o servidor configurado com apenas um thread, pois acho que isso não funcionará tão bem quando houver vários clientes, mas posso estar entendendo mal como isso funciona. Repeti os testes algumas vezes (alterando a configuração do servidor entre eles) e os resultados são bastante consistentes. Então minha pergunta é:por que o melhor desempenho é com 1 thread?

Algumas outras coisas que tentei mudar, com pouco ou nenhum efeito:

  • aumentando os valores de /proc/sys/net/ipv4/ipfrag_low_thresh e /proc/sys/net/ipv4/ipfrag_high_thresh para 512K, 1M do padrão 192K,256K

  • aumentando o valor de /proc/sys/net/core/rmem_default e /proc/sys/net/core/rmem_max para 1M do padrão de 128K

  • montagem com opções de cliente rsize=32768, wsize=32768

Pela saída de sar -d, entendo que os tamanhos reais de leitura que vão para o dispositivo subjacente são bastante pequenos (<100 bytes), mas isso não causa problemas ao ler o arquivo localmente no cliente.

O RevoDrive na verdade expõe dois dispositivos "SATA" /dev/sda e /dev/sdb, então o dmraid pega um fakeRAID-0 distribuído entre eles que eu montei em /mnt/ssd e depois montei em /export/ssd. Fiz testes locais em meu arquivo usando os dois locais e observei o bom desempenho mencionado acima. Se as respostas/comentários solicitarem mais detalhes, irei adicioná-los.

Responder1

Quando uma solicitação do cliente chega, ela é transferida para um dos threads e o restante dos threads é solicitado a realizar operações de leitura antecipada. A maneira mais rápida de ler um arquivo é fazer com que um thread faça isso sequencialmente... Portanto, para um arquivo, isso é um exagero e os threads estão, em essência, fazendo mais trabalho para si próprios. Mas o que é verdade para 1 cliente que lê 1 arquivo não será necessariamente verdade quando você implanta no mundo real, portanto, siga a fórmula para basear o número de threads e o número de leituras antecipadas nas especificações de largura de banda/CPU.

informação relacionada