|
|
|
#include <bitops.h>
|
|
|
|
#include <flash.h>
|
|
|
|
#include <macros.h>
|
|
|
|
|
|
|
|
#include <fs/mufs.h>
|
|
|
|
|
|
|
|
#include "block.h"
|
|
|
|
|
|
|
|
static int mufs_mark_block(struct mufs *fs, uint32_t block, int status)
|
|
|
|
{
|
|
|
|
char data[1 << fs->dev->log2_block_size];
|
|
|
|
uint8_t log2_bits_per_block = fs->dev->log2_block_size + ilog2(8);
|
|
|
|
size_t index;
|
|
|
|
|
|
|
|
index = block & ((UINT32_C(1) << log2_bits_per_block) - 1);
|
|
|
|
block >>= log2_bits_per_block;
|
|
|
|
|
|
|
|
if (flash_read(fs->dev, (1 + block) << fs->dev->log2_block_size, data,
|
|
|
|
sizeof data) == 0)
|
|
|
|
return -1;
|
|
|
|
|
|
|
|
if (status) {
|
|
|
|
set_bit(data, index);
|
|
|
|
} else {
|
|
|
|
clear_bit(data, index);
|
|
|
|
}
|
|
|
|
|
|
|
|
if (flash_write(fs->dev, (1 + block) << fs->dev->log2_block_size, data,
|
|
|
|
sizeof data) == 0)
|
|
|
|
return -1;
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
int mufs_alloc_block(struct mufs *fs, uint32_t *found)
|
|
|
|
{
|
|
|
|
char data[1 << fs->dev->log2_block_size];
|
|
|
|
uint32_t nblocks = fs->nblocks;
|
|
|
|
uint32_t nbits;
|
|
|
|
uint32_t block = 0;
|
|
|
|
size_t index;
|
|
|
|
uint8_t log2_bits_per_block = fs->dev->log2_block_size + ilog2(8);
|
|
|
|
|
|
|
|
while (nblocks) {
|
|
|
|
if (flash_read(fs->dev, (1 + block) << fs->dev->log2_block_size, data,
|
|
|
|
sizeof data) == 0)
|
|
|
|
return -1;
|
|
|
|
|
|
|
|
nbits = min(nblocks, UINT32_C(1) << log2_bits_per_block);
|
|
|
|
|
|
|
|
if ((index = next_clear_bit(data, nbits)) == SIZE_MAX) {
|
|
|
|
++block;
|
|
|
|
nblocks -= nbits;
|
|
|
|
continue;
|
|
|
|
}
|
|
|
|
|
|
|
|
*found = (block << log2_bits_per_block) + index;
|
|
|
|
|
|
|
|
return mufs_mark_block(fs, *found, 1);
|
|
|
|
}
|
|
|
|
|
|
|
|
return -1;
|
|
|
|
}
|
|
|
|
|
|
|
|
int mufs_free_block(struct mufs *fs, uint32_t block)
|
|
|
|
{
|
|
|
|
flash_erase(fs->dev, (1 + block) << fs->dev->log2_block_size,
|
|
|
|
1 << fs->dev->log2_block_size);
|
|
|
|
|
|
|
|
return mufs_mark_block(fs, block, 0);
|
|
|
|
}
|