The other day made an image from a SDcard carrying a Debian operating system for a Raspberry Pi. The card was 32GB in size and so was the image. In order to restore it onto a smaller SD card there is a few things to do to shrink the image size. So here is the cook book:
Load the loop
kernel module (most probably loaded already) and prepare the loop device:
$ sudo modprobe loop
$ sudo losetup -f
$ sudo losetup /dev/loopX ImageFile.img
$ sudo partprobe /dev/loopX
Now use gparted to resize the partition(s) and delete the loop device afterwards:
$ sudo gparted /dev/loop51
$ sudo losetup -d /dev/loop51
Then use fdisk to determine the border of the resized partition (ending block) in the image file:
$ sudo fdisk ImageFile.img
Welcome to fdisk (util-linux 2.39.3).
Changes will remain in memory only, until you decide to write them.
Be careful before using the write command.
Command (m for help): p
Disk ImageFile.img: 2,37 GiB, 2541748224 bytes, 4964352 sectors
Units: sectors of 1 * 512 = 512 bytes
Sector size (logical/physical): 512 bytes / 512 bytes
I/O size (minimum/optimal): 512 bytes / 512 bytes
Disklabel type: dos
Disk identifier: 0x662b4900
Device Boot Start End Sectors Size Id Type
ImageFile.img1 8192 1056767 1048576 512M c W95 FAT32 (LBA)
ImageFile.img2 i 1056768 4964351 3907584 1,9G 83 Linux
Command (m for help): q
And finally truncate the image using the end block number (pay attention to the unit size in fdisk’s output):
$ truncate --size=$[(4964351+1)*512] ImageFile.img
References
[1]: https://www.byteschmelze.de/imgshrink.php
[2]: https://softwarebakery.com/shrinking-images-on-linux