Na verdade, o espaço é recuperado pelo sistema de arquivos, mas o tamanho do arquivo é reduzido temporariamente para 0 até a próxima gravação pelo processo que ainda mantém o arquivo aberto. Nesse ponto, o tamanho é aumentado para o tamanho anterior, mais os dados recém-gravados, mas agora você tem um arquivo esparso , em que o início do arquivo está cheio de zeros nocionais, que não ocupam espaço o disco.
Você pode ver esse efeito com um teste simples. Crie um arquivo grande que seja atualizado lentamente a cada 10 segundos:
$ { dd count=1k if=/dev/zero; while sleep 10;do echo hi; done; } >/tmp/big &
[2] 1050
$ pid=$!
Verifique seu tamanho e o espaço em disco usado:
$ ls -ls /tmp/big
516 -rw-r--r-- 1 meuh users 524516 Aug 15 15:58 /tmp/big
$ du -a /tmp/big
516 /tmp/big
$ df /tmp
Filesystem 1K-blocks Used Available Use% Mounted on
tmpfs 1966228 2924 1963304 1% /tmp
O arquivo é 524516 bytes, 516 blocos e o sistema de arquivos usou 2924 blocos.
Agora use seu comando >
para truncar o arquivo e verifique imediatamente o tamanho:
$ > /proc/$pid/fd/1; ls -ls /tmp/big
0 -rw-r--r-- 1 meuh users 0 Aug 15 15:59 /tmp/big
É zero. Após 10 segundos, verifique novamente:
$ ls -ls /tmp/big
4 -rw-r--r-- 1 meuh users 524534 Aug 15 15:59 /tmp/big
$ df /tmp
Filesystem 1K-blocks Used Available Use% Mounted on
tmpfs 1966228 2416 1963812 1% /tmp
Como você pode ver o espaço foi recuperado pelo disco (de 2924 a 2416 usado), mas o tamanho do arquivo é como era antes, mais um pouco, mas o número de blocos que ocupa (4, o primeiro número do ls -ls
) é pequeno, daí a dispersão. lsof -p $pid
também mostra o deslocamento, não o tamanho.