Limpeza de memória cache no Linux

Dias atrás me deparei com algumas máquinas que estavam apresentando lentidão em qualquer comando executado. Um simples ls demorava uma eternidade para ser executado, o que não poderia acontecer, já que as máquinas possuem muito mais memória do que eu ;-).

Comecei verificando os processos que estavam sendo executados, quais usuários estavam conectados, fiquei observando o resultado do comando top e aparentemente tudo estava normal, vi que o consumo de CPU estava baixo, porém o consumo de memória estava lá nas alturas.

Já ia reiniciar a máquina quando olhei de novo para a saída do comando top e a linha que demonstra a estatística de uso do swap me chamou atenção (a saída abaixo é da minha máquina, a figura é somente para ilustrar):

Cabeçalho do comando top

O linux guarda um espaço na memória cache para programas e comandos que foram usados recentemente, permitindo que sejam executados de maneira mais rápida no futuro. E no caso das máquinas, esse espaço já estava chegando ao limite da memória física, causando lentidão na execução dos processos.

Ok, descobri o problema da lentidão, e um simples reboot resolveria o caso, mas em um ambiente de produção, isso não é interessante, então, pesquisando mais um pouco, localizei um procedimento que permite limpar a memória cache sem reiniciar a máquina.

Os procedimentos abaixo, devem ser executados como root:

# sync
# echo 3 > /proc/sys/vm/drop_caches

O comando sync faz com que todo o cache do sistema de arquivos que está temporariamente armazenado na memória, seja descarregado no disco e liberado, evitando a perda de dados.

Ao inserir o número “1” no arquivo /proc/sys/vm/drop_caches, é liberado somente pagecache, inserir o número “2” libera pagecache e inodes. A opção utilizada, número “3” faz como que o kernel libere pagecache, dentries e inodes.

Para checar novamente o uso da memória:

# free -m

ou

# top

Uma sugestão, para máquinas que ficam muito tempo ligadas, é criar um script com os comandos acima e inserir no cron, para ser executado regularmente.

Para saber mais:

http://www.kernel.org/doc/Documentation/sysctl/vm.txt
http://linux-mm.org/Drop_Caches
http://www.ibm.com/developerworks/linux/library/l-virtual-filesystem-switch/

Ferramentas que auxiliam na monitoração de processos

Em dois posts, comentei sobre os comandos ps, kill, fg, bg, nice, renice…

Nesse post, quero falar rapidamente sobre outros comandos que podem ser uma mão na roda para o administrador de sistemas quando precisa controlar os processos no sistema!

✔ pstree

Exibe os processos em forma de árvore. Assim, fica mais facil para visualizar o ‘pai’ de cada processo.

Sem opções, o comando pstree exibe a árvore somente com os nomes dos processos. Para ver a arvore de processos com pid, utilize a opção -p.

Experimente os comandos abaixo:

# pstree

# pstree -p

✔ top

O comando top exibe os processos em tempo real. O top é uma ferramenta de mil e uma utilidades; além de exibir os processos, top também permite mudar a prioridade e enviar sinais para os processos.

# top

Para sair do top, pressione <Q>.

Ahn, e no top, para enviar sinais para o processo ou então mudar a prioridade, é necessário saber o PID do processo!

Vamos ver um exemplo onde vamos mudar a prioridade do processo cron e depois enviar sinal de término para esse processo. Por partes, como faria Jack:

1) Localizar o PID do processo:

# pgrep cron

2400

2) Executar o comando top:

# top

Dentro do top, podemos teclar ‘r’ sem aspas para mudar a prioridade do cron; vai aparecer a seguinte frase:

PID to renice:

Dai, informamos o PID, e ele solicita o valor da prioridade; podemos colocar 5.

Como o top atualiza a lista de processos em tempo real, e, por padrão ele mostra somente quem está consumindo mais CPU e memória, pode ser que o cron não apareça na lista… então, para conferir se a prioridade que setamos está correta, basta sair do top e utilizar o comando ps:

# ps lax | grep cron
1     0  2400     1  24   5   3380   752 –      SNs  ?          0:00 /usr/sbin/cron

3) Agora, vamos enviar sinal de término; caso tenha saído do top, execute-o novamente; se não, basta teclar ‘k’ sem aspas; será solicitado o PID do processo, e, em seguida o sinal que você deseja enviar; no nosso caso, vamos enviar o sinal 15, que é o padrão.

O top tem mais opções, para conhece-las:

# man top

Aproveitando, existe uma interface mais bonita para o comando top… é o comando htop; ele é colorido e mais simples para visualizar uso de CPU, memória e etc. Para utilizar, basta teclar:

# htop

✔ pidof

O comando pidof, assim como o comando pgrep, localiza o ID de um processo. A diferença entre esses dois comandos, é que o pidof somente localiza o PID do processo através do nome; já o comando pgrep, além de localizar o PID pelo nome, também localiza por outros atributos, como usuário, por exemplo.

Exemplo do comando pidof:

# pidof cron
2775

Exemplo do comando pgrep:

# pgrep -u root ssh
1954
2516
2661

No exemplo acima, localizamos todos os processos ssh cujo dono é o root.

Para saber mais sobre o pidof e o pgrep:

# man pidof

# man pgrep

pkill

O comando pkill, é uma ferramenta da família pgrep. Ele tem a mesma função que o comando kill, porém pode enviar sinais para um processo utilizando o nome do processo e outros atributos.

Assim como no comando kill, o pkill envia o sinal 15 por padrão.

Exemplo:

# pkill -HUP syslogd

Acima, estamos enviando o sinal HUP (reload) para o processo syslogd.

Para conhecer mais sobre o comando pkill:

# man pkill

✔ killall

Finaliza processos por nome. Por exemplo, finalizar todos processos bash:

# kilall -9 bash

O comando killall também pode ser interativo; isto é, antes de matar o processo, ele pergunta! Para isso, basta utilizar o comando com a opçao -i.

Exemplo:

# killall -9 bash -i
Kill bash(3178) ? (y/N)

Para conhecer outras opções do comando killall, consulte o man:

# man killall

✔ nohup

Executa um comando ignorando os sinais de interrupção. Se executado em segundo plano, o processo continuará rodando mesmo depois que o usuário efetuar o logout.

Exemplo:

# nohup ls -lR / > diretorios.txt &

Para saber mais sobre o comando nohup:

# man nohup

✔ free
O comando free exibe a quantidade de memória livre e usada no sistema. Para usar:

# free
total       used       free     shared    buffers     cached
Mem:        257080      66364     190716          0      13268      37492
-/+ buffers/cache:      15604     241476
Swap:       257000          0     257000

Quando usado sem parâmetros, o valor exibido é em kbytes; para exibir em megas, basta utilizar a opção -m:

# free -m
total       used       free     shared    buffers     cached
Mem:           251         64        186          0         12         36
-/+ buffers/cache:         15        235
Swap:          250          0        250

Para saber mais sobre o comando free:

# man free

✔ vmstat

O comando vmstat exibe a estatística do uso da memória virtual (swap):

# vmstat -S M

Acima, teremos um relatório do uso da memória virtual em megabytes (opção. Sem essa opção, o relatório será exibido em kbytes (padrão).

Uma outra opção legal do vmstat, é o relatório do uso do disco. Para isso, basta executar o comando com a opção -d:

# vmstat -d

O vmstat tem mais opções, para conhece-las:

# man vmstat

Bem, é isso aí pessoal! Até o próximo post! 😀