Reduzindo a imagem qcow2 no Libvirt KVM

Você já reduziu o tamanho da imagem de disco qcow2 usada nas máquinas virtuais KVM-QEMU? Como você sabe, o processo de aumentar o tamanho de uma imagem é bastante simples e rápido, mas e a redução?



Neste artigo, vou falar sobre a situação em que você precisa reduzir a imagem qcow2 da máquina virtual KVM o mais rápido possível.



Formato de dispositivo de bloco - qcow2



Mas, no entanto, este esquema pode ser feito com imagens raw, basta convertê-lo para qcow2. Em geral, a instrução será relevante para tudo o que é convertido para qcow2.



Uma maneira fácil de reduzir o disco no KVM é a seguinte:



  1. Compactando um dispositivo de bloco qcow2 (disco VM)
  2. Fazendo um disco menor
  3. Montagem de imagem gparted, disco antigo e novo
  4. Preparando para inicializar o sistema operacional
  5. Especificações de VM e máquina host:


Host: CentOS 7 + QEMU 2.12 + LIBVIRT 4.5.0 + Kernel UEK5 v. 4.14

VM: CentOS 7 + 80GB HDD + Kernel std v. 3.10

O doador será uma máquina virtual CentOS 7 com uma imagem de disco rígido de 80 GB, ocupada na verdade por 20 GB e fisicamente por 80 GB. Vamos reduzir para 40 GB.



Qual é a diferença entre o tamanho da imagem, tamanho real e físico?

Digamos que a imagem qcow2 foi criada com um tamanho de 80 GB e sabemos sobre isso. Durante a operação, a imagem ficou obstruída com dados, alguns dados foram excluídos. Em termos gerais, devido às peculiaridades do processo de gravação e exclusão de dados, para o SO, os dados excluídos parecem não existir, mas permanecem gravados na imagem até que sejam substituídos por outros dados. Assim, mesmo no sistema operacional, você verá 20 GB de dados realmente ocupados, o host KVM mostrará uma imagem maravilhosa (usamos o utilitário qemu-img para obter informações):



qemu-img info qcow2_image.img
image: qcow2_image.img
file format: qcow2
virtual size: 80G (85899345920 bytes)
disk size: 80G
cluster_size: 65536
Format specific information:
compat: 0.10
refcount bits: 16


Você pode ver que tamanho virtual = tamanho do disco, bem como du -sh da imagem irá mostrar que ocupa 80G reais:



du -sh qcow2_image.img
80G    qcow2_image.img


E como precisamos reduzir o tamanho da imagem para 40 GB, vamos iniciar o processo.



Estágio 1 - Comprimir o dispositivo de bloco (imagem)



Antes de iniciar o procedimento de redução do disco, você precisa se certificar de que o espaço ocupado dentro do sistema operacional é menor do que o volume para o qual o disco será reduzido de uma forma ou de outra.



df -h /
Filesystem      Size  Used Avail Use% Mounted on
/dev/vda2        80G   18G   63G  22% /


Como podemos ver, 18 GB estão ocupados, o que é menos de 40 GB. Desligue a VM com o comando



shutdown -h now


E vá para a máquina host, verifique:



  • quanto a imagem pega fisicamente
  • quanto na verdade


# qemu-img info qcow_shrink
image: qcow_shrink
file format: qcow2
virtual size: 80G (85899345920 bytes)
disk size: 80G
cluster_size: 65536
Format specific information:
    compat: 0.10
    refcount bits: 16
# virt-df -h qcow_shrink
du -sh Filesystem                                Size       Used  Available  Use%
qcow_shrink:/dev/sda1                     488M       101M       351M   21%
qcow_shrink:/dev/sda2                      79G        17G        62G   22%
# du -sh qcow_shrink
80G     qcow_shrink


Para compactar a imagem, precisamos de um utilitário simples chamado virt-sparsify . Certifique-se de que a VM esteja inativa e execute o comando no diretório junto com a imagem do disco (observação importante: antes de iniciar o virt-sparsify , certifique-se de que haja espaço livre suficiente em / tmp e no armazenamento de imagem para realizar a operação)



virt-sparsify qcow_shrink qcow_shrink-new


A conclusão bem-sucedida da operação resultará na seguinte saída:



[   0.0] Create overlay file in /tmp to protect source disk
[   0.1] Examine source disk
[   1.2] Fill free space in /dev/sda1 with zero
[   1.5] Fill free space in /dev/sda2 with zero
 100% ⟦▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒▒⟧ 00:00
[  72.5] Copy to destination and make sparse
[  81.9] Sparsify operation completed with no errors.
virt-sparsify: Before deleting the old disk, carefully check that the
target disk boots and works correctly.


Em seguida, trocamos o disco (movemos qcow_shrink para algum lugar ao lado, por exemplo qcow_shrink-old e qcow_shrink-new em seu lugar - qcow_shrink ).



mv qcow_shrink qcow_shrink-old && mv qcow_shrink-new qcow_shrink


Começamos a VM. Se tudo começou, apagamos a VM e continuamos trabalhando.



Etapa 2 - Criar um disco menor



Um procedimento simples com apenas um comando:



qemu-img create -f qcow2 -o preallocation=metadata qcow_shrinked 40G


qcow_shrinked - novo nome de imagem

40G - novo tamanho



Estágio 3 - conectando gparted



Como às vezes os administradores preferem maneiras mais fáceis de resolver o problema, o pandeiro é colocado de lado (kpartx) e ISO e VNC vêm em seu lugar. Felizmente, não é muito difícil conectá-lo ao KVM.



O que estamos fazendo:



  • Conecte a imagem ISO GParted
  • Conecte qcow2_shrinked à VM
  • Inicie a VM, inicialize do ISO


