fs/spiffs: fs/spiffs: Fix several bugs: (1) Fix bad statfs return values. (2) Fix an error in spiffs_unlink(). Fix an in error detection logic when closing a file.
This commit is contained in:
parent
2d2dd5e9e3
commit
2ca8c6682c
@ -142,8 +142,8 @@ struct spiffs_s
|
||||
int lu_entry; /* Cursor when searching, entry index */
|
||||
uint32_t total_pages; /* Total number of pages on the media */
|
||||
uint32_t free_blocks; /* Current number of free blocks */
|
||||
uint32_t stats_p_allocated; /* Current number of busy pages */
|
||||
uint32_t stats_p_deleted; /* Current number of deleted pages */
|
||||
uint32_t alloc_pages; /* Current number of busy pages */
|
||||
uint32_t deleted_pages; /* Current number of deleted pages */
|
||||
#ifdef CONFIG_SPIFFS_GCDBG
|
||||
uint32_t stats_gc_runs;
|
||||
#endif
|
||||
|
@ -223,11 +223,11 @@ static int spiffs_objlu_scan_callback(FAR struct spiffs_s *fs, int16_t objid,
|
||||
}
|
||||
else if (objid == SPIFFS_OBJID_DELETED)
|
||||
{
|
||||
fs->stats_p_deleted++;
|
||||
fs->deleted_pages++;
|
||||
}
|
||||
else
|
||||
{
|
||||
fs->stats_p_allocated++;
|
||||
fs->alloc_pages++;
|
||||
}
|
||||
|
||||
return SPIFFS_VIS_COUNTINUE;
|
||||
@ -851,8 +851,8 @@ int spiffs_objlu_scan(FAR struct spiffs_s *fs)
|
||||
/* Count blocks */
|
||||
|
||||
fs->free_blocks = 0;
|
||||
fs->stats_p_allocated = 0;
|
||||
fs->stats_p_deleted = 0;
|
||||
fs->alloc_pages = 0;
|
||||
fs->deleted_pages = 0;
|
||||
|
||||
ret = spiffs_foreach_objlu(fs, 0, 0, 0, 0, spiffs_objlu_scan_callback,
|
||||
0, 0, &blkndx, &entry);
|
||||
@ -1082,7 +1082,7 @@ int spiffs_page_allocate_data(FAR struct spiffs_s *fs, int16_t objid,
|
||||
return ret;
|
||||
}
|
||||
|
||||
fs->stats_p_allocated++;
|
||||
fs->alloc_pages++;
|
||||
|
||||
/* Write page header */
|
||||
|
||||
@ -1225,7 +1225,7 @@ int spiffs_page_move(FAR struct spiffs_s *fs,
|
||||
return ret;
|
||||
}
|
||||
|
||||
fs->stats_p_allocated++;
|
||||
fs->alloc_pages++;
|
||||
|
||||
if (was_final)
|
||||
{
|
||||
@ -1276,8 +1276,8 @@ int spiffs_page_delete(FAR struct spiffs_s *fs, int16_t pgndx)
|
||||
return ret;
|
||||
}
|
||||
|
||||
fs->stats_p_deleted++;
|
||||
fs->stats_p_allocated--;
|
||||
fs->deleted_pages++;
|
||||
fs->alloc_pages--;
|
||||
|
||||
/* Mark deleted in source page */
|
||||
|
||||
@ -1363,7 +1363,7 @@ int spiffs_object_create(FAR struct spiffs_s *fs,
|
||||
return ret;
|
||||
}
|
||||
|
||||
fs->stats_p_allocated++;
|
||||
fs->alloc_pages++;
|
||||
|
||||
/* Write empty object index page */
|
||||
|
||||
|
@ -205,8 +205,8 @@ static int spiffs_gc_epage_stats(FAR struct spiffs_s *fs, int16_t blkndx)
|
||||
|
||||
spiffs_gcinfo("Wipe pallo=%d pdele=%d\n", allo, dele);
|
||||
|
||||
fs->stats_p_allocated -= allo;
|
||||
fs->stats_p_deleted -= dele;
|
||||
fs->alloc_pages -= allo;
|
||||
fs->deleted_pages -= dele;
|
||||
return ret;
|
||||
}
|
||||
|
||||
@ -1052,7 +1052,7 @@ int spiffs_gc_quick(FAR struct spiffs_s *fs, uint16_t max_free_pages)
|
||||
{
|
||||
/* Found a fully deleted block */
|
||||
|
||||
fs->stats_p_deleted -= deleted_pages_in_block;
|
||||
fs->deleted_pages -= deleted_pages_in_block;
|
||||
ret = spiffs_gc_erase_block(fs, cur_block);
|
||||
return ret;
|
||||
}
|
||||
@ -1112,10 +1112,10 @@ int spiffs_gc_check(FAR struct spiffs_s *fs, off_t len)
|
||||
|
||||
free_pages = (SPIFFS_GEO_PAGES_PER_BLOCK(fs) -
|
||||
SPIFFS_OBJ_LOOKUP_PAGES(fs)) * (SPIFFS_GEO_BLOCK_COUNT(fs) - 2) -
|
||||
fs->stats_p_allocated - fs->stats_p_deleted;
|
||||
fs->alloc_pages - fs->deleted_pages;
|
||||
|
||||
spiffs_gcinfo("len=%ld free_blocks=%lu\n free_pages=%ld",
|
||||
(long)len, (unsigned long)fs->free_blocksm,
|
||||
(long)len, (unsigned long)fs->free_blocks,
|
||||
(long)free_pages);
|
||||
|
||||
if (fs->free_blocks > 3 &&
|
||||
@ -1135,16 +1135,16 @@ int spiffs_gc_check(FAR struct spiffs_s *fs, off_t len)
|
||||
{
|
||||
spiffs_gcinfo("Full freeblk=%d" needed=%d" free=%d dele=%d\n",
|
||||
fs->free_blocks, needed_pages, free_pages,
|
||||
fs->stats_p_deleted);
|
||||
fs->deleted_pages);
|
||||
return -ENOSPC;
|
||||
}
|
||||
#endif
|
||||
|
||||
if ((int32_t)needed_pages > (int32_t)(free_pages + fs->stats_p_deleted))
|
||||
if ((int32_t)needed_pages > (int32_t)(free_pages + fs->deleted_pages))
|
||||
{
|
||||
spiffs_gcinfo("Full freeblk=%d needed=%d free=%d dele=%d\n",
|
||||
fs->free_blocks, needed_pages, free_pages,
|
||||
fs->stats_p_deleted);
|
||||
fs->deleted_pages);
|
||||
return -ENOSPC;
|
||||
}
|
||||
|
||||
@ -1157,8 +1157,8 @@ int spiffs_gc_check(FAR struct spiffs_s *fs, off_t len)
|
||||
|
||||
spiffs_gcinfo("#%d: run gc free_blocks=%d pfree=%d pallo=%d pdele=%d [%d] len=%d of %d\n",
|
||||
tries, fs->free_blocks, free_pages,
|
||||
fs->stats_p_allocated, fs->stats_p_deleted,
|
||||
(free_pages + fs->stats_p_allocated + fs->stats_p_deleted),
|
||||
fs->alloc_pages, fs->deleted_pages,
|
||||
(free_pages + fs->alloc_pages + fs->deleted_pages),
|
||||
len, (uint32_t)(free_pages * SPIFFS_DATA_PAGE_SIZE(fs)));
|
||||
|
||||
/* If the fs is crammed, ignore block age when selecting candidate - kind
|
||||
@ -1209,7 +1209,7 @@ int spiffs_gc_check(FAR struct spiffs_s *fs, off_t len)
|
||||
|
||||
free_pages = (SPIFFS_GEO_PAGES_PER_BLOCK(fs) -
|
||||
SPIFFS_OBJ_LOOKUP_PAGES(fs)) * (SPIFFS_GEO_BLOCK_COUNT(fs) - 2) -
|
||||
fs->stats_p_allocated - fs->stats_p_deleted;
|
||||
fs->alloc_pages - fs->deleted_pages;
|
||||
|
||||
if (prev_free_pages <= 0 && prev_free_pages == free_pages)
|
||||
{
|
||||
@ -1228,7 +1228,7 @@ int spiffs_gc_check(FAR struct spiffs_s *fs, off_t len)
|
||||
|
||||
free_pages = (SPIFFS_GEO_PAGES_PER_BLOCK(fs) -
|
||||
SPIFFS_OBJ_LOOKUP_PAGES(fs)) * (SPIFFS_GEO_BLOCK_COUNT(fs) - 2) -
|
||||
fs->stats_p_allocated - fs->stats_p_deleted;
|
||||
fs->alloc_pages - fs->deleted_pages;
|
||||
|
||||
if ((int32_t) len > free_pages * (int32_t)SPIFFS_DATA_PAGE_SIZE(fs))
|
||||
{
|
||||
@ -1237,7 +1237,7 @@ int spiffs_gc_check(FAR struct spiffs_s *fs, off_t len)
|
||||
|
||||
spiffs_gcinfo("Finished, %d dirty, blocks, %d free, %d pages free, "
|
||||
"%d tries, ret=%d\n",
|
||||
fs->stats_p_allocated + fs->stats_p_deleted,
|
||||
fs->alloc_pages + fs->deleted_pages,
|
||||
fs->free_blocks, free_pages, tries, ret);
|
||||
|
||||
return ret;
|
||||
|
@ -490,6 +490,7 @@ static int spiffs_open(FAR struct file *filep, FAR const char *relpath,
|
||||
|
||||
/* Add the new file object to the tail of the open file list */
|
||||
|
||||
finfo("Adding fobj for objid=%04x\n", fobj->objid);
|
||||
dq_addlast((FAR dq_entry_t *)fobj, &fs->objq);
|
||||
|
||||
spiffs_unlock_volume(fs);
|
||||
@ -1515,7 +1516,6 @@ static int spiffs_statfs(FAR struct inode *mountpt, FAR struct statfs *buf)
|
||||
uint32_t data_pgsize;
|
||||
uint32_t ndata_pages;
|
||||
uint32_t nfile_objs;
|
||||
uint32_t used;
|
||||
|
||||
finfo("mountpt=%p buf=%p\n", mountpt, buf);
|
||||
DEBUGASSERT(mountpt != NULL && buf != NULL);
|
||||
@ -1539,7 +1539,6 @@ static int spiffs_statfs(FAR struct inode *mountpt, FAR struct statfs *buf)
|
||||
/* -2 for spare blocks, +1 for emergency page */
|
||||
|
||||
ndata_pages = (blocks - 2) * (pages_per_block - obj_lupages) + 1;
|
||||
used = fs->stats_p_allocated * data_pgsize;
|
||||
|
||||
/* Count the number of file objects */
|
||||
|
||||
@ -1557,7 +1556,7 @@ static int spiffs_statfs(FAR struct inode *mountpt, FAR struct statfs *buf)
|
||||
buf->f_namelen = CONFIG_SPIFFS_NAME_MAX - 1;
|
||||
buf->f_bsize = data_pgsize;
|
||||
buf->f_blocks = ndata_pages;
|
||||
buf->f_bfree = ndata_pages - used;
|
||||
buf->f_bfree = ndata_pages - fs->alloc_pages;
|
||||
buf->f_bavail = buf->f_bfree;
|
||||
buf->f_files = nfile_objs;
|
||||
buf->f_ffree = buf->f_bfree; /* SWAG */
|
||||
@ -1599,12 +1598,12 @@ static int spiffs_unlink(FAR struct inode *mountpt, FAR const char *relpath)
|
||||
/* Find the page index to the object header associated with this path */
|
||||
|
||||
ret = spiffs_find_objhdr_pgndx(fs, (FAR const uint8_t *)relpath, &pgndx);
|
||||
if (ret < OK)
|
||||
if (ret == -ENOENT)
|
||||
{
|
||||
fwarn("WARNING: No objhdr found for relpath '%s': %d\n", relpath, ret);
|
||||
goto errout_with_lock;
|
||||
}
|
||||
else if (ret != -ENOENT)
|
||||
else if (ret < 0)
|
||||
{
|
||||
ferr("ERROR: spiffs_find_objhdr_pgndx failed: %d\n", ret);
|
||||
goto errout_with_lock;
|
||||
|
@ -428,6 +428,8 @@ void spiffs_fobj_free(FAR struct spiffs_s *fs, FAR struct spiffs_file_s *fobj)
|
||||
FAR struct spiffs_file_s *curr;
|
||||
int ret;
|
||||
|
||||
finfo("Removing fobj for objid=%04x\n", fobj->objid);
|
||||
|
||||
/* Flush any buffered write data */
|
||||
|
||||
ret = spiffs_fflush_cache(fs, fobj);
|
||||
@ -451,6 +453,7 @@ void spiffs_fobj_free(FAR struct spiffs_s *fs, FAR struct spiffs_file_s *fobj)
|
||||
/* Yes, remove it from the list of of file objects */
|
||||
|
||||
dq_rem((FAR dq_entry_t *)curr, &fs->objq);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user