Problemas ao zerar um volume LVM

3

Eu tenho um sistema com dois volumes LVM em um dispositivo eMMC, e estou tentando "limpar" um dos volumes, preenchendo-o com zeros. Esta é a primeira vez que trabalho com o LVM, então mostrarei o que tentei e não tive sorte.

Primeiro, usei pvdisplay -m para ver como meus volumes estão configurados:

# pvdisplay -m
  --- Physical volume ---
  PV Name               /dev/mmcblk0p2
  VG Name               vg0
  PV Size               3.42 GiB / not usable 3.00 MiB
  Allocatable           yes
  PE Size               4.00 MiB
  Total PE              876
  Free PE               776
  Allocated PE          100
  PV UUID               i2Abz2-4o2h-9hq4-Gk3h-b5SD-0r9M-7oDfh3

  --- Physical Segments ---
  Physical extent 0 to 49:
    Logical volume      /dev/vg0/volume_a
    Logical extents     0 to 49
  Physical extent 50 to 99:
    Logical volume      /dev/vg0/volume_b
    Logical extents     0 to 49
  Physical extent 100 to 875:
    FREE 

Isso parece simples

  • Existe um VG, vg0
  • vg0 consiste em um PV, /dev/mmcblk0p2
  • O PV é 3.42GiB, dividido em 876 PE de 4MiB
  • PEs [0, 49] armazenam o primeiro LV, volume_a
  • PEs [50, 99] estão armazenando o segundo LV, volume_b

Com isso em mente, fui em frente e tentei zerar volume_b com dd :

# dd if=/dev/zero of=/dev/vg0/volume_b bs=1M count=200
201+0 records in
200+0 records out
209715200 bytes (210 MB, 200 MiB) copied, 17.2374 s, 12.2 MB/s

Com base na saída de pvdisplay -m , assumi que os PEs [50, 99] (200M-400M) de /dev/mmcblk0p2 devem ser preenchidos com zeros. Mas aqui está o que eu vi:

# hexdump /dev/mmcblk0p2 -s 200m
c800000 0000 0000 0000 0000 0000 0000 0000 0000
*
c900400 c800 0000 2000 0003 2800 0000 f0ad 0002
c900410 c7f5 0000 0001 0000 0000 0000 0000 0000

Existem alguns zeros, mas apenas para 1 MiB. Eu tentei preenchê-lo com números aleatórios e verifiquei novamente.

# dd if=/dev/urandom of=/dev/vg0/volume_b bs=1M count=200
200+0 records in
200+0 records out
209715200 bytes (210 MB, 200 MiB) copied, 99.9135 s, 2.1 MB/s
# hexdump /dev/mmcblk0p2 -s 200m
c800000 0000 0000 0000 0000 0000 0000 0000 0000
*
c900400 c800 0000 2000 0003 2800 0000 f0ad 0002
c900410 c7f5 0000 0001 0000 0000 0000 0000 0000

Isso é o mesmo de antes, então parece que minhas chamadas dd não estão fazendo o que acho que estão fazendo. Minha suposição é que o LV /dev/vg0/volume_b é um tipo de dispositivo de bloco "virtual", e quando eu uso dd para gravar nele, o LVM mapeia isso para gravações de bloco reais nos PEs correspondentes. Infelizmente isso não se alinha com o que estou vendo.

[edit1] Eu usei hexdump para verificar o conteúdo de /dev/vg0/volume_b e, sem surpresa, ele está cheio de lixo aleatório. Acabou de aparecer em hexdump todo o /dev/mmcblk0p2 e use grep para descobrir onde os dados estão armazenados. Isso está ocorrendo atualmente e eu atualizarei isso se funcionar.

[edit2] A pesquisa não apareceu nada

    
por Matt K 30.11.2016 / 18:07

1 resposta

2

Após mais testes, parece que há um problema com o LVM e seu relacionamento com o kernel do Linux. Eu estou supondo que isso envolve o cache de disco, mas eu não tenho 100% de certeza. Aqui está o que eu encontrei:

Primeiro eu escrevi alguns dados inúteis para o meu volume LVM:

# dd if=/dev/urandom of=/dev/vg0/volume_b bs=1M count=1
1+0 records in
1+0 records out
1048576 bytes (1.0 MB, 1.0 MiB) copied, 0.600447 s, 1.7 MB/s

Depois, eu leio de volta o volume do LVM. Aqui está um trecho do lixo que foi escrito:

# hexdump /dev/vg0/volume_b -n 0x20
0000000 2358 898b a13b 8d94 39a1 bff6 8b38 79ec
0000010 9155 1202 ce46 938f 49dc 7687 f804 bf13
0000020

Mas, verificando o dispositivo de bloco em si, nada se alinhava.

# hexdump /dev/mmcblk0p2 -s 200M
c800000 0000 0000 0000 0000 0000 0000 0000 0000
*
c900000 2dee 8ea4 2116 1981 252f d113 afc1 3182
c900010 e6fc 7d1b d173 3cab 4399 8715 bcdf 2272

Houve 1 MiB de zeros seguido por algum lixo que não se alinha com o que acabou de ser escrito no volume do LVM. Mas só por diversão, eu tentei reiniciar o sistema e checar novamente.

# hexdump /dev/mmcblk0p2 -s 200M
c800000 0000 0000 0000 0000 0000 0000 0000 0000
*
c900000 2358 898b a13b 8d94 39a1 bff6 8b38 79ec
c900010 9155 1202 ce46 938f 49dc 7687 f804 bf13

Existem os dados! Ainda há uma seção de 1MiB de zeros (presumivelmente um cabeçalho?), Mas os dados que foram gravados em /dev/vg0/volume_b estão lá em /dev/mmcblk0p2 .

Eu não posso explicar isso. Meu palpite é que pode haver um problema com o link entre o LVM e o driver do kernel, ou, mais especificamente, como o kernel lida com o cache de disco. Se eu gravar em um disco físico por meio de um LV para uma área que está atualmente em cache, é possível que o cache não seja atualizado ou marcado como sujo?

Este é um sistema embarcado, então eu tentei reiniciar meu sistema removendo e reaplicando energia. O comportamento é exatamente o mesmo. Até a perda de energia, hexdump no dispositivo físico mostra os dados obsoletos e depois de reiniciar as atualizações para os dados recém-gravados. Isso sugere que as gravações são liberadas para o disco à medida que são concluídas e não fazem parte do processo de desligamento do Linux.

Vou deixar isso em aberto por um tempo, pois ainda não sei qual é a causa disso, mas pelo menos eu sei que o problema não é realmente um problema.

[edit] Definitivamente, parece que o cache é o culpado. A execução de echo 3 > /proc/sys/vm/drop_caches após a gravação faz com que o readback seja atualizado imediatamente. Welp

    
por 30.11.2016 / 21:10

Tags