У меня есть изображение DD с SD-карты 4 ГБ, которая имеет два раздела, эти два раздела занимают всего около 800 МБ, и поэтому я хочу уменьшить размер IMG-файла.
Кто-нибудь знает способ удаления "свободного места" из файла img?
Использование resize2fs
намного проще
resize2fs -M xxx.img
Сначала вас попросят e2fsck - так:
e2fsck -f -y xxx.img
(изображение НЕ должно быть смонтировано!)
Примечание: это будет работать, только если изображение состоит из одного раздела, если это целое блочное устройство с несколькими разделами, см. Ответ выше ...
Сначала убедитесь, что свободное место на самом деле пусто и не содержит остатков удаленных файлов. Самый простой способ добиться этого - создать на диске огромный файл, содержащий только нулевые байты, а затем удалить его.
# losetup --find --partscan foo.img
# lsblk
NAME MAJ:MIN RM SIZE RO TYPE MOUNTPOINT
loop0 7:0 0 4096M 0 loop
├─loop0p1 259:0 0 2048M 0 loop
└─loop0p2 259:1 0 2048M 0 loop
# for part in /dev/loop0p*; do
mount $part /mnt
dd if=/dev/zero of=/mnt/filler conv=fsync bs=1M
rm /mnt/filler
umount /mnt
done
dd: error writing ‘/mnt/filler’: No space left on device
dd: error writing ‘/mnt/filler’: No space left on device
# losetup --detach /dev/loop0
Затем сожмите его с помощью инструмента, такого как gzip
или xz
. Даже при самых низких уровнях сжатия длинная серия нулей будет хорошо сжиматься:
# ls -s
4096M foo.img
# gzip foo.img
# ls -s
11M foo.img.gz
Обратите внимание, что вы должны распаковать изображение при записи его обратно на диск. Это распакует его «вживую»:
# cat foo.img.gz | gunzip | dd of=/dev/sda
Обратите внимание, что устройство вывода (sda) должно быть достаточного размера, чтобы соответствовать исходному изображению, в противном случае данные будут потеряны или повреждены.
Альтернативный метод, если вы хотите продолжать использовать образ - например, с виртуальной машиной - это преобразовать необработанный образ в один из форматов изображений, используемых программным обеспечением для виртуализации; например, qcow2 для Qemu, VDI для VirtualBox или VMDK для VMware.
Обратите внимание, что для этого по- прежнему требуется подготовить изображение, очистив свободное место, используя вышеуказанный метод.
# qemu-img convert -f raw -O qcow2 foo.img foo.qcow
# qemu-img convert -f raw -O vmdk foo.img foo.vmdk
Но если он снова будет записан на реальный диск, вам придется преобразовать его обратно в необработанный образ.
Я также попробовал это с qemu-img, и это сработало как шарм:
qemu-img resize test.img 2G
Мы изменяем размеры test.img
чтобы сделать его 2G (2GB).
Работал безупречно для меня.