Você já viu um servidor Ubuntu travar não por falta de hardware, mas porque um único processo faminto consumiu toda a CPU e a memória disponível? Essa é a dor silenciosa de muitos administradores: a falta de controle granular sobre o que roda em sua máquina. Em ambientes de alta concorrência ou containers efêmeros, deixar o kernel decidir sozinho como distribuir recursos é jogar com a casa virada. O cgroups (control groups) surge exatamente para resolver isso, permitindo que você isole e limite a "fome" de cada aplicação.

Muitos profissionais de TI confundem cgroups com contêineres. É um erro comum. Os contêineres (como Docker ou LXC) são a interface de usuário que utiliza cgroups por baixo dos panos. Entender os cgroups é entender o motor, não apenas o carro. Se você administra servidores Ubuntu para hospedar múltiplos serviços críticos, dominar essa ferramenta significa evitar picos de latência e garantir que seu banco de dados nunca seja prejudicado por uma fila de impressão ou um script de backup mal otimizado.

O que são cgroups e por que eles importam

Os cgroups são um recurso do kernel Linux projetado para restringir, contar e isolar o uso de recursos do sistema, como CPU, memória, disco E/S e rede, por processos. Antes deles, não havia uma maneira nativa e eficiente de dizer: "este processo pode usar no máximo 50% da CPU" ou "esta aplicação não pode consumir mais de 1GB de RAM".

A importância disso cresce exponencialmente com a virtualização leve. No Ubuntu Server moderno, mesmo que você não esteja usando Docker explicitamente, muitos serviços do sistema operam como unidades isoladas. Ao configurar cgroups manualmente ou via ferramentas de orquestração, você ganha visibilidade e controle.

Imagine um cenário onde seu servidor hospeda um site WordPress e, simultaneamente, executa backups noturnos. Sem limites, o processo de backup pode saturar o disco e a CPU, deixando o site inacessível para seus clientes. Com cgroups, você cria um grupo para o serviço web (prioritário) e outro para o backup (limitado). O resultado é estabilidade previsível.

O isolamento é a chave aqui. Não se trata apenas de limitar recursos, mas de garantir que uma aplicação não consiga afetar negativamente a experiência de outra na mesma máquina física. Isso é fundamental para provedores de hospedagem e agências que gerenciam infraestrutura compartilhada.

Instalação e configuração inicial no Ubuntu Server

O Ubuntu Server já vem com suporte aos cgroups habilitado por padrão na maioria das versões recentes, especialmente aquelas que utilizam systemd como gerenciador de init. O systemd cria automaticamente hierarquias de cgroups para cada serviço.

No entanto, para configurações avançadas ou aprendizado profundo, é útil entender a estrutura de arquivos. No Linux moderno (kernel 5.8+), o padrão é usar cgroups v2. A maioria das distribuições Linux atuais migrou para essa versão unificada.

Para verificar qual versão está em uso, execute:

  • stat -f -c %T /sys/fs/cgroup/

Se o retorno for cgroup2fs, você está na versão 2. Se for cgroupfs, está na versão 1 (mais antiga e fragmentada).

A configuração manual direta nos arquivos de sistema pode ser complexa e propensa a erros, pois envolve criar diretórios na hierarquia do sistema de arquivos virtual /sys/fs/cgroup. A maneira mais robusta e recomendada para administradores é através do systemd, que abstrai a complexidade dos cgroups.

Vamos considerar um exemplo prático: limitar uma aplicação fictícia chamada app-filha para usar no máximo 25% da CPU e 512MB de RAM. Em vez de manipular arquivos diretamente, criamos ou editamos a unidade systemd correspondente.

Para criar uma configuração personalizada que sobreponha a padrão:

  1. Crie um arquivo de extensão em /etc/systemd/system/app-fila.service.d/
  2. Nomeie o arquivo, por exemplo, limits.conf.
  3. Dentro dele, defina as diretrizes de recursos.

Isso garante que suas alterações persistam e sejam gerenciadas corretamente pelo sistema de inicialização do Ubuntu.

Controle de CPU e memória na prática

Agora, vamos aplicar o controle de recursos. No mundo dos cgroups, existem diferentes formas de limitar a CPU e a memória, cada uma com suas nuances.

Limitação de CPU

O sistema de arquivos virtual expõe parâmetros como cpu.cfs_quota_us e cpu.cfs_period_us no cgroups v1. No cgroups v2, a lógica é simplificada com cpu.max.

A diretiva CPUQuota no systemd define a quantidade de CPU disponível para uma unidade. O valor é expresso em porcentagem do total de CPUs disponíveis. Por exemplo, em um servidor com 4 núcleos, 100% equivale a 1 núcleo completo.

Se você quer limitar um serviço a usar apenas 50% de um núcleo (ou 12,5% de um servidor de 4 núcleos), configuraria:

  • CPUQuota=12.5%

Isso impede que o processo entre em "runaway state", consumindo ciclos de processamento infinitos e travando a resposta do sistema.

Limitação de Memória

