Minor NXFFS fixes
git-svn-id: svn://svn.code.sf.net/p/nuttx/code/trunk@3563 42af7a65-404d-4744-a932-0658087f49c3
This commit is contained in:
parent
9721078fdd
commit
d6812a0f9f
@ -136,9 +136,6 @@ blocked waiting for itself to close the first file.
|
|||||||
Things to Do
|
Things to Do
|
||||||
============
|
============
|
||||||
|
|
||||||
- The implementation is not yet finished. It needs at, a minimum,
|
|
||||||
completion of the file system packing logic. It is not usuable without
|
|
||||||
that feature.
|
|
||||||
- The statfs() implementation is minimal. It whould have some calcuation
|
- The statfs() implementation is minimal. It whould have some calcuation
|
||||||
of the f_bfree, f_bavail, f_files, f_ffree return values.
|
of the f_bfree, f_bavail, f_files, f_ffree return values.
|
||||||
- There are too many allocs and frees. More structures may need to be
|
- There are too many allocs and frees. More structures may need to be
|
||||||
@ -153,4 +150,11 @@ Things to Do
|
|||||||
information in the read open file structure.
|
information in the read open file structure.
|
||||||
- Fault tolerance must be improved. We need to be absolutely certain that
|
- Fault tolerance must be improved. We need to be absolutely certain that
|
||||||
any FLASH errors do not cause the file system to behavior incorrectly.
|
any FLASH errors do not cause the file system to behavior incorrectly.
|
||||||
|
- Wear leveling could be improved as well. Files are re-packed at the front
|
||||||
|
of FLASH as part of the clean-up operation. However, that means the files
|
||||||
|
that are not modified often become fixed in place at the beginning of
|
||||||
|
FLASH. This reduces the size of the pool moving files at the end of the
|
||||||
|
FLASH. As the file system becomes more filled with fixed files at the
|
||||||
|
front of the device, the level of wear on the blocks at the end of the
|
||||||
|
FLASH increases.
|
||||||
|
|
||||||
|
@ -258,19 +258,24 @@ static inline off_t nxffs_mediacheck(FAR struct nxffs_volume_s *volume,
|
|||||||
* Input Parameters:
|
* Input Parameters:
|
||||||
* volume - The volume to be packed
|
* volume - The volume to be packed
|
||||||
* pack - The volume packing state structure.
|
* pack - The volume packing state structure.
|
||||||
* offset - location to return the pointer to first valid inode header.
|
* froffset - On input, this is the location where we should be searching
|
||||||
|
* for the location to begin packing. If -ENOSPC is returned -- meaning
|
||||||
|
* that the FLASH -- then no packing can be performed. In this case
|
||||||
|
* (only) , then the free flash offset is returned through this location.
|
||||||
*
|
*
|
||||||
* Returned Values:
|
* Returned Values:
|
||||||
* Zero on success; Otherwise, a negated errno value is returned to
|
* Zero on success; Otherwise, a negated errno value is returned to
|
||||||
* indicate the nature of the failure.
|
* indicate the nature of the failure. If -ENOSPC is returned then the
|
||||||
|
* free FLASH offset is also returned.
|
||||||
*
|
*
|
||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
|
||||||
static inline int nxffs_startpos(FAR struct nxffs_volume_s *volume,
|
static inline int nxffs_startpos(FAR struct nxffs_volume_s *volume,
|
||||||
FAR struct nxffs_pack_s *pack,
|
FAR struct nxffs_pack_s *pack,
|
||||||
off_t offset)
|
off_t *froffset)
|
||||||
{
|
{
|
||||||
struct nxffs_blkentry_s blkentry;
|
struct nxffs_blkentry_s blkentry;
|
||||||
|
off_t offset = *froffset;
|
||||||
off_t wasted;
|
off_t wasted;
|
||||||
off_t nbytes;
|
off_t nbytes;
|
||||||
int ret;
|
int ret;
|
||||||
@ -352,6 +357,7 @@ static inline int nxffs_startpos(FAR struct nxffs_volume_s *volume,
|
|||||||
* the end-of-flash indication.
|
* the end-of-flash indication.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
*froffset = volume->froffset;
|
||||||
return -ENOSPC;
|
return -ENOSPC;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -365,9 +371,11 @@ static inline int nxffs_startpos(FAR struct nxffs_volume_s *volume,
|
|||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
{
|
{
|
||||||
/* No more valid inode entries. Just return an end-of-flash error
|
/* No more valid inode entries. Just return an end-of-flash error
|
||||||
* indication.
|
* indication. However, there could be many deleted inodes; set
|
||||||
|
* volume->froffset to indicate the true free FLASH position.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
*froffset = offset;
|
||||||
return -ENOSPC;
|
return -ENOSPC;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -975,14 +983,43 @@ int nxffs_pack(FAR struct nxffs_volume_s *volume)
|
|||||||
* begin the packing operation.
|
* begin the packing operation.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
ret = nxffs_startpos(volume, &pack, iooffset);
|
packed = false;
|
||||||
|
ret = nxffs_startpos(volume, &pack, &iooffset);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
{
|
{
|
||||||
/* This is a normal situation if the volume is full */
|
/* This is a normal situation if the volume is full */
|
||||||
|
|
||||||
if (ret == -ENOSPC)
|
if (ret == -ENOSPC)
|
||||||
{
|
{
|
||||||
return OK;
|
/* In the case where the volume is full, nxffs_startpos() will
|
||||||
|
* recalculate the free FLASH offset and store in in iooffset. There
|
||||||
|
* may be deleted files at the end of FLASH. In this case, we don't
|
||||||
|
* have to pack any files, we simply have to erase FLASH at the end.
|
||||||
|
* But don't do this unless there is some particularly big FLASH
|
||||||
|
* savings (otherwise, we risk wearing out these final blocks).
|
||||||
|
*/
|
||||||
|
|
||||||
|
if (iooffset + CONFIG_NXFFS_TAILTHRESHOLD < volume->froffset)
|
||||||
|
{
|
||||||
|
/* Yes... we can recover CONFIG_NXFFS_TAILTHRESHOLD bytes */
|
||||||
|
|
||||||
|
pack.ioblock = nxffs_getblock(volume, iooffset);
|
||||||
|
pack.iooffset = nxffs_getoffset(volume, iooffset, pack.ioblock);
|
||||||
|
volume->froffset = iooffset;
|
||||||
|
|
||||||
|
/* Setting packed to true will supress all packing operations */
|
||||||
|
|
||||||
|
packed = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Otherwise return OK.. meaning that there is nothing more we can
|
||||||
|
* do to recover FLASH space.
|
||||||
|
*/
|
||||||
|
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return OK;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@ -990,26 +1027,27 @@ int nxffs_pack(FAR struct nxffs_volume_s *volume)
|
|||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
/* Otherwise, begin pack at this src/dest block combination. Initialize
|
||||||
|
* ioblock and iooffset with the position of the first inode header.
|
||||||
|
*/
|
||||||
|
|
||||||
/* Otherwise, begin pack at this src/dest block combination. Initialize
|
pack.ioblock = nxffs_getblock(volume, pack.dest.entry.hoffset);
|
||||||
* ioblock and iooffset with the position of the first inode header.
|
pack.iooffset = nxffs_getoffset(volume, pack.dest.entry.hoffset, pack.ioblock);
|
||||||
*/
|
|
||||||
|
|
||||||
pack.ioblock = nxffs_getblock(volume, pack.dest.entry.hoffset);
|
/* Reserve space for the inode header. Note we are guaranteed by
|
||||||
pack.iooffset = nxffs_getoffset(volume, pack.dest.entry.hoffset, pack.ioblock);
|
* nxffs_startpos() that the inode header will fit at hoffset.
|
||||||
|
*/
|
||||||
|
|
||||||
/* Reserve space for the inode header. Note we are guaranteed by
|
pack.iooffset += SIZEOF_NXFFS_INODE_HDR;
|
||||||
* nxffs_startpos() that the inode header will fit at hoffset.
|
volume->froffset = nxffs_packtell(volume, &pack);
|
||||||
*/
|
}
|
||||||
|
|
||||||
pack.iooffset += SIZEOF_NXFFS_INODE_HDR;
|
|
||||||
volume->froffset = nxffs_packtell(volume, &pack);
|
|
||||||
|
|
||||||
/* Then pack all erase blocks starting with the erase block that contains
|
/* Then pack all erase blocks starting with the erase block that contains
|
||||||
* the ioblock and through the final erase block on the FLASH.
|
* the ioblock and through the final erase block on the FLASH.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
packed = false;
|
|
||||||
for (eblock = pack.ioblock / volume->blkper;
|
for (eblock = pack.ioblock / volume->blkper;
|
||||||
eblock < volume->geo.neraseblocks;
|
eblock < volume->geo.neraseblocks;
|
||||||
eblock++)
|
eblock++)
|
||||||
|
@ -59,14 +59,32 @@
|
|||||||
# error "CONFIG_NXFFS_ERASEDSTATE must be either 0x00 or 0xff"
|
# error "CONFIG_NXFFS_ERASEDSTATE must be either 0x00 or 0xff"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
/* Don't bother trying to pack things closer together than this. */
|
||||||
|
|
||||||
#ifndef CONFIG_NXFFS_PACKTHRESHOLD
|
#ifndef CONFIG_NXFFS_PACKTHRESHOLD
|
||||||
# define CONFIG_NXFFS_PACKTHRESHOLD 32
|
# define CONFIG_NXFFS_PACKTHRESHOLD 32
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
/* This is how big an inode name is permitted to be. */
|
||||||
|
|
||||||
#ifndef CONFIG_NXFFS_MAXNAMLEN
|
#ifndef CONFIG_NXFFS_MAXNAMLEN
|
||||||
# define CONFIG_NXFFS_MAXNAMLEN 255
|
# define CONFIG_NXFFS_MAXNAMLEN 255
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
/* Clean-up can either mean packing files together toward the end of the file
|
||||||
|
* or, if file are deleted at the end of the file, clean up can simply mean
|
||||||
|
* erasing the end of FLASH memory so that it can be re-used again. However,
|
||||||
|
* doing this can also harm the life of the FLASH part because it can mean
|
||||||
|
* that the tail end of the FLASH is re-used too often.
|
||||||
|
*
|
||||||
|
* This threshold determines if/when it is worth erased the tail end of FLASH
|
||||||
|
* and making it available for re-use (and possible over-wear).
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef CONFIG_NXFFS_TAILTHRESHOLD
|
||||||
|
# define CONFIG_NXFFS_TAILTHRESHOLD (8*1024)
|
||||||
|
#endif
|
||||||
|
|
||||||
/* At present, only a single pre-allocated NXFFS volume is supported. This
|
/* At present, only a single pre-allocated NXFFS volume is supported. This
|
||||||
* is because here can be only a single NXFFS volume mounted at any time.
|
* is because here can be only a single NXFFS volume mounted at any time.
|
||||||
* This has to do with the fact that we bind to an MTD driver (instead of a
|
* This has to do with the fact that we bind to an MTD driver (instead of a
|
||||||
|
Loading…
Reference in New Issue
Block a user