Btrfs no SSD, “sem espaço no dispositivo”; catch-22 com `fstrim` e `btrfs balance`; como recuperar?

Btrfs no SSD, “sem espaço no dispositivo”; catch-22 com `fstrim` e `btrfs balance`; como recuperar?

O sistema de arquivos raiz do meu Kubuntu (montado em /) é o Btrfs. Eu não uso -o discardcomo opção de montagem. Isso significaEu preciso correr fstrimsob demanda.

No passado, encontrei este problema:btrfs, não resta espaço em disco. Percebi fstrim -v /que quase nenhum espaço estava sendo cortado. Minha solução foi rodar btrfs balance start /antes do fstrim. Esta é a essênciaminha resposta aí.

Hoje é diferente. Talvez eu esteja atrasado com a manutenção. Isto é o que acontece:

# fstrim -v /
/: 24 KiB (24576 bytes) trimmed
# btrfs balance start /
ERROR: error during balancing '/': No space left on device

Excluí alguns subvolumes (instantâneos) btrfs subvolume delete …e isso não ajudou. Não consigo me lembrar dos detalhes muito bem, mas acho que anteriormente eu poderia correr btrfs balance …porque fstrimcortei preliminarmente pelo menos alguns MiB, não tão pouco quanto 24 KiB como hoje. Agora parece uma situação complicada em que fstrimou btrfs balancesó funcionaria se o outro fizesse o seu trabalho primeiro.

Para que conste, estas são algumas estatísticas que mostram que tenho de fato muito espaço:

# df -h /
Filesystem      Size  Used Avail Use% Mounted on
/dev/sda1       112G   43G   68G  39% /

# btrfs fi df /
Data, single: total=108.73GiB, used=41.00GiB
System, single: total=64.00MiB, used=16.00KiB
Metadata, single: total=3.00GiB, used=1.02GiB
GlobalReserve, single: total=352.00MiB, used=0.00B

Observe que ainda não tenho "nenhum espaço no dispositivo" durante a operação normal. Acho que o Btrfs continua ajustando novas gravações em pedaços já obtidos. Porém, no passado, apertei "sem espaço sobrando…" durante apt-get upgrade, depois me recuperei com btrfs balancee fstrim. Não sei quando (se) isso me ocorrerá novamente. Gostaria de fazer minha manutenção antes de "não sobrar espaço..." ao fazer algo importante.

Como se recuperar dessa situação fstrime btrfs balancenão bloquear um ao outro?Posso corrigir isso no meu sistema em execução?

Na verdade eu já consertei isso, minha resposta está abaixo. A questão é para referência futura. Sinta-se à vontade para adicionar outra solução.


Informações adicionais:

$ uname -a
Linux foobar 4.4.0-78-generic #99-Ubuntu SMP […] x86_64 x86_64 x86_64 GNU/Linux

$ cat /etc/issue
Ubuntu 16.04.3 LTS \n \l

# dpkg -l | grep btrfs
ii  btrfs-tools  4.4-1ubuntu1  amd64  Checksumming Copy on Write Filesystem utilities

Responder1

Sim, você pode recuperar dentro do seu sistema em execução. Minha abordagem original está abaixo; no entanto, graças ao comentário de Zan Lynx, encontrei uma maneira mais fácil.

Minha abordagem aprimorada

Este é o comentário mencionado:

Ou se você estiver pensando no futuro, você pode dizer ao btrfs para usar menos que o máximo do dispositivo combtrfs filesystem resize

(Comparando com minha abordagem original, o objetivo é ter deliberadamente algum espaço livre neste dispositivo específico e expandir o sistema de arquivos lá, em vez de adicionar um dispositivo separado, o que pode não ser tão fácil.)

Boas notícias: meus testes indicam que não preciso pensar no futuro! Mesmo que btrfs balance start /gere "sem espaço sobrando…", ainda sou capaz de reduzir o sistema de arquivos, se houver espaço para ele (ou seja, todos os arquivos e metadados cabem no novo tamanho). Isto leva à seguinte solução:

# btrfs filesystem resize -100M /  # shrink a little...
Resize '/' of '-100M'
# btrfs filesystem resize +100M /  # ... and expand back
Resize '/' of '+100M'
# btrfs balance start /            # should work now
Done, had to relocate 88 out of 88 chunks
# fstrim -v /
/: 67,8 GiB (72753831936 bytes) trimmed

Minha abordagem original

Isto é o que você precisa fazer (descrição detalhada abaixo):

  1. Adicione um dispositivo extra ao sistema de arquivos Btrfs.
  2. btrfs balance start …
  3. fstrim …
  4. Exclua o dispositivo extra do sistema de arquivos Btrfs.
  5. btrfs balance start …
  6. fstrim …

O truque é adicionar um dispositivo extra ao sistema de arquivos Btrfs, para que btrfs balance …haja algum espaço adicional. O dispositivo pode ser como /dev/sdbou /dev/sdb3. Neste exemplo, estou usando um arquivo normal de 1 GiB no meu HDD (muito importante:Verifico novamente se o arquivo não pertence ao sistema de arquivos Btrfs que desejo expandir! isso pode ser fatal). Eu acho que um arquivo na RAM (por exemplo, em /dev/shm/) deve funcionar bem.

# tmpf=/mnt/hdd/tempfile   # if this file exists, it will be overwritten!
# truncate -s 1G "$tmpf"
# extra=$(losetup -f --show "$tmpf")

Agora $extraé tipo /dev/loop0ou algo assim.

# btrfs device add "$extra" /

Neste momento não devo reiniciar meu sistema operacional. Se eu fizesse isso, faltaria uma parte de seu sistema de arquivos raiz porque não /dev/loop*estaria associado a /mnt/hdd/tempfile. Isso não será um problema se você usar um dispositivo normal (ou uma partição) como dispositivo extra, pois btrfs device scandurante a inicialização ele será detectado.

# btrfs balance start /

No meu caso, tempfileé um arquivo esparso. Em outro console eu executo watch ls -hls /mnt/hdd/tempfilee percebo quando ele atinge seu tamanho (quase) máximo. Dessa forma eu sei quando alguns pedaços do Btrfs são movidos do SSD. Na dúvida, vamos btrfs ballance …terminar; mas invoco btrfs balance cancel /para economizar algum tempo. Agora vamos voltar ao console principal.

Nota: a primeira linha abaixo é do btrfs balance start /comando acima que foi interrompido.

balance canceled by user
# fstrim -v /
/: 26,7 GiB (28696862720 bytes) trimmed

fstrimaparado muito mais do que antes. Não preciso mais do meu dispositivo extra.

# btrfs device delete "$extra" /   # may take a while
# btrfs balance start /            # should work now
Done, had to relocate 88 out of 88 chunks
# fstrim -v /
/: 67,8 GiB (72753831936 bytes) trimmed

E é isso. Agora é hora de limpar:

# losetup -d "$extra"
# rm "$tmpf"

informação relacionada