Limitação de recursos com o cgroups – parte 1

cgroups-1_abertura.png

Os control groups — ou cgroups para encurtar — foram criados em 2006 por Paul Menage e Rohit Seth, integram o Linux desde a versão 2.6.4 (janeiro de 2008) e de forma bem simplificada consistem em um mecanismo que se encarrega de limitar, contabilizar e isolar recursos do sistema. Junto com o Linux Namespaces compõe a infraestrutura que implementa os contêineres neste sistema operacional.

Mas os cgroups não são de uso exclusivo dos contêineres e é possível utilizá-los para limitar e isolar os recursos do sistema também para os processos na “máquina física” e nesta primeira parte: processador.

ATENÇÃO — Após a publicação corrigi a concordância no texto já que cgroups está no plural e não no singular.

Grupo de controle

A criação do grupo de controle é feita com o comando cgcreate¹, cada grupo necessita estar associado a um controlador especifico (CPU, memória, E/S etc). Algo bastante útil é a possibilidade de se definir a propriedade do grupo para que usuários comuns possam administrar ou executar os processos.

$ sudo cgcreate -a giovanni:giovanni -t giovanni:giovanni -g cpu:/limitado
$ sudo cgcreate -a giovanni:giovanni -t giovanni:giovanni -g cpuset:/limitado

Neste caso criei dois grupos de controle — ambos com o original nome de “limitado” (apesar do mesmo nome são independentes) — dentro dos controladores “cpu” e “cpuset” que, respectivamente, servirão para a restrição da capacidade de processamento e do número de processadores disponíveis.

Indiquei meu próprio usuário como administrador e executor deles (podem ser diferentes) mas se não o fizesse seriam aplicadas as definições do grupo de controle pai e que neste caso seria o usuário “root”.

(¹) Caso não esteja instalado, nas distribuições baseadas em Debian ele está no pacote cgroup-tools e nas baseadas em RedHat no pacote cgroup.

Limitando o tempo de processador

Primeiro uma informação importante: o Linux define como 1024 o valor total de tempo que um processo poderá usar da CPU. Assim, para que um processo só utilize 50% do tempo que deveria este valor é de 512 (1024÷2), para 25% é 256 (1024÷4) etc.

Um programa de teste

Antes de seguir adiante um programa bem simples (e bem feio também):

Este sujeito tem as nobre missão de encontrar números primos e consumir tempo de processamento ao fazê-lo.

Compile-o com:

$ cc -o primes primes.c

E o deixe reservado por enquanto. 🙂

Configurando o grupo de controle

Como meu usuário é administrador do grupo de controle, basta usar diretamente o comando cgset (não há mais a’ necessidade de sudo):

$ cgset -r cpu.shares=128 limitado

Este valor, o 128, corresponde a 12,5% (1024÷8) do tempo CPU.

Calculando números primos

Como o computador que estou usando para os testes tem “dois” processadores² precisarei duplicar as ações para poder demonstrar o funcionamento — explico o motivo mais abaixo.

cgroups-1_cpu_4_livre

Aqui há quatro instâncias do primes sendo executadas e com cada uma delas compartilhando (quase que) igualmente o mesmo tempo de processador. Neste caso, cerca de 50% do total do processador — ou  25% do total do sistema já que há “dois” processadores aqui (não são números exatos pois há outras coisas em execução aqui).

Calculando primos e usando o cgroups

Também quatro instâncias do primes mas iniciando normalmente duas e executando as demais dentro do grupo de controle “limitado” através do comando cgexec.

$ nohup cgexec -g cpu:limitado ./primes 1000000 >/dev/null

Como o sistema operacional foi instruído a tratar os processos de um jeito diferente o resultado é o seguinte:

cgroups-1_cpu_4_limitado.png

Os processos iniciados dentro do grupo de controle estão limitados a cerca 12,5% do tempo de processador e as demais instâncias, aquelas fora do grupo, acabam se beneficiando e ganhando um pouco mais para elas (assim como os demais processos em execução).’

Vale lembrar que se houvesse apenas um processo em execução, limitado ou não, ele consumiria 100% do tempo de processamento visto que não haveria ninguém para concorrer com ele com os recursos.

(²) Na verdade um só processador com dois núcleos.

Limite de processadores

Agora um outro tipo de limitação, o de processadores (físico, núcleo ou thread). Como no exemplos anterior a configuração do grupo:

$ cgset -r cpuset.cpus=0 limitado
$ cgset -r cpuset.mems=0 limitado

O que é isto? O primeiro é simples de ser explicado e diz quais, no caso qual, processador será executado; no caso apenas a CPU0 (é possível usar faixas com “0-3”, especificar em uma lista “0,2,4,6” ou então combinar as duas coisas). O segundo tem a mesma sintaxe e diz respeito aos nós de memória instalados no sistema e é relacionado à arquitetura NUMA onde processadores tem bancos de memória próprios.

Claro, dentro do controlador “cpuset” estes são parâmetros obrigatórios e devem estar devidamente definidos.

Daí é executar com:

$ nohup cgexec -g cpuset:limitado ./primes 1000000 >/dev/null 2>&1 &
$ nohup cgexec -g cpu,cpuset:limitado ./primes 1000000 >/dev/null 2>&1 &

Obtendo o seguinte resultado (lembrando que os 11.1% dizem respeito a outros processos em execução).

cgroups-1_cpu0_limitado

Neste caso o grupo de controle dentro do controlador “cpuset” define que os processos utilizarão apenas a CPU0 (ou o primeiro núcleo se preferir). Aliás o exemplo também demonstra como é que se adiciona mais de um grupo de controle.

cgroups-1_cpu0_limitado_2

E, para fechar, também é possível alterar estes parâmetros com o processo estando em execução.

Fim desta parte

Por enquanto é só. Tanto o controlador “cpu” quanto o “cpuset” possuem diversos outros parâmetros, bem mais que os três que foram citados, e que permitem ajustar diversos aspectos da execução de processos dentro do Linux. E na próxima parte: memória.

Até!

Anúncios

Deixe um comentário

Preencha os seus dados abaixo ou clique em um ícone para log in:

Logotipo do WordPress.com

Você está comentando utilizando sua conta WordPress.com. Sair / Alterar )

Imagem do Twitter

Você está comentando utilizando sua conta Twitter. Sair / Alterar )

Foto do Facebook

Você está comentando utilizando sua conta Facebook. Sair / Alterar )

Foto do Google+

Você está comentando utilizando sua conta Google+. Sair / Alterar )

Conectando a %s