forked from Imagelibrary/littlefs
Merge pull request #514 from mon/feature/assert_early_return
lfs_fs_preporphans: return int to alllow graceful LFS_ASSERT
This commit is contained in:
16
.travis.yml
16
.travis.yml
@@ -224,6 +224,22 @@ jobs:
|
||||
# report-size will compile littlefs and report the size
|
||||
script: [*report-size]
|
||||
|
||||
# test compilation with asserts that return -1
|
||||
- stage: test
|
||||
env:
|
||||
- NAME=littlefs-assert-return
|
||||
- CC="arm-linux-gnueabi-gcc --static -mthumb"
|
||||
- CFLAGS="-Werror -D'LFS_ASSERT(test)=do {if(!(test)) {return -1;}} while(0)'"
|
||||
if: branch !~ -prefix$
|
||||
install:
|
||||
- *install-common
|
||||
- sudo apt-get install
|
||||
gcc-arm-linux-gnueabi
|
||||
libc6-dev-armel-cross
|
||||
- arm-linux-gnueabi-gcc --version
|
||||
# report-size will compile littlefs and report the size
|
||||
script: [*report-size]
|
||||
|
||||
# test compilation in thread-safe mode
|
||||
- stage: test
|
||||
env:
|
||||
|
||||
51
lfs.c
51
lfs.c
@@ -467,7 +467,7 @@ static int lfs_file_rawsync(lfs_t *lfs, lfs_file_t *file);
|
||||
static int lfs_file_outline(lfs_t *lfs, lfs_file_t *file);
|
||||
static int lfs_file_flush(lfs_t *lfs, lfs_file_t *file);
|
||||
|
||||
static void lfs_fs_preporphans(lfs_t *lfs, int8_t orphans);
|
||||
static int lfs_fs_preporphans(lfs_t *lfs, int8_t orphans);
|
||||
static void lfs_fs_prepmove(lfs_t *lfs,
|
||||
uint16_t id, const lfs_block_t pair[2]);
|
||||
static int lfs_fs_pred(lfs_t *lfs, const lfs_block_t dir[2],
|
||||
@@ -2066,7 +2066,10 @@ static int lfs_rawmkdir(lfs_t *lfs, const char *path) {
|
||||
// current block end of list?
|
||||
if (cwd.m.split) {
|
||||
// update tails, this creates a desync
|
||||
lfs_fs_preporphans(lfs, +1);
|
||||
err = lfs_fs_preporphans(lfs, +1);
|
||||
if (err) {
|
||||
return err;
|
||||
}
|
||||
|
||||
// it's possible our predecessor has to be relocated, and if
|
||||
// our parent is our predecessor's predecessor, this could have
|
||||
@@ -2086,7 +2089,10 @@ static int lfs_rawmkdir(lfs_t *lfs, const char *path) {
|
||||
}
|
||||
|
||||
lfs->mlist = cwd.next;
|
||||
lfs_fs_preporphans(lfs, -1);
|
||||
err = lfs_fs_preporphans(lfs, -1);
|
||||
if (err) {
|
||||
return err;
|
||||
}
|
||||
}
|
||||
|
||||
// now insert into our parent block
|
||||
@@ -3219,7 +3225,10 @@ static int lfs_rawremove(lfs_t *lfs, const char *path) {
|
||||
}
|
||||
|
||||
// mark fs as orphaned
|
||||
lfs_fs_preporphans(lfs, +1);
|
||||
err = lfs_fs_preporphans(lfs, +1);
|
||||
if (err) {
|
||||
return err;
|
||||
}
|
||||
|
||||
// I know it's crazy but yes, dir can be changed by our parent's
|
||||
// commit (if predecessor is child)
|
||||
@@ -3239,7 +3248,10 @@ static int lfs_rawremove(lfs_t *lfs, const char *path) {
|
||||
lfs->mlist = dir.next;
|
||||
if (lfs_tag_type3(tag) == LFS_TYPE_DIR) {
|
||||
// fix orphan
|
||||
lfs_fs_preporphans(lfs, -1);
|
||||
err = lfs_fs_preporphans(lfs, -1);
|
||||
if (err) {
|
||||
return err;
|
||||
}
|
||||
|
||||
err = lfs_fs_pred(lfs, dir.m.pair, &cwd);
|
||||
if (err) {
|
||||
@@ -3325,7 +3337,10 @@ static int lfs_rawrename(lfs_t *lfs, const char *oldpath, const char *newpath) {
|
||||
}
|
||||
|
||||
// mark fs as orphaned
|
||||
lfs_fs_preporphans(lfs, +1);
|
||||
err = lfs_fs_preporphans(lfs, +1);
|
||||
if (err) {
|
||||
return err;
|
||||
}
|
||||
|
||||
// I know it's crazy but yes, dir can be changed by our parent's
|
||||
// commit (if predecessor is child)
|
||||
@@ -3368,7 +3383,10 @@ static int lfs_rawrename(lfs_t *lfs, const char *oldpath, const char *newpath) {
|
||||
lfs->mlist = prevdir.next;
|
||||
if (prevtag != LFS_ERR_NOENT && lfs_tag_type3(prevtag) == LFS_TYPE_DIR) {
|
||||
// fix orphan
|
||||
lfs_fs_preporphans(lfs, -1);
|
||||
err = lfs_fs_preporphans(lfs, -1);
|
||||
if (err) {
|
||||
return err;
|
||||
}
|
||||
|
||||
err = lfs_fs_pred(lfs, prevdir.m.pair, &newcwd);
|
||||
if (err) {
|
||||
@@ -4001,7 +4019,10 @@ static int lfs_fs_relocate(lfs_t *lfs,
|
||||
|
||||
if (tag != LFS_ERR_NOENT) {
|
||||
// update disk, this creates a desync
|
||||
lfs_fs_preporphans(lfs, +1);
|
||||
int err = lfs_fs_preporphans(lfs, +1);
|
||||
if (err) {
|
||||
return err;
|
||||
}
|
||||
|
||||
// fix pending move in this pair? this looks like an optimization but
|
||||
// is in fact _required_ since relocating may outdate the move.
|
||||
@@ -4018,7 +4039,7 @@ static int lfs_fs_relocate(lfs_t *lfs,
|
||||
}
|
||||
|
||||
lfs_pair_tole32(newpair);
|
||||
int err = lfs_dir_commit(lfs, &parent, LFS_MKATTRS(
|
||||
err = lfs_dir_commit(lfs, &parent, LFS_MKATTRS(
|
||||
{LFS_MKTAG_IF(moveid != 0x3ff,
|
||||
LFS_TYPE_DELETE, moveid, 0), NULL},
|
||||
{tag, newpair}));
|
||||
@@ -4028,7 +4049,10 @@ static int lfs_fs_relocate(lfs_t *lfs,
|
||||
}
|
||||
|
||||
// next step, clean up orphans
|
||||
lfs_fs_preporphans(lfs, -1);
|
||||
err = lfs_fs_preporphans(lfs, -1);
|
||||
if (err) {
|
||||
return err;
|
||||
}
|
||||
}
|
||||
|
||||
// find pred
|
||||
@@ -4067,11 +4091,13 @@ static int lfs_fs_relocate(lfs_t *lfs,
|
||||
#endif
|
||||
|
||||
#ifndef LFS_READONLY
|
||||
static void lfs_fs_preporphans(lfs_t *lfs, int8_t orphans) {
|
||||
static int lfs_fs_preporphans(lfs_t *lfs, int8_t orphans) {
|
||||
LFS_ASSERT(lfs_tag_size(lfs->gstate.tag) > 0 || orphans >= 0);
|
||||
lfs->gstate.tag += orphans;
|
||||
lfs->gstate.tag = ((lfs->gstate.tag & ~LFS_MKTAG(0x800, 0, 0)) |
|
||||
((uint32_t)lfs_gstate_hasorphans(&lfs->gstate) << 31));
|
||||
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -4188,8 +4214,7 @@ static int lfs_fs_deorphan(lfs_t *lfs) {
|
||||
}
|
||||
|
||||
// mark orphans as fixed
|
||||
lfs_fs_preporphans(lfs, -lfs_gstate_getorphans(&lfs->gstate));
|
||||
return 0;
|
||||
return lfs_fs_preporphans(lfs, -lfs_gstate_getorphans(&lfs->gstate));
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
Reference in New Issue
Block a user