blob: 72e075e1ed7de87f10f643b0e522d02c8f54fa8b [file] [log] [blame]
// Copyright 2016 The Fuchsia Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
package bootrecord
import "errors"
// brSmall is the prefix of the first sector of the FAT12/16 filesystem.
type brSmall struct {
bsPrefix bootsectorPrefix
bpb bpbShared
bsSuffix bootsectorSuffix
padding [448]uint8 // Padding so struct is 512 bytes long.
bootSectorSig [2]uint8
}
func (b *brSmall) Validate() (FATType, error) {
sizeClassLarge := false
if err := bootSectorSignatureValid(b.bootSectorSig[:]); err != nil {
return FATInvalid, err
} else if err := b.bsPrefix.validate(); err != nil {
return FATInvalid, err
} else if err := b.bpb.validate(sizeClassLarge); err != nil {
return FATInvalid, err
} else if err := b.bsSuffix.validate(); err != nil {
return FATInvalid, err
}
numUsableClusters := b.bpb.TotalClusters(b.FirstDataSector())
if numUsableClusters == 0 {
return FATInvalid, errors.New("No usable clusters")
} else if numUsableClusters < 4085 {
return FAT12, nil
} else if numUsableClusters < 65525 {
return FAT16, nil
}
return FATInvalid, errors.New("Too many clusters for FAT12/16")
}
func (b *brSmall) NumRootDirSectors() uint32 {
numRootEntries := b.bpb.NumRootEntries()
bytesPerSector := b.bpb.BytesPerSec()
return ((numRootEntries * 32) + (bytesPerSector - 1)) / bytesPerSector
}
func (b *brSmall) FirstDataSector() uint32 {
return b.bpb.NumSectorsReserved() + (b.bpb.NumFATs() * b.bpb.SectorsPerFAT16()) + b.NumRootDirSectors()
}