Estamos enfrentando um comportamento estranho, em que vemos alta utilização da CPU, mas média de carga bastante baixa.
O comportamento é melhor ilustrado pelos gráficos a seguir do nosso sistema de monitoramento.
Por volta das 11:57, a utilização da CPU varia de 25% a 75%. A média de carga não é alterada significativamente.
Executamos servidores com 12 núcleos com 2 hiper threads cada. O sistema operacional vê isso como 24 CPUs.
Os dados de utilização da CPU são coletados executando /usr/bin/mpstat 60 1
cada minuto. Os dados para a all
linha e a %usr
coluna são mostrados no gráfico acima. Estou certo de que isso mostra a média por dados da CPU, não a utilização "empilhada". Enquanto observamos 75% de utilização no gráfico, vemos um processo mostrando o uso de cerca de 2000% da CPU "empilhada" top
.
O valor médio da carga é obtido a /proc/loadavg
cada minuto.
uname -a
dá:
Linux ab04 2.6.32-279.el6.x86_64 #1 SMP Wed Jun 13 18:24:36 EDT 2012 x86_64 x86_64 x86_64 GNU/Linux
Dist Linux é Red Hat Enterprise Linux Server release 6.3 (Santiago)
Executamos um par de aplicativos da Web Java com uma carga bastante pesada nas máquinas, pensamos em 100 solicitações / s por máquina.
Se eu interpretar os dados de utilização da CPU corretamente, quando tivermos 75% de utilização da CPU, isso significa que nossas CPUs estão executando um processo 75% do tempo, em média. No entanto, se nossas CPUs estiverem ocupadas 75% das vezes, não devemos ver uma média de carga mais alta? Como as CPUs podem estar 75% ocupadas enquanto temos apenas 2 a 4 trabalhos na fila de execução?
Estamos interpretando nossos dados corretamente? O que pode causar esse comportamento?
fonte
Respostas:
No Linux, pelo menos, a média de carga e a utilização da CPU são na verdade duas coisas diferentes. A média de carga é uma medida de quantas tarefas estão aguardando em uma fila de execução do kernel (não apenas o tempo da CPU, mas também a atividade do disco) durante um período de tempo. A utilização da CPU é uma medida de quão ocupada a CPU está no momento. A maior carga que um único encadeamento de CPU atrelado a 100% por um minuto pode "contribuir" para a média de carga de 1 minuto é 1. Uma CPU de 4 núcleos com hyperthreading (8 núcleos virtuais) todos a 100% por 1 minuto contribuiria 8 para a média de carga de 1 minuto.
Muitas vezes, esses dois números têm padrões que se correlacionam, mas você não pode pensar neles como o mesmo. Você pode ter uma carga alta com quase 0% de utilização da CPU (como quando você tem muitos dados de E / S bloqueados no estado de espera) e pode ter uma carga de 1 e 100% da CPU, quando você tem um único processo encadeado em execução inclinação total. Também por curtos períodos de tempo, você pode ver a CPU perto de 100%, mas a carga ainda está abaixo de 1 porque as métricas médias ainda não "alcançaram".
Vi um servidor ter uma carga de mais de 15.000 (sim, na verdade isso não é um erro de digitação) e uma porcentagem de CPU de quase 0%. Isso aconteceu porque um compartilhamento do Samba estava com problemas e muitos clientes começaram a ficar presos em um estado de espera de E / S. As chances são de que, se você estiver vendo um número regular de carga alta sem nenhuma atividade de CPU correspondente, esteja tendo algum tipo de problema de armazenamento. Nas máquinas virtuais, isso também pode significar que há outras VMs competindo fortemente por recursos de armazenamento no mesmo host da VM.
Carga alta também não é necessariamente uma coisa ruim, na maioria das vezes significa apenas que o sistema está sendo utilizado em sua capacidade máxima ou talvez esteja além da capacidade de mantê-lo (se o número de carga for maior que o número de núcleos do processador). Em um lugar que eu costumava ser um administrador de sistemas, eles tinham alguém que observava a carga média em seu sistema primário mais próxima do que Nagios. Quando a carga era alta, eles me chamavam 24/7 mais rápido do que você poderia dizer SMTP. Na maioria das vezes, nada estava realmente errado, mas eles associaram o número de carga a algo errado e o observaram como um falcão. Após a verificação, minha resposta foi geralmente que o sistema estava apenas fazendo seu trabalho. É claro que este foi o mesmo local em que a carga aumentou mais de 15000 (embora não seja o mesmo servidor), então às vezes isso significa que algo está errado. Você deve considerar o objetivo do seu sistema. Se for um cavalo de batalha, espere que a carga seja naturalmente alta.
fonte
Carga é um número muito enganador. Tome com um grão de sal.
Se você gerar muitas tarefas em sucessão muito rápida e concluídas muito rapidamente, o número de processos na fila de execução é muito pequeno para registrar a carga para eles (o kernel conta a carga uma vez a cada cinco segundos).
Considere este exemplo: no meu host, que possui 8 núcleos lógicos, esse script python registrará um grande uso da CPU no topo (cerca de 85%), mas quase nenhuma carga.
Outra implementação, esta evita
wait
em grupos de 8 (o que distorceria o teste). Aqui, o pai sempre tenta manter o número de filhos no número de CPUs ativas, de modo que seja muito mais ocupado que o primeiro método e, esperançosamente, mais preciso.A razão para esse comportamento é que o algoritmo gasta mais tempo criando processos filhos do que executando a tarefa real (contando até 10000). As tarefas ainda não criadas não podem contar para o estado 'executável', mas ocuparão% sys no tempo da CPU à medida que são geradas.
Portanto, a resposta poderia realmente estar no seu caso: qualquer que seja o trabalho que está sendo realizado, gera um grande número de tarefas em rápida sucessão (threads ou processos).
fonte
Se a média de carga não aumentar muito, significa que as especificações de seu hardware e a natureza das tarefas a serem processadas resultam em um bom rendimento geral, evitando que elas sejam empilhadas na fila de tarefas por algum tempo.
Se houve um fenômeno de contenção porque, por exemplo, a complexidade média da tarefa é muito alta ou o tempo médio de processamento da tarefa leva muitos ciclos de CPU, então sim, a média da carga aumentaria.
ATUALIZAÇÃO:
Pode não estar claro na minha resposta original, então estou esclarecendo agora:
A fórmula de cálculo exacto médio de carregamento é:
loadvg = tasks running + tasks waiting (for cores) + tasks blocked
.Você pode definitivamente ter uma boa taxa de transferência e chegar perto de uma carga média de 24, mas sem penalizar o tempo de processamento das tarefas. Por outro lado, você também pode ter de 2 a 4 tarefas periódicas não concluindo com rapidez suficiente, e você verá o número de tarefas em espera (por ciclos de CPU) crescendo e, eventualmente, atingirá uma alta média de carga. Outra coisa que pode acontecer é ter tarefas executando excelentes operações de E / S síncrona, bloqueando um núcleo, reduzindo a taxa de transferência e aumentando a fila de tarefas em espera (nesse caso, a
iowait
métrica pode ser alterada)fonte
A média de carga inclui tarefas bloqueadas no IO do disco, para que você possa facilmente ter zero utilização da CPU e uma média de carga de 10 apenas com 10 tarefas tentando ler de um disco muito lento. Portanto, é comum que um servidor ocupado comece a debulhar o disco e todas as buscas causem muitas tarefas bloqueadas, aumentando a média de carga, enquanto o uso da CPU diminui, pois todas as tarefas estão bloqueadas no disco.
fonte
Embora a resposta de Matthew Ife tenha sido muito útil e nos tenha levado na direção certa, não foi exatamente isso que causou o comportamento no nosso caso. No nosso caso, temos um aplicativo Java multiencadeado que usa pool de encadeamentos, por que nenhum trabalho é feito na criação das tarefas reais.
No entanto, o trabalho real dos encadeamentos é de curta duração e inclui esperas de E / S ou de sincronização. Como Matthew menciona em sua resposta, a média de carga é amostrada pelo sistema operacional, portanto, tarefas de curta duração podem ser perdidas.
Eu criei um programa Java que reproduzia o comportamento. A classe Java a seguir gera uma utilização da CPU de 28% (650% empilhada) em um de nossos servidores. Enquanto isso, a média de carga é de cerca de 1,3. A chave aqui é o sleep () dentro do encadeamento, sem ele o cálculo da carga está correto.
Para resumir, a teoria é que os encadeamentos em nossos aplicativos ficam ociosos e, em seguida, executam trabalhos de curta duração, por que as tarefas não são amostradas corretamente pelo cálculo da média de carga.
fonte
Load average é o número médio de processos na fila da CPU. É específico para cada sistema, você não pode dizer que um LA é genericamente alto em todos os sistemas e outro é baixo. Então você tem 12 núcleos e, para LA aumentar significativamente, o número de processos deve ser realmente alto.
Outra pergunta é o que significa o gráfico "Uso da CPU". Se for retirado do SNMP, como deveria ser, e sua implementação SNMP for
net-snmp
, apenas empilha a carga da CPU de cada uma das 12 CPUs. Portanto,net-snmp
a quantidade total de carga da CPU é de 1200%.Se minhas suposições estiverem corretas, o uso da CPU não aumentou significativamente. Assim, LA não aumentou significativamente.
fonte
all
linha. Estou bastante certo de que é uma média em todas as CPUs, não está empilhado. Por exemplo, quando o problema ocorre, o topo mostra 2000% de uso da CPU para um processo. Esse é o uso empilhado.O cenário aqui não é particularmente inesperado, embora seja um pouco incomum. O que Xavier aborda, mas não desenvolve muito, é que, embora o Linux (por padrão) e a maioria dos tipos de Unix implementem multitarefas preventivas, em uma máquina saudável, as tarefas raramente serão antecipadas. Cada tarefa recebe um intervalo de tempo para ocupar a CPU; ela é antecipada apenas se exceder esse tempo e houver outras tarefas aguardando para serem executadas (observe que load informa o número médio de processos na CPU e aguardando para executar) . Na maioria das vezes, um processo renderá em vez de ser interrompido.
(em geral, você só precisa se preocupar com a carga quando se aproxima o número de CPUs - ou seja, quando o agendador começa a antecipar tarefas).
Tudo sobre o padrão de atividade, claramente aumentou a utilização da CPU em algumas tarefas (provavelmente uma pequena minoria), não tendo um efeito adverso no processamento de outras tarefas. Se você pudesse isolar as transações sendo processadas, esperaria que surgisse um novo grupo durante a desaceleração, enquanto o conjunto de tarefas existente não foi afetado.
atualizar
Um cenário comum em que a alta CPU pode ocorrer sem um grande aumento de carga é quando uma tarefa dispara uma (ou uma sequência) de outras tarefas, por exemplo, ao receber uma solicitação de rede, o manipulador direciona a solicitação para um encadeamento separado, o encadeamento separado em seguida, faz algumas chamadas assíncronas para outros processos .... a amostragem da fila de execução faz com que a carga seja menor do que realmente é - mas não aumenta linearmente com o uso da CPU - a cadeia de tarefas acionadas não seria executável sem o evento inicial e, como ocorrem (mais ou menos) seqüencialmente, a fila de execução não é inflada.
fonte
all
linha ainda mostra a média por CPU. Vou esclarecer a questão.