[DFC] Digital Forensics Challenge 2025 - Write-up & Paper Review
In this post, we will solve a challenge from the 2025 "Digital Forensics Challenge."
First, the "Digital Forensics Challenge" is a digital forensics competition hosted by the Korea Institute of Information Security and Cryptology.
As of 2025, the competition was held from August 1 to September 30 and consisted of the Problem-Solving Division and the Tech Contest Division.
In the Problem-Solving Division, 20 challenges are released simultaneously on the first day of the competition, and participants are required to submit a written report containing their solutions within the given period.
In this report, we will solve Challenge 205 while referencing the related research paper.
205 – Hide and Seek
Overview :
A disk image from a data server was seized. Multiple hidden files and data are suspected to exist within the disk image. Using filesystem metadata (Superblock, Inode, Timestamp, etc.), identify and recover the hidden data.
The challenge provided a single file named "disk.img", and the filesystem used was XFS.
Before starting the analysis, I conducted background research to determine an appropriate approach and discovered the paper titled "Data Hiding in the XFS File System."
The paper explains five possible methods for hiding data within the XFS filesystem.
- 1. Superblock Slack Space
- 2. Inode Slack Space
- 3. Free List Area
- 4. Free Inodes
- 5. Nanosecond Timestamps
Some of these techniques were used in this challenge, and a brief summary is provided below.
1. Superbloack Slack Space
According to the paper, the XFS superblock occupies the first sector of each Allocation Group (AG), but the actual superblock only uses 272 bytes out of the available 512 bytes.
Therefore, the remaining 240 bytes can be used to hide data, although this method is relatively easy to detect.
However, since XFS stores a CRC-32C checksum in the superblock, the checksum must also be modified after embedding hidden data.
The size of the superblock slack space depends on the number of Allocation Groups in the filesystem.
By default, most XFS systems use four AGs, providing approximately 960 bytes of hidden storage space, although this can increase depending on the AG configuration.
2. Inode Slack Space
An XFS inode consists of the inode core, data forks, and attribute forks.
The inode core occupies 176 bytes, and when no attribute fork exists, the available slack space within an inode is as follows.
512-(176+(16 * X))
In this formula, X represents the number of data forks contained in the inode.
For a contiguous file (single extent), each inode provides approximately 320 bytes of slack space.
3. Free List Area
Each Allocation Group (AG) in XFS contains a free list area. This space is reserved for future expansion of the inode B+Tree.
Initially, the inode B+Tree occupies one block within the AG, and four additional blocks are reserved for future expansion.
By inserting data into these reserved blocks, information can be hidden.
With the default XFS block size of 4096 bytes and four AGs in filesystems smaller than 4 TiB, this method provides approximately 65,536 bytes of hidden storage space.
4. Free Inodes
XFS allocates inodes in chunks of 64. Some inodes may already be allocated internally but remain unused.
When an inode is created, only minimal metadata (such as the XFS version, checksum, and UUID) is initialized, while the remaining space remains empty.
Hidden data can be inserted into this unused area, and the inode bitmap can be modified to mark the inode as “in use,” preventing reallocation.
If all inode chunks are already occupied, creating additional regular files can force allocation of a new chunk, thereby creating more free inodes. However, this increases the likelihood that a user may discover the hidden data.
5. Nanosecond timestamps
Like modern filesystems, XFS supports nanosecond-resolution timestamps.
The paper explains that most users do not inspect nanosecond-level timestamp values, making them suitable for data hiding.
An XFS inode stores timestamps in MACB (Modify, Access, Change, Birth) format, where each timestamp consists of a 4-byte Unix time value and a 4-byte nanosecond component.
By overwriting the nanosecond component, hidden data can be embedded. However, because the nanosecond component may increase from 9 digits to 10 digits after modification, the paper recommends using only the lower 3 bytes for data hiding.
6. Challenge Write-up
1. "What is the SHA-256 hash of the first recovered hidden file? (40 points)"
The first hidden data was located in the superblock slack space.
Hidden data existed after the 272-byte boundary, and the header signature was 00 00 00 38 39 61, while the footer signature was 00 3B.
The GIF file signature is normally 47 49 46 38 39 61, with the footer signature 00 3B, indicating that the file was likely a partially corrupted GIF image.
Therefore, after extracting the data and restoring the missing signature bytes 47 49 46, a small image was successfully recovered.
SHA-256 : “764308a95688be904762c4732c39863d3de02db4bb3537b4801c577d7cfdb0ef”
2. "What is the SHA-256 hash of the second recovered hidden file? (40 points)"
The second hidden data was stored in the inode slack space described in the paper.
Upon examining inode 249, the same signature 00 00 00 38 39 61 was identified, and additional hidden data was also found in the slack spaces of inodes 250 and 251.
The end of the hidden data in inode 251 contained the same footer signature 00 3B, and the hidden data from inode 249 through inode 251 was concatenated and extracted as a single file.
After restoring the damaged GIF signature, another small image was successfully recovered.
SHA-256 : “eb7b360ee39a2005c8192118736169ab555317ddff0a76c21ca330749959d762”
3. "What is the SHA-256 hash of the third hidden data? (50 points)"
The challenge description explicitly stated that the hidden data utilized filesystem metadata such as the superblock, inode structures, and timestamps.
Since the first and second hidden data were found in the superblock and inode slack spaces, it was reasonable to assume that the third hidden data involved timestamps.
The paper also introduced a data hiding technique using nanosecond timestamps, so this method was investigated.
First, the disk image was mounted in WSL2.
After mounting, the following command was used to collect MACB (Modify/Access/Change/Birth) timestamps in inode order and save them into a text file.
cut -d'|' -f2 ~/xfswork/files_with_inodes.txt | tr '\n' '\0' | xargs -0 stat -c '%n|%y|%x|%z|%w' > /mnt/e/2025dfc/testd/times_by_inode.txt
After analyzing the generated text file, the file "./ai/1000_F_564265464_mp9OwlBNexenRBJcwg5qhCwOxr4TC3gk.jpg" was found to have a unique Modify timestamp of 2024-02-10 19:09:30.000016160, unlike the other files.
This file corresponded to inode 222, and the nanosecond timestamp area contained the string "DFC 2025", while the inode slack space contained the string "Here it is!".
SHA-256 : “146a481b7b2b5f879612637a0683a3a4d693df3d19763e61aef1866e648ce301”
4. "Describe how to remove all hidden data and restore the original disk image. (Verification MD5 hash of the original disk image: b79ff8b1a233eb2406aa4508d765c961) (70 points)"
The hidden data existed in the superblock and inodes 222, 249, 250, and 251.
XFS uses CRC-32C checksums to ensure filesystem integrity.
Since the challenge required restoring the disk image to its original state, all hidden data needed to be overwritten with 00 values, and the original CRC-32C checksum values for the superblock and inodes had to be restored.
However, inode 222 contained hidden data within the nanosecond timestamp fields, so the original nanosecond timestamps had to be restored before clearing the slack space.
Analysis of nearby inodes (217–224) revealed that their Modify timestamps were all 2024-02-10 19:09:30.000000000.
A timestamp pattern was also observed in which the Change time of inode 217 matched the Access time of inode 218.
Therefore, according to this pattern, the original timestamps of inode 222 could be reconstructed as follows.
inode Number : 222
Name : 1000_F_564265464_mp9OwlBNexenRBJcwg5qhCwOxr4TC3gk.jpg
Modify : 2024-02-10 19:09:30.000000000
Access : 2025-07-26 19:54:20.748569413
Change : 2025-07-26 19:54:20.749545926
Birth : 2025-07-26 19:54:20.748569413
Additionally, xfs_repair was used to remove the hidden data from the superblock, while inodes 222, 249, 250, and 251 were manually modified.
The CRC32c values of inodes 249, 250, and 251 were also updated, and the hidden data stored in the slack spaces was removed successfully.
(inode 249 CRC32c – 75 1A DA B4, inode 250 CRC32c – 85 DE 83 36, inode 251 CRC32c – 24 E8 A0 E9)
Finally, the hex values of the repaired sectors from disk_repair.img — superblock (sector 0), inode 222 (sector 222), inode 249 (sector 249), inode 250 (sector 250), and inode 251 (sector 251) — were copied into the corresponding locations of disk_origin.img.
After completing these modifications, the resulting disk image produced the same MD5 hash specified in the challenge: b79ff8b1a233eb2406aa4508d765c961.
7. Reference
[1] Data Hiding in the XFS File System, Toolan, F., & Humphries, G. (2025). Data hiding in the XFS file system. Forensic Science International: Digital Investigation, 52, 301884. https://doi.org/10.1016/j.fsidi.2025.301884