Como definir permanentemente os ajustes do OOM killer para daemons?

12

Executando alguns servidores Linux com um ou apenas alguns daemons vitais de serviço do sistema, eu gostaria de ajustar o OOM killer para esses processos daemonizados, caso algo estranho aconteça. Por exemplo, hoje algum servidor Ubuntu executando o MySQL tem um daemon MySQL morto por causa de toneladas de apt-checkerprocessos foram consumindo toda a memória eo kernel pensei que era uma boa idéia para matar o MySQL.

Eu sei que posso ajustar a pontuação usando o /proc/$(pidof mysqld)/oom_score_adjarquivo para dar ao kernel alguma pista de que eu não prefiro que o MySQL seja morto, mas isso não sobrevive ao reinício do serviço. Devo editar scripts init / upstart do pacote para incluir esses ajustes? Não acho que seja uma solução muito elegante, pois faria ajustes nos arquivos pertencentes a um pacote. Seria possível conectar-se a scripts upstart / init em geral e ajustá-lo condicionalmente? Ou você sugeriria executar um script indefinido como while true{ adjust_oom(); sleep 60;}?

gertvdijk
fonte
Interessante que existe a possibilidade de ajustar isso. Eu acho que não há nada melhor que o seu loop infinito para realizar o trabalho. O OOM-killer está enterrado no fundo do kernel e possui um algoritmo muito obscuro.
Nils

Respostas:

8

Vários sistemas modernos de supervisão de daemon têm meios para fazer isso. (De fato, como existe uma ferramenta de carregamento em cadeia para o trabalho, sem dúvida todos eles têm um meio para fazer isso.)

  • Iniciante: use oom scoreno arquivo de trabalho.
    pontuação oom -500
  • systemd: use a OOMScoreAdjust=configuração na unidade de serviço. Você pode usar os arquivos de correção da unidade de serviço para afetar as unidades de serviço pré-empacotadas.
    [Serviço] 
    OOMScoreAdjust = -500
  • família daemontools : use aoom-kill-protectferramenta do conjunto de ferramentas nosh norunprograma para o serviço.

    Se você estiver convertendo uma unidade de serviço do sistema, a convert-systemd-unitsferramenta de fato converterá a OOMScoreAdjust=configuração em uma chamada de oom-kill-protect.

    #! / bin / nosh 

    oom-kill-protect - -500
    argumentos do
    programa
    Como bônus, você pode torná-lo parametrizável:
    oom-kill-protect - fromenv
    e defina o valor do parâmetro no ambiente do serviço (presume-se que seja lido a partir de um ambiente associado ao serviço, aqui manipulado com o rcctlcalço do conjunto de ferramentas nosh ):
    rcctl conjunto servicename oomprotect -500

Leitura adicional

  • Jonathan de Boyne Pollard (2016). oom-kill-protect. conjunto de ferramentas nosh. Programas.
  • James Hunt e Clint Byrum (2014). " oom score" Livro de receitas inicial .
  • Lennart Poettering (07-10-2013). " OOMScoreAdjust" systemd.exec. páginas de manual do systemd. freedesktop.org.
  • Jonathan de Boyne Pollard. rcctl. conjunto de ferramentas nosh. Programas.
  • /unix//a/409454/5132
JdeBP
fonte
9

Isso é possível no Ubuntu usando o Upstart e a oom scoreopção de configuração.

oom score

O Linux possui um recurso matador "Out of Memory". [...]

Normalmente, o assassino da OOM considera todos os processos igualmente; essa estrofe aconselha o kernel a tratar esse trabalho de maneira diferente.

O valor de "ajuste" fornecido para essa estrofe pode ser um valor inteiro de -999 (muito improvável de ser morto pelo killer do OOM) até 1000 (muito provavelmente morto pelo killer do OOM). [...]

Exemplo:

# this application is a "resource hog"
oom score 1000

expect daemon
respawn
exec /usr/bin/leaky-app
gertvdijk
fonte
Para os leitores que usam o Ubuntu 16.04+, isso se tornou obsoleto agora que o Upstart foi substituído pelo systemd.
gertvdijk
4

Você pode invadir o MySQL (por exemplo, o OpenSSH sshd faz isso), mas isso é um pouco pesado e muito sujo (problemas com atualizações etc.)

Você pode fazer isso em um wrapper ou no script init - a pontuação deve ser herdada (e em um wrapper que você provavelmente desejaria exec mysqld "$@" qualquer maneira).

Uso cgroups- isso lhe dará um pouco mais de flexibilidade e pode ser permanente, no sentido de que as configurações apropriadas possam ser aplicadas automaticamente na reinicialização do serviço. Veja, por exemplo, controle de prioridade de aplicativos usando cgroups para obter mais informações. Para alcançar o automatismo que você está procurando, provavelmente você desejará dar uma olhada no libcgroup , que contém um daemon que pode lidar com a mudança de cgroups de um processo em execução de acordo com um conjunto de regras, ou apenas usar o cgexecwrapper ( do mesmo pacote).

peterph
fonte