Como fazer isso, irei omitir deste artigo, pois presume-se que quem está fazendo tudo isso já sabe como acontece, mas o resultado será o seguinte:



imagem



Inicie a VM e veja a tela de boot do GParted:



imagem



Selecione o primeiro item e siga as instruções na tela. Eu geralmente pressiono Enter até o fim.



imagem



Vendo o próprio GParted, vamos começar a agir. Verificamos rapidamente se / dev / vda tem uma tabela de partição - msdos ou gpt . Isso é importante:



imagem



Mude para o segundo disco / dev / vdb e crie a tabela de partição:



imagem



imagem



Ao criar a tabela, selecione o tipo msdos como aprendemos anteriormente.



Em seguida, volte para / dev / vdae sequencialmente, a partir dos primeiros discos, começamos a copiar partições, alternando entre vda e vdb :



imagem



O resultado final será:



imagem



Pressione Aplicar e espere o resultado terminar:



imagem



Como resultado:



imagem



Isso já parece verdade. Mas como fizemos alguma manipulação que levará a uma alteração no UUID dos discos, potencialmente não inicializaremos no sistema operacional. Por quê? O CentOS 7 usa UUIDs de disco no fstab, Grub2 usa UUIDs de disco, então entre no console e faça magia negra.



Gparted funciona inicialmente como um usuário, então nós saltamos para root com o comando sudo su - root :



imagem



Vamos blkid para ter certeza que o UUID das partições mudou



imagem



Pode-se ver que o UUID vda1 = vdb1, mas para vdb2 mudou. Tudo bem - você pode viver com isso.



Monte o vdb completamente, junto com a partição / boot, e monte algumas partições para nossa conveniência.



mkdir vdb2
mount /dev/vdb2 vdb2
mount /dev/vdb1 vdb2/boot
cd vdb2
mount --bind /dev dev
mount --bind /sys sys
mount --bind /proc proc
chroot .


Vamos começar com fstab - uma vez que não é muito conveniente digitar o UUID no VNC, vamos substituí-lo pelo nome de dispositivo familiar.



imagem



Substituímos a linha por UUID = ... por, atenção :



especificamos / dev / vdb2 , se o disco antigo não foi planejado para ser desconectado,

especificamos / dev / vda2 , se o disco antigo foi desconectado.



Visto que desconectamos o disco antigo antes de carregar o SO, então escrevemos / dev / vda2



Próximo vamos mudar o bootloader, colocá-lo em ordem. Suponha que tudo esteja em / boot / grub2, grub.cfg está no mesmo lugar, mas efi não (tabela msdos, que é efi :)):



grub2-install /dev/vdb
cd /boot/grub2
grub2-mkconfig -o grub.cfg


Com isso, você pode ficar feliz por si mesmo e ao desabilitar o gparted, inicialize no sistema operacional.



Etapa 4 - inicializar o sistema operacional



Antes de carregar o sistema operacional, ainda recomendo desconectar o disco antigo do servidor. Portanto, no estágio anterior, vda2 tinha que ser registrado no fstab, mas se você for um usuário de PC atento e não desconectou nada, então não deverá haver problemas. Com um disco antigo, é muito provável que você inicialize a partir dele.



Não houve problemas durante o processo de inicialização, o servidor inicializou conforme o esperado. Vamos verificar isso:



[root@shrink ~]# df -h
Filesystem      Size  Used Avail Use% Mounted on
devtmpfs        484M     0  484M   0% /dev
tmpfs           496M     0  496M   0% /dev/shm
tmpfs           496M  6.7M  489M   2% /run
tmpfs           496M     0  496M   0% /sys/fs/cgroup
/dev/vdb2        40G   18G   23G  44% /
/dev/vdb1       488M  101M  352M  23% /boot
tmpfs           100M     0  100M   0% /run/user/0

[root@shrink ~]# blkid
/dev/vda1: UUID="ea505196-32fb-4df6-8bed-0a0ab2d0b726" TYPE="ext4"
/dev/vda2: UUID="30ec1bc6-658f-4611-8708-5e3b7ebaa467" TYPE="xfs"
/dev/vdb1: UUID="ea505196-32fb-4df6-8bed-0a0ab2d0b726" TYPE="ext4"
/dev/vdb2: UUID="c8548834-272b-4331-a9bf-aa99fb41a434" TYPE="xfs"
/dev/sr0: UUID="2019-03-21-13-42-32-00" LABEL="GParted-live" TYPE="iso9660" PTTYPE="dos"


Vemos que / boot e / são necessários, 40 GB de tamanho, o sistema operacional está em execução. Felicidade, de outra forma não!



Bônus



Algo que você terá que enfrentar em algumas situações.



  1. VM Windows, virt-sparsify . , , ( blkid), Windows , . ( ) fixmbr + rebuildbcd. — man
  2. — xfs Superblock has unknown read-only compatible features (0x4) enabled. read-only, . :


Provavelmente, quando tudo foi feito no gparted ou outro ambiente, a versão do kernel deste ambiente era muito nova, no qual o xfs foi ligeiramente alterado, ou seja, os metadados e sua versão são diferentes. Como resultado, o xfs feito no novo kernel se transforma em uma abóbora no antigo. O que fazemos é inicializar novamente no resgate gparted, aumentar a rede neste ambiente de resgate e instalar o kernel mais recente no sistema operacional. Instalei o 5.x no CentOS 7, talvez o 4.x sirva, ainda não testei, mas no final deu certo. Além disso, sem problemas.



Isso é tudo!



Como você pode ver, não há nada de complicado nisso. Claro, você pode usar LVM, resize2fs e outras coisas, mas ainda assim qcow2 é usado em outro lugar e até mesmo necessário por alguém.



Se você conhece um método ainda mais simples, escreva sobre ele nos comentários.



All Articles