Ive done some extensive research on this, as it seems, surprisingly, there is very few info available online on how Recycle Bin actually implemented.
Everything is not that hard to grasp. When you delete file in the Bin, it is not actually moved to it.
First, lets take a look at the subfolders of $Recycle.Bin
:
C:\$Recycle.Bin\S-1-5-18
is folder for built-in SYSTEM account
C:\$Recycle.Bin\S-1-5-21-XXXXXXXXXX-XXXXXXXXXX-XXXXXXXXXX-1XXX\
, starting from 1000 are non-built in user folders. You should first check which one of them is the one you need by typing whoami /all
in command prompt to get your SID, or wmic useraccount get name,sid
to get all local accounts SIDs, then choose the folder matching with SID.
If you give security rights to your account to all this folders, Explorer might show your deleted files in every folder, however its just Explorer bug. If you navigate to, say, C:\$Recycle.Bin\S-1-5-18
folder and type dir /a
, you will see that its actually empty, and only folder that match with your SID contains your deleted files.
Note that even if you are the only user on the PC, you might still have folder C:\$Recycle.Bin\S-1-5-21-XXXXXXXXXX-XXXXXXXXXX-XXXXXXXXXX-1000\
that most likely will be empty. Then your actual folder will be ...-1001\
. User "1000" seems to be dangling folder for user that was created automatically by Windows on installation or some updates, then deleted. But Recycle.Bin
folder wasn't destroyed and just stayed there. I assume that its safe to delete this dangling folder. I'm not so sure about C:\$Recycle.Bin\S-1-5-18
, but I'm fairly sure its safe too, as there is no need for OS SYSTEM account to use the Bin, anyway.
So, here is deletion algorithm:
- System creates hardlink of the deleted file in
C:\$Recycle.Bin\S-1-5-21-XXXXXXXXXX-XXXXXXXXXX-XXXXXXXXXX-1XXX\
folder with the name $RXXXXXX.<file_ext>
, where XXXXXX
is 6 symbols HASH calculated based on the file contents, as I assume.
- Metadata file is created in the same folder with the name
$IXXXXXX.<file_ext>
. I will show you the content of this file later.
- Original file is deleted, but because of extra hardlink in
$Recycle.Bin
, actual file's data stays in the same location on the drive as if file where never touched. It is not moved anywhere. This is why each logical volume must have it's own $Recycle.Bin
folder, as hardlinks only work within the same volume.
That's about it. Restoration algorithm:
- Metadata file is read and hardlink of
$RXXXXXX.<file_ext>
is created based on $IXXXXXX.<file_ext>
's info in original file location, with original file name.
- Both metadata and backup file are deleted from
$Recycle.Bin
Pretty simple, ain't it?
Now, the most interesting part is that metadata file:
0000 02 00 00 00 00 00 00 00 <-- File header (QW)
0008 00 7C 0A 00 00 00 00 00 <-- File size (QW)
0010 90 83 72 44 28 9C D8 01 <-- File deletion date (QW)
0018 18 00 00 00|43 00 3A 00 <-- File path string length (DW)
0020 5C 00 24 00 52 00 65 00
0028 63 00 79 00 63 00 6C 00
0030 65 00 2E 00 42 00 69 00
0038 6E 00 5C 00 66 00 73 00
0040 73 00 2E 00 65 00 78 00
0048 65 00 00 00| <-- |Null-terminated path string| (wchar_t)
All values are in Little Endian format.
Header is fixed and its identical for all the files. Be warned that some $I
files might have some junk bytes FF FE
appear before the Header. I have no idea what are this for, so you should check for full header before reading further.
Deletion date is in FILETIME format and can be converted to usual SYSTEMTIME via FileTimeToSystemTime. It represents 100-nanosecond intervals since January 1, 1601 (UTC).
So it's not super complicated file format, but quite interesting design.
I'm planing to use this info myself by creating custom "garbage collector" for Windows, that I will add to task scheduler to launch periodically and scan\delete files that where deleted more than 24 hours ago, etc. I know that Windows 10 has built-in option for this, but it's not flexible and not reliable (it sometimes leaves metadata files, while only deleteing $R
files). Also, I think, previous Windows versions doesn't have this feature at all.
I encourage you to experiment with this too! For example, your program might save metadata info of all files it removes into some database, so you would have full history of all files you ever deleted!