Directory Entry

Directory entries are used to store the name of a file or directory. They are located in the blocks allocated to a directory, and they contain the address of the inode that the file or directory has allocated.

The directory entry structure comes in two formats, but both are the same size. The second format makes better use of the available space. The incompatible features value in the superblock will identify which version is being used. The original format is not the default in current systems, but it has the fields given in Table 15.22.

Table 15.22. Data structure for the original directory entry.

Byte Range

Description

Essential

03

Inode value

Yes

45

Length of this entry

Yes

67

Name length

Yes

8+

Name in ASCII

Yes

This is a very basic data structure where all the fields are essential. One structure exists for each name in a directory, and the structure points to the inode where the metadata can be found. The name is not null terminated, so the name length field is needed. Linux aligns these data structures on 4-byte boundaries.

The second version of these data structures makes better use of the name length field. The maximum number of characters in a file name is 255, so only one byte is needed. The second version of the directory entry uses the other byte to store the file type, which also can be found in the inode. It has the fields given in Table 15.23.

Table 15.23. Data structure for the second version of the directory entry.

Byte Range

Description

Essential

03

Inode value

Yes

45

Length of this entry

Yes

66

Name length

Yes

77

File type (see Table 15.24)

No

8+

Name in ASCII

Yes

The file type value is not an essential value, and it can have one of the values given in table 15.24.

Table 15.24. Values for the directory entry type field.

 

Description

0

Unknown type

1

Regular file

2

Directory

3

Character device

4

Block device

5

FIFO

6

Unix Socket

7

Symbolic link

To look at the raw contents of a directory, we can use the icat command. Our test image uses the new version 2 directory entries, and inode 69,457 corresponds to a directory:

# icat f linux-ext3 ext3.dd 69457 | xxd 0000000: 510f 0100 0c00 0102 2e00 0000 00d0 0000 Q............... 0000016: 0c00 0202 2e2e 0000 520f 0100 2800 0b01 ........R...(... 0000032: 6162 6364 6566 672e 7478 7400 530f 0100 abcdefg.txt.S... 0000048: 1400 0c01 6669 6c65 2074 776f 2e64 6174 ....file two.dat 0000064: 540f 0100 1000 0702 7375 6264 6972 3100 T.......subdir1. 0000080: 550f 0100 b003 0801 5253 5455 5657 5859 U.......RSTUVWXY 0000096: 0000 0000 0000 0000 0000 0000 0000 0000 ................ [REMOVED]

We see in bytes 0 to 3 that the inode corresponding to the first entry is 64,457 (0x010f51), and bytes 4 to 5 show that the directory entry is 12 bytes (0x0c). Byte 6 shows that the name is 1 byte long, and byte 7 shows that the entry is for a directory (0x02). The name is given in byte 8 and we see that it is '..' This corresponds to the directory entry for the current directory. We can do a sanity check by comparing the inode in the entry with the inode value we used with icat to display the contents, and we see that they are both 64,457.

To find the second entry, we add the length of the first entry to its start, which means that the second entry will start in byte 12. We see in bytes 16 to 17 that the length of this entry is also 12 bytes, and it is for the '..' directory.

To find the third entry, we add the length of the second entry to its start and get byte 24. We see in bytes 28 to 29 that the entry length is 40 bytes (0x28). Byte 30 shows the name length is 11 (0x0b). The name starts at byte 32 and extends until byte 42, and it contains the string abcdefg.txt.

If we jump ahead from the start of the previous entry at byte 24 to the next entry, we get to byte 64. You might notice that the last entry ended in byte 42, so there are 20 unused bytes in between. The space in between contains a deleted file name, and its entry starts in byte 42 with a name of file two.dat.

The rest of the data is left for you to parse if you would like. We can see the output of running the fls tool on the same directory:

# fls -f linux-ext3 a ext3.dd 69457 d/d 69457: . d/d 53248: .. r/r 69458: abcdefg.txt r/r * 69459: file two.dat d/d 69460: subdir1 r/r 69461: RSTUVWXY

Категории