No Linux, suponha que eu tenha um arquivo executável. Vejamos dois casos:
(A) Uma grande parte do que o executável faz é E/S de disco;
(B) o executável não faz nenhuma E/S de disco.
Para cada um dos casos A e B , devo esperar uma diferença significativa no tempo de execução do executável entre esses dois cenários?
(1) O executável e todos os arquivos envolvidos estão em uma pasta tmpfs (uma pasta RAM);
(2) O executável e todos os arquivos envolvidos estão em pastas de disco "normais".
Também estou interessado em saber se devo esperar uma diferença significativa entre esses três cenários relacionados ao Docker:
(3) O executável é executado de dentro de um contêiner do Docker, e o executável e todos os arquivos envolvidos estão em uma pasta tmpfs criada de dentro o contêiner em uma unidade de disco que foi montada usando docker run -v ...
(4) O executável é executado de dentro de um contêiner do Docker, e o executável e todos os arquivos envolvidos estão em uma pasta tmpfs criada de dentro do contêiner, em uma unidade "interna" (que não não persiste depois que o contêiner é interrompido).
(5) O executável é executado a partir de um contêiner do Docker, e o executável e todos os arquivos envolvidos estão em pastas de disco "regulares".
Minha expectativa é que, em geral, a execução de uma pasta tmpfs seja mais rápida, principalmente quando há muita E/S de disco envolvida. Mas não vejo isso na prática, então gostaria de ver se minhas expectativas estão corretas.
A execução em tmpfs será mais rápida apenas se você tiver muita E/S de disco que não seja atendida pelo cache da página.
Se o I/O for lido e os arquivos já estiverem no cache, o tmpfs não fará diferença.
Se a E/S for gravação assíncrona sem liberação e a carga de trabalho for intermitente em vez de contínua e houver cache suficiente para absorver uma rajada de gravações e as gravações puderem ser liberadas em segundo plano entre as rajadas, o tmpfs não fará diferença.
Se não houver E/S de disco a ser executada, o tmpfs não fará diferença.
Se você tiver muita E/S de disco e seu processo estiver bloqueado ioesperando que o armazenamento seja atualizado, a execução em tmpfs fará uma enorme diferença. Quanto mais lentos seus discos, mais diferença isso fará, até o ponto em que você fica com o gargalo da CPU.
Deixando de lado o Tmpfs (que já foi abordado), você não notará nenhuma diferença entre executar executáveis no host e de dentro de um contêiner do Docker. Mesmo com armazenamento de volume. O Docker é executado usando um sistema de arquivos de sobreposição e provavelmente há um desempenho muito pequeno para a sobreposição, mas o host vê o executável em execução como um processo como se tivesse sido iniciado no host.
Realisticamente, deve haver diferença quase zero ou zero. Pode haver razões válidas para fazer tal coisa, mas ouso dizer que para 99,9% de todos os casos é uma anti-otimização.
A E/S normal irá para o cache do buffer e as páginas sujas serão gravadas de forma assíncrona por um thread do kernel. Largura de banda = velocidade da RAM, atraso = atraso da RAM (mais, talvez alguns µs para uma falha de página aqui e ali).
Quando o sistema ficar sem RAM física, você vai bloquear (obviamente), não tem outro jeito. Quando não houver mais páginas nas quais você possa escrever, você terá que esperar até que algumas sejam liberadas. Não há outro caminho.
Ficar sem RAM, no entanto, por definição, não é provável (ou possível) acontecer em seu caso particular. Caso contrário, se houver uma possibilidade real de ficar sem RAM, a ideia de criar um tmpfs seria bastante estúpida em primeiro lugar.
I/O para tmpfs irá para... o cache do buffer. Sim, agora ele é executado com um nome diferente, mas na realidade é exatamente o mesmo, devido ao sistema VM unificado. Largura de banda e atraso são exatamente os mesmos (mais ou menos 1% de diferença devido a sutilezas do sistema de arquivos que podem ser ligeiramente diferentes). Nenhum write-back está acontecendo, sim. Mas quem se importa, vendo como isso aconteceria de forma assíncrona, de qualquer maneira. Pelo contrário, agora você não tem o luxo de alguém liberar páginas sujas em segundo plano, então a probabilidade de atingir o teto, se isso for possível, é realmente maior.
Quando o sistema fica sem RAM física, você ainda está apenas gravando em páginas mapeadas na memória; portanto, em teoria, você deve ser capaz de fazer isso mais rapidamente. No entanto, na prática, ainda há apenas tanta e tanta RAM física, e você acabou de ficar sem ela! Claro, ainda pode haver espaço em seu tmpfs, mas, por algum motivo, você também precisa escrever uma página de memória, caso contrário, e não sobrou nenhuma.
Portanto, o kernel deve fazer algo para manter o sistema funcionando. Ele precisa reorganizar seus recursos de alguma forma para mitigar o problema (possivelmente trocar o processo do docker e todo o contêiner?!). O kernel vai tentar muito, mas não é como se ele pudesse fazer mágica, ele tem que fazer alguma coisa, e suas escolhas são limitadas. Ainda mais porque você deliberadamente retirou um grande número de páginas que, de outra forma, poderiam ser usadas livremente conforme necessário para qualquer finalidade (incluindo a solicitação que deve ser atendida agora).