Em um de nossos mestres no MySQL, o OOM Killer foi chamado e matou o servidor MySQL, o que levou a uma grande interrupção. A seguir está o log do kernel:
[2006013.230723] mysqld invoked oom-killer: gfp_mask=0x201da, order=0, oom_adj=0
[2006013.230733] Pid: 1319, comm: mysqld Tainted: P 2.6.32-5-amd64 #1
[2006013.230735] Call Trace:
[2006013.230744] [<ffffffff810b6708>] ? oom_kill_process+0x7f/0x23f
[2006013.230750] [<ffffffff8106bde2>] ? timekeeping_get_ns+0xe/0x2e
[2006013.230754] [<ffffffff810b6c2c>] ? __out_of_memory+0x12a/0x141
[2006013.230757] [<ffffffff810b6d83>] ? out_of_memory+0x140/0x172
[2006013.230762] [<ffffffff810baae8>] ? __alloc_pages_nodemask+0x4ec/0x5fc
[2006013.230768] [<ffffffff812fca02>] ? io_schedule+0x93/0xb7
[2006013.230773] [<ffffffff810bc051>] ? __do_page_cache_readahead+0x9b/0x1b4
[2006013.230778] [<ffffffff810652f8>] ? wake_bit_function+0x0/0x23
[2006013.230782] [<ffffffff810bc186>] ? ra_submit+0x1c/0x20
[2006013.230785] [<ffffffff810b4e53>] ? filemap_fault+0x17d/0x2f6
[2006013.230790] [<ffffffff810cae1e>] ? __do_fault+0x54/0x3c3
[2006013.230794] [<ffffffff812fce29>] ? __wait_on_bit_lock+0x76/0x84
[2006013.230798] [<ffffffff810cd172>] ? handle_mm_fault+0x3b8/0x80f
[2006013.230803] [<ffffffff8103a9a0>] ? pick_next_task+0x21/0x3c
[2006013.230808] [<ffffffff810168ba>] ? sched_clock+0x5/0x8
[2006013.230813] [<ffffffff81300186>] ? do_page_fault+0x2e0/0x2fc
[2006013.230817] [<ffffffff812fe025>] ? page_fault+0x25/0x30
Esta máquina possui 64 GB de RAM.
A seguir estão as variáveis de configuração do mysql:
innodb_buffer_pool_size = 48G
innodb_additional_mem_pool_size = 512M
innodb_log_buffer_size = 64M
Exceto alguns plug-ins e scripts de coleção de métricas do nagios, nada mais roda nesta máquina. Alguém pode me ajudar a descobrir por que o OOM killer foi invocado e como posso impedir que ele seja invocado no futuro. Existe alguma maneira de dizer ao OOM killer para não matar o servidor mysql. Eu sei que podemos definir um oom_adj
valor muito menor para um processo para impedir que ele seja morto pelo assassino do OOM. Mas existe outra maneira de evitar isso.
linux
mysql
out-of-memory
pradeepchhetri
fonte
fonte
48G
+512M
+64M
porque também há algumas sobrecargas e outras estruturas a serem consideradas; havia uma fórmula para isso em algum lugar, mas não consigo encontrá-la agora. Não tenho certeza se isso faria com que ele explodisse o64G
. Apenas para ter certeza,free
confirma que64G
estão disponíveis em primeiro lugar?Respostas:
Linux faz overcommit de memória. Isso significa que ele permite que o processo solicite mais memória do que realmente está disponível no sistema. Quando um programa tenta malloc (), o kernel diz "OK, você conseguiu a memória", mas não a reserva. A memória será reservada apenas quando o processo escrever algo neste espaço.
Para ver a diferença, você tem 2 indicadores: Memória virtual e Memória residente. Virtual é a memória solicitada pelo processo, Residente é a memória realmente usada pelo processo.
Com este sistema, você pode entrar em "overbooking", o kernel concede mais memória do que o disponível. Então, quando seu sistema passa a 0 byte de memória livre e troca, ele deve sacrificar (matar) um processo para obter memória livre.
É quando o OOM Killer entra em ação. O OOM seleciona um processo baseado em seu consumo de memória, e muitos outros elementos (ganhos pais 1/2 da pontuação dos seus filhos, se é um processo raiz de propriedade, o resultado é dividido por 4, etc .. Dê uma olhada em Linux- MM.org/OOM_Killer
Você pode influenciar a pontuação do OOM, ajustando o
/proc/MySQL_PID/oom_adj
arquivo. Ao defini-lo como-17
, seu processo nunca será eliminado. Mas antes de fazer isso , você deve ajustar seu arquivo de configuração do MySQL para limitar o uso da memória do MySQL. Caso contrário, o OOM Killer matará outro processo do sistema (como SSH, crontab, etc ...) e o servidor estará em um estado muito instável, talvez levando a corrupção de dados, pior do que qualquer coisa.Além disso, você pode considerar o uso de mais trocas.
[EDITAR]
Você também pode alterar seu comportamento de supercomprometimento por meio desses 2 sysctls:
Conforme declarado na Documentação do Kernel
[/EDITAR]
fonte
oom_score_adj
para corrigir isso, mas eles realmente não entendem o mecanismo de pontuação.