ck: Traded ckmeta/ckdata for flag-based ck functions
TLDR: Replaced lfs3_file_ckmeta/ckdata and lfs3_fs_ckmeta/ckdata with
flag based ck functions:
- lfs3_file_ckmeta -> lfs3_file_ck + LFS3_CK_CKMETA
- lfs3_file_ckdata -> lfs3_file_ck + LFS3_CK_CKDATA
- lfs3_fs_ckmeta -> lfs3_fs_ck + LFS3_FSCK_CKMETA
- lfs3_fs_ckdata -> lfs3_fs_ck + LFS3_FSCK_CKDATA
Note lfs3_fs_ck is equivalent to lfs3_fs_gc, but:
1. Performs the work in one call (equivalent to littlefs2's lfs2_fs_gc)
2. Takes flags at call time (like lfs3_mount) instead of cfg time (like
lfs3_fs_gc)
3. Avoids the constant RAM necessary to track incremental GC state
---
Motivation:
I've been thinking: It's a bit weird that users are able to one-shot
janitorial work in lfs3_mount, but there's no equivalent function after
the filesystem is mounted.
Originally this is what lfs3_fs_gc was for, but after adding support for
incremental GC, it made sense to hide lfs3_fs_gc behind the opt-in
LFS3_GC ifdef due to the extra (ironically non-gc-able) state.
In theory lfs3_trv_t fills a bit of the gap, but, without the internal
i_flag handling and traversal restarts, it's a bit hard to use. And
basically requires duplicating said log, which we need anyways for
lfs3_mount!
So ideally we'd add an explicit one-shot GC function, but now lfs3_fs_gc
is taken.
While thinking about alternative names, I realized we can just call this
lfs3_fs_ck and completely replace lfs3_fs_ckmeta/ckdata.
This has some extra benefits:
- Avoids an explosion of ckmeta/ckdata/repairmeta/repairdata functions
- Discourages redundant traversals that could accomplish more work
- Makes it less confusing that ckdata implies ckmeta
---
I also tweaked lfs3_file_ck to match, but note that lfs3_file_ck is
internally very different from lfs3_fs_ck. For one, lfs3_file_ck only
supports "actual" check flags (LFS3_CK_*) vs all gc flags (LFS3_FSCK_*):
lfs3_file_ck:
LFS3_CK_CKMETA 0x00010000 Check metadata checksums
LFS3_CK_CKDATA 0x00020000 Check metadata + data checksums
LFS3_CK_REPAIRMETA* 0x00040000 Repair metadata blocks
LFS3_CK_REPAIRDATA* 0x00080000 Repair metadata + data blocks
* Planned
lfs3_fs_ck:
LFS3_FSCK_MKCONSISTENT 0x00000800 Make the filesystem consistent
LFS3_FSCK_LOOKAHEAD 0x00001000 Repopulate lookahead buffer
LFS3_FSCK_LOOKGBMAP 0x00002000 Repopulate the gbmap
LFS3_FSCK_PREERASE* 0x00004000 Pre-erase unused blocks
LFS3_FSCK_COMPACTMETA 0x00008000 Compact metadata logs
LFS3_FSCK_CKMETA 0x00010000 Check metadata checksums
LFS3_FSCK_CKDATA 0x00020000 Check metadata + data checksums
LFS3_FSCK_REPAIRMETA* 0x00040000 Repair metadata blocks
LFS3_FSCK_REPAIRDATA* 0x00080000 Repair metadata + data blocks
* Planned
As a plus, this also saves a bit of code:
code stack ctx
before: 35968 2280 660
after: 35924 (-0.1%) 2280 (+0.0%) 660 (+0.0%)
code stack ctx
gbmap before: 38828 2296 772
gbmap after: 38812 (-0.0%) 2296 (+0.0%) 772 (+0.0%)
This commit is contained in:
+45
-45
@@ -180,7 +180,7 @@ code = '''
|
||||
|
||||
# test we can detect at least fully clobbered blocks
|
||||
[cases.test_ck_ckmeta_easy]
|
||||
# METHOD=0 => lfs3_fs_ckmeta
|
||||
# METHOD=0 => lfs3_fs_ck
|
||||
# METHOD=1 => lfs3_fs_gc
|
||||
# METHOD=2 => lfs3_trv_read
|
||||
# METHOD=3 => lfs3_mount
|
||||
@@ -268,9 +268,9 @@ code = '''
|
||||
}
|
||||
|
||||
clobbered:;
|
||||
// find clobbered blocks with lfs3_fs_ckmeta
|
||||
// find clobbered blocks with lfs3_fs_ck
|
||||
if (METHOD == 0) {
|
||||
lfs3_fs_ckmeta(&lfs3) => LFS3_ERR_CORRUPT;
|
||||
lfs3_fs_ck(&lfs3, LFS3_FSCK_CKMETA) => LFS3_ERR_CORRUPT;
|
||||
|
||||
// find clobbered blocks with lfs3_fs_gc
|
||||
} else if (METHOD == 1) {
|
||||
@@ -317,7 +317,7 @@ done:;
|
||||
'''
|
||||
|
||||
[cases.test_ck_ckdata_easy]
|
||||
# METHOD=0 => lfs3_fs_ckdata
|
||||
# METHOD=0 => lfs3_fs_ck
|
||||
# METHOD=1 => lfs3_fs_gc
|
||||
# METHOD=2 => lfs3_trv_read
|
||||
# METHOD=3 => lfs3_mount
|
||||
@@ -406,9 +406,9 @@ code = '''
|
||||
}
|
||||
|
||||
clobbered:;
|
||||
// find clobbered blocks with lfs3_fs_ckmeta
|
||||
// find clobbered blocks with lfs3_fs_ck
|
||||
if (METHOD == 0) {
|
||||
lfs3_fs_ckdata(&lfs3) => LFS3_ERR_CORRUPT;
|
||||
lfs3_fs_ck(&lfs3, LFS3_FSCK_CKDATA) => LFS3_ERR_CORRUPT;
|
||||
|
||||
// find clobbered blocks with lfs3_fs_gc
|
||||
} else if (METHOD == 1) {
|
||||
@@ -456,7 +456,7 @@ done:;
|
||||
|
||||
# test some more interesting errors
|
||||
[cases.test_ck_ckmeta_hard]
|
||||
# METHOD=0 => lfs3_fs_ckmeta
|
||||
# METHOD=0 => lfs3_fs_ck
|
||||
# METHOD=1 => lfs3_fs_gc
|
||||
# METHOD=2 => lfs3_trv_read
|
||||
# METHOD=3 => lfs3_mount
|
||||
@@ -550,9 +550,9 @@ code = '''
|
||||
printf("flipping 0x%x.%x+%x\n", badblock, badbit/8, badbit%8);
|
||||
lfs3_emubd_flipbit(CFG, badblock, badbit) => 0;
|
||||
|
||||
// find clobbered blocks with lfs3_fs_ckmeta
|
||||
// find clobbered blocks with lfs3_fs_ck
|
||||
if (METHOD == 0) {
|
||||
int err = lfs3_fs_ckmeta(&lfs3);
|
||||
int err = lfs3_fs_ck(&lfs3, LFS3_FSCK_CKMETA);
|
||||
assert(!err || err == LFS3_ERR_CORRUPT);
|
||||
if (err == LFS3_ERR_CORRUPT) {
|
||||
goto detected;
|
||||
@@ -711,7 +711,7 @@ done:;
|
||||
'''
|
||||
|
||||
[cases.test_ck_ckdata_hard]
|
||||
# METHOD=0 => lfs3_fs_ckdata
|
||||
# METHOD=0 => lfs3_fs_ck
|
||||
# METHOD=1 => lfs3_fs_gc
|
||||
# METHOD=2 => lfs3_trv_read
|
||||
# METHOD=3 => lfs3_mount
|
||||
@@ -806,9 +806,9 @@ code = '''
|
||||
printf("flipping 0x%x.%x+%x\n", badblock, badbit/8, badbit%8);
|
||||
lfs3_emubd_flipbit(CFG, badblock, badbit) => 0;
|
||||
|
||||
// find clobbered blocks with lfs3_fs_ckdata
|
||||
// find clobbered blocks with lfs3_fs_ck
|
||||
if (METHOD == 0) {
|
||||
int err = lfs3_fs_ckdata(&lfs3);
|
||||
int err = lfs3_fs_ck(&lfs3, LFS3_FSCK_CKDATA);
|
||||
assert(!err || err == LFS3_ERR_CORRUPT);
|
||||
if (err == LFS3_ERR_CORRUPT) {
|
||||
goto detected;
|
||||
@@ -971,8 +971,8 @@ done:;
|
||||
|
||||
# test we can detect at least fully clobbered blocks
|
||||
[cases.test_ck_file_ckmeta_easy]
|
||||
# METHOD=0 => lfs3_file_ckmeta
|
||||
# METHOD=1 => lfs3_file_close+open+ckmeta
|
||||
# METHOD=0 => lfs3_file_ck
|
||||
# METHOD=1 => lfs3_file_close+open+ck
|
||||
# METHOD=2 => lfs3_file_close+open
|
||||
defines.METHOD = [0, 1, 2]
|
||||
defines.N = [1, 2, 4, 8, 16, 32, 64]
|
||||
@@ -1042,15 +1042,15 @@ code = '''
|
||||
}
|
||||
|
||||
clobbered:;
|
||||
// find clobbered blocks with lfs3_file_ckmeta
|
||||
// find clobbered blocks with lfs3_file_ck
|
||||
if (METHOD == 0) {
|
||||
lfs3_file_ckmeta(&lfs3, &file) => LFS3_ERR_CORRUPT;
|
||||
lfs3_file_ck(&lfs3, &file, LFS3_CK_CKMETA) => LFS3_ERR_CORRUPT;
|
||||
|
||||
// find clobbered blocks with lfs3_file_close+open+ckmeta
|
||||
// find clobbered blocks with lfs3_file_close+open+ck
|
||||
} else if (METHOD == 1) {
|
||||
lfs3_file_close(&lfs3, &file) => 0;
|
||||
lfs3_file_open(&lfs3, &file, "octopus", LFS3_O_RDONLY) => 0;
|
||||
lfs3_file_ckmeta(&lfs3, &file) => LFS3_ERR_CORRUPT;
|
||||
lfs3_file_ck(&lfs3, &file, LFS3_CK_CKMETA) => LFS3_ERR_CORRUPT;
|
||||
|
||||
// find clobbered blocks with lfs3_file_close+open
|
||||
} else if (METHOD == 2) {
|
||||
@@ -1070,8 +1070,8 @@ done:;
|
||||
'''
|
||||
|
||||
[cases.test_ck_file_ckdata_easy]
|
||||
# METHOD=0 => lfs3_file_ckdata
|
||||
# METHOD=1 => lfs3_file_close+open+ckdata
|
||||
# METHOD=0 => lfs3_file_ck
|
||||
# METHOD=1 => lfs3_file_close+open+ck
|
||||
# METHOD=2 => lfs3_file_close+open
|
||||
defines.METHOD = [0, 1, 2]
|
||||
defines.N = [1, 2, 4, 8, 16, 32, 64]
|
||||
@@ -1142,15 +1142,15 @@ code = '''
|
||||
}
|
||||
|
||||
clobbered:;
|
||||
// find clobbered blocks with lfs3_file_ckmeta
|
||||
// find clobbered blocks with lfs3_file_ck
|
||||
if (METHOD == 0) {
|
||||
lfs3_file_ckdata(&lfs3, &file) => LFS3_ERR_CORRUPT;
|
||||
lfs3_file_ck(&lfs3, &file, LFS3_CK_CKDATA) => LFS3_ERR_CORRUPT;
|
||||
|
||||
// find clobbered blocks with lfs3_file_close+open+ckmeta
|
||||
// find clobbered blocks with lfs3_file_close+open+ck
|
||||
} else if (METHOD == 1) {
|
||||
lfs3_file_close(&lfs3, &file) => 0;
|
||||
lfs3_file_open(&lfs3, &file, "octopus", LFS3_O_RDONLY) => 0;
|
||||
lfs3_file_ckdata(&lfs3, &file) => LFS3_ERR_CORRUPT;
|
||||
lfs3_file_ck(&lfs3, &file, LFS3_CK_CKDATA) => LFS3_ERR_CORRUPT;
|
||||
|
||||
// find clobbered blocks with lfs3_file_close+open
|
||||
} else if (METHOD == 2) {
|
||||
@@ -1172,8 +1172,8 @@ done:;
|
||||
|
||||
# test some more interesting errors
|
||||
[cases.test_ck_file_ckmeta_hard]
|
||||
# METHOD=0 => lfs3_file_ckmeta
|
||||
# METHOD=1 => lfs3_file_close+open+ckmeta
|
||||
# METHOD=0 => lfs3_file_ck
|
||||
# METHOD=1 => lfs3_file_close+open+ck
|
||||
# METHOD=2 => lfs3_file_close+open
|
||||
defines.METHOD = [0, 1, 2]
|
||||
defines.N = [1, 2, 4, 8, 16, 32, 64]
|
||||
@@ -1251,19 +1251,19 @@ code = '''
|
||||
printf("flipping 0x%x.%x+%x\n", badblock, badbit/8, badbit%8);
|
||||
lfs3_emubd_flipbit(CFG, badblock, badbit) => 0;
|
||||
|
||||
// find clobbered blocks with lfs3_file_ckmeta
|
||||
// find clobbered blocks with lfs3_file_ck
|
||||
if (METHOD == 0) {
|
||||
int err = lfs3_file_ckmeta(&lfs3, &file);
|
||||
int err = lfs3_file_ck(&lfs3, &file, LFS3_CK_CKMETA);
|
||||
assert(!err || err == LFS3_ERR_CORRUPT);
|
||||
if (err == LFS3_ERR_CORRUPT) {
|
||||
goto detected;
|
||||
}
|
||||
|
||||
// find clobbered blocks with lfs3_file_close+open+ckmeta
|
||||
// find clobbered blocks with lfs3_file_close+open+ck
|
||||
} else if (METHOD == 1) {
|
||||
lfs3_file_close(&lfs3, &file) => 0;
|
||||
lfs3_file_open(&lfs3, &file, "octopus", LFS3_O_RDONLY) => 0;
|
||||
int err = lfs3_file_ckmeta(&lfs3, &file);
|
||||
int err = lfs3_file_ck(&lfs3, &file, LFS3_CK_CKMETA);
|
||||
assert(!err || err == LFS3_ERR_CORRUPT);
|
||||
if (err == LFS3_ERR_CORRUPT) {
|
||||
goto detected;
|
||||
@@ -1322,8 +1322,8 @@ done:;
|
||||
'''
|
||||
|
||||
[cases.test_ck_file_ckdata_hard]
|
||||
# METHOD=0 => lfs3_file_ckdata
|
||||
# METHOD=1 => lfs3_file_close+open+ckdata
|
||||
# METHOD=0 => lfs3_file_ck
|
||||
# METHOD=1 => lfs3_file_close+open+ck
|
||||
# METHOD=2 => lfs3_file_close+open
|
||||
defines.METHOD = [0, 1, 2]
|
||||
defines.N = [1, 2, 4, 8, 16, 32, 64]
|
||||
@@ -1402,9 +1402,9 @@ code = '''
|
||||
printf("flipping 0x%x.%x+%x\n", badblock, badbit/8, badbit%8);
|
||||
lfs3_emubd_flipbit(CFG, badblock, badbit) => 0;
|
||||
|
||||
// find clobbered blocks with lfs3_file_ckdata
|
||||
// find clobbered blocks with lfs3_file_ck
|
||||
if (METHOD == 0) {
|
||||
int err = lfs3_file_ckdata(&lfs3, &file);
|
||||
int err = lfs3_file_ck(&lfs3, &file, LFS3_CK_CKDATA);
|
||||
assert(!err || err == LFS3_ERR_CORRUPT);
|
||||
if (err == LFS3_ERR_CORRUPT) {
|
||||
goto detected;
|
||||
@@ -1414,7 +1414,7 @@ code = '''
|
||||
} else if (METHOD == 1) {
|
||||
lfs3_file_close(&lfs3, &file) => 0;
|
||||
lfs3_file_open(&lfs3, &file, "octopus", LFS3_O_RDONLY) => 0;
|
||||
int err = lfs3_file_ckdata(&lfs3, &file);
|
||||
int err = lfs3_file_ck(&lfs3, &file, LFS3_CK_CKDATA);
|
||||
assert(!err || err == LFS3_ERR_CORRUPT);
|
||||
if (err == LFS3_ERR_CORRUPT) {
|
||||
goto detected;
|
||||
@@ -2827,14 +2827,14 @@ code = '''
|
||||
|
||||
// run ckdata?
|
||||
if (CKDATA) {
|
||||
int err = lfs3_fs_ckdata(&lfs3);
|
||||
int err = lfs3_fs_ck(&lfs3, LFS3_FSCK_CKDATA);
|
||||
assert(!err || err == LFS3_ERR_CORRUPT);
|
||||
if (err == LFS3_ERR_CORRUPT) {
|
||||
goto corrupt_mounted;
|
||||
}
|
||||
// run ckmeta?
|
||||
} else if (CKMETA && !MTREEONLY) {
|
||||
int err = lfs3_fs_ckmeta(&lfs3);
|
||||
int err = lfs3_fs_ck(&lfs3, LFS3_FSCK_CKMETA);
|
||||
assert(!err || err == LFS3_ERR_CORRUPT);
|
||||
if (err == LFS3_ERR_CORRUPT) {
|
||||
goto corrupt_mounted;
|
||||
@@ -3145,14 +3145,14 @@ code = '''
|
||||
|
||||
// run ckdata?
|
||||
if (CKDATA) {
|
||||
int err = lfs3_fs_ckdata(&lfs3);
|
||||
int err = lfs3_fs_ck(&lfs3, LFS3_FSCK_CKDATA);
|
||||
assert(!err || err == LFS3_ERR_CORRUPT);
|
||||
if (err == LFS3_ERR_CORRUPT) {
|
||||
goto corrupt_mounted;
|
||||
}
|
||||
// run ckmeta?
|
||||
} else if (CKMETA && !MTREEONLY) {
|
||||
int err = lfs3_fs_ckmeta(&lfs3);
|
||||
int err = lfs3_fs_ck(&lfs3, LFS3_FSCK_CKMETA);
|
||||
assert(!err || err == LFS3_ERR_CORRUPT);
|
||||
if (err == LFS3_ERR_CORRUPT) {
|
||||
goto corrupt_mounted;
|
||||
@@ -3561,14 +3561,14 @@ code = '''
|
||||
|
||||
// run ckdata?
|
||||
if (CKDATA) {
|
||||
int err = lfs3_fs_ckdata(&lfs3);
|
||||
int err = lfs3_fs_ck(&lfs3, LFS3_FSCK_CKDATA);
|
||||
assert(!err || err == LFS3_ERR_CORRUPT);
|
||||
if (err == LFS3_ERR_CORRUPT) {
|
||||
goto corrupt_open;
|
||||
}
|
||||
// run ckmeta?
|
||||
} else if (CKMETA && !MTREEONLY) {
|
||||
int err = lfs3_fs_ckmeta(&lfs3);
|
||||
int err = lfs3_fs_ck(&lfs3, LFS3_FSCK_CKMETA);
|
||||
assert(!err || err == LFS3_ERR_CORRUPT);
|
||||
if (err == LFS3_ERR_CORRUPT) {
|
||||
goto corrupt_open;
|
||||
@@ -3846,14 +3846,14 @@ code = '''
|
||||
|
||||
// run ckdata?
|
||||
if (CKDATA) {
|
||||
int err = lfs3_fs_ckdata(&lfs3);
|
||||
int err = lfs3_fs_ck(&lfs3, LFS3_FSCK_CKDATA);
|
||||
assert(!err || err == LFS3_ERR_CORRUPT);
|
||||
if (err == LFS3_ERR_CORRUPT) {
|
||||
goto corrupt_mounted;
|
||||
}
|
||||
// run ckmeta?
|
||||
} else if (CKMETA && !MTREEONLY) {
|
||||
int err = lfs3_fs_ckmeta(&lfs3);
|
||||
int err = lfs3_fs_ck(&lfs3, LFS3_FSCK_CKMETA);
|
||||
assert(!err || err == LFS3_ERR_CORRUPT);
|
||||
if (err == LFS3_ERR_CORRUPT) {
|
||||
goto corrupt_mounted;
|
||||
@@ -4450,14 +4450,14 @@ code = '''
|
||||
|
||||
// run ckdata?
|
||||
if (CKDATA) {
|
||||
int err = lfs3_fs_ckdata(&lfs3);
|
||||
int err = lfs3_fs_ck(&lfs3, LFS3_FSCK_CKDATA);
|
||||
assert(!err || err == LFS3_ERR_CORRUPT);
|
||||
if (err == LFS3_ERR_CORRUPT) {
|
||||
goto corrupt_mounted;
|
||||
}
|
||||
// run ckmeta?
|
||||
} else if (CKMETA && !MTREEONLY) {
|
||||
int err = lfs3_fs_ckmeta(&lfs3);
|
||||
int err = lfs3_fs_ck(&lfs3, LFS3_FSCK_CKMETA);
|
||||
assert(!err || err == LFS3_ERR_CORRUPT);
|
||||
if (err == LFS3_ERR_CORRUPT) {
|
||||
goto corrupt_mounted;
|
||||
|
||||
Reference in New Issue
Block a user