Por que o IO do memmap é ignorado em / proc / [PID] / io

3

Eu tenho um problema / proc / [PID] / io e memmap Eu preciso perfil de aplicativo IO que usa biblioteca python astropar .
Um dos problemas que tenho é que o total de bytes de leitura / gravação de E / S está incorreto em / proc / [PID] / io.

Eu tenho um script copy.sh :

#!/bin/bash
cp huge.fits huge.2.fits
#python copyfits.py
#python copyfitsMemmapOFF.py
sleep 5 
cat /proc/$$/io

Comento a linha cp e a linha que quero executar para cada teste.

copyfits.py contém:

from astropy.io import fits    
hdulist = fits.open('huge.fits', mode='readonly')
hdulist.writeto('huge.2.fits')
hdulist.close()

copyfitsMemmapOFF.py contém:

    from astropy.io import fits    
    hdulist = fits.open('huge.fits', mode='readonly', memmap=False)
    hdulist.writeto('huge.2.fits')
    hdulist.close()

heres os resultados de IO para cada solução:

cp huge.fits huge.2.fits

rchar: 9749929202
wchar: 9749551680

python copyfits.py

**rchar: 8399421**
wchar: 9749551685

python copyfitsMemmapOFF.py

rchar: 9757502959
wchar: 9749551685

Eu entendo que o memmap sendo desativado levará a resultados IO inconsistentes ao usar esta variável para monitorar quanto o aplicativo leu arquivos. Como / Por que o memmap não é contado no IO padrão e como posso saber sobre esses IO?
Porque se é o kernel em vez do arquivo de leitura do aplicativo, o arquivo ainda é acessado.

    
por Kiwy 26.04.2018 / 16:21

1 resposta

5

O /proc ' io apenas rastreia E / S' explícita ', ou seja, E / S executada usando um número pequeno de chamadas do sistema. Para leituras, elas são read , readv , preadv , sendfile e copy_file_range ; você pode ver as estatísticas acumuladas usando add_rchar em fs/read_write.c .

E / S para arquivos mapeados na memória é bem diferente; durante a leitura, ele depende do manuseio de falhas de página, com várias otimizações para aumentar o desempenho (leitura antecipada, etc.). Você pode controlar isso até certo ponto, examinando falhas de página em /proc/${pid}/stat (campos 10 e 12). A parte difícil é descobrir quantos dados são lidos com cada falha de página; meus experimentos sugerem 64 KiB por falha, mas não encontrei dados concretos para comprovar isso (e isso provavelmente depende das circunstâncias).

Eu não conheço nenhum modo pronto para uso de rastrear E / S mapeada do ponto de vista do processo (bytes ie lidos no processo, independentemente de qualquer bloco E / S realmente ocorreu).

A contabilidade de leituras com mapeamento de memória é um problema bastante difícil, principalmente devido à forma como a contabilidade deve refletir a intenção. io conta bytes que um programa pediu explicitamente para ler ou escrever; mas quando um processo mapeia um arquivo para sua memória, as leituras ocorrem com uma granularidade determinada pelo kernel, não pelo processo de leitura. Você pode ler apenas um byte a cada 4KiB, e o kernel lerá todo o arquivo para você - o que a contabilidade deve refletir? Ele não pode refletir facilmente os bytes realmente lidos na memória pelo processo, o que teria um enorme impacto no desempenho (além de ser impossível implementar em todas as arquiteturas).

    
por 26.04.2018 / 19:33

Tags