ddrescue
(GNU) ddrescue is a data recovery tool. It copies data from one file or block device (hard disc, cdrom, etc) to another, trying to rescue the good parts first in case of read errors.
Table of Content
Installation
Debian
$ apt install gddrescue
Sample with USB stick
dmesg shows now errros during mount, but when you try to access it, it looks like this:
total 48
drwxr-xr-x 7 root root 16384 Jan 1 1970 .
drwxr-xr-x 1 root root 254 Jul 15 09:09 ..
-rwxr-xr-x 1 root root 0 Jul 5 2037 '-'$'\036''┌4ΘDex."s╚'
-r-xr-xr-x 1 root root 0 Aug 2 2042 ''$'\v''â.'$'\005''ü'$'\006'
-r-xr-xr-x 1 root root 0 Dec 29 2030 'Ejc#╒'$'\f\016''B.τ}>'
drwxr-xr-x 2 root root 16384 Jul 7 2022 .fseventsd
-r-xr-xr-x 1 root root 0 Jul 11 2012 '∙ke"<#│h.mcT'
-rwxr-xr-x 1 root root 0 Jul 25 2001 '╕lk|`'$'\016''ªq.tGÿ'
-r-xr-xr-x 1 root root 0 Jan 5 2026 'öf%0'$'\177''p>l.╬'$'\006''%'
-r-xr-xr-x 1 root root 0 Aug 9 2009 ''$'\006''q'
-r-xr-xr-x 1 root root 0 Jan 25 1982 '±'$'\036''SY,LòI.½[Θ'
drwxr-xr-x 4 root root 16384 May 5 2022 .Trashes
-r-xr-xr-x 1 root root 0 Aug 6 2052 ''$'\n''»'$'\006''¡'$'\b''¡'$'\v''-.'$'\v''w'$'\001'
-r-xr-xr-x 1 root root 0 Aug 1 1996 ''$'\a''w.'$'\v''1'$'\001'
-rwxr-xr-x 1 root root 0 Jan 25 2042 'πi\~t'$'\a''ûd."@'$'\021'
-rwxr-xr-x 1 root root 0 Oct 11 1993 'φ_µ'$'\020''α|,\.╔4▀'
So something is broken and of course you don't want to mess arround with maybe the only copy you have. dd could be used now, but can run into issues when it gets suck on bad blocks.
Instead of dd we used in this case ddrescue.
Don't forget to unmount it first ;)
The command what we used to get a save copy of the device looked like this:
$ ddrescue -v -d -r 3 /dev/sdb /var/tmp/usbg.img /var/tmp/usbg.log
Lets have a look at the seperate arguements:
-v: Verbose-d: Direct input access-r 3: number of passed retries/dev/sdb: our source/var/tmp/usbg.img: our destination/var/tmp/usbg.log: log wirtten by ddrescue
When you start the command it will take a while to complete and you will get the following output:
(%-)Numbers changes of course during the time
GNU ddrescue 1.30
About to copy 31457 MBytes from '/dev/sdb' to '/var/tmp/usbg.img'
Starting positions: infile = 0 B, outfile = 0 B
Copy block size: 128 sectors Initial skip size: 1920 sectors
Sector size: 512 Bytes
Press Ctrl-C to interrupt
ipos: 31457 MB, non-trimmed: 0 B, current rate: 20709 kB/s
opos: 31457 MB, non-scraped: 0 B, average rate: 20867 kB/s
non-tried: 0 B, bad-sector: 0 B, error rate: 0 B/s
rescued: 31457 MB, bad areas: 0, run time: 25m 7s
pct rescued: 100.00%, read errors: 0, remaining time: 0s
time since last successful read: 0s
Copying non-tried blocks... Pass 1 (forwards)
Finished
When it has finished and you have only one parition, you can go and mount it already. But if you are in the same situation we have been and you have two then you first need to make your OS aware that there are more then one partitions stored in there.
We have used the OS default losetup. The full command looked like that:
$ losetup -Pf /var/tmp/usbg_image.img
It will try to detect all available partitions in there and enables them for your system.
To see what device you have to use you can run losetup with the parameter -l and get then something like that:
$ losetup -l
NAME SIZELIMIT OFFSET AUTOCLEAR RO BACK-FILE DIO LOG-SEC
/dev/loop0 0 0 0 0 /var/tmp/usbg.img 0 512
So we knew now that we have to look for a device like /dev/loop0pX as our borken USB stick had one partions instead of direct usage.
ll /dev/loop0p*
brw-rw---- root disk 0 B 2026-08-06 19:54:48 /dev/loop0p1
Next up was to run fsck against the loop device like so:
$ fsck.vfat -a /dev/loop0p1
And after it finished and was able to restore the FS sucessfully we could use mount -t vfat -o iocharset=utf8 /dev/loop0p1 /mnt -o uid=1000,gid=1000 to get it mounted and were able to restore the files to put them on a save place.
To unmount the loop device we used unmount /mnt as usual and for the loopdevice the command losetup -d /dev/loop0 to detach it.