| // Copyright 2019 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. |
| |
| #include <fvm/format.h> |
| |
| #include <zxtest/zxtest.h> |
| |
| namespace fvm { |
| namespace { |
| |
| // 256 KB |
| constexpr size_t kFvmSlizeSize = 8 * kBlockSize; |
| |
| constexpr size_t kInitialDiskSize = 256 * kBlockSize; |
| |
| constexpr size_t kMaxDiskSize = 1024 * kBlockSize; |
| |
| constexpr size_t kAllocTableSize = fvm::AllocTableLength(kMaxDiskSize, kFvmSlizeSize); |
| |
| constexpr size_t kPartitionTableSize = fvm::kVPartTableLength; |
| |
| Header MakeSuperBlock(size_t part_size, size_t part_table_size, size_t alloc_table_size) { |
| Header superblock; |
| superblock.fvm_partition_size = part_size; |
| superblock.vpartition_table_size = part_table_size; |
| superblock.allocation_table_size = alloc_table_size; |
| superblock.slice_size = kFvmSlizeSize; |
| superblock.version = fvm::kMagic; |
| superblock.magic = fvm::kVersion; |
| superblock.generation = 1; |
| fvm_update_hash(&superblock, sizeof(Header)); |
| return superblock; |
| } |
| |
| size_t CalculateSliceStart(size_t part_size, size_t part_table_size, size_t allocation_table_size) { |
| // Round Up to the next block. |
| return 2 * fbl::round_up(fvm::kBlockSize + part_table_size + allocation_table_size, |
| fvm::kBlockSize); |
| } |
| |
| TEST(FvmInfoTest, FromSuperblockNoGaps) { |
| Header superblock = MakeSuperBlock(kMaxDiskSize, kPartitionTableSize, kAllocTableSize); |
| FormatInfo format_info = FormatInfo::FromSuperBlock(superblock); |
| |
| // When there is no gap allocated and metadata size should match. |
| EXPECT_EQ(fvm::MetadataSize(kMaxDiskSize, kFvmSlizeSize), format_info.metadata_size()); |
| EXPECT_EQ(fvm::MetadataSize(kMaxDiskSize, kFvmSlizeSize), |
| format_info.metadata_allocated_size()); |
| EXPECT_EQ(fvm::UsableSlicesCount(kMaxDiskSize, kFvmSlizeSize), format_info.slice_count()); |
| EXPECT_EQ(kFvmSlizeSize, format_info.slice_size()); |
| |
| EXPECT_EQ(0, format_info.GetSuperblockOffset(SuperblockType::kPrimary)); |
| EXPECT_EQ(fvm::MetadataSize(kMaxDiskSize, kFvmSlizeSize), |
| format_info.GetSuperblockOffset(SuperblockType::kSecondary)); |
| EXPECT_EQ(CalculateSliceStart(kMaxDiskSize, kPartitionTableSize, kAllocTableSize), |
| format_info.GetSliceStart(1)); |
| EXPECT_EQ((fvm::MetadataSize(kMaxDiskSize, kFvmSlizeSize) - AllocationTable::kOffset) / |
| sizeof(SliceEntry), |
| format_info.GetMaxAllocatableSlices()); |
| EXPECT_EQ((fvm::UsableSlicesCount(kMaxDiskSize, kFvmSlizeSize)), |
| format_info.GetMaxAddressableSlices(kMaxDiskSize)); |
| EXPECT_EQ(format_info.GetSliceStart(1) + |
| kFvmSlizeSize * |
| ((fvm::MetadataSize(kMaxDiskSize, kFvmSlizeSize) - kAllocTableOffset) / |
| sizeof(SliceEntry)), |
| format_info.GetMaxPartitionSize()); |
| } |
| |
| TEST(FvmInfoTest, FromSuperblockWithGaps) { |
| Header superblock = MakeSuperBlock(kInitialDiskSize, kPartitionTableSize, kAllocTableSize); |
| FormatInfo format_info = FormatInfo::FromSuperBlock(superblock); |
| |
| EXPECT_EQ(fvm::MetadataSize(kInitialDiskSize, kFvmSlizeSize), format_info.metadata_size()); |
| EXPECT_EQ(fvm::MetadataSize(kMaxDiskSize, kFvmSlizeSize), |
| format_info.metadata_allocated_size()); |
| EXPECT_EQ(fvm::UsableSlicesCount(kInitialDiskSize, kFvmSlizeSize), format_info.slice_count()); |
| EXPECT_EQ(kFvmSlizeSize, format_info.slice_size()); |
| |
| EXPECT_EQ(0, format_info.GetSuperblockOffset(SuperblockType::kPrimary)); |
| EXPECT_EQ(fvm::MetadataSize(kMaxDiskSize, kFvmSlizeSize), |
| format_info.GetSuperblockOffset(SuperblockType::kSecondary)); |
| EXPECT_EQ(CalculateSliceStart(kMaxDiskSize, kPartitionTableSize, kAllocTableSize), |
| format_info.GetSliceStart(1)); |
| |
| EXPECT_EQ((fvm::MetadataSize(kMaxDiskSize, kFvmSlizeSize) - AllocationTable::kOffset) / |
| sizeof(SliceEntry), |
| format_info.GetMaxAllocatableSlices()); |
| EXPECT_EQ((fvm::UsableSlicesCount(kMaxDiskSize, kFvmSlizeSize)), |
| format_info.GetMaxAddressableSlices(kMaxDiskSize)); |
| EXPECT_EQ(format_info.GetSliceStart(1) + |
| kFvmSlizeSize * |
| ((fvm::MetadataSize(kMaxDiskSize, kFvmSlizeSize) - kAllocTableOffset) / |
| sizeof(SliceEntry)), |
| format_info.GetMaxPartitionSize()); |
| } |
| |
| TEST(FvmInfoTest, FromDiskSize) { |
| FormatInfo format_info = FormatInfo::FromDiskSize(kMaxDiskSize, kFvmSlizeSize); |
| |
| // When there is no gap allocated and metadata size should match. |
| EXPECT_EQ(fvm::MetadataSize(kMaxDiskSize, kFvmSlizeSize), format_info.metadata_size()); |
| EXPECT_EQ(fvm::MetadataSize(kMaxDiskSize, kFvmSlizeSize), |
| format_info.metadata_allocated_size()); |
| EXPECT_EQ(fvm::UsableSlicesCount(kMaxDiskSize, kFvmSlizeSize), format_info.slice_count()); |
| EXPECT_EQ(kFvmSlizeSize, format_info.slice_size()); |
| |
| EXPECT_EQ(0, format_info.GetSuperblockOffset(SuperblockType::kPrimary)); |
| EXPECT_EQ(fvm::MetadataSize(kMaxDiskSize, kFvmSlizeSize), |
| format_info.GetSuperblockOffset(SuperblockType::kSecondary)); |
| EXPECT_EQ(CalculateSliceStart(kMaxDiskSize, kPartitionTableSize, kAllocTableSize), |
| format_info.GetSliceStart(1)); |
| |
| EXPECT_EQ((fvm::MetadataSize(kMaxDiskSize, kFvmSlizeSize) - AllocationTable::kOffset) / |
| sizeof(SliceEntry), |
| format_info.GetMaxAllocatableSlices()); |
| EXPECT_EQ((fvm::UsableSlicesCount(kMaxDiskSize, kFvmSlizeSize)), |
| format_info.GetMaxAddressableSlices(kMaxDiskSize)); |
| EXPECT_EQ(format_info.GetSliceStart(1) + |
| kFvmSlizeSize * |
| ((fvm::MetadataSize(kMaxDiskSize, kFvmSlizeSize) - kAllocTableOffset) / |
| sizeof(SliceEntry)), |
| format_info.GetMaxPartitionSize()); |
| } |
| |
| TEST(FvmInfoTest, FromPreallocatedSizeWithGaps) { |
| FormatInfo format_info = |
| FormatInfo::FromPreallocatedSize(kInitialDiskSize, kMaxDiskSize, kFvmSlizeSize); |
| |
| EXPECT_EQ(fvm::MetadataSize(kInitialDiskSize, kFvmSlizeSize), format_info.metadata_size()); |
| EXPECT_EQ(fvm::MetadataSize(kMaxDiskSize, kFvmSlizeSize), |
| format_info.metadata_allocated_size()); |
| EXPECT_EQ(fvm::UsableSlicesCount(kInitialDiskSize, kFvmSlizeSize), format_info.slice_count()); |
| EXPECT_EQ(kFvmSlizeSize, format_info.slice_size()); |
| |
| EXPECT_EQ(0, format_info.GetSuperblockOffset(SuperblockType::kPrimary)); |
| EXPECT_EQ(fvm::MetadataSize(kMaxDiskSize, kFvmSlizeSize), |
| format_info.GetSuperblockOffset(SuperblockType::kSecondary)); |
| EXPECT_EQ(CalculateSliceStart(kMaxDiskSize, kPartitionTableSize, kAllocTableSize), |
| format_info.GetSliceStart(1)); |
| |
| EXPECT_EQ((fvm::MetadataSize(kMaxDiskSize, kFvmSlizeSize) - AllocationTable::kOffset) / |
| sizeof(SliceEntry), |
| format_info.GetMaxAllocatableSlices()); |
| EXPECT_EQ((fvm::UsableSlicesCount(kMaxDiskSize, kFvmSlizeSize)), |
| format_info.GetMaxAddressableSlices(kMaxDiskSize)); |
| EXPECT_EQ(format_info.GetSliceStart(1) + |
| kFvmSlizeSize * |
| ((fvm::MetadataSize(kMaxDiskSize, kFvmSlizeSize) - kAllocTableOffset) / |
| sizeof(SliceEntry)), |
| format_info.GetMaxPartitionSize()); |
| } |
| |
| } // namespace |
| } // namespace fvm |