1

I am currently doing some OS development on a Linux machine. In the process I want to create a FAT12 filesystem on a file (Eg. Disk.img). I use the mkfs command as follows:

touch Disk.img
truncate Disk.img -s 1M
mkfs.vfat -F12 Disk.img

On viewing with a hex editor, I observe that the 'SECTORS_PER_FAT' is 2 by default. I want to make it 9.. How can I do this??

edit: The BIOS parameter block has the following information (that I simply don't want to do by hand and want to use mkfs instead)

(This is an assebly snippet from http://www.brokenthorn.com/Resources/OSDev5.html)

bpbBytesPerSector:      DW 512
bpbSectorsPerCluster:   DB 1
bpbReservedSectors:     DW 1
bpbNumberOfFATs:    DB 2
bpbRootEntries:     DW 224
bpbTotalSectors:    DW 2880
bpbMedia:       DB 0xF0
bpbSectorsPerFAT:   DW 9    ;!!!!This is the thing I want to control!!!!
bpbSectorsPerTrack:     DW 18
bpbHeadsPerCylinder:    DW 2
bpbHiddenSectors:   DD 0
bpbTotalSectorsBig:     DD 0
bsDriveNumber:          DB 0
bsUnused:       DB 0
bsExtBootSignature:     DB 0x29
bsSerialNumber:         DD 0xa0a1a2a3
bsVolumeLabel:          DB "MOS FLOPPY "
bsFileSystem:           DB "FAT12   "

BTW... I think that the total number of clusters and sectors per cluster should automatically determine the size of FAT(in number of sectors)... So defining sectors_per_fat in the BPB might be redundant... Meaning that it can not take any arbitary value....

1
  • Sectors per track are usually 9. Do you have special reason to set sectors per FAT? Dec 14, 2019 at 12:11

1 Answer 1

1

I observe that the 'SECTORS_PER_FAT' is 2 by default. I want to make it 9. How can I do this?

It seems this number is automatically calculated. Since the File Allocation Table has one entry per cluster and the number of clusters is finite and known in advance, there is no point of allocating more sectors to FAT.

In your case 2 is not "by default", it's determined mostly by the filesystem size (the size of Disk.img) and the cluster size.

Take the minimal possible cluster size (i.e. minimal logical sector size (-S512) and minimal number of sectors per cluster (-s1)):

# 'touch' is not needed, 'truncate' is enough
truncate Disk.img -s 1M
mkfs.vfat -F12 -S512 -s1 Disk.img
# the below line extracts the value we're after
<Disk.img od -j22 -N2 -tu2 | awk 'NR==1{print $2}'

This gives you the maximal number of clusters for the given file size, so the maximal number of entries in FAT, so the maximal FAT size, so the maximal number of sectors needed per FAT. Still it's only 6.

I think in theory you can formally allocate more sectors and the filesystem will be valid. The point is any additional sector in FAT would never be used because all clusters are already covered by entries in these 6 sectors. In practice mkfs.vfat doesn't waste sectors like this.


Rough calculation how 1 MiB and -S512 -s1 give 6 sectors per FAT:

  1. We neglect structures other than clusters as if all the space contributed to clusters. With -S512 -s1 a cluster takes 0.5 KiB. 1 MiB holds exactly 2 Ki of such clusters. Note in this calculation the number of clusters is inflated with respect to the strict value.
  2. In FAT12 one entry takes 12 bits (2 entries per 3 bytes), so 1.5 B. We need one entry per cluster. 2 Ki of entries take 3 KiB. So FAT should take 3 KiB and this number is also inflated.
  3. A single sector is 0.5 KiB. You need 6 sectors to hold 3 KiB. Since 3 KiB was somewhat inflated, you need at most 6 sectors.

The tool calculates this number more strictly.


The number of FATs (-f) hardly matters. It's not that clusters are divided among separate FATs. Additional FATs are just copies and each still serves all clusters. More FATs take more space, this slightly reduces the number of clusters. For some "threshold sizes" of the filesystem this phenomenon affects the number of sectors per FAT. However for 1 MiB and -S512 -s1 the needed number of sectors per FAT is 6 regardless of -f (note: in my tests mkfs.vfat refused to create more than 4 FATs).

After we maximized the number of clusters for the given filsystem size, the easiest way to increase the number of sectors per FAT is to make the filesystem bigger. We got 6 for 1 MiB, so probably we will get 9 for 1.5 MiB. Indeed:

truncate Disk.img -s 1536k
mkfs.vfat -F12 -S512 -s1 Disk.img
<Disk.img od -j22 -N2 -tu2 | awk 'NR==1{print $2}'

Note 1536k is not the minimal size to get 9. In my tests 1389k gave me 9 and 1388k gave me 8. Now one can see how -f affects the number. For 1389k -f2 (the default value) gives 9 and -f3 gives 8. For 1388k -f1 gives 9 and -f2 gives 8.


My testbed:

  • Debian GNU/Linux 9
  • mkfs.vfat as symlink to mkfs.fat
  • mkfs.fat version: 4.1 (2017-01-24)

References:

  1. The FAT filesystem by Andries Brouwer
    (It's from 2002 but I don't think FAT12 has significantly changed since)
  2. Design of the FAT file system on Wikipedia
2
  • I knew this is your answer before looking at the username ;) I didn't know truncate can create files.
    – gronostaj
    Dec 14, 2019 at 13:20
  • This seems right... Btw, I don't really think it's an XY problem... I was reading about OS development and was writing a simple OS. I wanted to incorporate FAT12 filesystem in the OS, but didn't want to do the dirty/ugly stuff myself :). this is the reason that I wanted to use mkfs to do it for me
    – Suraaj K S
    Dec 15, 2019 at 8:52

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .