blob: 32927987377fdd989c19607430313cc7eb931589 [file] [log] [blame]
Tim Windelschmidt6d33a432025-02-04 14:34:25 +01001// Copyright The Monogon Project Authors.
2// SPDX-License-Identifier: Apache-2.0
3
Lorenz Brunbd2ce6d2022-07-22 00:00:13 +00004package fat32
5
6const (
7 // FAT32 entries are only 28 bits
8 fatMask = 0x0fffffff
9 // Free entries are 0
10 fatFree = 0x0
11 // Entry at the end of a cluster chain
12 fatEOF = 0x0ffffff8
13)
14
15// FAT32 Boot Sector and BIOS Parameter Block. This structure is 512 bytes long,
16// even if the logical block size is longer. The rest should be filled up with
17// zeroes.
18type bootSector struct {
19 // Jump instruction to boot code.
20 JmpInstruction [3]byte
21 // Creator name. "MSWIN4.1" recommended for compatibility.
22 OEMName [8]byte
23 // Count of bytes per block (i.e. logical block size)
24 // Must be one of 512, 1024, 2048 or 4096
25 BlockSize uint16
26 // Number of blocks per allocation unit (cluster).
27 // Must be a power of 2 that is greater than 0.
28 BlocksPerCluster uint8
29 // Number of reserved blocks in the reserved region of the volume starting
30 // at the first block of the volume. This field must not be 0.
31 ReservedBlocks uint16
32 // The count of FAT data structures on the volume. This field should always
33 // contain the value of 2 for any FAT volume of any type.
34 NumFATs uint8
35 _ [4]byte
36 // Legacy value for media determination, must be 0xf8.
37 MediaCode uint8
38 _ [2]byte
39 // Number of sectors per track for 0x13 interrupts.
40 SectorsPerTrack uint16
41 // Number of heads for 0x13 interrupts.
42 NumHeads uint16
43 // Count of hidden blocks preceding the partition that contains this FAT
44 // volume.
45 HiddenBlocks uint32
46 // Total count of blocks on the volume.
47 TotalBlocks uint32
48 // Count of blocks per FAT.
49 BlocksPerFAT uint32
50 // Flags for FAT32
51 Flags uint16
52 _ [2]byte
53 // Cluster number of the first cluster of the root directory. Usually 2.
54 RootClusterNumber uint32
55 // Block number of the FSINFO structure in the reserved area.
56 FSInfoBlock uint16
57 // Block number of the copy of the boot record in the reserved area.
58 BackupStartBlock uint16
59 _ [12]byte
60 // Drive number for 0x13 interrupts.
61 DriveNumber uint8
62 _ [1]byte
63 BootSignature uint8
64 // ID of this filesystem
65 ID uint32
66 // Human-readable label of this filesystem, padded with spaces (0x20)
67 Label [11]byte
68 // Always set to ASCII "FAT32 "
69 Type [8]byte
70 _ [420]byte
71 // Always 0x55, 0xAA
72 Signature [2]byte
73}
74
75// Special block (usually at block 1) containing additional metadata,
76// specifically the number of free clusters and the next free cluster.
77// Always 512 bytes, rest of the block should be padded with zeroes.
78type fsinfo struct {
79 // Validates that this is an FSINFO block. Always 0x52, 0x52, 0x61, 0x41
80 LeadSignature [4]byte
81 _ [480]byte
82 // Another signature. Always 0x72, 0x72, 0x41, 0x61
83 StructSignature [4]byte
84 // Last known number of free clusters on the volume.
85 FreeCount uint32
86 // Next free cluster hint. All 1's is interpreted as undefined.
87 NextFreeCluster uint32
88 _ [14]byte
89 // One more signature. Always 0x55, 0xAA.
90 TrailingSignature [2]byte
91}
92
93// Directory entry
94type dirEntry struct {
95 // DOS 8.3 file name.
96 DOSName [11]byte
97 // Attribtes of the file or directory, 0x0f reserved to mark entry as a
98 // LFN entry (see lfnEntry below)
99 Attributes uint8
100 _ byte
101 CreationTenMilli uint8 // Actually 10ms units, 0-199 range
102 CreationTime uint16
103 CreationDate uint16
104 _ [2]byte
105 FirstClusterHigh uint16
106 LastWrittenToTime uint16
107 LastWrittenToDate uint16
108 FirstClusterLow uint16
109 FileSize uint32
110}
111
112const (
113 // lastSequenceNumberFlag is logically-ORed with the sequence number of the
114 // last Long File Name entry to mark it as such.
115 lastSequenceNumberFlag = 0x40
116 // codepointsPerEntry is the number of UTF-16 codepoints that fit into a
117 // single Long File Name entry.
118 codepointsPerEntry = 5 + 6 + 2
119)
120
121// VFAT long file name prepended entry
122type lfnEntry struct {
123 SequenceNumber uint8
124 // First 5 UTF-16 code units
125 NamePart1 [5]uint16
126 // Attributes (must be 0x0f)
127 Attributes uint8
128 _ byte
129 // Checksum of the 8.3 name.
130 Checksum uint8
131 // Next 6 UTF-16 code units
132 NamePart2 [6]uint16
133 _ [2]byte
134 // Next 2 UTF-16 code units
135 NamePart3 [2]uint16
136}