A memória é mais crítica. O Linux tem um comportamento agressivo de cache, mas limites rígidos podem causar o OOM Killer (Out of Memory Killer), que mata processos para liberar espaço.

Para definir um limite de memória no systemd, usa-se a diretiva MemoryMax.

  • MemoryMax=512M

É importante diferenciar MemoryMax de MemoryHigh. O MemoryMax é um limite rígido: se a aplicação tentar alocar mais, o kernel bloqueará a alocação ou matará o processo. O MemoryHigh é uma "zona de advertência": quando atingida, o kernel tenta liberar memória agressivamente, mas não mata o processo imediatamente, evitando falhas catastróficas.

Para servidores de produção, recomenda-se usar MemoryHigh para evitar quedas bruscas, monitorando os logs em busca de sinais de pressão de memória.

Cgroups v1 vs Cgroups v2: Qual escolher?

A transição do cgroups v1 para o v2 não foi apenas uma atualização de versão, mas uma reformulação arquitetural. O v1 era fragmentado em subsistemas separados (cpu, memory, blkio, net_cls), o que causava conflitos e complexidade na hierarquia.

O cgroups v2 unificou tudo em uma única hierarquia. Isso facilita a gestão de recursos combinados e resolve muitos bugs históricos de isolamento.

A tabela abaixo resume as diferenças principais para ajudar na decisão técnica:

Característica Cgroups v1 Cgroups v2
Hierarquia Múltiplas hierarquias (uma por subsistema) Única hierarquia unificada
Complexidade Alta, propensa a conflitos de namespace Baixa, mais intuitiva
Controle de Memória Separado do controle de CPU Recursos combinados e isolados
Suporte Ubuntu Legado, ainda suportado mas em desuso Padrão em versões 22.04+
Isolemento Básico Mais robusto e seguro

Se você está iniciando um novo projeto ou migrando infraestrutura no Ubuntu Server, foque exclusivamente em cgroups v2. O suporte a v1 está sendo gradualmente removido do kernel upstream. Ignorar essa mudança significará refatorar suas configurações de limitação de recursos dentro de poucos anos.

Além disso, o v2 oferece melhorias no controle de E/S de disco e rede, permitindo políticas mais finas para aplicações que dependem fortemente de leitura/gravação, como bancos de dados SQL.

Perguntas frequentes

Posso usar cgroups sem systemd?

Sim, é possível criar e gerenciar cgroups manualmente através dos arquivos em /sys/fs/cgroup. No entanto, isso é desencorajado em ambientes de produção modernos devido à complexidade de gerenciamento de ciclo de vida e persistência. O systemd é o gerenciador padrão na maioria das distribuições Linux, incluindo Ubuntu, e oferece uma interface declarativa muito mais segura.

O que acontece se um processo ultrapassar o limite de memória?

Depende da configuração. Se você usar MemoryMax, o kernel negará novas alocações de memória ao processo (retornando erro ENOMEM). Se a aplicação tentar escrever dados que excedam o limite, ela pode falhar ou ser terminada pelo OOM Killer se não houver memória suficiente no sistema. Já com MemoryHigh, o processo continua rodando, mas sofre pressão para liberar cache e buffers.

Cgroups afetam a performance do servidor?

O overhead dos cgroups é mínimo. O kernel Linux foi projetado para lidar com essas estruturas de forma eficiente. A principal "perda" de performance ocorre se você configurar limites muito apertados, forçando o processo a esperar por recursos que ele não pode usar. O ideal é monitorar o uso real e ajustar os limites para um valor seguro, mas permissivo.

Como monitorei o uso de recursos de um cgroup?

Você pode ler os arquivos de estatísticas na hierarquia do cgroups. Para systemd, a ferramenta systemd-cgtop é excelente para visualizar em tempo real o consumo de CPU e memória por unidade. Para análises mais detalhadas, ferramentas como cgroup-tools ou integração com Prometheus/Grafana são recomendadas.

Posso limitar a rede com cgroups?

O cgroups v2 introduziu suporte básico para controle de rede (limites de taxa e prioridade), mas ele é menos maduro e flexível do que as ferramentas tradicionais de QoS do Linux, como tc (traffic control). Para limitações rigorosas de largura de banda, recomenda-se combinar cgroups com scripts de tc.

Conclusão

Configurar cgroups no Ubuntu Server não é um exercício acadêmico; é uma necessidade operacional para qualquer administrador que valorize a estabilidade e a previsibilidade. Ao isolar processos e limitar o consumo de CPU e memória, você protege seu servidor contra picos de demanda e falhas em cascata.

A migração para cgroups v2 e o uso do systemd como interface de gestão são os caminhos mais seguros e modernos. Não espere o problema acontecer para implementar controles. A infraestrutura resiliente é construída com limites claros e monitoramento constante.

Se você precisa de uma infraestrutura onde esses conceitos sejam aplicados automaticamente, garantindo alta disponibilidade e isolamento total para suas aplicações, conte com a expertise da Toda Solução. Oferecemos soluções de hospedagem e cloud pensadas para quem exige performance sem surpresas.