Compare commits

..

1 Commits

Author SHA1 Message Date
Christopher Haster
8bf45c3a29 Fixed issue with writes following a truncate
The problem was not setting the file state correctly after the truncate.
To truncate < size, we end up using the cache to traverse the ctz
skip-list far away from where our file->pos is.

We can leave the last block in the cache in case we're going to append
to the file, but if we do this we need to set up file->block+file->off
to tell use where we are in the file, and set the LFS_F_READING flag to
indicate that our cache contains read data.

Note this is different than the LFS_F_DIRTY, which we need also. The
purpose of the flags are as follows:
- LFS_F_DIRTY - file ctz skip-list branch is out of sync with
  filesystem, need to update metadata
- LFS_F_READING - file cache is in use for reading, need to drop cache
- LFS_F_WRITING - file cache is in use for writing, need to write out
  cache to disk

The difference between flags is subtle but important because read/prog
caches are handled differently. Prog caches have asserts in place to
catch programs without erases (the infamous pcache->block == 0xffffffff
assert).

Though maybe the names deserve an update...

Found by ebinans
2019-05-22 14:46:59 -05:00
28 changed files with 1401 additions and 2035 deletions

View File

@@ -23,20 +23,8 @@ script:
- make test QUIET=1 CFLAGS+="-DLFS_BLOCK_COUNT=1023 -DLFS_LOOKAHEAD_SIZE=256" - make test QUIET=1 CFLAGS+="-DLFS_BLOCK_COUNT=1023 -DLFS_LOOKAHEAD_SIZE=256"
- make clean test QUIET=1 CFLAGS+="-DLFS_INLINE_MAX=0" - make clean test QUIET=1 CFLAGS+="-DLFS_INLINE_MAX=0"
- make clean test QUIET=1 CFLAGS+="-DLFS_EMUBD_ERASE_VALUE=0xff"
- make clean test QUIET=1 CFLAGS+="-DLFS_NO_INTRINSICS" - make clean test QUIET=1 CFLAGS+="-DLFS_NO_INTRINSICS"
# additional configurations that don't support all tests (this should be
# fixed but at the moment it is what it is)
- make test_files QUIET=1
CFLAGS+="-DLFS_READ_SIZE=1 -DLFS_BLOCK_SIZE=4096"
- make test_files QUIET=1
CFLAGS+="-DLFS_READ_SIZE=\(2*1024\) -DLFS_BLOCK_SIZE=\(64*1024\)"
- make test_files QUIET=1
CFLAGS+="-DLFS_READ_SIZE=\(8*1024\) -DLFS_BLOCK_SIZE=\(64*1024\)"
- make test_files QUIET=1
CFLAGS+="-DLFS_READ_SIZE=11 -DLFS_BLOCK_SIZE=704"
# compile and find the code size with the smallest configuration # compile and find the code size with the smallest configuration
- make clean size - make clean size
OBJ="$(ls lfs*.o | tr '\n' ' ')" OBJ="$(ls lfs*.o | tr '\n' ' ')"
@@ -78,10 +66,7 @@ jobs:
- CC="arm-linux-gnueabi-gcc --static -mthumb" - CC="arm-linux-gnueabi-gcc --static -mthumb"
- EXEC="qemu-arm" - EXEC="qemu-arm"
install: install:
- sudo apt-get install - sudo apt-get install gcc-arm-linux-gnueabi qemu-user
gcc-arm-linux-gnueabi
libc6-dev-armel-cross
qemu-user
- arm-linux-gnueabi-gcc --version - arm-linux-gnueabi-gcc --version
- qemu-arm -version - qemu-arm -version
@@ -93,10 +78,7 @@ jobs:
- CC="powerpc-linux-gnu-gcc --static" - CC="powerpc-linux-gnu-gcc --static"
- EXEC="qemu-ppc" - EXEC="qemu-ppc"
install: install:
- sudo apt-get install - sudo apt-get install gcc-powerpc-linux-gnu qemu-user
gcc-powerpc-linux-gnu
libc6-dev-powerpc-cross
qemu-user
- powerpc-linux-gnu-gcc --version - powerpc-linux-gnu-gcc --version
- qemu-ppc -version - qemu-ppc -version
@@ -108,10 +90,9 @@ jobs:
- CC="mips-linux-gnu-gcc --static" - CC="mips-linux-gnu-gcc --static"
- EXEC="qemu-mips" - EXEC="qemu-mips"
install: install:
- sudo apt-get install - sudo add-apt-repository -y "deb http://archive.ubuntu.com/ubuntu/ xenial main universe"
gcc-mips-linux-gnu - sudo apt-get -qq update
libc6-dev-mips-cross - sudo apt-get install gcc-mips-linux-gnu qemu-user
qemu-user
- mips-linux-gnu-gcc --version - mips-linux-gnu-gcc --version
- qemu-mips -version - qemu-mips -version
@@ -123,7 +104,7 @@ jobs:
if: branch !~ -prefix$ if: branch !~ -prefix$
install: install:
- sudo apt-get install libfuse-dev - sudo apt-get install libfuse-dev
- git clone --depth 1 https://github.com/geky/littlefs-fuse -b v2 - git clone --depth 1 https://github.com/geky/littlefs-fuse -b v2-alpha
- fusermount -V - fusermount -V
- gcc --version - gcc --version
before_script: before_script:
@@ -158,7 +139,7 @@ jobs:
if: branch !~ -prefix$ if: branch !~ -prefix$
install: install:
- sudo apt-get install libfuse-dev - sudo apt-get install libfuse-dev
- git clone --depth 1 https://github.com/geky/littlefs-fuse -b v2 v2 - git clone --depth 1 https://github.com/geky/littlefs-fuse -b v2-alpha v2
- git clone --depth 1 https://github.com/geky/littlefs-fuse -b v1 v1 - git clone --depth 1 https://github.com/geky/littlefs-fuse -b v1 v1
- fusermount -V - fusermount -V
- gcc --version - gcc --version
@@ -248,30 +229,34 @@ jobs:
-m "Generated v$LFS_VERSION_MAJOR prefixes") -m "Generated v$LFS_VERSION_MAJOR prefixes")
git reset --hard git reset --hard
# Update major version branches (vN and vN-prefix) # Update major version branches (vN and vN-prefix)
git push --atomic https://$GEKY_BOT_RELEASES@github.com/$TRAVIS_REPO_SLUG.git \ git push https://$GEKY_BOT_RELEASES@github.com/$TRAVIS_REPO_SLUG.git \
v$LFS_VERSION_MAJOR \ v$LFS_VERSION_MAJOR \
v$LFS_VERSION_MAJOR-prefix v$LFS_VERSION_MAJOR-prefix
# Create patch version tag (vN.N.N)
curl -f -u "$GEKY_BOT_RELEASES" -X POST \
https://api.github.com/repos/$TRAVIS_REPO_SLUG/git/refs \
-d "{
\"ref\": \"refs/tags/$LFS_VERSION\",
\"sha\": \"$TRAVIS_COMMIT\"
}"
# Create minor release?
[[ "$LFS_VERSION" == *.0 ]] || exit 0
# Build release notes # Build release notes
PREV=$(git tag --sort=-v:refname -l "v*" | head -1) PREV=$(git tag --sort=-v:refname -l "v*.0" | head -1)
if [ ! -z "$PREV" ] if [ ! -z "$PREV" ]
then then
echo "PREV $PREV" echo "PREV $PREV"
CHANGES=$(git log --oneline $PREV.. --grep='^Merge' --invert-grep) CHANGES=$'### Changes\n\n'$( \
git log --oneline $PREV.. --grep='^Merge' --invert-grep)
printf "CHANGES\n%s\n\n" "$CHANGES" printf "CHANGES\n%s\n\n" "$CHANGES"
fi fi
case ${GEKY_BOT_DRAFT:-minor} in # Create the release
true) DRAFT=true ;;
minor) DRAFT=$(jq -R 'endswith(".0")' <<< "$LFS_VERSION") ;;
false) DRAFT=false ;;
esac
# Create the release and patch version tag (vN.N.N)
curl -f -u "$GEKY_BOT_RELEASES" -X POST \ curl -f -u "$GEKY_BOT_RELEASES" -X POST \
https://api.github.com/repos/$TRAVIS_REPO_SLUG/releases \ https://api.github.com/repos/$TRAVIS_REPO_SLUG/releases \
-d "{ -d "{
\"tag_name\": \"$LFS_VERSION\", \"tag_name\": \"$LFS_VERSION\",
\"name\": \"${LFS_VERSION%.0}\", \"name\": \"${LFS_VERSION%.0}\",
\"target_commitish\": \"$TRAVIS_COMMIT\", \"draft\": true,
\"draft\": $DRAFT,
\"body\": $(jq -sR '.' <<< "$CHANGES") \"body\": $(jq -sR '.' <<< "$CHANGES")
}" #" }" #"
SCRIPT SCRIPT

View File

@@ -24,12 +24,9 @@ endif
ifdef WORD ifdef WORD
override CFLAGS += -m$(WORD) override CFLAGS += -m$(WORD)
endif endif
ifdef TRACE
override CFLAGS += -DLFS_YES_TRACE
endif
override CFLAGS += -I. override CFLAGS += -I.
override CFLAGS += -std=c99 -Wall -pedantic override CFLAGS += -std=c99 -Wall -pedantic
override CFLAGS += -Wextra -Wshadow -Wjump-misses-init -Wundef override CFLAGS += -Wextra -Wshadow -Wjump-misses-init
# Remove missing-field-initializers because of GCC bug # Remove missing-field-initializers because of GCC bug
override CFLAGS += -Wno-missing-field-initializers override CFLAGS += -Wno-missing-field-initializers
@@ -42,25 +39,14 @@ size: $(OBJ)
$(SIZE) -t $^ $(SIZE) -t $^
.SUFFIXES: .SUFFIXES:
test: \ test: test_format test_dirs test_files test_seek test_truncate \
test_format \ test_entries test_interspersed test_alloc test_paths test_attrs \
test_dirs \ test_move test_orphan test_corrupt
test_files \
test_seek \
test_truncate \
test_entries \
test_interspersed \
test_alloc \
test_paths \
test_attrs \
test_move \
test_orphan \
test_corrupt
@rm test.c @rm test.c
test_%: tests/test_%.sh test_%: tests/test_%.sh
ifdef QUIET ifdef QUIET
@./$< | sed -nu '/^[-=]/p' @./$< | sed -n '/^[-=]/p'
else else
./$< ./$<
endif endif

View File

@@ -11,6 +11,7 @@
#include <stdlib.h> #include <stdlib.h>
#include <stdio.h> #include <stdio.h>
#include <limits.h> #include <limits.h>
#include <dirent.h>
#include <sys/stat.h> #include <sys/stat.h>
#include <unistd.h> #include <unistd.h>
#include <assert.h> #include <assert.h>
@@ -54,15 +55,6 @@ static inline void lfs_emubd_fromle32(lfs_emubd_t *emu) {
// Block device emulated on existing filesystem // Block device emulated on existing filesystem
int lfs_emubd_create(const struct lfs_config *cfg, const char *path) { int lfs_emubd_create(const struct lfs_config *cfg, const char *path) {
LFS_TRACE("lfs_emubd_create(%p {.context=%p, "
".read=%p, .prog=%p, .erase=%p, .sync=%p, "
".read_size=%"PRIu32", .prog_size=%"PRIu32", "
".block_size=%"PRIu32", .block_count=%"PRIu32"}, \"%s\")",
(void*)cfg, cfg->context,
(void*)(uintptr_t)cfg->read, (void*)(uintptr_t)cfg->prog,
(void*)(uintptr_t)cfg->erase, (void*)(uintptr_t)cfg->sync,
cfg->read_size, cfg->prog_size, cfg->block_size, cfg->block_count,
path);
lfs_emubd_t *emu = cfg->context; lfs_emubd_t *emu = cfg->context;
emu->cfg.read_size = cfg->read_size; emu->cfg.read_size = cfg->read_size;
emu->cfg.prog_size = cfg->prog_size; emu->cfg.prog_size = cfg->prog_size;
@@ -73,9 +65,7 @@ int lfs_emubd_create(const struct lfs_config *cfg, const char *path) {
size_t pathlen = strlen(path); size_t pathlen = strlen(path);
emu->path = malloc(pathlen + 1 + LFS_NAME_MAX + 1); emu->path = malloc(pathlen + 1 + LFS_NAME_MAX + 1);
if (!emu->path) { if (!emu->path) {
int err = -ENOMEM; return -ENOMEM;
LFS_TRACE("lfs_emubd_create -> %"PRId32, err);
return err;
} }
strcpy(emu->path, path); strcpy(emu->path, path);
@@ -86,30 +76,24 @@ int lfs_emubd_create(const struct lfs_config *cfg, const char *path) {
// Create directory if it doesn't exist // Create directory if it doesn't exist
int err = mkdir(path, 0777); int err = mkdir(path, 0777);
if (err && errno != EEXIST) { if (err && errno != EEXIST) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_create -> %"PRId32, err);
return err;
} }
// Load stats to continue incrementing // Load stats to continue incrementing
snprintf(emu->child, LFS_NAME_MAX, ".stats"); snprintf(emu->child, LFS_NAME_MAX, ".stats");
FILE *f = fopen(emu->path, "r"); FILE *f = fopen(emu->path, "r");
if (!f) { if (!f) {
memset(&emu->stats, LFS_EMUBD_ERASE_VALUE, sizeof(emu->stats)); memset(&emu->stats, 0, sizeof(emu->stats));
} else { } else {
size_t res = fread(&emu->stats, sizeof(emu->stats), 1, f); size_t res = fread(&emu->stats, sizeof(emu->stats), 1, f);
lfs_emubd_fromle32(emu); lfs_emubd_fromle32(emu);
if (res < 1) { if (res < 1) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_create -> %"PRId32, err);
return err;
} }
err = fclose(f); err = fclose(f);
if (err) { if (err) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_create -> %"PRId32, err);
return err;
} }
} }
@@ -122,36 +106,27 @@ int lfs_emubd_create(const struct lfs_config *cfg, const char *path) {
size_t res = fread(&emu->history, sizeof(emu->history), 1, f); size_t res = fread(&emu->history, sizeof(emu->history), 1, f);
lfs_emubd_fromle32(emu); lfs_emubd_fromle32(emu);
if (res < 1) { if (res < 1) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_create -> %"PRId32, err);
return err;
} }
err = fclose(f); err = fclose(f);
if (err) { if (err) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_create -> %"PRId32, err);
return err;
} }
} }
LFS_TRACE("lfs_emubd_create -> %"PRId32, 0);
return 0; return 0;
} }
void lfs_emubd_destroy(const struct lfs_config *cfg) { void lfs_emubd_destroy(const struct lfs_config *cfg) {
LFS_TRACE("lfs_emubd_destroy(%p)", (void*)cfg);
lfs_emubd_sync(cfg); lfs_emubd_sync(cfg);
lfs_emubd_t *emu = cfg->context; lfs_emubd_t *emu = cfg->context;
free(emu->path); free(emu->path);
LFS_TRACE("lfs_emubd_destroy -> %s", "void");
} }
int lfs_emubd_read(const struct lfs_config *cfg, lfs_block_t block, int lfs_emubd_read(const struct lfs_config *cfg, lfs_block_t block,
lfs_off_t off, void *buffer, lfs_size_t size) { lfs_off_t off, void *buffer, lfs_size_t size) {
LFS_TRACE("lfs_emubd_read(%p, 0x%"PRIx32", %"PRIu32", %p, %"PRIu32")",
(void*)cfg, block, off, buffer, size);
lfs_emubd_t *emu = cfg->context; lfs_emubd_t *emu = cfg->context;
uint8_t *data = buffer; uint8_t *data = buffer;
@@ -168,43 +143,32 @@ int lfs_emubd_read(const struct lfs_config *cfg, lfs_block_t block,
FILE *f = fopen(emu->path, "rb"); FILE *f = fopen(emu->path, "rb");
if (!f && errno != ENOENT) { if (!f && errno != ENOENT) {
int err = -errno; return -errno;
LFS_TRACE("lfs_emubd_read -> %d", err);
return err;
} }
if (f) { if (f) {
int err = fseek(f, off, SEEK_SET); int err = fseek(f, off, SEEK_SET);
if (err) { if (err) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_read -> %d", err);
return err;
} }
size_t res = fread(data, 1, size, f); size_t res = fread(data, 1, size, f);
if (res < size && !feof(f)) { if (res < size && !feof(f)) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_read -> %d", err);
return err;
} }
err = fclose(f); err = fclose(f);
if (err) { if (err) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_read -> %d", err);
return err;
} }
} }
emu->stats.read_count += size; emu->stats.read_count += 1;
LFS_TRACE("lfs_emubd_read -> %d", 0);
return 0; return 0;
} }
int lfs_emubd_prog(const struct lfs_config *cfg, lfs_block_t block, int lfs_emubd_prog(const struct lfs_config *cfg, lfs_block_t block,
lfs_off_t off, const void *buffer, lfs_size_t size) { lfs_off_t off, const void *buffer, lfs_size_t size) {
LFS_TRACE("lfs_emubd_prog(%p, 0x%"PRIx32", %"PRIu32", %p, %"PRIu32")",
(void*)cfg, block, off, buffer, size);
lfs_emubd_t *emu = cfg->context; lfs_emubd_t *emu = cfg->context;
const uint8_t *data = buffer; const uint8_t *data = buffer;
@@ -218,9 +182,7 @@ int lfs_emubd_prog(const struct lfs_config *cfg, lfs_block_t block,
FILE *f = fopen(emu->path, "r+b"); FILE *f = fopen(emu->path, "r+b");
if (!f) { if (!f) {
int err = (errno == EACCES) ? 0 : -errno; return (errno == EACCES) ? 0 : -errno;
LFS_TRACE("lfs_emubd_prog -> %d", err);
return err;
} }
// Check that file was erased // Check that file was erased
@@ -228,54 +190,42 @@ int lfs_emubd_prog(const struct lfs_config *cfg, lfs_block_t block,
int err = fseek(f, off, SEEK_SET); int err = fseek(f, off, SEEK_SET);
if (err) { if (err) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_prog -> %d", err);
return err;
} }
size_t res = fwrite(data, 1, size, f); size_t res = fwrite(data, 1, size, f);
if (res < size) { if (res < size) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_prog -> %d", err);
return err;
} }
err = fseek(f, off, SEEK_SET); err = fseek(f, off, SEEK_SET);
if (err) { if (err) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_prog -> %d", err);
return err;
} }
uint8_t dat; uint8_t dat;
res = fread(&dat, 1, 1, f); res = fread(&dat, 1, 1, f);
if (res < 1) { if (res < 1) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_prog -> %d", err);
return err;
} }
err = fclose(f); err = fclose(f);
if (err) { if (err) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_prog -> %d", err);
return err;
} }
// update history and stats // update history and stats
if (block != emu->history.blocks[0]) { if (block != emu->history.blocks[0]) {
memmove(&emu->history.blocks[1], &emu->history.blocks[0], memcpy(&emu->history.blocks[1], &emu->history.blocks[0],
sizeof(emu->history) - sizeof(emu->history.blocks[0])); sizeof(emu->history) - sizeof(emu->history.blocks[0]));
emu->history.blocks[0] = block; emu->history.blocks[0] = block;
} }
emu->stats.prog_count += size; emu->stats.prog_count += 1;
LFS_TRACE("lfs_emubd_prog -> %d", 0);
return 0; return 0;
} }
int lfs_emubd_erase(const struct lfs_config *cfg, lfs_block_t block) { int lfs_emubd_erase(const struct lfs_config *cfg, lfs_block_t block) {
LFS_TRACE("lfs_emubd_erase(%p, 0x%"PRIx32")", (void*)cfg, block);
lfs_emubd_t *emu = cfg->context; lfs_emubd_t *emu = cfg->context;
// Check if erase is valid // Check if erase is valid
@@ -286,118 +236,89 @@ int lfs_emubd_erase(const struct lfs_config *cfg, lfs_block_t block) {
struct stat st; struct stat st;
int err = stat(emu->path, &st); int err = stat(emu->path, &st);
if (err && errno != ENOENT) { if (err && errno != ENOENT) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_erase -> %d", err);
return err;
} }
if (!err && S_ISREG(st.st_mode) && (S_IWUSR & st.st_mode)) { if (!err && S_ISREG(st.st_mode) && (S_IWUSR & st.st_mode)) {
err = unlink(emu->path); err = unlink(emu->path);
if (err) { if (err) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_erase -> %d", err);
return err;
} }
} }
if (err || (S_ISREG(st.st_mode) && (S_IWUSR & st.st_mode))) { if (err || (S_ISREG(st.st_mode) && (S_IWUSR & st.st_mode))) {
FILE *f = fopen(emu->path, "w"); FILE *f = fopen(emu->path, "w");
if (!f) { if (!f) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_erase -> %d", err);
return err;
} }
err = fclose(f); err = fclose(f);
if (err) { if (err) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_erase -> %d", err);
return err;
} }
} }
emu->stats.erase_count += cfg->block_size; emu->stats.erase_count += 1;
LFS_TRACE("lfs_emubd_erase -> %d", 0);
return 0; return 0;
} }
int lfs_emubd_sync(const struct lfs_config *cfg) { int lfs_emubd_sync(const struct lfs_config *cfg) {
LFS_TRACE("lfs_emubd_sync(%p)", (void*)cfg);
lfs_emubd_t *emu = cfg->context; lfs_emubd_t *emu = cfg->context;
// Just write out info/stats for later lookup // Just write out info/stats for later lookup
snprintf(emu->child, LFS_NAME_MAX, ".config"); snprintf(emu->child, LFS_NAME_MAX, ".config");
FILE *f = fopen(emu->path, "w"); FILE *f = fopen(emu->path, "w");
if (!f) { if (!f) {
int err = -errno; return -errno;
LFS_TRACE("lfs_emubd_sync -> %d", err);
return err;
} }
lfs_emubd_tole32(emu); lfs_emubd_tole32(emu);
size_t res = fwrite(&emu->cfg, sizeof(emu->cfg), 1, f); size_t res = fwrite(&emu->cfg, sizeof(emu->cfg), 1, f);
lfs_emubd_fromle32(emu); lfs_emubd_fromle32(emu);
if (res < 1) { if (res < 1) {
int err = -errno; return -errno;
LFS_TRACE("lfs_emubd_sync -> %d", err);
return err;
} }
int err = fclose(f); int err = fclose(f);
if (err) { if (err) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_sync -> %d", err);
return err;
} }
snprintf(emu->child, LFS_NAME_MAX, ".stats"); snprintf(emu->child, LFS_NAME_MAX, ".stats");
f = fopen(emu->path, "w"); f = fopen(emu->path, "w");
if (!f) { if (!f) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_sync -> %d", err);
return err;
} }
lfs_emubd_tole32(emu); lfs_emubd_tole32(emu);
res = fwrite(&emu->stats, sizeof(emu->stats), 1, f); res = fwrite(&emu->stats, sizeof(emu->stats), 1, f);
lfs_emubd_fromle32(emu); lfs_emubd_fromle32(emu);
if (res < 1) { if (res < 1) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_sync -> %d", err);
return err;
} }
err = fclose(f); err = fclose(f);
if (err) { if (err) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_sync -> %d", err);
return err;
} }
snprintf(emu->child, LFS_NAME_MAX, ".history"); snprintf(emu->child, LFS_NAME_MAX, ".history");
f = fopen(emu->path, "w"); f = fopen(emu->path, "w");
if (!f) { if (!f) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_sync -> %d", err);
return err;
} }
lfs_emubd_tole32(emu); lfs_emubd_tole32(emu);
res = fwrite(&emu->history, sizeof(emu->history), 1, f); res = fwrite(&emu->history, sizeof(emu->history), 1, f);
lfs_emubd_fromle32(emu); lfs_emubd_fromle32(emu);
if (res < 1) { if (res < 1) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_sync -> %d", err);
return err;
} }
err = fclose(f); err = fclose(f);
if (err) { if (err) {
err = -errno; return -errno;
LFS_TRACE("lfs_emubd_sync -> %d", err);
return err;
} }
LFS_TRACE("lfs_emubd_sync -> %d", 0);
return 0; return 0;
} }

View File

@@ -17,8 +17,20 @@ extern "C"
// Config options // Config options
#ifndef LFS_EMUBD_ERASE_VALUE #ifndef LFS_EMUBD_READ_SIZE
#define LFS_EMUBD_ERASE_VALUE 0x00 #define LFS_EMUBD_READ_SIZE 1
#endif
#ifndef LFS_EMUBD_PROG_SIZE
#define LFS_EMUBD_PROG_SIZE 1
#endif
#ifndef LFS_EMUBD_ERASE_SIZE
#define LFS_EMUBD_ERASE_SIZE 512
#endif
#ifndef LFS_EMUBD_TOTAL_SIZE
#define LFS_EMUBD_TOTAL_SIZE 524288
#endif #endif

643
lfs.c

File diff suppressed because it is too large Load Diff

21
lfs.h
View File

@@ -21,7 +21,7 @@ extern "C"
// Software library version // Software library version
// Major (top-nibble), incremented on backwards incompatible changes // Major (top-nibble), incremented on backwards incompatible changes
// Minor (bottom-nibble), incremented on feature additions // Minor (bottom-nibble), incremented on feature additions
#define LFS_VERSION 0x00020001 #define LFS_VERSION 0x00020000
#define LFS_VERSION_MAJOR (0xffff & (LFS_VERSION >> 16)) #define LFS_VERSION_MAJOR (0xffff & (LFS_VERSION >> 16))
#define LFS_VERSION_MINOR (0xffff & (LFS_VERSION >> 0)) #define LFS_VERSION_MINOR (0xffff & (LFS_VERSION >> 0))
@@ -136,7 +136,6 @@ enum lfs_open_flags {
LFS_F_READING = 0x040000, // File has been read since last flush LFS_F_READING = 0x040000, // File has been read since last flush
LFS_F_ERRED = 0x080000, // An error occured during write LFS_F_ERRED = 0x080000, // An error occured during write
LFS_F_INLINE = 0x100000, // Currently inlined in directory entry LFS_F_INLINE = 0x100000, // Currently inlined in directory entry
LFS_F_OPENED = 0x200000, // File has been opened
}; };
// File seek flags // File seek flags
@@ -191,13 +190,9 @@ struct lfs_config {
// Number of erasable blocks on the device. // Number of erasable blocks on the device.
lfs_size_t block_count; lfs_size_t block_count;
// Number of erase cycles before littlefs evicts metadata logs and moves // Number of erase cycles before we should move data to another block.
// the metadata to another block. Suggested values are in the // May be zero, in which case no block-level wear-leveling is performed.
// range 100-1000, with large values having better performance at the cost uint32_t block_cycles;
// of less consistent wear distribution.
//
// Set to -1 to disable block-level wear-leveling.
int32_t block_cycles;
// Size of block caches. Each cache buffers a portion of a block in RAM. // Size of block caches. Each cache buffers a portion of a block in RAM.
// The littlefs needs a read cache, a program cache, and one additional // The littlefs needs a read cache, a program cache, and one additional
@@ -209,7 +204,7 @@ struct lfs_config {
// Size of the lookahead buffer in bytes. A larger lookahead buffer // Size of the lookahead buffer in bytes. A larger lookahead buffer
// increases the number of blocks found during an allocation pass. The // increases the number of blocks found during an allocation pass. The
// lookahead buffer is stored as a compact bitmap, so each byte of RAM // lookahead buffer is stored as a compact bitmap, so each byte of RAM
// can track 8 blocks. Must be a multiple of 8. // can track 8 blocks. Must be a multiple of 4.
lfs_size_t lookahead_size; lfs_size_t lookahead_size;
// Optional statically allocated read buffer. Must be cache_size. // Optional statically allocated read buffer. Must be cache_size.
@@ -221,7 +216,7 @@ struct lfs_config {
void *prog_buffer; void *prog_buffer;
// Optional statically allocated lookahead buffer. Must be lookahead_size // Optional statically allocated lookahead buffer. Must be lookahead_size
// and aligned to a 32-bit boundary. By default lfs_malloc is used to // and aligned to a 64-bit boundary. By default lfs_malloc is used to
// allocate this buffer. // allocate this buffer.
void *lookahead_buffer; void *lookahead_buffer;
@@ -533,7 +528,7 @@ lfs_ssize_t lfs_file_write(lfs_t *lfs, lfs_file_t *file,
// Change the position of the file // Change the position of the file
// //
// The change in position is determined by the offset and whence flag. // The change in position is determined by the offset and whence flag.
// Returns the new position of the file, or a negative error code on failure. // Returns the old position of the file, or a negative error code on failure.
lfs_soff_t lfs_file_seek(lfs_t *lfs, lfs_file_t *file, lfs_soff_t lfs_file_seek(lfs_t *lfs, lfs_file_t *file,
lfs_soff_t off, int whence); lfs_soff_t off, int whence);
@@ -550,7 +545,7 @@ lfs_soff_t lfs_file_tell(lfs_t *lfs, lfs_file_t *file);
// Change the position of the file to the beginning of the file // Change the position of the file to the beginning of the file
// //
// Equivalent to lfs_file_seek(lfs, file, 0, LFS_SEEK_SET) // Equivalent to lfs_file_seek(lfs, file, 0, LFS_SEEK_CUR)
// Returns a negative error code on failure. // Returns a negative error code on failure.
int lfs_file_rewind(lfs_t *lfs, lfs_file_t *file); int lfs_file_rewind(lfs_t *lfs, lfs_file_t *file);

View File

@@ -31,10 +31,7 @@
#ifndef LFS_NO_ASSERT #ifndef LFS_NO_ASSERT
#include <assert.h> #include <assert.h>
#endif #endif
#if !defined(LFS_NO_DEBUG) || \ #if !defined(LFS_NO_DEBUG) || !defined(LFS_NO_WARN) || !defined(LFS_NO_ERROR)
!defined(LFS_NO_WARN) || \
!defined(LFS_NO_ERROR) || \
defined(LFS_YES_TRACE)
#include <stdio.h> #include <stdio.h>
#endif #endif
@@ -49,30 +46,23 @@ extern "C"
// code footprint // code footprint
// Logging functions // Logging functions
#ifdef LFS_YES_TRACE
#define LFS_TRACE(fmt, ...) \
printf("lfs_trace:%d: " fmt "\n", __LINE__, __VA_ARGS__)
#else
#define LFS_TRACE(fmt, ...)
#endif
#ifndef LFS_NO_DEBUG #ifndef LFS_NO_DEBUG
#define LFS_DEBUG(fmt, ...) \ #define LFS_DEBUG(fmt, ...) \
printf("lfs_debug:%d: " fmt "\n", __LINE__, __VA_ARGS__) printf("lfs debug:%d: " fmt "\n", __LINE__, __VA_ARGS__)
#else #else
#define LFS_DEBUG(fmt, ...) #define LFS_DEBUG(fmt, ...)
#endif #endif
#ifndef LFS_NO_WARN #ifndef LFS_NO_WARN
#define LFS_WARN(fmt, ...) \ #define LFS_WARN(fmt, ...) \
printf("lfs_warn:%d: " fmt "\n", __LINE__, __VA_ARGS__) printf("lfs warn:%d: " fmt "\n", __LINE__, __VA_ARGS__)
#else #else
#define LFS_WARN(fmt, ...) #define LFS_WARN(fmt, ...)
#endif #endif
#ifndef LFS_NO_ERROR #ifndef LFS_NO_ERROR
#define LFS_ERROR(fmt, ...) \ #define LFS_ERROR(fmt, ...) \
printf("lfs_error:%d: " fmt "\n", __LINE__, __VA_ARGS__) printf("lfs error:%d: " fmt "\n", __LINE__, __VA_ARGS__)
#else #else
#define LFS_ERROR(fmt, ...) #define LFS_ERROR(fmt, ...)
#endif #endif
@@ -153,14 +143,14 @@ static inline int lfs_scmp(uint32_t a, uint32_t b) {
// Convert between 32-bit little-endian and native order // Convert between 32-bit little-endian and native order
static inline uint32_t lfs_fromle32(uint32_t a) { static inline uint32_t lfs_fromle32(uint32_t a) {
#if !defined(LFS_NO_INTRINSICS) && ( \ #if !defined(LFS_NO_INTRINSICS) && ( \
(defined( BYTE_ORDER ) && defined( ORDER_LITTLE_ENDIAN ) && BYTE_ORDER == ORDER_LITTLE_ENDIAN ) || \ (defined( BYTE_ORDER ) && BYTE_ORDER == ORDER_LITTLE_ENDIAN ) || \
(defined(__BYTE_ORDER ) && defined(__ORDER_LITTLE_ENDIAN ) && __BYTE_ORDER == __ORDER_LITTLE_ENDIAN ) || \ (defined(__BYTE_ORDER ) && __BYTE_ORDER == __ORDER_LITTLE_ENDIAN ) || \
(defined(__BYTE_ORDER__) && defined(__ORDER_LITTLE_ENDIAN__) && __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__)) (defined(__BYTE_ORDER__) && __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__))
return a; return a;
#elif !defined(LFS_NO_INTRINSICS) && ( \ #elif !defined(LFS_NO_INTRINSICS) && ( \
(defined( BYTE_ORDER ) && defined( ORDER_BIG_ENDIAN ) && BYTE_ORDER == ORDER_BIG_ENDIAN ) || \ (defined( BYTE_ORDER ) && BYTE_ORDER == ORDER_BIG_ENDIAN ) || \
(defined(__BYTE_ORDER ) && defined(__ORDER_BIG_ENDIAN ) && __BYTE_ORDER == __ORDER_BIG_ENDIAN ) || \ (defined(__BYTE_ORDER ) && __BYTE_ORDER == __ORDER_BIG_ENDIAN ) || \
(defined(__BYTE_ORDER__) && defined(__ORDER_BIG_ENDIAN__) && __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__)) (defined(__BYTE_ORDER__) && __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__))
return __builtin_bswap32(a); return __builtin_bswap32(a);
#else #else
return (((uint8_t*)&a)[0] << 0) | return (((uint8_t*)&a)[0] << 0) |
@@ -177,14 +167,14 @@ static inline uint32_t lfs_tole32(uint32_t a) {
// Convert between 32-bit big-endian and native order // Convert between 32-bit big-endian and native order
static inline uint32_t lfs_frombe32(uint32_t a) { static inline uint32_t lfs_frombe32(uint32_t a) {
#if !defined(LFS_NO_INTRINSICS) && ( \ #if !defined(LFS_NO_INTRINSICS) && ( \
(defined( BYTE_ORDER ) && defined( ORDER_LITTLE_ENDIAN ) && BYTE_ORDER == ORDER_LITTLE_ENDIAN ) || \ (defined( BYTE_ORDER ) && BYTE_ORDER == ORDER_LITTLE_ENDIAN ) || \
(defined(__BYTE_ORDER ) && defined(__ORDER_LITTLE_ENDIAN ) && __BYTE_ORDER == __ORDER_LITTLE_ENDIAN ) || \ (defined(__BYTE_ORDER ) && __BYTE_ORDER == __ORDER_LITTLE_ENDIAN ) || \
(defined(__BYTE_ORDER__) && defined(__ORDER_LITTLE_ENDIAN__) && __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__)) (defined(__BYTE_ORDER__) && __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__))
return __builtin_bswap32(a); return __builtin_bswap32(a);
#elif !defined(LFS_NO_INTRINSICS) && ( \ #elif !defined(LFS_NO_INTRINSICS) && ( \
(defined( BYTE_ORDER ) && defined( ORDER_BIG_ENDIAN ) && BYTE_ORDER == ORDER_BIG_ENDIAN ) || \ (defined( BYTE_ORDER ) && BYTE_ORDER == ORDER_BIG_ENDIAN ) || \
(defined(__BYTE_ORDER ) && defined(__ORDER_BIG_ENDIAN ) && __BYTE_ORDER == __ORDER_BIG_ENDIAN ) || \ (defined(__BYTE_ORDER ) && __BYTE_ORDER == __ORDER_BIG_ENDIAN ) || \
(defined(__BYTE_ORDER__) && defined(__ORDER_BIG_ENDIAN__) && __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__)) (defined(__BYTE_ORDER__) && __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__))
return a; return a;
#else #else
return (((uint8_t*)&a)[0] << 24) | return (((uint8_t*)&a)[0] << 24) |

View File

@@ -1,4 +1,4 @@
#!/usr/bin/env python2 #!/usr/bin/env python
# This script replaces prefixes of files, and symbols in that file. # This script replaces prefixes of files, and symbols in that file.
# Useful for creating different versions of the codebase that don't # Useful for creating different versions of the codebase that don't

View File

@@ -1,28 +0,0 @@
#!/usr/bin/env python2
import struct
import sys
import time
import os
import re
def main():
with open('blocks/.config') as file:
read_size, prog_size, block_size, block_count = (
struct.unpack('<LLLL', file.read()))
real_size = sum(
os.path.getsize(os.path.join('blocks', f))
for f in os.listdir('blocks') if re.match('\d+', f))
with open('blocks/.stats') as file:
read_count, prog_count, erase_count = (
struct.unpack('<QQQ', file.read()))
runtime = time.time() - os.stat('blocks').st_ctime
print 'results: %dB %dB %dB %.3fs' % (
read_count, prog_count, erase_count, runtime)
if __name__ == "__main__":
main(*sys.argv[1:])

View File

@@ -1,81 +0,0 @@
#!/usr/bin/env python2
import re
import sys
import subprocess
import os
def generate(test):
with open("scripts/template.fmt") as file:
template = file.read()
haslines = 'TEST_LINE' in os.environ and 'TEST_FILE' in os.environ
lines = []
for offset, line in enumerate(
re.split('(?<=(?:.;| [{}]))\n', test.read())):
match = re.match('((?: *\n)*)( *)(.*)=>(.*);',
line, re.DOTALL | re.MULTILINE)
if match:
preface, tab, test, expect = match.groups()
lines.extend(['']*preface.count('\n'))
lines.append(tab+'test_assert({test}, {expect});'.format(
test=test.strip(), expect=expect.strip()))
else:
lines.append(line)
# Create test file
with open('test.c', 'w') as file:
if 'TEST_LINE' in os.environ and 'TEST_FILE' in os.environ:
lines.insert(0, '#line %d "%s"' % (
int(os.environ['TEST_LINE']) + 1,
os.environ['TEST_FILE']))
lines.append('#line %d "test.c"' % (
template[:template.find('{tests}')].count('\n')
+ len(lines) + 2))
file.write(template.format(tests='\n'.join(lines)))
# Remove build artifacts to force rebuild
try:
os.remove('test.o')
os.remove('lfs')
except OSError:
pass
def compile():
subprocess.check_call([
os.environ.get('MAKE', 'make'),
'--no-print-directory', '-s'])
def execute():
if 'EXEC' in os.environ:
subprocess.check_call([os.environ['EXEC'], "./lfs"])
else:
subprocess.check_call(["./lfs"])
def main(test=None):
try:
if test and not test.startswith('-'):
with open(test) as file:
generate(file)
else:
generate(sys.stdin)
compile()
if test == '-s':
sys.exit(1)
execute()
except subprocess.CalledProcessError:
# Python stack trace is counterproductive, just exit
sys.exit(2)
except KeyboardInterrupt:
# Python stack trace is counterproductive, just exit
sys.exit(3)
if __name__ == "__main__":
main(*sys.argv[1:])

View File

@@ -1,4 +1,4 @@
#!/usr/bin/env python2 #!/usr/bin/env python
import struct import struct
import sys import sys

View File

@@ -95,7 +95,7 @@ def main(*blocks):
print '%04x: %08x %-15s %3s %4s %-23s %-8s' % ( print '%04x: %08x %-15s %3s %4s %-23s %-8s' % (
off, tag, off, tag,
typeof(type) + (' bad!' if iscrc and ~crc else ''), typeof(type) + (' bad!' if iscrc and ~crc else ''),
hex(id)[2:] if id != 0x3ff else '.', id if id != 0x3ff else '.',
size if size != 0x3ff else 'x', size if size != 0x3ff else 'x',
' '.join('%02x' % ord(c) for c in data[:8]), ' '.join('%02x' % ord(c) for c in data[:8]),
''.join(c if c >= ' ' and c <= '~' else '.' for c in data[:8])) ''.join(c if c >= ' ' and c <= '~' else '.' for c in data[:8]))

30
tests/stats.py Executable file
View File

@@ -0,0 +1,30 @@
#!/usr/bin/env python
import struct
import sys
import time
import os
import re
def main():
with open('blocks/.config') as file:
s = struct.unpack('<LLLL', file.read())
print 'read_size: %d' % s[0]
print 'prog_size: %d' % s[1]
print 'block_size: %d' % s[2]
print 'block_size: %d' % s[3]
print 'real_size: %d' % sum(
os.path.getsize(os.path.join('blocks', f))
for f in os.listdir('blocks') if re.match('\d+', f))
with open('blocks/.stats') as file:
s = struct.unpack('<QQQ', file.read())
print 'read_count: %d' % s[0]
print 'prog_count: %d' % s[1]
print 'erase_count: %d' % s[2]
print 'runtime: %.3f' % (time.time() - os.stat('blocks').st_ctime)
if __name__ == "__main__":
main(*sys.argv[1:])

View File

@@ -7,21 +7,34 @@
// test stuff // test stuff
static void test_log(const char *s, uintmax_t v) {{
printf("%s: %jd\n", s, v);
}}
static void test_assert(const char *file, unsigned line, static void test_assert(const char *file, unsigned line,
const char *s, uintmax_t v, uintmax_t e) {{ const char *s, uintmax_t v, uintmax_t e) {{
static const char *last[6] = {{0, 0}};
if (v != e || !(last[0] == s || last[1] == s ||
last[2] == s || last[3] == s ||
last[4] == s || last[5] == s)) {{
test_log(s, v);
last[0] = last[1];
last[1] = last[2];
last[2] = last[3];
last[3] = last[4];
last[4] = last[5];
last[5] = s;
}}
if (v != e) {{ if (v != e) {{
fprintf(stderr, "\033[97m%s:%u: \033[91m" fprintf(stderr, "\033[31m%s:%u: assert %s failed with %jd, "
"assert failed with %jd, expected %jd\033[0m\n" "expected %jd\033[0m\n", file, line, s, v, e);
" %s\n\n", file, line, v, e, s);
exit(-2); exit(-2);
}} }}
}} }}
#define test_assert(v, e) \ #define test_assert(s, v, e) test_assert(__FILE__, __LINE__, s, v, e)
test_assert(__FILE__, __LINE__, #v " => " #e, v, e)
// implicit variable for asserts
uintmax_t test;
// utility functions for traversals // utility functions for traversals
static int __attribute__((used)) test_count(void *p, lfs_block_t b) {{ static int __attribute__((used)) test_count(void *p, lfs_block_t b) {{
@@ -31,17 +44,23 @@ static int __attribute__((used)) test_count(void *p, lfs_block_t b) {{
return 0; return 0;
}} }}
// lfs declarations // lfs declarations
lfs_t lfs; lfs_t lfs;
lfs_emubd_t bd; lfs_emubd_t bd;
// other declarations for convenience lfs_file_t file[4];
lfs_file_t file; lfs_dir_t dir[4];
lfs_dir_t dir;
struct lfs_info info; struct lfs_info info;
uint8_t buffer[1024];
char path[1024];
// test configuration options uint8_t buffer[1024];
uint8_t wbuffer[1024];
uint8_t rbuffer[1024];
lfs_size_t size;
lfs_size_t wsize;
lfs_size_t rsize;
uintmax_t test;
#ifndef LFS_READ_SIZE #ifndef LFS_READ_SIZE
#define LFS_READ_SIZE 16 #define LFS_READ_SIZE 16
#endif #endif
@@ -63,7 +82,7 @@ char path[1024];
#endif #endif
#ifndef LFS_CACHE_SIZE #ifndef LFS_CACHE_SIZE
#define LFS_CACHE_SIZE (64 % LFS_PROG_SIZE == 0 ? 64 : LFS_PROG_SIZE) #define LFS_CACHE_SIZE 64
#endif #endif
#ifndef LFS_LOOKAHEAD_SIZE #ifndef LFS_LOOKAHEAD_SIZE
@@ -92,5 +111,6 @@ int main(void) {{
lfs_emubd_create(&cfg, "blocks"); lfs_emubd_create(&cfg, "blocks");
{tests} {tests}
lfs_emubd_destroy(&cfg); lfs_emubd_destroy(&cfg);
}} }}

61
tests/test.py Executable file
View File

@@ -0,0 +1,61 @@
#!/usr/bin/env python
import re
import sys
import subprocess
import os
def generate(test):
with open("tests/template.fmt") as file:
template = file.read()
lines = []
for line in re.split('(?<=(?:.;| [{}]))\n', test.read()):
match = re.match('(?: *\n)*( *)(.*)=>(.*);', line, re.DOTALL | re.MULTILINE)
if match:
tab, test, expect = match.groups()
lines.append(tab+'test = {test};'.format(test=test.strip()))
lines.append(tab+'test_assert("{name}", test, {expect});'.format(
name = re.match('\w*', test.strip()).group(),
expect = expect.strip()))
else:
lines.append(line)
# Create test file
with open('test.c', 'w') as file:
file.write(template.format(tests='\n'.join(lines)))
# Remove build artifacts to force rebuild
try:
os.remove('test.o')
os.remove('lfs')
except OSError:
pass
def compile():
subprocess.check_call([
os.environ.get('MAKE', 'make'),
'--no-print-directory', '-s'])
def execute():
if 'EXEC' in os.environ:
subprocess.check_call([os.environ['EXEC'], "./lfs"])
else:
subprocess.check_call(["./lfs"])
def main(test=None):
if test and not test.startswith('-'):
with open(test) as file:
generate(file)
else:
generate(sys.stdin)
compile()
if test == '-s':
sys.exit(1)
execute()
if __name__ == "__main__":
main(*sys.argv[1:])

View File

@@ -1,18 +1,16 @@
#!/bin/bash #!/bin/bash
set -euE set -eu
export TEST_FILE=$0
trap 'export TEST_LINE=$LINENO' DEBUG
echo "=== Allocator tests ===" echo "=== Allocator tests ==="
rm -rf blocks rm -rf blocks
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
TEST TEST
SIZE=15000 SIZE=15000
lfs_mkdir() { lfs_mkdir() {
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_mkdir(&lfs, "$1") => 0; lfs_mkdir(&lfs, "$1") => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
@@ -20,7 +18,7 @@ TEST
} }
lfs_remove() { lfs_remove() {
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_remove(&lfs, "$1/eggs") => 0; lfs_remove(&lfs, "$1/eggs") => 0;
lfs_remove(&lfs, "$1/bacon") => 0; lfs_remove(&lfs, "$1/bacon") => 0;
@@ -31,23 +29,22 @@ TEST
} }
lfs_alloc_singleproc() { lfs_alloc_singleproc() {
scripts/test.py << TEST tests/test.py << TEST
const char *names[] = {"bacon", "eggs", "pancakes"}; const char *names[] = {"bacon", "eggs", "pancakes"};
lfs_file_t files[sizeof(names)/sizeof(names[0])];
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
for (unsigned n = 0; n < sizeof(names)/sizeof(names[0]); n++) { for (unsigned n = 0; n < sizeof(names)/sizeof(names[0]); n++) {
sprintf(path, "$1/%s", names[n]); sprintf((char*)buffer, "$1/%s", names[n]);
lfs_file_open(&lfs, &files[n], path, lfs_file_open(&lfs, &file[n], (char*)buffer,
LFS_O_WRONLY | LFS_O_CREAT | LFS_O_APPEND) => 0; LFS_O_WRONLY | LFS_O_CREAT | LFS_O_APPEND) => 0;
} }
for (unsigned n = 0; n < sizeof(names)/sizeof(names[0]); n++) { for (unsigned n = 0; n < sizeof(names)/sizeof(names[0]); n++) {
lfs_size_t size = strlen(names[n]); size = strlen(names[n]);
for (int i = 0; i < $SIZE; i++) { for (int i = 0; i < $SIZE; i++) {
lfs_file_write(&lfs, &files[n], names[n], size) => size; lfs_file_write(&lfs, &file[n], names[n], size) => size;
} }
} }
for (unsigned n = 0; n < sizeof(names)/sizeof(names[0]); n++) { for (unsigned n = 0; n < sizeof(names)/sizeof(names[0]); n++) {
lfs_file_close(&lfs, &files[n]) => 0; lfs_file_close(&lfs, &file[n]) => 0;
} }
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
@@ -56,16 +53,16 @@ TEST
lfs_alloc_multiproc() { lfs_alloc_multiproc() {
for name in bacon eggs pancakes for name in bacon eggs pancakes
do do
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "$1/$name", lfs_file_open(&lfs, &file[0], "$1/$name",
LFS_O_WRONLY | LFS_O_CREAT | LFS_O_APPEND) => 0; LFS_O_WRONLY | LFS_O_CREAT | LFS_O_APPEND) => 0;
lfs_size_t size = strlen("$name"); size = strlen("$name");
memcpy(buffer, "$name", size); memcpy(buffer, "$name", size);
for (int i = 0; i < $SIZE; i++) { for (int i = 0; i < $SIZE; i++) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
done done
@@ -74,15 +71,15 @@ done
lfs_verify() { lfs_verify() {
for name in bacon eggs pancakes for name in bacon eggs pancakes
do do
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "$1/$name", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], "$1/$name", LFS_O_RDONLY) => 0;
lfs_size_t size = strlen("$name"); size = strlen("$name");
for (int i = 0; i < $SIZE; i++) { for (int i = 0; i < $SIZE; i++) {
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "$name", size) => 0; memcmp(buffer, "$name", size) => 0;
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
done done
@@ -118,19 +115,19 @@ lfs_remove multiprocreuse
lfs_remove singleprocreuse lfs_remove singleprocreuse
echo "--- Exhaustion test ---" echo "--- Exhaustion test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "exhaustion", LFS_O_WRONLY | LFS_O_CREAT); lfs_file_open(&lfs, &file[0], "exhaustion", LFS_O_WRONLY | LFS_O_CREAT);
lfs_size_t size = strlen("exhaustion"); size = strlen("exhaustion");
memcpy(buffer, "exhaustion", size); memcpy(buffer, "exhaustion", size);
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
lfs_file_sync(&lfs, &file) => 0; lfs_file_sync(&lfs, &file[0]) => 0;
size = strlen("blahblahblahblah"); size = strlen("blahblahblahblah");
memcpy(buffer, "blahblahblahblah", size); memcpy(buffer, "blahblahblahblah", size);
lfs_ssize_t res; lfs_ssize_t res;
while (true) { while (true) {
res = lfs_file_write(&lfs, &file, buffer, size); res = lfs_file_write(&lfs, &file[0], buffer, size);
if (res < 0) { if (res < 0) {
break; break;
} }
@@ -139,45 +136,45 @@ scripts/test.py << TEST
} }
res => LFS_ERR_NOSPC; res => LFS_ERR_NOSPC;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "exhaustion", LFS_O_RDONLY); lfs_file_open(&lfs, &file[0], "exhaustion", LFS_O_RDONLY);
lfs_size_t size = strlen("exhaustion"); size = strlen("exhaustion");
lfs_file_size(&lfs, &file) => size; lfs_file_size(&lfs, &file[0]) => size;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "exhaustion", size) => 0; memcmp(buffer, "exhaustion", size) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Exhaustion wraparound test ---" echo "--- Exhaustion wraparound test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_remove(&lfs, "exhaustion") => 0; lfs_remove(&lfs, "exhaustion") => 0;
lfs_file_open(&lfs, &file, "padding", LFS_O_WRONLY | LFS_O_CREAT); lfs_file_open(&lfs, &file[0], "padding", LFS_O_WRONLY | LFS_O_CREAT);
lfs_size_t size = strlen("buffering"); size = strlen("buffering");
memcpy(buffer, "buffering", size); memcpy(buffer, "buffering", size);
for (int i = 0; i < $SIZE; i++) { for (int i = 0; i < $SIZE; i++) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_remove(&lfs, "padding") => 0; lfs_remove(&lfs, "padding") => 0;
lfs_file_open(&lfs, &file, "exhaustion", LFS_O_WRONLY | LFS_O_CREAT); lfs_file_open(&lfs, &file[0], "exhaustion", LFS_O_WRONLY | LFS_O_CREAT);
size = strlen("exhaustion"); size = strlen("exhaustion");
memcpy(buffer, "exhaustion", size); memcpy(buffer, "exhaustion", size);
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
lfs_file_sync(&lfs, &file) => 0; lfs_file_sync(&lfs, &file[0]) => 0;
size = strlen("blahblahblahblah"); size = strlen("blahblahblahblah");
memcpy(buffer, "blahblahblahblah", size); memcpy(buffer, "blahblahblahblah", size);
lfs_ssize_t res; lfs_ssize_t res;
while (true) { while (true) {
res = lfs_file_write(&lfs, &file, buffer, size); res = lfs_file_write(&lfs, &file[0], buffer, size);
if (res < 0) { if (res < 0) {
break; break;
} }
@@ -186,34 +183,34 @@ scripts/test.py << TEST
} }
res => LFS_ERR_NOSPC; res => LFS_ERR_NOSPC;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "exhaustion", LFS_O_RDONLY); lfs_file_open(&lfs, &file[0], "exhaustion", LFS_O_RDONLY);
lfs_size_t size = strlen("exhaustion"); size = strlen("exhaustion");
lfs_file_size(&lfs, &file) => size; lfs_file_size(&lfs, &file[0]) => size;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "exhaustion", size) => 0; memcmp(buffer, "exhaustion", size) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_remove(&lfs, "exhaustion") => 0; lfs_remove(&lfs, "exhaustion") => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Dir exhaustion test ---" echo "--- Dir exhaustion test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
// find out max file size // find out max file size
lfs_mkdir(&lfs, "exhaustiondir") => 0; lfs_mkdir(&lfs, "exhaustiondir") => 0;
lfs_size_t size = strlen("blahblahblahblah"); size = strlen("blahblahblahblah");
memcpy(buffer, "blahblahblahblah", size); memcpy(buffer, "blahblahblahblah", size);
lfs_file_open(&lfs, &file, "exhaustion", LFS_O_WRONLY | LFS_O_CREAT); lfs_file_open(&lfs, &file[0], "exhaustion", LFS_O_WRONLY | LFS_O_CREAT);
int count = 0; int count = 0;
int err; int err;
while (true) { while (true) {
err = lfs_file_write(&lfs, &file, buffer, size); err = lfs_file_write(&lfs, &file[0], buffer, size);
if (err < 0) { if (err < 0) {
break; break;
} }
@@ -221,28 +218,28 @@ scripts/test.py << TEST
count += 1; count += 1;
} }
err => LFS_ERR_NOSPC; err => LFS_ERR_NOSPC;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_remove(&lfs, "exhaustion") => 0; lfs_remove(&lfs, "exhaustion") => 0;
lfs_remove(&lfs, "exhaustiondir") => 0; lfs_remove(&lfs, "exhaustiondir") => 0;
// see if dir fits with max file size // see if dir fits with max file size
lfs_file_open(&lfs, &file, "exhaustion", LFS_O_WRONLY | LFS_O_CREAT); lfs_file_open(&lfs, &file[0], "exhaustion", LFS_O_WRONLY | LFS_O_CREAT);
for (int i = 0; i < count; i++) { for (int i = 0; i < count; i++) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_mkdir(&lfs, "exhaustiondir") => 0; lfs_mkdir(&lfs, "exhaustiondir") => 0;
lfs_remove(&lfs, "exhaustiondir") => 0; lfs_remove(&lfs, "exhaustiondir") => 0;
lfs_remove(&lfs, "exhaustion") => 0; lfs_remove(&lfs, "exhaustion") => 0;
// see if dir fits with > max file size // see if dir fits with > max file size
lfs_file_open(&lfs, &file, "exhaustion", LFS_O_WRONLY | LFS_O_CREAT); lfs_file_open(&lfs, &file[0], "exhaustion", LFS_O_WRONLY | LFS_O_CREAT);
for (int i = 0; i < count+1; i++) { for (int i = 0; i < count+1; i++) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_mkdir(&lfs, "exhaustiondir") => LFS_ERR_NOSPC; lfs_mkdir(&lfs, "exhaustiondir") => LFS_ERR_NOSPC;
@@ -251,22 +248,22 @@ scripts/test.py << TEST
TEST TEST
echo "--- Chained dir exhaustion test ---" echo "--- Chained dir exhaustion test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
// find out max file size // find out max file size
lfs_mkdir(&lfs, "exhaustiondir") => 0; lfs_mkdir(&lfs, "exhaustiondir") => 0;
for (int i = 0; i < 10; i++) { for (int i = 0; i < 10; i++) {
sprintf(path, "dirwithanexhaustivelylongnameforpadding%d", i); sprintf((char*)buffer, "dirwithanexhaustivelylongnameforpadding%d", i);
lfs_mkdir(&lfs, path) => 0; lfs_mkdir(&lfs, (char*)buffer) => 0;
} }
lfs_size_t size = strlen("blahblahblahblah"); size = strlen("blahblahblahblah");
memcpy(buffer, "blahblahblahblah", size); memcpy(buffer, "blahblahblahblah", size);
lfs_file_open(&lfs, &file, "exhaustion", LFS_O_WRONLY | LFS_O_CREAT); lfs_file_open(&lfs, &file[0], "exhaustion", LFS_O_WRONLY | LFS_O_CREAT);
int count = 0; int count = 0;
int err; int err;
while (true) { while (true) {
err = lfs_file_write(&lfs, &file, buffer, size); err = lfs_file_write(&lfs, &file[0], buffer, size);
if (err < 0) { if (err < 0) {
break; break;
} }
@@ -274,25 +271,25 @@ scripts/test.py << TEST
count += 1; count += 1;
} }
err => LFS_ERR_NOSPC; err => LFS_ERR_NOSPC;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_remove(&lfs, "exhaustion") => 0; lfs_remove(&lfs, "exhaustion") => 0;
lfs_remove(&lfs, "exhaustiondir") => 0; lfs_remove(&lfs, "exhaustiondir") => 0;
for (int i = 0; i < 10; i++) { for (int i = 0; i < 10; i++) {
sprintf(path, "dirwithanexhaustivelylongnameforpadding%d", i); sprintf((char*)buffer, "dirwithanexhaustivelylongnameforpadding%d", i);
lfs_remove(&lfs, path) => 0; lfs_remove(&lfs, (char*)buffer) => 0;
} }
// see that chained dir fails // see that chained dir fails
lfs_file_open(&lfs, &file, "exhaustion", LFS_O_WRONLY | LFS_O_CREAT); lfs_file_open(&lfs, &file[0], "exhaustion", LFS_O_WRONLY | LFS_O_CREAT);
for (int i = 0; i < count+1; i++) { for (int i = 0; i < count+1; i++) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_sync(&lfs, &file) => 0; lfs_file_sync(&lfs, &file[0]) => 0;
for (int i = 0; i < 10; i++) { for (int i = 0; i < 10; i++) {
sprintf(path, "dirwithanexhaustivelylongnameforpadding%d", i); sprintf((char*)buffer, "dirwithanexhaustivelylongnameforpadding%d", i);
lfs_mkdir(&lfs, path) => 0; lfs_mkdir(&lfs, (char*)buffer) => 0;
} }
lfs_mkdir(&lfs, "exhaustiondir") => LFS_ERR_NOSPC; lfs_mkdir(&lfs, "exhaustiondir") => LFS_ERR_NOSPC;
@@ -304,44 +301,45 @@ scripts/test.py << TEST
break; break;
} }
lfs_ssize_t filesize = lfs_file_size(&lfs, &file); lfs_ssize_t filesize = lfs_file_size(&lfs, &file[0]);
filesize > 0 => true; filesize > 0 => true;
lfs_file_truncate(&lfs, &file, filesize - size) => 0; lfs_file_truncate(&lfs, &file[0], filesize - size) => 0;
lfs_file_sync(&lfs, &file) => 0; lfs_file_sync(&lfs, &file[0]) => 0;
} }
err => 0; err => 0;
lfs_mkdir(&lfs, "exhaustiondir2") => LFS_ERR_NOSPC; lfs_mkdir(&lfs, "exhaustiondir2") => LFS_ERR_NOSPC;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Split dir test ---" echo "--- Split dir test ---"
scripts/test.py << TEST rm -rf blocks
tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
// create one block hole for half a directory // create one block hole for half a directory
lfs_file_open(&lfs, &file, "bump", LFS_O_WRONLY | LFS_O_CREAT) => 0; lfs_file_open(&lfs, &file[0], "bump", LFS_O_WRONLY | LFS_O_CREAT) => 0;
for (lfs_size_t i = 0; i < cfg.block_size; i += 2) { for (lfs_size_t i = 0; i < cfg.block_size; i += 2) {
memcpy(&buffer[i], "hi", 2); memcpy(&buffer[i], "hi", 2);
} }
lfs_file_write(&lfs, &file, buffer, cfg.block_size) => cfg.block_size; lfs_file_write(&lfs, &file[0], buffer, cfg.block_size) => cfg.block_size;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_file_open(&lfs, &file, "exhaustion", LFS_O_WRONLY | LFS_O_CREAT); lfs_file_open(&lfs, &file[0], "exhaustion", LFS_O_WRONLY | LFS_O_CREAT);
lfs_size_t size = strlen("blahblahblahblah"); size = strlen("blahblahblahblah");
memcpy(buffer, "blahblahblahblah", size); memcpy(buffer, "blahblahblahblah", size);
for (lfs_size_t i = 0; for (lfs_size_t i = 0;
i < (cfg.block_count-4)*(cfg.block_size-8); i < (cfg.block_count-4)*(cfg.block_size-8);
i += size) { i += size) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
// remount to force reset of lookahead // remount to force reset of lookahead
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
@@ -351,134 +349,137 @@ scripts/test.py << TEST
lfs_remove(&lfs, "bump") => 0; lfs_remove(&lfs, "bump") => 0;
lfs_mkdir(&lfs, "splitdir") => 0; lfs_mkdir(&lfs, "splitdir") => 0;
lfs_file_open(&lfs, &file, "splitdir/bump", lfs_file_open(&lfs, &file[0], "splitdir/bump",
LFS_O_WRONLY | LFS_O_CREAT) => 0; LFS_O_WRONLY | LFS_O_CREAT) => 0;
for (lfs_size_t i = 0; i < cfg.block_size; i += 2) { for (lfs_size_t i = 0; i < cfg.block_size; i += 2) {
memcpy(&buffer[i], "hi", 2); memcpy(&buffer[i], "hi", 2);
} }
lfs_file_write(&lfs, &file, buffer, 2*cfg.block_size) => LFS_ERR_NOSPC; lfs_file_write(&lfs, &file[0], buffer, 2*cfg.block_size) => LFS_ERR_NOSPC;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Outdated lookahead test ---" echo "--- Outdated lookahead test ---"
scripts/test.py << TEST rm -rf blocks
tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
// fill completely with two files // fill completely with two files
lfs_file_open(&lfs, &file, "exhaustion1", lfs_file_open(&lfs, &file[0], "exhaustion1",
LFS_O_WRONLY | LFS_O_CREAT) => 0; LFS_O_WRONLY | LFS_O_CREAT) => 0;
lfs_size_t size = strlen("blahblahblahblah"); size = strlen("blahblahblahblah");
memcpy(buffer, "blahblahblahblah", size); memcpy(buffer, "blahblahblahblah", size);
for (lfs_size_t i = 0; for (lfs_size_t i = 0;
i < ((cfg.block_count-2)/2)*(cfg.block_size-8); i < ((cfg.block_count-2)/2)*(cfg.block_size-8);
i += size) { i += size) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_file_open(&lfs, &file, "exhaustion2", lfs_file_open(&lfs, &file[0], "exhaustion2",
LFS_O_WRONLY | LFS_O_CREAT) => 0; LFS_O_WRONLY | LFS_O_CREAT) => 0;
size = strlen("blahblahblahblah"); size = strlen("blahblahblahblah");
memcpy(buffer, "blahblahblahblah", size); memcpy(buffer, "blahblahblahblah", size);
for (lfs_size_t i = 0; for (lfs_size_t i = 0;
i < ((cfg.block_count-2+1)/2)*(cfg.block_size-8); i < ((cfg.block_count-2+1)/2)*(cfg.block_size-8);
i += size) { i += size) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
// remount to force reset of lookahead // remount to force reset of lookahead
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
// rewrite one file // rewrite one file
lfs_file_open(&lfs, &file, "exhaustion1", lfs_file_open(&lfs, &file[0], "exhaustion1",
LFS_O_WRONLY | LFS_O_TRUNC) => 0; LFS_O_WRONLY | LFS_O_TRUNC) => 0;
lfs_file_sync(&lfs, &file) => 0; lfs_file_sync(&lfs, &file[0]) => 0;
size = strlen("blahblahblahblah"); size = strlen("blahblahblahblah");
memcpy(buffer, "blahblahblahblah", size); memcpy(buffer, "blahblahblahblah", size);
for (lfs_size_t i = 0; for (lfs_size_t i = 0;
i < ((cfg.block_count-2)/2)*(cfg.block_size-8); i < ((cfg.block_count-2)/2)*(cfg.block_size-8);
i += size) { i += size) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
// rewrite second file, this requires lookahead does not // rewrite second file, this requires lookahead does not
// use old population // use old population
lfs_file_open(&lfs, &file, "exhaustion2", lfs_file_open(&lfs, &file[0], "exhaustion2",
LFS_O_WRONLY | LFS_O_TRUNC) => 0; LFS_O_WRONLY | LFS_O_TRUNC) => 0;
lfs_file_sync(&lfs, &file) => 0; lfs_file_sync(&lfs, &file[0]) => 0;
size = strlen("blahblahblahblah"); size = strlen("blahblahblahblah");
memcpy(buffer, "blahblahblahblah", size); memcpy(buffer, "blahblahblahblah", size);
for (lfs_size_t i = 0; for (lfs_size_t i = 0;
i < ((cfg.block_count-2+1)/2)*(cfg.block_size-8); i < ((cfg.block_count-2+1)/2)*(cfg.block_size-8);
i += size) { i += size) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
TEST TEST
echo "--- Outdated lookahead and split dir test ---" echo "--- Outdated lookahead and split dir test ---"
scripts/test.py << TEST rm -rf blocks
tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
// fill completely with two files // fill completely with two files
lfs_file_open(&lfs, &file, "exhaustion1", lfs_file_open(&lfs, &file[0], "exhaustion1",
LFS_O_WRONLY | LFS_O_CREAT) => 0; LFS_O_WRONLY | LFS_O_CREAT) => 0;
lfs_size_t size = strlen("blahblahblahblah"); size = strlen("blahblahblahblah");
memcpy(buffer, "blahblahblahblah", size); memcpy(buffer, "blahblahblahblah", size);
for (lfs_size_t i = 0; for (lfs_size_t i = 0;
i < ((cfg.block_count-2)/2)*(cfg.block_size-8); i < ((cfg.block_count-2)/2)*(cfg.block_size-8);
i += size) { i += size) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_file_open(&lfs, &file, "exhaustion2", lfs_file_open(&lfs, &file[0], "exhaustion2",
LFS_O_WRONLY | LFS_O_CREAT) => 0; LFS_O_WRONLY | LFS_O_CREAT) => 0;
size = strlen("blahblahblahblah"); size = strlen("blahblahblahblah");
memcpy(buffer, "blahblahblahblah", size); memcpy(buffer, "blahblahblahblah", size);
for (lfs_size_t i = 0; for (lfs_size_t i = 0;
i < ((cfg.block_count-2+1)/2)*(cfg.block_size-8); i < ((cfg.block_count-2+1)/2)*(cfg.block_size-8);
i += size) { i += size) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
// remount to force reset of lookahead // remount to force reset of lookahead
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
// rewrite one file with a hole of one block // rewrite one file with a hole of one block
lfs_file_open(&lfs, &file, "exhaustion1", lfs_file_open(&lfs, &file[0], "exhaustion1",
LFS_O_WRONLY | LFS_O_TRUNC) => 0; LFS_O_WRONLY | LFS_O_TRUNC) => 0;
lfs_file_sync(&lfs, &file) => 0; lfs_file_sync(&lfs, &file[0]) => 0;
size = strlen("blahblahblahblah"); size = strlen("blahblahblahblah");
memcpy(buffer, "blahblahblahblah", size); memcpy(buffer, "blahblahblahblah", size);
for (lfs_size_t i = 0; for (lfs_size_t i = 0;
i < ((cfg.block_count-2)/2 - 1)*(cfg.block_size-8); i < ((cfg.block_count-2)/2 - 1)*(cfg.block_size-8);
i += size) { i += size) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
// try to allocate a directory, should fail! // try to allocate a directory, should fail!
lfs_mkdir(&lfs, "split") => LFS_ERR_NOSPC; lfs_mkdir(&lfs, "split") => LFS_ERR_NOSPC;
// file should not fail // file should not fail
lfs_file_open(&lfs, &file, "notasplit", lfs_file_open(&lfs, &file[0], "notasplit",
LFS_O_WRONLY | LFS_O_CREAT) => 0; LFS_O_WRONLY | LFS_O_CREAT) => 0;
lfs_file_write(&lfs, &file, "hi", 2) => 2; lfs_file_write(&lfs, &file[0], "hi", 2) => 2;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/results.py echo "--- Results ---"
tests/stats.py

View File

@@ -1,27 +1,24 @@
#!/bin/bash #!/bin/bash
set -eu set -eu
export TEST_FILE=$0
trap 'export TEST_LINE=$LINENO' DEBUG
echo "=== Attr tests ===" echo "=== Attr tests ==="
rm -rf blocks rm -rf blocks
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_mkdir(&lfs, "hello") => 0; lfs_mkdir(&lfs, "hello") => 0;
lfs_file_open(&lfs, &file, "hello/hello", lfs_file_open(&lfs, &file[0], "hello/hello",
LFS_O_WRONLY | LFS_O_CREAT) => 0; LFS_O_WRONLY | LFS_O_CREAT) => 0;
lfs_file_write(&lfs, &file, "hello", strlen("hello")) lfs_file_write(&lfs, &file[0], "hello", strlen("hello"))
=> strlen("hello"); => strlen("hello");
lfs_file_close(&lfs, &file); lfs_file_close(&lfs, &file[0]);
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Set/get attribute ---" echo "--- Set/get attribute ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
memset(buffer, 0, sizeof(buffer));
lfs_setattr(&lfs, "hello", 'A', "aaaa", 4) => 0; lfs_setattr(&lfs, "hello", 'A', "aaaa", 4) => 0;
lfs_setattr(&lfs, "hello", 'B', "bbbbbb", 6) => 0; lfs_setattr(&lfs, "hello", 'B', "bbbbbb", 6) => 0;
lfs_setattr(&lfs, "hello", 'C', "ccccc", 5) => 0; lfs_setattr(&lfs, "hello", 'C', "ccccc", 5) => 0;
@@ -72,9 +69,8 @@ scripts/test.py << TEST
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
memset(buffer, 0, sizeof(buffer));
lfs_getattr(&lfs, "hello", 'A', buffer, 4) => 4; lfs_getattr(&lfs, "hello", 'A', buffer, 4) => 4;
lfs_getattr(&lfs, "hello", 'B', buffer+4, 9) => 9; lfs_getattr(&lfs, "hello", 'B', buffer+4, 9) => 9;
lfs_getattr(&lfs, "hello", 'C', buffer+13, 5) => 5; lfs_getattr(&lfs, "hello", 'C', buffer+13, 5) => 5;
@@ -82,17 +78,16 @@ scripts/test.py << TEST
memcmp(buffer+4, "fffffffff", 9) => 0; memcmp(buffer+4, "fffffffff", 9) => 0;
memcmp(buffer+13, "ccccc", 5) => 0; memcmp(buffer+13, "ccccc", 5) => 0;
lfs_file_open(&lfs, &file, "hello/hello", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], "hello/hello", LFS_O_RDONLY) => 0;
lfs_file_read(&lfs, &file, buffer, sizeof(buffer)) => strlen("hello"); lfs_file_read(&lfs, &file[0], buffer, sizeof(buffer)) => strlen("hello");
memcmp(buffer, "hello", strlen("hello")) => 0; memcmp(buffer, "hello", strlen("hello")) => 0;
lfs_file_close(&lfs, &file); lfs_file_close(&lfs, &file[0]);
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Set/get root attribute ---" echo "--- Set/get root attribute ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
memset(buffer, 0, sizeof(buffer));
lfs_setattr(&lfs, "/", 'A', "aaaa", 4) => 0; lfs_setattr(&lfs, "/", 'A', "aaaa", 4) => 0;
lfs_setattr(&lfs, "/", 'B', "bbbbbb", 6) => 0; lfs_setattr(&lfs, "/", 'B', "bbbbbb", 6) => 0;
lfs_setattr(&lfs, "/", 'C', "ccccc", 5) => 0; lfs_setattr(&lfs, "/", 'C', "ccccc", 5) => 0;
@@ -142,9 +137,8 @@ scripts/test.py << TEST
lfs_getattr(&lfs, "/", 'C', buffer+10, 5) => 5; lfs_getattr(&lfs, "/", 'C', buffer+10, 5) => 5;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
memset(buffer, 0, sizeof(buffer));
lfs_getattr(&lfs, "/", 'A', buffer, 4) => 4; lfs_getattr(&lfs, "/", 'A', buffer, 4) => 4;
lfs_getattr(&lfs, "/", 'B', buffer+4, 9) => 9; lfs_getattr(&lfs, "/", 'B', buffer+4, 9) => 9;
lfs_getattr(&lfs, "/", 'C', buffer+13, 5) => 5; lfs_getattr(&lfs, "/", 'C', buffer+13, 5) => 5;
@@ -152,17 +146,16 @@ scripts/test.py << TEST
memcmp(buffer+4, "fffffffff", 9) => 0; memcmp(buffer+4, "fffffffff", 9) => 0;
memcmp(buffer+13, "ccccc", 5) => 0; memcmp(buffer+13, "ccccc", 5) => 0;
lfs_file_open(&lfs, &file, "hello/hello", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], "hello/hello", LFS_O_RDONLY) => 0;
lfs_file_read(&lfs, &file, buffer, sizeof(buffer)) => strlen("hello"); lfs_file_read(&lfs, &file[0], buffer, sizeof(buffer)) => strlen("hello");
memcmp(buffer, "hello", strlen("hello")) => 0; memcmp(buffer, "hello", strlen("hello")) => 0;
lfs_file_close(&lfs, &file); lfs_file_close(&lfs, &file[0]);
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Set/get file attribute ---" echo "--- Set/get file attribute ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
memset(buffer, 0, sizeof(buffer));
struct lfs_attr attrs1[] = { struct lfs_attr attrs1[] = {
{'A', buffer, 4}, {'A', buffer, 4},
{'B', buffer+4, 6}, {'B', buffer+4, 6},
@@ -170,55 +163,55 @@ scripts/test.py << TEST
}; };
struct lfs_file_config cfg1 = {.attrs=attrs1, .attr_count=3}; struct lfs_file_config cfg1 = {.attrs=attrs1, .attr_count=3};
lfs_file_opencfg(&lfs, &file, "hello/hello", LFS_O_WRONLY, &cfg1) => 0; lfs_file_opencfg(&lfs, &file[0], "hello/hello", LFS_O_WRONLY, &cfg1) => 0;
memcpy(buffer, "aaaa", 4); memcpy(buffer, "aaaa", 4);
memcpy(buffer+4, "bbbbbb", 6); memcpy(buffer+4, "bbbbbb", 6);
memcpy(buffer+10, "ccccc", 5); memcpy(buffer+10, "ccccc", 5);
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
memset(buffer, 0, 15); memset(buffer, 0, 15);
lfs_file_opencfg(&lfs, &file, "hello/hello", LFS_O_RDONLY, &cfg1) => 0; lfs_file_opencfg(&lfs, &file[0], "hello/hello", LFS_O_RDONLY, &cfg1) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
memcmp(buffer, "aaaa", 4) => 0; memcmp(buffer, "aaaa", 4) => 0;
memcmp(buffer+4, "bbbbbb", 6) => 0; memcmp(buffer+4, "bbbbbb", 6) => 0;
memcmp(buffer+10, "ccccc", 5) => 0; memcmp(buffer+10, "ccccc", 5) => 0;
attrs1[1].size = 0; attrs1[1].size = 0;
lfs_file_opencfg(&lfs, &file, "hello/hello", LFS_O_WRONLY, &cfg1) => 0; lfs_file_opencfg(&lfs, &file[0], "hello/hello", LFS_O_WRONLY, &cfg1) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
memset(buffer, 0, 15); memset(buffer, 0, 15);
attrs1[1].size = 6; attrs1[1].size = 6;
lfs_file_opencfg(&lfs, &file, "hello/hello", LFS_O_RDONLY, &cfg1) => 0; lfs_file_opencfg(&lfs, &file[0], "hello/hello", LFS_O_RDONLY, &cfg1) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
memcmp(buffer, "aaaa", 4) => 0; memcmp(buffer, "aaaa", 4) => 0;
memcmp(buffer+4, "\0\0\0\0\0\0", 6) => 0; memcmp(buffer+4, "\0\0\0\0\0\0", 6) => 0;
memcmp(buffer+10, "ccccc", 5) => 0; memcmp(buffer+10, "ccccc", 5) => 0;
attrs1[1].size = 6; attrs1[1].size = 6;
lfs_file_opencfg(&lfs, &file, "hello/hello", LFS_O_WRONLY, &cfg1) => 0; lfs_file_opencfg(&lfs, &file[0], "hello/hello", LFS_O_WRONLY, &cfg1) => 0;
memcpy(buffer+4, "dddddd", 6); memcpy(buffer+4, "dddddd", 6);
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
memset(buffer, 0, 15); memset(buffer, 0, 15);
attrs1[1].size = 6; attrs1[1].size = 6;
lfs_file_opencfg(&lfs, &file, "hello/hello", LFS_O_RDONLY, &cfg1) => 0; lfs_file_opencfg(&lfs, &file[0], "hello/hello", LFS_O_RDONLY, &cfg1) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
memcmp(buffer, "aaaa", 4) => 0; memcmp(buffer, "aaaa", 4) => 0;
memcmp(buffer+4, "dddddd", 6) => 0; memcmp(buffer+4, "dddddd", 6) => 0;
memcmp(buffer+10, "ccccc", 5) => 0; memcmp(buffer+10, "ccccc", 5) => 0;
attrs1[1].size = 3; attrs1[1].size = 3;
lfs_file_opencfg(&lfs, &file, "hello/hello", LFS_O_WRONLY, &cfg1) => 0; lfs_file_opencfg(&lfs, &file[0], "hello/hello", LFS_O_WRONLY, &cfg1) => 0;
memcpy(buffer+4, "eee", 3); memcpy(buffer+4, "eee", 3);
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
memset(buffer, 0, 15); memset(buffer, 0, 15);
attrs1[1].size = 6; attrs1[1].size = 6;
lfs_file_opencfg(&lfs, &file, "hello/hello", LFS_O_RDONLY, &cfg1) => 0; lfs_file_opencfg(&lfs, &file[0], "hello/hello", LFS_O_RDONLY, &cfg1) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
memcmp(buffer, "aaaa", 4) => 0; memcmp(buffer, "aaaa", 4) => 0;
memcmp(buffer+4, "eee\0\0\0", 6) => 0; memcmp(buffer+4, "eee\0\0\0", 6) => 0;
memcmp(buffer+10, "ccccc", 5) => 0; memcmp(buffer+10, "ccccc", 5) => 0;
attrs1[0].size = LFS_ATTR_MAX+1; attrs1[0].size = LFS_ATTR_MAX+1;
lfs_file_opencfg(&lfs, &file, "hello/hello", LFS_O_WRONLY, &cfg1) lfs_file_opencfg(&lfs, &file[0], "hello/hello", LFS_O_WRONLY, &cfg1)
=> LFS_ERR_NOSPC; => LFS_ERR_NOSPC;
struct lfs_attr attrs2[] = { struct lfs_attr attrs2[] = {
@@ -227,18 +220,17 @@ scripts/test.py << TEST
{'C', buffer+13, 5}, {'C', buffer+13, 5},
}; };
struct lfs_file_config cfg2 = {.attrs=attrs2, .attr_count=3}; struct lfs_file_config cfg2 = {.attrs=attrs2, .attr_count=3};
lfs_file_opencfg(&lfs, &file, "hello/hello", LFS_O_RDWR, &cfg2) => 0; lfs_file_opencfg(&lfs, &file[0], "hello/hello", LFS_O_RDWR, &cfg2) => 0;
memcpy(buffer+4, "fffffffff", 9); memcpy(buffer+4, "fffffffff", 9);
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
attrs1[0].size = 4; attrs1[0].size = 4;
lfs_file_opencfg(&lfs, &file, "hello/hello", LFS_O_RDONLY, &cfg1) => 0; lfs_file_opencfg(&lfs, &file[0], "hello/hello", LFS_O_RDONLY, &cfg1) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
memset(buffer, 0, sizeof(buffer));
struct lfs_attr attrs2[] = { struct lfs_attr attrs2[] = {
{'A', buffer, 4}, {'A', buffer, 4},
{'B', buffer+4, 9}, {'B', buffer+4, 9},
@@ -246,23 +238,22 @@ scripts/test.py << TEST
}; };
struct lfs_file_config cfg2 = {.attrs=attrs2, .attr_count=3}; struct lfs_file_config cfg2 = {.attrs=attrs2, .attr_count=3};
lfs_file_opencfg(&lfs, &file, "hello/hello", LFS_O_RDONLY, &cfg2) => 0; lfs_file_opencfg(&lfs, &file[0], "hello/hello", LFS_O_RDONLY, &cfg2) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
memcmp(buffer, "aaaa", 4) => 0; memcmp(buffer, "aaaa", 4) => 0;
memcmp(buffer+4, "fffffffff", 9) => 0; memcmp(buffer+4, "fffffffff", 9) => 0;
memcmp(buffer+13, "ccccc", 5) => 0; memcmp(buffer+13, "ccccc", 5) => 0;
lfs_file_open(&lfs, &file, "hello/hello", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], "hello/hello", LFS_O_RDONLY) => 0;
lfs_file_read(&lfs, &file, buffer, sizeof(buffer)) => strlen("hello"); lfs_file_read(&lfs, &file[0], buffer, sizeof(buffer)) => strlen("hello");
memcmp(buffer, "hello", strlen("hello")) => 0; memcmp(buffer, "hello", strlen("hello")) => 0;
lfs_file_close(&lfs, &file); lfs_file_close(&lfs, &file[0]);
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Deferred file attributes ---" echo "--- Deferred file attributes ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
memset(buffer, 0, sizeof(buffer));
struct lfs_attr attrs1[] = { struct lfs_attr attrs1[] = {
{'B', "gggg", 4}, {'B', "gggg", 4},
{'C', "", 0}, {'C', "", 0},
@@ -270,7 +261,7 @@ scripts/test.py << TEST
}; };
struct lfs_file_config cfg1 = {.attrs=attrs1, .attr_count=3}; struct lfs_file_config cfg1 = {.attrs=attrs1, .attr_count=3};
lfs_file_opencfg(&lfs, &file, "hello/hello", LFS_O_WRONLY, &cfg1) => 0; lfs_file_opencfg(&lfs, &file[0], "hello/hello", LFS_O_WRONLY, &cfg1) => 0;
lfs_getattr(&lfs, "hello/hello", 'B', buffer, 9) => 9; lfs_getattr(&lfs, "hello/hello", 'B', buffer, 9) => 9;
lfs_getattr(&lfs, "hello/hello", 'C', buffer+9, 9) => 5; lfs_getattr(&lfs, "hello/hello", 'C', buffer+9, 9) => 5;
@@ -279,7 +270,7 @@ scripts/test.py << TEST
memcmp(buffer+9, "ccccc\0\0\0\0", 9) => 0; memcmp(buffer+9, "ccccc\0\0\0\0", 9) => 0;
memcmp(buffer+18, "\0\0\0\0\0\0\0\0\0", 9) => 0; memcmp(buffer+18, "\0\0\0\0\0\0\0\0\0", 9) => 0;
lfs_file_sync(&lfs, &file) => 0; lfs_file_sync(&lfs, &file[0]) => 0;
lfs_getattr(&lfs, "hello/hello", 'B', buffer, 9) => 4; lfs_getattr(&lfs, "hello/hello", 'B', buffer, 9) => 4;
lfs_getattr(&lfs, "hello/hello", 'C', buffer+9, 9) => 0; lfs_getattr(&lfs, "hello/hello", 'C', buffer+9, 9) => 0;
lfs_getattr(&lfs, "hello/hello", 'D', buffer+18, 9) => 4; lfs_getattr(&lfs, "hello/hello", 'D', buffer+18, 9) => 4;
@@ -287,8 +278,9 @@ scripts/test.py << TEST
memcmp(buffer+9, "\0\0\0\0\0\0\0\0\0", 9) => 0; memcmp(buffer+9, "\0\0\0\0\0\0\0\0\0", 9) => 0;
memcmp(buffer+18, "hhhh\0\0\0\0\0", 9) => 0; memcmp(buffer+18, "hhhh\0\0\0\0\0", 9) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/results.py echo "--- Results ---"
tests/stats.py

View File

@@ -1,7 +1,5 @@
#!/bin/bash #!/bin/bash
set -eu set -eu
export TEST_FILE=$0
trap 'export TEST_LINE=$LINENO' DEBUG
echo "=== Corrupt tests ===" echo "=== Corrupt tests ==="
@@ -9,7 +7,7 @@ NAMEMULT=64
FILEMULT=1 FILEMULT=1
lfs_mktree() { lfs_mktree() {
scripts/test.py ${1:-} << TEST tests/test.py ${1:-} << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
@@ -25,22 +23,22 @@ scripts/test.py ${1:-} << TEST
buffer[j+$NAMEMULT+1] = '0'+i; buffer[j+$NAMEMULT+1] = '0'+i;
} }
buffer[2*$NAMEMULT+1] = '\0'; buffer[2*$NAMEMULT+1] = '\0';
lfs_file_open(&lfs, &file, (char*)buffer, lfs_file_open(&lfs, &file[0], (char*)buffer,
LFS_O_WRONLY | LFS_O_CREAT) => 0; LFS_O_WRONLY | LFS_O_CREAT) => 0;
lfs_size_t size = $NAMEMULT; size = $NAMEMULT;
for (int j = 0; j < i*$FILEMULT; j++) { for (int j = 0; j < i*$FILEMULT; j++) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
} }
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
} }
lfs_chktree() { lfs_chktree() {
scripts/test.py ${1:-} << TEST tests/test.py ${1:-} << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
for (int i = 1; i < 10; i++) { for (int i = 1; i < 10; i++) {
for (int j = 0; j < $NAMEMULT; j++) { for (int j = 0; j < $NAMEMULT; j++) {
@@ -55,16 +53,15 @@ scripts/test.py ${1:-} << TEST
buffer[j+$NAMEMULT+1] = '0'+i; buffer[j+$NAMEMULT+1] = '0'+i;
} }
buffer[2*$NAMEMULT+1] = '\0'; buffer[2*$NAMEMULT+1] = '\0';
lfs_file_open(&lfs, &file, (char*)buffer, LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], (char*)buffer, LFS_O_RDONLY) => 0;
lfs_size_t size = $NAMEMULT; size = $NAMEMULT;
for (int j = 0; j < i*$FILEMULT; j++) { for (int j = 0; j < i*$FILEMULT; j++) {
uint8_t rbuffer[1024]; lfs_file_read(&lfs, &file[0], rbuffer, size) => size;
lfs_file_read(&lfs, &file, rbuffer, size) => size;
memcmp(buffer, rbuffer, size) => 0; memcmp(buffer, rbuffer, size) => 0;
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
} }
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
@@ -117,4 +114,5 @@ done
lfs_mktree lfs_mktree
lfs_chktree lfs_chktree
scripts/results.py echo "--- Results ---"
tests/stats.py

View File

@@ -1,191 +1,188 @@
#!/bin/bash #!/bin/bash
set -eu set -eu
export TEST_FILE=$0
trap 'export TEST_LINE=$LINENO' DEBUG
echo "=== Directory tests ==="
LARGESIZE=128 LARGESIZE=128
echo "=== Directory tests ==="
rm -rf blocks rm -rf blocks
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
TEST TEST
echo "--- Root directory ---" echo "--- Root directory ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "/") => 0; lfs_dir_open(&lfs, &dir[0], "/") => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Directory creation ---" echo "--- Directory creation ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_mkdir(&lfs, "potato") => 0; lfs_mkdir(&lfs, "potato") => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- File creation ---" echo "--- File creation ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "burito", LFS_O_CREAT | LFS_O_WRONLY) => 0; lfs_file_open(&lfs, &file[0], "burito", LFS_O_CREAT | LFS_O_WRONLY) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Directory iteration ---" echo "--- Directory iteration ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "/") => 0; lfs_dir_open(&lfs, &dir[0], "/") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "burito") => 0; strcmp(info.name, "burito") => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "potato") => 0; strcmp(info.name, "potato") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Directory failures ---" echo "--- Directory failures ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_mkdir(&lfs, "potato") => LFS_ERR_EXIST; lfs_mkdir(&lfs, "potato") => LFS_ERR_EXIST;
lfs_dir_open(&lfs, &dir, "tomato") => LFS_ERR_NOENT; lfs_dir_open(&lfs, &dir[0], "tomato") => LFS_ERR_NOENT;
lfs_dir_open(&lfs, &dir, "burito") => LFS_ERR_NOTDIR; lfs_dir_open(&lfs, &dir[0], "burito") => LFS_ERR_NOTDIR;
lfs_file_open(&lfs, &file, "tomato", LFS_O_RDONLY) => LFS_ERR_NOENT; lfs_file_open(&lfs, &file[0], "tomato", LFS_O_RDONLY) => LFS_ERR_NOENT;
lfs_file_open(&lfs, &file, "potato", LFS_O_RDONLY) => LFS_ERR_ISDIR; lfs_file_open(&lfs, &file[0], "potato", LFS_O_RDONLY) => LFS_ERR_ISDIR;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Nested directories ---" echo "--- Nested directories ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_mkdir(&lfs, "potato/baked") => 0; lfs_mkdir(&lfs, "potato/baked") => 0;
lfs_mkdir(&lfs, "potato/sweet") => 0; lfs_mkdir(&lfs, "potato/sweet") => 0;
lfs_mkdir(&lfs, "potato/fried") => 0; lfs_mkdir(&lfs, "potato/fried") => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "potato") => 0; lfs_dir_open(&lfs, &dir[0], "potato") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "baked") => 0; strcmp(info.name, "baked") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "fried") => 0; strcmp(info.name, "fried") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "sweet") => 0; strcmp(info.name, "sweet") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Multi-block directory ---" echo "--- Multi-block directory ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_mkdir(&lfs, "cactus") => 0; lfs_mkdir(&lfs, "cactus") => 0;
for (int i = 0; i < $LARGESIZE; i++) { for (int i = 0; i < $LARGESIZE; i++) {
sprintf(path, "cactus/test%03d", i); sprintf((char*)buffer, "cactus/test%03d", i);
lfs_mkdir(&lfs, path) => 0; lfs_mkdir(&lfs, (char*)buffer) => 0;
} }
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "cactus") => 0; lfs_dir_open(&lfs, &dir[0], "cactus") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
for (int i = 0; i < $LARGESIZE; i++) { for (int i = 0; i < $LARGESIZE; i++) {
sprintf(path, "test%03d", i); sprintf((char*)buffer, "test%03d", i);
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, path) => 0; strcmp(info.name, (char*)buffer) => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
} }
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Directory remove ---" echo "--- Directory remove ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_remove(&lfs, "potato") => LFS_ERR_NOTEMPTY; lfs_remove(&lfs, "potato") => LFS_ERR_NOTEMPTY;
lfs_remove(&lfs, "potato/sweet") => 0; lfs_remove(&lfs, "potato/sweet") => 0;
lfs_remove(&lfs, "potato/baked") => 0; lfs_remove(&lfs, "potato/baked") => 0;
lfs_remove(&lfs, "potato/fried") => 0; lfs_remove(&lfs, "potato/fried") => 0;
lfs_dir_open(&lfs, &dir, "potato") => 0; lfs_dir_open(&lfs, &dir[0], "potato") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_remove(&lfs, "potato") => 0; lfs_remove(&lfs, "potato") => 0;
lfs_dir_open(&lfs, &dir, "/") => 0; lfs_dir_open(&lfs, &dir[0], "/") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "burito") => 0; strcmp(info.name, "burito") => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "cactus") => 0; strcmp(info.name, "cactus") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "/") => 0; lfs_dir_open(&lfs, &dir[0], "/") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "burito") => 0; strcmp(info.name, "burito") => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "cactus") => 0; strcmp(info.name, "cactus") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Directory rename ---" echo "--- Directory rename ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_mkdir(&lfs, "coldpotato") => 0; lfs_mkdir(&lfs, "coldpotato") => 0;
lfs_mkdir(&lfs, "coldpotato/baked") => 0; lfs_mkdir(&lfs, "coldpotato/baked") => 0;
@@ -193,34 +190,34 @@ scripts/test.py << TEST
lfs_mkdir(&lfs, "coldpotato/fried") => 0; lfs_mkdir(&lfs, "coldpotato/fried") => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_rename(&lfs, "coldpotato", "hotpotato") => 0; lfs_rename(&lfs, "coldpotato", "hotpotato") => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "hotpotato") => 0; lfs_dir_open(&lfs, &dir[0], "hotpotato") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "baked") => 0; strcmp(info.name, "baked") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "fried") => 0; strcmp(info.name, "fried") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "sweet") => 0; strcmp(info.name, "sweet") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_mkdir(&lfs, "warmpotato") => 0; lfs_mkdir(&lfs, "warmpotato") => 0;
lfs_mkdir(&lfs, "warmpotato/mushy") => 0; lfs_mkdir(&lfs, "warmpotato/mushy") => 0;
@@ -231,29 +228,29 @@ scripts/test.py << TEST
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "warmpotato") => 0; lfs_dir_open(&lfs, &dir[0], "warmpotato") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "baked") => 0; strcmp(info.name, "baked") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "fried") => 0; strcmp(info.name, "fried") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "sweet") => 0; strcmp(info.name, "sweet") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_mkdir(&lfs, "coldpotato") => 0; lfs_mkdir(&lfs, "coldpotato") => 0;
lfs_rename(&lfs, "warmpotato/baked", "coldpotato/baked") => 0; lfs_rename(&lfs, "warmpotato/baked", "coldpotato/baked") => 0;
@@ -263,227 +260,225 @@ scripts/test.py << TEST
lfs_remove(&lfs, "warmpotato") => 0; lfs_remove(&lfs, "warmpotato") => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "coldpotato") => 0; lfs_dir_open(&lfs, &dir[0], "coldpotato") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "baked") => 0; strcmp(info.name, "baked") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "fried") => 0; strcmp(info.name, "fried") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "sweet") => 0; strcmp(info.name, "sweet") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Recursive remove ---" echo "--- Recursive remove ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_remove(&lfs, "coldpotato") => LFS_ERR_NOTEMPTY; lfs_remove(&lfs, "coldpotato") => LFS_ERR_NOTEMPTY;
lfs_dir_open(&lfs, &dir, "coldpotato") => 0; lfs_dir_open(&lfs, &dir[0], "coldpotato") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
while (true) { while (true) {
int err = lfs_dir_read(&lfs, &dir, &info); int err = lfs_dir_read(&lfs, &dir[0], &info);
err >= 0 => 1; err >= 0 => 1;
if (err == 0) { if (err == 0) {
break; break;
} }
strcpy(path, "coldpotato/"); strcpy((char*)buffer, "coldpotato/");
strcat(path, info.name); strcat((char*)buffer, info.name);
lfs_remove(&lfs, path) => 0; lfs_remove(&lfs, (char*)buffer) => 0;
} }
lfs_remove(&lfs, "coldpotato") => 0; lfs_remove(&lfs, "coldpotato") => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "/") => 0; lfs_dir_open(&lfs, &dir[0], "/") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "burito") => 0; strcmp(info.name, "burito") => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "cactus") => 0; strcmp(info.name, "cactus") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Multi-block rename ---" echo "--- Multi-block rename ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
for (int i = 0; i < $LARGESIZE; i++) { for (int i = 0; i < $LARGESIZE; i++) {
char oldpath[1024]; sprintf((char*)buffer, "cactus/test%03d", i);
char newpath[1024]; sprintf((char*)wbuffer, "cactus/tedd%03d", i);
sprintf(oldpath, "cactus/test%03d", i); lfs_rename(&lfs, (char*)buffer, (char*)wbuffer) => 0;
sprintf(newpath, "cactus/tedd%03d", i);
lfs_rename(&lfs, oldpath, newpath) => 0;
} }
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "cactus") => 0; lfs_dir_open(&lfs, &dir[0], "cactus") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
for (int i = 0; i < $LARGESIZE; i++) { for (int i = 0; i < $LARGESIZE; i++) {
sprintf(path, "tedd%03d", i); sprintf((char*)buffer, "tedd%03d", i);
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, path) => 0; strcmp(info.name, (char*)buffer) => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
} }
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Multi-block remove ---" echo "--- Multi-block remove ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_remove(&lfs, "cactus") => LFS_ERR_NOTEMPTY; lfs_remove(&lfs, "cactus") => LFS_ERR_NOTEMPTY;
for (int i = 0; i < $LARGESIZE; i++) { for (int i = 0; i < $LARGESIZE; i++) {
sprintf(path, "cactus/tedd%03d", i); sprintf((char*)buffer, "cactus/tedd%03d", i);
lfs_remove(&lfs, path) => 0; lfs_remove(&lfs, (char*)buffer) => 0;
} }
lfs_remove(&lfs, "cactus") => 0; lfs_remove(&lfs, "cactus") => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "/") => 0; lfs_dir_open(&lfs, &dir[0], "/") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "burito") => 0; strcmp(info.name, "burito") => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Multi-block directory with files ---" echo "--- Multi-block directory with files ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_mkdir(&lfs, "prickly-pear") => 0; lfs_mkdir(&lfs, "prickly-pear") => 0;
for (int i = 0; i < $LARGESIZE; i++) { for (int i = 0; i < $LARGESIZE; i++) {
sprintf(path, "prickly-pear/test%03d", i); sprintf((char*)buffer, "prickly-pear/test%03d", i);
lfs_file_open(&lfs, &file, path, LFS_O_WRONLY | LFS_O_CREAT) => 0; lfs_file_open(&lfs, &file[0], (char*)buffer,
lfs_size_t size = 6; LFS_O_WRONLY | LFS_O_CREAT) => 0;
memcpy(buffer, "Hello", size); size = 6;
lfs_file_write(&lfs, &file, buffer, size) => size; memcpy(wbuffer, "Hello", size);
lfs_file_close(&lfs, &file) => 0; lfs_file_write(&lfs, &file[0], wbuffer, size) => size;
lfs_file_close(&lfs, &file[0]) => 0;
} }
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "prickly-pear") => 0; lfs_dir_open(&lfs, &dir[0], "prickly-pear") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
for (int i = 0; i < $LARGESIZE; i++) { for (int i = 0; i < $LARGESIZE; i++) {
sprintf(path, "test%03d", i); sprintf((char*)buffer, "test%03d", i);
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, path) => 0; strcmp(info.name, (char*)buffer) => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
info.size => 6; info.size => 6;
} }
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Multi-block rename with files ---" echo "--- Multi-block rename with files ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
for (int i = 0; i < $LARGESIZE; i++) { for (int i = 0; i < $LARGESIZE; i++) {
char oldpath[1024]; sprintf((char*)buffer, "prickly-pear/test%03d", i);
char newpath[1024]; sprintf((char*)wbuffer, "prickly-pear/tedd%03d", i);
sprintf(oldpath, "prickly-pear/test%03d", i); lfs_rename(&lfs, (char*)buffer, (char*)wbuffer) => 0;
sprintf(newpath, "prickly-pear/tedd%03d", i);
lfs_rename(&lfs, oldpath, newpath) => 0;
} }
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "prickly-pear") => 0; lfs_dir_open(&lfs, &dir[0], "prickly-pear") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
for (int i = 0; i < $LARGESIZE; i++) { for (int i = 0; i < $LARGESIZE; i++) {
sprintf(path, "tedd%03d", i); sprintf((char*)buffer, "tedd%03d", i);
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, path) => 0; strcmp(info.name, (char*)buffer) => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
info.size => 6; info.size => 6;
} }
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Multi-block remove with files ---" echo "--- Multi-block remove with files ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_remove(&lfs, "prickly-pear") => LFS_ERR_NOTEMPTY; lfs_remove(&lfs, "prickly-pear") => LFS_ERR_NOTEMPTY;
for (int i = 0; i < $LARGESIZE; i++) { for (int i = 0; i < $LARGESIZE; i++) {
sprintf(path, "prickly-pear/tedd%03d", i); sprintf((char*)buffer, "prickly-pear/tedd%03d", i);
lfs_remove(&lfs, path) => 0; lfs_remove(&lfs, (char*)buffer) => 0;
} }
lfs_remove(&lfs, "prickly-pear") => 0; lfs_remove(&lfs, "prickly-pear") => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "/") => 0; lfs_dir_open(&lfs, &dir[0], "/") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "burito") => 0; strcmp(info.name, "burito") => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/results.py echo "--- Results ---"
tests/stats.py

View File

@@ -1,22 +1,19 @@
#!/bin/bash #!/bin/bash
set -eu set -eu
export TEST_FILE=$0
trap 'export TEST_LINE=$LINENO' DEBUG
echo "=== Entry tests ==="
# Note: These tests are intended for 512 byte inline size at different # Note: These tests are intended for 512 byte inline size at different
# inline sizes they should still pass, but won't be testing anything # inline sizes they should still pass, but won't be testing anything
echo "=== Entry tests ==="
rm -rf blocks rm -rf blocks
function read_file { function read_file {
cat << TEST cat << TEST
size = $2; size = $2;
lfs_file_open(&lfs, &file, "$1", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], "$1", LFS_O_RDONLY) => 0;
lfs_file_read(&lfs, &file, rbuffer, size) => size; lfs_file_read(&lfs, &file[0], rbuffer, size) => size;
memcmp(rbuffer, wbuffer, size) => 0; memcmp(rbuffer, wbuffer, size) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
TEST TEST
} }
@@ -24,22 +21,18 @@ function write_file {
cat << TEST cat << TEST
size = $2; size = $2;
lfs_file_open(&lfs, &file, "$1", lfs_file_open(&lfs, &file[0], "$1",
LFS_O_WRONLY | LFS_O_CREAT | LFS_O_TRUNC) => 0; LFS_O_WRONLY | LFS_O_CREAT | LFS_O_TRUNC) => 0;
memset(wbuffer, 'c', size); memset(wbuffer, 'c', size);
lfs_file_write(&lfs, &file, wbuffer, size) => size; lfs_file_write(&lfs, &file[0], wbuffer, size) => size;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
TEST TEST
} }
echo "--- Entry grow test ---" echo "--- Entry grow test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
uint8_t wbuffer[1024];
uint8_t rbuffer[1024];
lfs_size_t size;
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
$(write_file "hi0" 20) $(write_file "hi0" 20)
$(write_file "hi1" 20) $(write_file "hi1" 20)
@@ -57,13 +50,9 @@ scripts/test.py << TEST
TEST TEST
echo "--- Entry shrink test ---" echo "--- Entry shrink test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
uint8_t wbuffer[1024];
uint8_t rbuffer[1024];
lfs_size_t size;
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
$(write_file "hi0" 20) $(write_file "hi0" 20)
$(write_file "hi1" 200) $(write_file "hi1" 200)
@@ -81,13 +70,9 @@ scripts/test.py << TEST
TEST TEST
echo "--- Entry spill test ---" echo "--- Entry spill test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
uint8_t wbuffer[1024];
uint8_t rbuffer[1024];
lfs_size_t size;
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
$(write_file "hi0" 200) $(write_file "hi0" 200)
$(write_file "hi1" 200) $(write_file "hi1" 200)
@@ -102,13 +87,9 @@ scripts/test.py << TEST
TEST TEST
echo "--- Entry push spill test ---" echo "--- Entry push spill test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
uint8_t wbuffer[1024];
uint8_t rbuffer[1024];
lfs_size_t size;
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
$(write_file "hi0" 200) $(write_file "hi0" 200)
$(write_file "hi1" 20) $(write_file "hi1" 20)
@@ -126,13 +107,9 @@ scripts/test.py << TEST
TEST TEST
echo "--- Entry push spill two test ---" echo "--- Entry push spill two test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
uint8_t wbuffer[1024];
uint8_t rbuffer[1024];
lfs_size_t size;
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
$(write_file "hi0" 200) $(write_file "hi0" 200)
$(write_file "hi1" 20) $(write_file "hi1" 20)
@@ -152,13 +129,9 @@ scripts/test.py << TEST
TEST TEST
echo "--- Entry drop test ---" echo "--- Entry drop test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
uint8_t wbuffer[1024];
uint8_t rbuffer[1024];
lfs_size_t size;
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
$(write_file "hi0" 200) $(write_file "hi0" 200)
$(write_file "hi1" 200) $(write_file "hi1" 200)
@@ -186,66 +159,63 @@ scripts/test.py << TEST
TEST TEST
echo "--- Create too big ---" echo "--- Create too big ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
memset(path, 'm', 200); memset(buffer, 'm', 200);
path[200] = '\0'; buffer[200] = '\0';
lfs_size_t size = 400;
lfs_file_open(&lfs, &file, path,
LFS_O_WRONLY | LFS_O_CREAT | LFS_O_TRUNC) => 0;
uint8_t wbuffer[1024];
memset(wbuffer, 'c', size);
lfs_file_write(&lfs, &file, wbuffer, size) => size;
lfs_file_close(&lfs, &file) => 0;
size = 400; size = 400;
lfs_file_open(&lfs, &file, path, LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], (char*)buffer,
uint8_t rbuffer[1024]; LFS_O_WRONLY | LFS_O_CREAT | LFS_O_TRUNC) => 0;
lfs_file_read(&lfs, &file, rbuffer, size) => size; memset(wbuffer, 'c', size);
lfs_file_write(&lfs, &file[0], wbuffer, size) => size;
lfs_file_close(&lfs, &file[0]) => 0;
size = 400;
lfs_file_open(&lfs, &file[0], (char*)buffer, LFS_O_RDONLY) => 0;
lfs_file_read(&lfs, &file[0], rbuffer, size) => size;
memcmp(rbuffer, wbuffer, size) => 0; memcmp(rbuffer, wbuffer, size) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Resize too big ---" echo "--- Resize too big ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
memset(path, 'm', 200); memset(buffer, 'm', 200);
path[200] = '\0'; buffer[200] = '\0';
lfs_size_t size = 40;
lfs_file_open(&lfs, &file, path,
LFS_O_WRONLY | LFS_O_CREAT | LFS_O_TRUNC) => 0;
uint8_t wbuffer[1024];
memset(wbuffer, 'c', size);
lfs_file_write(&lfs, &file, wbuffer, size) => size;
lfs_file_close(&lfs, &file) => 0;
size = 40; size = 40;
lfs_file_open(&lfs, &file, path, LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], (char*)buffer,
uint8_t rbuffer[1024];
lfs_file_read(&lfs, &file, rbuffer, size) => size;
memcmp(rbuffer, wbuffer, size) => 0;
lfs_file_close(&lfs, &file) => 0;
size = 400;
lfs_file_open(&lfs, &file, path,
LFS_O_WRONLY | LFS_O_CREAT | LFS_O_TRUNC) => 0; LFS_O_WRONLY | LFS_O_CREAT | LFS_O_TRUNC) => 0;
memset(wbuffer, 'c', size); memset(wbuffer, 'c', size);
lfs_file_write(&lfs, &file, wbuffer, size) => size; lfs_file_write(&lfs, &file[0], wbuffer, size) => size;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
size = 40;
lfs_file_open(&lfs, &file[0], (char*)buffer, LFS_O_RDONLY) => 0;
lfs_file_read(&lfs, &file[0], rbuffer, size) => size;
memcmp(rbuffer, wbuffer, size) => 0;
lfs_file_close(&lfs, &file[0]) => 0;
size = 400; size = 400;
lfs_file_open(&lfs, &file, path, LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], (char*)buffer,
lfs_file_read(&lfs, &file, rbuffer, size) => size; LFS_O_WRONLY | LFS_O_CREAT | LFS_O_TRUNC) => 0;
memset(wbuffer, 'c', size);
lfs_file_write(&lfs, &file[0], wbuffer, size) => size;
lfs_file_close(&lfs, &file[0]) => 0;
size = 400;
lfs_file_open(&lfs, &file[0], (char*)buffer, LFS_O_RDONLY) => 0;
lfs_file_read(&lfs, &file[0], rbuffer, size) => size;
memcmp(rbuffer, wbuffer, size) => 0; memcmp(rbuffer, wbuffer, size) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/results.py echo "--- Results ---"
tests/stats.py

View File

@@ -1,76 +1,71 @@
#!/bin/bash #!/bin/bash
set -eu set -eu
export TEST_FILE=$0
trap 'export TEST_LINE=$LINENO' DEBUG
echo "=== File tests ==="
SMALLSIZE=32 SMALLSIZE=32
MEDIUMSIZE=8192 MEDIUMSIZE=8192
LARGESIZE=262144 LARGESIZE=262144
echo "=== File tests ==="
rm -rf blocks rm -rf blocks
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
TEST TEST
echo "--- Simple file test ---" echo "--- Simple file test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "hello", LFS_O_WRONLY | LFS_O_CREAT) => 0; lfs_file_open(&lfs, &file[0], "hello", LFS_O_WRONLY | LFS_O_CREAT) => 0;
lfs_size_t size = strlen("Hello World!\n");
uint8_t wbuffer[1024];
memcpy(wbuffer, "Hello World!\n", size);
lfs_file_write(&lfs, &file, wbuffer, size) => size;
lfs_file_close(&lfs, &file) => 0;
lfs_file_open(&lfs, &file, "hello", LFS_O_RDONLY) => 0;
size = strlen("Hello World!\n"); size = strlen("Hello World!\n");
uint8_t rbuffer[1024]; memcpy(wbuffer, "Hello World!\n", size);
lfs_file_read(&lfs, &file, rbuffer, size) => size; lfs_file_write(&lfs, &file[0], wbuffer, size) => size;
lfs_file_close(&lfs, &file[0]) => 0;
lfs_file_open(&lfs, &file[0], "hello", LFS_O_RDONLY) => 0;
size = strlen("Hello World!\n");
lfs_file_read(&lfs, &file[0], rbuffer, size) => size;
memcmp(rbuffer, wbuffer, size) => 0; memcmp(rbuffer, wbuffer, size) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
w_test() { w_test() {
scripts/test.py ${4:-} << TEST tests/test.py ${4:-} << TEST
lfs_size_t size = $1; size = $1;
lfs_size_t chunk = 31; lfs_size_t chunk = 31;
srand(0); srand(0);
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "$2", lfs_file_open(&lfs, &file[0], "$2",
${3:-LFS_O_WRONLY | LFS_O_CREAT | LFS_O_TRUNC}) => 0; ${3:-LFS_O_WRONLY | LFS_O_CREAT | LFS_O_TRUNC}) => 0;
for (lfs_size_t i = 0; i < size; i += chunk) { for (lfs_size_t i = 0; i < size; i += chunk) {
chunk = (chunk < size - i) ? chunk : size - i; chunk = (chunk < size - i) ? chunk : size - i;
for (lfs_size_t b = 0; b < chunk; b++) { for (lfs_size_t b = 0; b < chunk; b++) {
buffer[b] = rand() & 0xff; buffer[b] = rand() & 0xff;
} }
lfs_file_write(&lfs, &file, buffer, chunk) => chunk; lfs_file_write(&lfs, &file[0], buffer, chunk) => chunk;
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
} }
r_test() { r_test() {
scripts/test.py << TEST tests/test.py << TEST
lfs_size_t size = $1; size = $1;
lfs_size_t chunk = 29; lfs_size_t chunk = 29;
srand(0); srand(0);
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_stat(&lfs, "$2", &info) => 0; lfs_stat(&lfs, "$2", &info) => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
info.size => size; info.size => size;
lfs_file_open(&lfs, &file, "$2", ${3:-LFS_O_RDONLY}) => 0; lfs_file_open(&lfs, &file[0], "$2", ${3:-LFS_O_RDONLY}) => 0;
for (lfs_size_t i = 0; i < size; i += chunk) { for (lfs_size_t i = 0; i < size; i += chunk) {
chunk = (chunk < size - i) ? chunk : size - i; chunk = (chunk < size - i) ? chunk : size - i;
lfs_file_read(&lfs, &file, buffer, chunk) => chunk; lfs_file_read(&lfs, &file[0], buffer, chunk) => chunk;
for (lfs_size_t b = 0; b < chunk && i+b < size; b++) { for (lfs_size_t b = 0; b < chunk && i+b < size; b++) {
buffer[b] => rand() & 0xff; buffer[b] => rand() & 0xff;
} }
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
} }
@@ -110,112 +105,54 @@ r_test $LARGESIZE largeavacado
r_test 0 noavacado r_test 0 noavacado
echo "--- Dir check ---" echo "--- Dir check ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "/") => 0; lfs_dir_open(&lfs, &dir[0], "/") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "hello") => 0; strcmp(info.name, "hello") => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
info.size => strlen("Hello World!\n"); info.size => strlen("Hello World!\n");
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "largeavacado") => 0; strcmp(info.name, "largeavacado") => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
info.size => $LARGESIZE; info.size => $LARGESIZE;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "mediumavacado") => 0; strcmp(info.name, "mediumavacado") => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
info.size => $MEDIUMSIZE; info.size => $MEDIUMSIZE;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "noavacado") => 0; strcmp(info.name, "noavacado") => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
info.size => 0; info.size => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "smallavacado") => 0; strcmp(info.name, "smallavacado") => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
info.size => $SMALLSIZE; info.size => $SMALLSIZE;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Many files test ---" echo "--- Many file test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
// Create 300 files of 7 bytes // Create 300 files of 6 bytes
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_mkdir(&lfs, "directory") => 0;
for (unsigned i = 0; i < 300; i++) { for (unsigned i = 0; i < 300; i++) {
sprintf(path, "file_%03d", i); snprintf((char*)buffer, sizeof(buffer), "file_%03d", i);
lfs_file_open(&lfs, &file, path, lfs_file_open(&lfs, &file[0], (char*)buffer, LFS_O_WRONLY | LFS_O_CREAT) => 0;
LFS_O_RDWR | LFS_O_CREAT | LFS_O_EXCL) => 0; size = 6;
lfs_size_t size = 7; memcpy(wbuffer, "Hello", size);
uint8_t wbuffer[1024]; lfs_file_write(&lfs, &file[0], wbuffer, size) => size;
uint8_t rbuffer[1024]; lfs_file_close(&lfs, &file[0]) => 0;
snprintf((char*)wbuffer, size, "Hi %03d", i);
lfs_file_write(&lfs, &file, wbuffer, size) => size;
lfs_file_rewind(&lfs, &file) => 0;
lfs_file_read(&lfs, &file, rbuffer, size) => size;
memcmp(wbuffer, rbuffer, size) => 0;
lfs_file_close(&lfs, &file) => 0;
} }
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Many files with flush test ---" echo "--- Results ---"
scripts/test.py << TEST tests/stats.py
lfs_format(&lfs, &cfg) => 0;
TEST
scripts/test.py << TEST
// Create 300 files of 7 bytes
lfs_mount(&lfs, &cfg) => 0;
for (unsigned i = 0; i < 300; i++) {
sprintf(path, "file_%03d", i);
lfs_file_open(&lfs, &file, path,
LFS_O_WRONLY | LFS_O_CREAT | LFS_O_EXCL) => 0;
lfs_size_t size = 7;
uint8_t wbuffer[1024];
uint8_t rbuffer[1024];
snprintf((char*)wbuffer, size, "Hi %03d", i);
lfs_file_write(&lfs, &file, wbuffer, size) => size;
lfs_file_close(&lfs, &file) => 0;
lfs_file_open(&lfs, &file, path, LFS_O_RDONLY) => 0;
lfs_file_read(&lfs, &file, rbuffer, size) => size;
memcmp(wbuffer, rbuffer, size) => 0;
lfs_file_close(&lfs, &file) => 0;
}
lfs_unmount(&lfs) => 0;
TEST
echo "--- Many files with power cycle test ---"
scripts/test.py << TEST
lfs_format(&lfs, &cfg) => 0;
TEST
scripts/test.py << TEST
// Create 300 files of 7 bytes
lfs_mount(&lfs, &cfg) => 0;
for (unsigned i = 0; i < 300; i++) {
sprintf(path, "file_%03d", i);
lfs_file_open(&lfs, &file, path,
LFS_O_WRONLY | LFS_O_CREAT | LFS_O_EXCL) => 0;
lfs_size_t size = 7;
uint8_t wbuffer[1024];
uint8_t rbuffer[1024];
snprintf((char*)wbuffer, size, "Hi %03d", i);
lfs_file_write(&lfs, &file, wbuffer, size) => size;
lfs_file_close(&lfs, &file) => 0;
lfs_unmount(&lfs) => 0;
lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, path, LFS_O_RDONLY) => 0;
lfs_file_read(&lfs, &file, rbuffer, size) => size;
memcmp(wbuffer, rbuffer, size) => 0;
lfs_file_close(&lfs, &file) => 0;
}
lfs_unmount(&lfs) => 0;
TEST
scripts/results.py

View File

@@ -1,18 +1,16 @@
#!/bin/bash #!/bin/bash
set -eu set -eu
export TEST_FILE=$0
trap 'export TEST_LINE=$LINENO' DEBUG
echo "=== Formatting tests ===" echo "=== Formatting tests ==="
rm -rf blocks rm -rf blocks
echo "--- Basic formatting ---" echo "--- Basic formatting ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
TEST TEST
echo "--- Basic mounting ---" echo "--- Basic mounting ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
@@ -22,18 +20,18 @@ TEST
echo "--- Invalid superblocks ---" echo "--- Invalid superblocks ---"
ln -f -s /dev/zero blocks/0 ln -f -s /dev/zero blocks/0
ln -f -s /dev/zero blocks/1 ln -f -s /dev/zero blocks/1
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => LFS_ERR_NOSPC; lfs_format(&lfs, &cfg) => LFS_ERR_NOSPC;
TEST TEST
rm blocks/0 blocks/1 rm blocks/0 blocks/1
echo "--- Invalid mount ---" echo "--- Invalid mount ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => LFS_ERR_CORRUPT; lfs_mount(&lfs, &cfg) => LFS_ERR_CORRUPT;
TEST TEST
echo "--- Expanding superblock ---" echo "--- Expanding superblock ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
for (int i = 0; i < 100; i++) { for (int i = 0; i < 100; i++) {
@@ -42,10 +40,11 @@ scripts/test.py << TEST
} }
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_mkdir(&lfs, "dummy") => 0; lfs_mkdir(&lfs, "dummy") => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/results.py echo "--- Results ---"
tests/stats.py

View File

@@ -1,93 +1,89 @@
#!/bin/bash #!/bin/bash
set -eu set -eu
export TEST_FILE=$0
trap 'export TEST_LINE=$LINENO' DEBUG
echo "=== Interspersed tests ===" echo "=== Interspersed tests ==="
rm -rf blocks rm -rf blocks
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
TEST TEST
echo "--- Interspersed file test ---" echo "--- Interspersed file test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_t files[4]; lfs_file_open(&lfs, &file[0], "a", LFS_O_WRONLY | LFS_O_CREAT) => 0;
lfs_file_open(&lfs, &files[0], "a", LFS_O_WRONLY | LFS_O_CREAT) => 0; lfs_file_open(&lfs, &file[1], "b", LFS_O_WRONLY | LFS_O_CREAT) => 0;
lfs_file_open(&lfs, &files[1], "b", LFS_O_WRONLY | LFS_O_CREAT) => 0; lfs_file_open(&lfs, &file[2], "c", LFS_O_WRONLY | LFS_O_CREAT) => 0;
lfs_file_open(&lfs, &files[2], "c", LFS_O_WRONLY | LFS_O_CREAT) => 0; lfs_file_open(&lfs, &file[3], "d", LFS_O_WRONLY | LFS_O_CREAT) => 0;
lfs_file_open(&lfs, &files[3], "d", LFS_O_WRONLY | LFS_O_CREAT) => 0;
for (int i = 0; i < 10; i++) { for (int i = 0; i < 10; i++) {
lfs_file_write(&lfs, &files[0], (const void*)"a", 1) => 1; lfs_file_write(&lfs, &file[0], (const void*)"a", 1) => 1;
lfs_file_write(&lfs, &files[1], (const void*)"b", 1) => 1; lfs_file_write(&lfs, &file[1], (const void*)"b", 1) => 1;
lfs_file_write(&lfs, &files[2], (const void*)"c", 1) => 1; lfs_file_write(&lfs, &file[2], (const void*)"c", 1) => 1;
lfs_file_write(&lfs, &files[3], (const void*)"d", 1) => 1; lfs_file_write(&lfs, &file[3], (const void*)"d", 1) => 1;
} }
lfs_file_close(&lfs, &files[0]); lfs_file_close(&lfs, &file[0]);
lfs_file_close(&lfs, &files[1]); lfs_file_close(&lfs, &file[1]);
lfs_file_close(&lfs, &files[2]); lfs_file_close(&lfs, &file[2]);
lfs_file_close(&lfs, &files[3]); lfs_file_close(&lfs, &file[3]);
lfs_dir_open(&lfs, &dir, "/") => 0; lfs_dir_open(&lfs, &dir[0], "/") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "a") => 0; strcmp(info.name, "a") => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
info.size => 10; info.size => 10;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "b") => 0; strcmp(info.name, "b") => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
info.size => 10; info.size => 10;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "c") => 0; strcmp(info.name, "c") => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
info.size => 10; info.size => 10;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "d") => 0; strcmp(info.name, "d") => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
info.size => 10; info.size => 10;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_file_open(&lfs, &files[0], "a", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], "a", LFS_O_RDONLY) => 0;
lfs_file_open(&lfs, &files[1], "b", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[1], "b", LFS_O_RDONLY) => 0;
lfs_file_open(&lfs, &files[2], "c", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[2], "c", LFS_O_RDONLY) => 0;
lfs_file_open(&lfs, &files[3], "d", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[3], "d", LFS_O_RDONLY) => 0;
for (int i = 0; i < 10; i++) { for (int i = 0; i < 10; i++) {
lfs_file_read(&lfs, &files[0], buffer, 1) => 1; lfs_file_read(&lfs, &file[0], buffer, 1) => 1;
buffer[0] => 'a'; buffer[0] => 'a';
lfs_file_read(&lfs, &files[1], buffer, 1) => 1; lfs_file_read(&lfs, &file[1], buffer, 1) => 1;
buffer[0] => 'b'; buffer[0] => 'b';
lfs_file_read(&lfs, &files[2], buffer, 1) => 1; lfs_file_read(&lfs, &file[2], buffer, 1) => 1;
buffer[0] => 'c'; buffer[0] => 'c';
lfs_file_read(&lfs, &files[3], buffer, 1) => 1; lfs_file_read(&lfs, &file[3], buffer, 1) => 1;
buffer[0] => 'd'; buffer[0] => 'd';
} }
lfs_file_close(&lfs, &files[0]); lfs_file_close(&lfs, &file[0]);
lfs_file_close(&lfs, &files[1]); lfs_file_close(&lfs, &file[1]);
lfs_file_close(&lfs, &files[2]); lfs_file_close(&lfs, &file[2]);
lfs_file_close(&lfs, &files[3]); lfs_file_close(&lfs, &file[3]);
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Interspersed remove file test ---" echo "--- Interspersed remove file test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_t files[4]; lfs_file_open(&lfs, &file[0], "e", LFS_O_WRONLY | LFS_O_CREAT) => 0;
lfs_file_open(&lfs, &files[0], "e", LFS_O_WRONLY | LFS_O_CREAT) => 0;
for (int i = 0; i < 5; i++) { for (int i = 0; i < 5; i++) {
lfs_file_write(&lfs, &files[0], (const void*)"e", 1) => 1; lfs_file_write(&lfs, &file[0], (const void*)"e", 1) => 1;
} }
lfs_remove(&lfs, "a") => 0; lfs_remove(&lfs, "a") => 0;
@@ -96,95 +92,95 @@ scripts/test.py << TEST
lfs_remove(&lfs, "d") => 0; lfs_remove(&lfs, "d") => 0;
for (int i = 0; i < 5; i++) { for (int i = 0; i < 5; i++) {
lfs_file_write(&lfs, &files[0], (const void*)"e", 1) => 1; lfs_file_write(&lfs, &file[0], (const void*)"e", 1) => 1;
} }
lfs_file_close(&lfs, &files[0]); lfs_file_close(&lfs, &file[0]);
lfs_dir_open(&lfs, &dir, "/") => 0; lfs_dir_open(&lfs, &dir[0], "/") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "e") => 0; strcmp(info.name, "e") => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
info.size => 10; info.size => 10;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_file_open(&lfs, &files[0], "e", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], "e", LFS_O_RDONLY) => 0;
for (int i = 0; i < 10; i++) { for (int i = 0; i < 10; i++) {
lfs_file_read(&lfs, &files[0], buffer, 1) => 1; lfs_file_read(&lfs, &file[0], buffer, 1) => 1;
buffer[0] => 'e'; buffer[0] => 'e';
} }
lfs_file_close(&lfs, &files[0]); lfs_file_close(&lfs, &file[0]);
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Remove inconveniently test ---" echo "--- Remove inconveniently test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_t files[4]; lfs_file_open(&lfs, &file[0], "e", LFS_O_WRONLY | LFS_O_TRUNC) => 0;
lfs_file_open(&lfs, &files[0], "e", LFS_O_WRONLY | LFS_O_TRUNC) => 0; lfs_file_open(&lfs, &file[1], "f", LFS_O_WRONLY | LFS_O_CREAT) => 0;
lfs_file_open(&lfs, &files[1], "f", LFS_O_WRONLY | LFS_O_CREAT) => 0; lfs_file_open(&lfs, &file[2], "g", LFS_O_WRONLY | LFS_O_CREAT) => 0;
lfs_file_open(&lfs, &files[2], "g", LFS_O_WRONLY | LFS_O_CREAT) => 0;
for (int i = 0; i < 5; i++) { for (int i = 0; i < 5; i++) {
lfs_file_write(&lfs, &files[0], (const void*)"e", 1) => 1; lfs_file_write(&lfs, &file[0], (const void*)"e", 1) => 1;
lfs_file_write(&lfs, &files[1], (const void*)"f", 1) => 1; lfs_file_write(&lfs, &file[1], (const void*)"f", 1) => 1;
lfs_file_write(&lfs, &files[2], (const void*)"g", 1) => 1; lfs_file_write(&lfs, &file[2], (const void*)"g", 1) => 1;
} }
lfs_remove(&lfs, "f") => 0; lfs_remove(&lfs, "f") => 0;
for (int i = 0; i < 5; i++) { for (int i = 0; i < 5; i++) {
lfs_file_write(&lfs, &files[0], (const void*)"e", 1) => 1; lfs_file_write(&lfs, &file[0], (const void*)"e", 1) => 1;
lfs_file_write(&lfs, &files[1], (const void*)"f", 1) => 1; lfs_file_write(&lfs, &file[1], (const void*)"f", 1) => 1;
lfs_file_write(&lfs, &files[2], (const void*)"g", 1) => 1; lfs_file_write(&lfs, &file[2], (const void*)"g", 1) => 1;
} }
lfs_file_close(&lfs, &files[0]); lfs_file_close(&lfs, &file[0]);
lfs_file_close(&lfs, &files[1]); lfs_file_close(&lfs, &file[1]);
lfs_file_close(&lfs, &files[2]); lfs_file_close(&lfs, &file[2]);
lfs_dir_open(&lfs, &dir, "/") => 0; lfs_dir_open(&lfs, &dir[0], "/") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "e") => 0; strcmp(info.name, "e") => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
info.size => 10; info.size => 10;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "g") => 0; strcmp(info.name, "g") => 0;
info.type => LFS_TYPE_REG; info.type => LFS_TYPE_REG;
info.size => 10; info.size => 10;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_file_open(&lfs, &files[0], "e", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], "e", LFS_O_RDONLY) => 0;
lfs_file_open(&lfs, &files[1], "g", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[1], "g", LFS_O_RDONLY) => 0;
for (int i = 0; i < 10; i++) { for (int i = 0; i < 10; i++) {
lfs_file_read(&lfs, &files[0], buffer, 1) => 1; lfs_file_read(&lfs, &file[0], buffer, 1) => 1;
buffer[0] => 'e'; buffer[0] => 'e';
lfs_file_read(&lfs, &files[1], buffer, 1) => 1; lfs_file_read(&lfs, &file[1], buffer, 1) => 1;
buffer[0] => 'g'; buffer[0] => 'g';
} }
lfs_file_close(&lfs, &files[0]); lfs_file_close(&lfs, &file[0]);
lfs_file_close(&lfs, &files[1]); lfs_file_close(&lfs, &file[1]);
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/results.py echo "--- Results ---"
tests/stats.py

View File

@@ -1,11 +1,9 @@
#!/bin/bash #!/bin/bash
set -eu set -eu
export TEST_FILE=$0
trap 'export TEST_LINE=$LINENO' DEBUG
echo "=== Move tests ===" echo "=== Move tests ==="
rm -rf blocks rm -rf blocks
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
@@ -19,272 +17,272 @@ scripts/test.py << TEST
lfs_mkdir(&lfs, "a/hi/bonjour") => 0; lfs_mkdir(&lfs, "a/hi/bonjour") => 0;
lfs_mkdir(&lfs, "a/hi/ohayo") => 0; lfs_mkdir(&lfs, "a/hi/ohayo") => 0;
lfs_file_open(&lfs, &file, "a/hello", LFS_O_CREAT | LFS_O_WRONLY) => 0; lfs_file_open(&lfs, &file[0], "a/hello", LFS_O_CREAT | LFS_O_WRONLY) => 0;
lfs_file_write(&lfs, &file, "hola\n", 5) => 5; lfs_file_write(&lfs, &file[0], "hola\n", 5) => 5;
lfs_file_write(&lfs, &file, "bonjour\n", 8) => 8; lfs_file_write(&lfs, &file[0], "bonjour\n", 8) => 8;
lfs_file_write(&lfs, &file, "ohayo\n", 6) => 6; lfs_file_write(&lfs, &file[0], "ohayo\n", 6) => 6;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Move file ---" echo "--- Move file ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_rename(&lfs, "a/hello", "b/hello") => 0; lfs_rename(&lfs, "a/hello", "b/hello") => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "a") => 0; lfs_dir_open(&lfs, &dir[0], "a") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "hi") => 0; strcmp(info.name, "hi") => 0;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_dir_open(&lfs, &dir, "b") => 0; lfs_dir_open(&lfs, &dir[0], "b") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "hello") => 0; strcmp(info.name, "hello") => 0;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Move file corrupt source ---" echo "--- Move file corrupt source ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_rename(&lfs, "b/hello", "c/hello") => 0; lfs_rename(&lfs, "b/hello", "c/hello") => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/corrupt.py -n 1 tests/corrupt.py -n 1
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "b") => 0; lfs_dir_open(&lfs, &dir[0], "b") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_dir_open(&lfs, &dir, "c") => 0; lfs_dir_open(&lfs, &dir[0], "c") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "hello") => 0; strcmp(info.name, "hello") => 0;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Move file corrupt source and dest ---" echo "--- Move file corrupt source and dest ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_rename(&lfs, "c/hello", "d/hello") => 0; lfs_rename(&lfs, "c/hello", "d/hello") => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/corrupt.py -n 2 tests/corrupt.py -n 2
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "c") => 0; lfs_dir_open(&lfs, &dir[0], "c") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "hello") => 0; strcmp(info.name, "hello") => 0;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_dir_open(&lfs, &dir, "d") => 0; lfs_dir_open(&lfs, &dir[0], "d") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Move file after corrupt ---" echo "--- Move file after corrupt ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_rename(&lfs, "c/hello", "d/hello") => 0; lfs_rename(&lfs, "c/hello", "d/hello") => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "c") => 0; lfs_dir_open(&lfs, &dir[0], "c") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_dir_open(&lfs, &dir, "d") => 0; lfs_dir_open(&lfs, &dir[0], "d") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "hello") => 0; strcmp(info.name, "hello") => 0;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Move dir ---" echo "--- Move dir ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_rename(&lfs, "a/hi", "b/hi") => 0; lfs_rename(&lfs, "a/hi", "b/hi") => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "a") => 0; lfs_dir_open(&lfs, &dir[0], "a") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_dir_open(&lfs, &dir, "b") => 0; lfs_dir_open(&lfs, &dir[0], "b") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "hi") => 0; strcmp(info.name, "hi") => 0;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Move dir corrupt source ---" echo "--- Move dir corrupt source ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_rename(&lfs, "b/hi", "c/hi") => 0; lfs_rename(&lfs, "b/hi", "c/hi") => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/corrupt.py -n 1 tests/corrupt.py -n 1
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "b") => 0; lfs_dir_open(&lfs, &dir[0], "b") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_dir_open(&lfs, &dir, "c") => 0; lfs_dir_open(&lfs, &dir[0], "c") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "hi") => 0; strcmp(info.name, "hi") => 0;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Move dir corrupt source and dest ---" echo "--- Move dir corrupt source and dest ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_rename(&lfs, "c/hi", "d/hi") => 0; lfs_rename(&lfs, "c/hi", "d/hi") => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/corrupt.py -n 2 tests/corrupt.py -n 2
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "c") => 0; lfs_dir_open(&lfs, &dir[0], "c") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "hi") => 0; strcmp(info.name, "hi") => 0;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_dir_open(&lfs, &dir, "d") => 0; lfs_dir_open(&lfs, &dir[0], "d") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "hello") => 0; strcmp(info.name, "hello") => 0;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Move dir after corrupt ---" echo "--- Move dir after corrupt ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_rename(&lfs, "c/hi", "d/hi") => 0; lfs_rename(&lfs, "c/hi", "d/hi") => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "c") => 0; lfs_dir_open(&lfs, &dir[0], "c") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_dir_open(&lfs, &dir, "d") => 0; lfs_dir_open(&lfs, &dir[0], "d") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "hello") => 0; strcmp(info.name, "hello") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "hi") => 0; strcmp(info.name, "hi") => 0;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Move check ---" echo "--- Move check ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "a/hi") => LFS_ERR_NOENT; lfs_dir_open(&lfs, &dir[0], "a/hi") => LFS_ERR_NOENT;
lfs_dir_open(&lfs, &dir, "b/hi") => LFS_ERR_NOENT; lfs_dir_open(&lfs, &dir[0], "b/hi") => LFS_ERR_NOENT;
lfs_dir_open(&lfs, &dir, "c/hi") => LFS_ERR_NOENT; lfs_dir_open(&lfs, &dir[0], "c/hi") => LFS_ERR_NOENT;
lfs_dir_open(&lfs, &dir, "d/hi") => 0; lfs_dir_open(&lfs, &dir[0], "d/hi") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "bonjour") => 0; strcmp(info.name, "bonjour") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "hola") => 0; strcmp(info.name, "hola") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "ohayo") => 0; strcmp(info.name, "ohayo") => 0;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_dir_open(&lfs, &dir, "a/hello") => LFS_ERR_NOENT; lfs_dir_open(&lfs, &dir[0], "a/hello") => LFS_ERR_NOENT;
lfs_dir_open(&lfs, &dir, "b/hello") => LFS_ERR_NOENT; lfs_dir_open(&lfs, &dir[0], "b/hello") => LFS_ERR_NOENT;
lfs_dir_open(&lfs, &dir, "c/hello") => LFS_ERR_NOENT; lfs_dir_open(&lfs, &dir[0], "c/hello") => LFS_ERR_NOENT;
lfs_file_open(&lfs, &file, "d/hello", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], "d/hello", LFS_O_RDONLY) => 0;
lfs_file_read(&lfs, &file, buffer, 5) => 5; lfs_file_read(&lfs, &file[0], buffer, 5) => 5;
memcmp(buffer, "hola\n", 5) => 0; memcmp(buffer, "hola\n", 5) => 0;
lfs_file_read(&lfs, &file, buffer, 8) => 8; lfs_file_read(&lfs, &file[0], buffer, 8) => 8;
memcmp(buffer, "bonjour\n", 8) => 0; memcmp(buffer, "bonjour\n", 8) => 0;
lfs_file_read(&lfs, &file, buffer, 6) => 6; lfs_file_read(&lfs, &file[0], buffer, 6) => 6;
memcmp(buffer, "ohayo\n", 6) => 0; memcmp(buffer, "ohayo\n", 6) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Move state stealing ---" echo "--- Move state stealing ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_remove(&lfs, "b") => 0; lfs_remove(&lfs, "b") => 0;
@@ -292,42 +290,43 @@ scripts/test.py << TEST
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "a/hi") => LFS_ERR_NOENT; lfs_dir_open(&lfs, &dir[0], "a/hi") => LFS_ERR_NOENT;
lfs_dir_open(&lfs, &dir, "b") => LFS_ERR_NOENT; lfs_dir_open(&lfs, &dir[0], "b") => LFS_ERR_NOENT;
lfs_dir_open(&lfs, &dir, "c") => LFS_ERR_NOENT; lfs_dir_open(&lfs, &dir[0], "c") => LFS_ERR_NOENT;
lfs_dir_open(&lfs, &dir, "d/hi") => 0; lfs_dir_open(&lfs, &dir[0], "d/hi") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "bonjour") => 0; strcmp(info.name, "bonjour") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "hola") => 0; strcmp(info.name, "hola") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "ohayo") => 0; strcmp(info.name, "ohayo") => 0;
lfs_dir_read(&lfs, &dir, &info) => 0; lfs_dir_read(&lfs, &dir[0], &info) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_dir_open(&lfs, &dir, "a/hello") => LFS_ERR_NOENT; lfs_dir_open(&lfs, &dir[0], "a/hello") => LFS_ERR_NOENT;
lfs_dir_open(&lfs, &dir, "b") => LFS_ERR_NOENT; lfs_dir_open(&lfs, &dir[0], "b") => LFS_ERR_NOENT;
lfs_dir_open(&lfs, &dir, "c") => LFS_ERR_NOENT; lfs_dir_open(&lfs, &dir[0], "c") => LFS_ERR_NOENT;
lfs_file_open(&lfs, &file, "d/hello", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], "d/hello", LFS_O_RDONLY) => 0;
lfs_file_read(&lfs, &file, buffer, 5) => 5; lfs_file_read(&lfs, &file[0], buffer, 5) => 5;
memcmp(buffer, "hola\n", 5) => 0; memcmp(buffer, "hola\n", 5) => 0;
lfs_file_read(&lfs, &file, buffer, 8) => 8; lfs_file_read(&lfs, &file[0], buffer, 8) => 8;
memcmp(buffer, "bonjour\n", 8) => 0; memcmp(buffer, "bonjour\n", 8) => 0;
lfs_file_read(&lfs, &file, buffer, 6) => 6; lfs_file_read(&lfs, &file[0], buffer, 6) => 6;
memcmp(buffer, "ohayo\n", 6) => 0; memcmp(buffer, "ohayo\n", 6) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/results.py echo "--- Results ---"
tests/stats.py

View File

@@ -1,16 +1,14 @@
#!/bin/bash #!/bin/bash
set -eu set -eu
export TEST_FILE=$0
trap 'export TEST_LINE=$LINENO' DEBUG
echo "=== Orphan tests ===" echo "=== Orphan tests ==="
rm -rf blocks rm -rf blocks
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
TEST TEST
echo "--- Orphan test ---" echo "--- Orphan test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_mkdir(&lfs, "parent") => 0; lfs_mkdir(&lfs, "parent") => 0;
lfs_mkdir(&lfs, "parent/orphan") => 0; lfs_mkdir(&lfs, "parent/orphan") => 0;
@@ -19,8 +17,8 @@ scripts/test.py << TEST
TEST TEST
# corrupt most recent commit, this should be the update to the previous # corrupt most recent commit, this should be the update to the previous
# linked-list entry and should orphan the child # linked-list entry and should orphan the child
scripts/corrupt.py tests/corrupt.py
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_stat(&lfs, "parent/orphan", &info) => LFS_ERR_NOENT; lfs_stat(&lfs, "parent/orphan", &info) => LFS_ERR_NOENT;
@@ -43,4 +41,5 @@ scripts/test.py << TEST
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/results.py echo "--- Results ---"
tests/stats.py

View File

@@ -1,15 +1,13 @@
#!/bin/bash #!/bin/bash
set -eu set -eu
export TEST_FILE=$0
trap 'export TEST_LINE=$LINENO' DEBUG
echo "=== Path tests ===" echo "=== Path tests ==="
rm -rf blocks rm -rf blocks
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_mkdir(&lfs, "tea") => 0; lfs_mkdir(&lfs, "tea") => 0;
lfs_mkdir(&lfs, "coffee") => 0; lfs_mkdir(&lfs, "coffee") => 0;
@@ -27,7 +25,7 @@ scripts/test.py << TEST
TEST TEST
echo "--- Root path tests ---" echo "--- Root path tests ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_stat(&lfs, "tea/hottea", &info) => 0; lfs_stat(&lfs, "tea/hottea", &info) => 0;
strcmp(info.name, "hottea") => 0; strcmp(info.name, "hottea") => 0;
@@ -41,7 +39,7 @@ scripts/test.py << TEST
TEST TEST
echo "--- Redundant slash path tests ---" echo "--- Redundant slash path tests ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_stat(&lfs, "/tea/hottea", &info) => 0; lfs_stat(&lfs, "/tea/hottea", &info) => 0;
strcmp(info.name, "hottea") => 0; strcmp(info.name, "hottea") => 0;
@@ -57,7 +55,7 @@ scripts/test.py << TEST
TEST TEST
echo "--- Dot path tests ---" echo "--- Dot path tests ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_stat(&lfs, "./tea/hottea", &info) => 0; lfs_stat(&lfs, "./tea/hottea", &info) => 0;
strcmp(info.name, "hottea") => 0; strcmp(info.name, "hottea") => 0;
@@ -75,7 +73,7 @@ scripts/test.py << TEST
TEST TEST
echo "--- Dot dot path tests ---" echo "--- Dot dot path tests ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_stat(&lfs, "coffee/../tea/hottea", &info) => 0; lfs_stat(&lfs, "coffee/../tea/hottea", &info) => 0;
strcmp(info.name, "hottea") => 0; strcmp(info.name, "hottea") => 0;
@@ -93,7 +91,7 @@ scripts/test.py << TEST
TEST TEST
echo "--- Trailing dot path tests ---" echo "--- Trailing dot path tests ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_stat(&lfs, "tea/hottea/", &info) => 0; lfs_stat(&lfs, "tea/hottea/", &info) => 0;
strcmp(info.name, "hottea") => 0; strcmp(info.name, "hottea") => 0;
@@ -109,7 +107,7 @@ scripts/test.py << TEST
TEST TEST
echo "--- Root dot dot path tests ---" echo "--- Root dot dot path tests ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_stat(&lfs, "coffee/../../../../../../tea/hottea", &info) => 0; lfs_stat(&lfs, "coffee/../../../../../../tea/hottea", &info) => 0;
strcmp(info.name, "hottea") => 0; strcmp(info.name, "hottea") => 0;
@@ -121,14 +119,14 @@ scripts/test.py << TEST
TEST TEST
echo "--- Root tests ---" echo "--- Root tests ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_stat(&lfs, "/", &info) => 0; lfs_stat(&lfs, "/", &info) => 0;
info.type => LFS_TYPE_DIR; info.type => LFS_TYPE_DIR;
strcmp(info.name, "/") => 0; strcmp(info.name, "/") => 0;
lfs_mkdir(&lfs, "/") => LFS_ERR_EXIST; lfs_mkdir(&lfs, "/") => LFS_ERR_EXIST;
lfs_file_open(&lfs, &file, "/", LFS_O_WRONLY | LFS_O_CREAT) lfs_file_open(&lfs, &file[0], "/", LFS_O_WRONLY | LFS_O_CREAT)
=> LFS_ERR_ISDIR; => LFS_ERR_ISDIR;
// more corner cases // more corner cases
@@ -142,7 +140,7 @@ scripts/test.py << TEST
TEST TEST
echo "--- Sketchy path tests ---" echo "--- Sketchy path tests ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_mkdir(&lfs, "dirt/ground") => LFS_ERR_NOENT; lfs_mkdir(&lfs, "dirt/ground") => LFS_ERR_NOENT;
lfs_mkdir(&lfs, "dirt/ground/earth") => LFS_ERR_NOENT; lfs_mkdir(&lfs, "dirt/ground/earth") => LFS_ERR_NOENT;
@@ -150,7 +148,7 @@ scripts/test.py << TEST
TEST TEST
echo "--- Superblock conflict test ---" echo "--- Superblock conflict test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_mkdir(&lfs, "littlefs") => 0; lfs_mkdir(&lfs, "littlefs") => 0;
lfs_remove(&lfs, "littlefs") => 0; lfs_remove(&lfs, "littlefs") => 0;
@@ -158,45 +156,46 @@ scripts/test.py << TEST
TEST TEST
echo "--- Max path test ---" echo "--- Max path test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
memset(path, 'w', LFS_NAME_MAX+1); memset(buffer, 'w', LFS_NAME_MAX+1);
path[LFS_NAME_MAX+2] = '\0'; buffer[LFS_NAME_MAX+2] = '\0';
lfs_mkdir(&lfs, path) => LFS_ERR_NAMETOOLONG; lfs_mkdir(&lfs, (char*)buffer) => LFS_ERR_NAMETOOLONG;
lfs_file_open(&lfs, &file, path, lfs_file_open(&lfs, &file[0], (char*)buffer,
LFS_O_WRONLY | LFS_O_CREAT) => LFS_ERR_NAMETOOLONG; LFS_O_WRONLY | LFS_O_CREAT) => LFS_ERR_NAMETOOLONG;
memcpy(path, "coffee/", strlen("coffee/")); memcpy(buffer, "coffee/", strlen("coffee/"));
memset(path+strlen("coffee/"), 'w', LFS_NAME_MAX+1); memset(buffer+strlen("coffee/"), 'w', LFS_NAME_MAX+1);
path[strlen("coffee/")+LFS_NAME_MAX+2] = '\0'; buffer[strlen("coffee/")+LFS_NAME_MAX+2] = '\0';
lfs_mkdir(&lfs, path) => LFS_ERR_NAMETOOLONG; lfs_mkdir(&lfs, (char*)buffer) => LFS_ERR_NAMETOOLONG;
lfs_file_open(&lfs, &file, path, lfs_file_open(&lfs, &file[0], (char*)buffer,
LFS_O_WRONLY | LFS_O_CREAT) => LFS_ERR_NAMETOOLONG; LFS_O_WRONLY | LFS_O_CREAT) => LFS_ERR_NAMETOOLONG;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Really big path test ---" echo "--- Really big path test ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
memset(path, 'w', LFS_NAME_MAX); memset(buffer, 'w', LFS_NAME_MAX);
path[LFS_NAME_MAX+1] = '\0'; buffer[LFS_NAME_MAX+1] = '\0';
lfs_mkdir(&lfs, path) => 0; lfs_mkdir(&lfs, (char*)buffer) => 0;
lfs_remove(&lfs, path) => 0; lfs_remove(&lfs, (char*)buffer) => 0;
lfs_file_open(&lfs, &file, path, lfs_file_open(&lfs, &file[0], (char*)buffer,
LFS_O_WRONLY | LFS_O_CREAT) => 0; LFS_O_WRONLY | LFS_O_CREAT) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_remove(&lfs, path) => 0; lfs_remove(&lfs, (char*)buffer) => 0;
memcpy(path, "coffee/", strlen("coffee/")); memcpy(buffer, "coffee/", strlen("coffee/"));
memset(path+strlen("coffee/"), 'w', LFS_NAME_MAX); memset(buffer+strlen("coffee/"), 'w', LFS_NAME_MAX);
path[strlen("coffee/")+LFS_NAME_MAX+1] = '\0'; buffer[strlen("coffee/")+LFS_NAME_MAX+1] = '\0';
lfs_mkdir(&lfs, path) => 0; lfs_mkdir(&lfs, (char*)buffer) => 0;
lfs_remove(&lfs, path) => 0; lfs_remove(&lfs, (char*)buffer) => 0;
lfs_file_open(&lfs, &file, path, lfs_file_open(&lfs, &file[0], (char*)buffer,
LFS_O_WRONLY | LFS_O_CREAT) => 0; LFS_O_WRONLY | LFS_O_CREAT) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_remove(&lfs, path) => 0; lfs_remove(&lfs, (char*)buffer) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/results.py echo "--- Results ---"
tests/stats.py

View File

@@ -1,431 +1,361 @@
#!/bin/bash #!/bin/bash
set -eu set -eu
export TEST_FILE=$0
trap 'export TEST_LINE=$LINENO' DEBUG
echo "=== Seek tests ==="
SMALLSIZE=4 SMALLSIZE=4
MEDIUMSIZE=128 MEDIUMSIZE=128
LARGESIZE=132 LARGESIZE=132
echo "=== Seek tests ==="
rm -rf blocks rm -rf blocks
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_mkdir(&lfs, "hello") => 0; lfs_mkdir(&lfs, "hello") => 0;
for (int i = 0; i < $LARGESIZE; i++) { for (int i = 0; i < $LARGESIZE; i++) {
sprintf(path, "hello/kitty%03d", i); sprintf((char*)buffer, "hello/kitty%03d", i);
lfs_file_open(&lfs, &file, path, lfs_file_open(&lfs, &file[0], (char*)buffer,
LFS_O_WRONLY | LFS_O_CREAT | LFS_O_APPEND) => 0; LFS_O_WRONLY | LFS_O_CREAT | LFS_O_APPEND) => 0;
lfs_size_t size = strlen("kittycatcat"); size = strlen("kittycatcat");
memcpy(buffer, "kittycatcat", size); memcpy(buffer, "kittycatcat", size);
for (int j = 0; j < $LARGESIZE; j++) { for (int j = 0; j < $LARGESIZE; j++) {
lfs_file_write(&lfs, &file, buffer, size); lfs_file_write(&lfs, &file[0], buffer, size);
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
} }
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Simple dir seek ---" echo "--- Simple dir seek ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "hello") => 0; lfs_dir_open(&lfs, &dir[0], "hello") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_soff_t pos; lfs_soff_t pos;
int i; int i;
for (i = 0; i < $SMALLSIZE; i++) { for (i = 0; i < $SMALLSIZE; i++) {
sprintf(path, "kitty%03d", i); sprintf((char*)buffer, "kitty%03d", i);
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, path) => 0; strcmp(info.name, (char*)buffer) => 0;
pos = lfs_dir_tell(&lfs, &dir); pos = lfs_dir_tell(&lfs, &dir[0]);
} }
pos >= 0 => 1; pos >= 0 => 1;
lfs_dir_seek(&lfs, &dir, pos) => 0; lfs_dir_seek(&lfs, &dir[0], pos) => 0;
sprintf(path, "kitty%03d", i); sprintf((char*)buffer, "kitty%03d", i);
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, path) => 0; strcmp(info.name, (char*)buffer) => 0;
lfs_dir_rewind(&lfs, &dir) => 0; lfs_dir_rewind(&lfs, &dir[0]) => 0;
sprintf(path, "kitty%03d", 0); sprintf((char*)buffer, "kitty%03d", 0);
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, path) => 0; strcmp(info.name, (char*)buffer) => 0;
lfs_dir_seek(&lfs, &dir, pos) => 0; lfs_dir_seek(&lfs, &dir[0], pos) => 0;
sprintf(path, "kitty%03d", i); sprintf((char*)buffer, "kitty%03d", i);
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, path) => 0; strcmp(info.name, (char*)buffer) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Large dir seek ---" echo "--- Large dir seek ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_dir_open(&lfs, &dir, "hello") => 0; lfs_dir_open(&lfs, &dir[0], "hello") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_soff_t pos; lfs_soff_t pos;
int i; int i;
for (i = 0; i < $MEDIUMSIZE; i++) { for (i = 0; i < $MEDIUMSIZE; i++) {
sprintf(path, "kitty%03d", i); sprintf((char*)buffer, "kitty%03d", i);
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, path) => 0; strcmp(info.name, (char*)buffer) => 0;
pos = lfs_dir_tell(&lfs, &dir); pos = lfs_dir_tell(&lfs, &dir[0]);
} }
pos >= 0 => 1; pos >= 0 => 1;
lfs_dir_seek(&lfs, &dir, pos) => 0; lfs_dir_seek(&lfs, &dir[0], pos) => 0;
sprintf(path, "kitty%03d", i); sprintf((char*)buffer, "kitty%03d", i);
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, path) => 0; strcmp(info.name, (char*)buffer) => 0;
lfs_dir_rewind(&lfs, &dir) => 0; lfs_dir_rewind(&lfs, &dir[0]) => 0;
sprintf(path, "kitty%03d", 0); sprintf((char*)buffer, "kitty%03d", 0);
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, ".") => 0; strcmp(info.name, ".") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, "..") => 0; strcmp(info.name, "..") => 0;
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, path) => 0; strcmp(info.name, (char*)buffer) => 0;
lfs_dir_seek(&lfs, &dir, pos) => 0; lfs_dir_seek(&lfs, &dir[0], pos) => 0;
sprintf(path, "kitty%03d", i); sprintf((char*)buffer, "kitty%03d", i);
lfs_dir_read(&lfs, &dir, &info) => 1; lfs_dir_read(&lfs, &dir[0], &info) => 1;
strcmp(info.name, path) => 0; strcmp(info.name, (char*)buffer) => 0;
lfs_dir_close(&lfs, &dir) => 0; lfs_dir_close(&lfs, &dir[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Simple file seek ---" echo "--- Simple file seek ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "hello/kitty042", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], "hello/kitty042", LFS_O_RDONLY) => 0;
lfs_soff_t pos; lfs_soff_t pos;
lfs_size_t size = strlen("kittycatcat"); size = strlen("kittycatcat");
for (int i = 0; i < $SMALLSIZE; i++) { for (int i = 0; i < $SMALLSIZE; i++) {
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
pos = lfs_file_tell(&lfs, &file); pos = lfs_file_tell(&lfs, &file[0]);
} }
pos >= 0 => 1; pos >= 0 => 1;
lfs_file_seek(&lfs, &file, pos, LFS_SEEK_SET) => pos; lfs_file_seek(&lfs, &file[0], pos, LFS_SEEK_SET) => pos;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
lfs_file_rewind(&lfs, &file) => 0; lfs_file_rewind(&lfs, &file[0]) => 0;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
lfs_file_seek(&lfs, &file, 0, LFS_SEEK_CUR) => size; lfs_file_seek(&lfs, &file[0], 0, LFS_SEEK_CUR) => size;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
lfs_file_seek(&lfs, &file, size, LFS_SEEK_CUR) => 3*size; lfs_file_seek(&lfs, &file[0], size, LFS_SEEK_CUR) => 3*size;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
lfs_file_seek(&lfs, &file, pos, LFS_SEEK_SET) => pos; lfs_file_seek(&lfs, &file[0], pos, LFS_SEEK_SET) => pos;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
lfs_file_seek(&lfs, &file, -size, LFS_SEEK_CUR) => pos; lfs_file_seek(&lfs, &file[0], -size, LFS_SEEK_CUR) => pos;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
lfs_file_seek(&lfs, &file, -size, LFS_SEEK_END) >= 0 => 1; lfs_file_seek(&lfs, &file[0], -size, LFS_SEEK_END) >= 0 => 1;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
size = lfs_file_size(&lfs, &file); size = lfs_file_size(&lfs, &file[0]);
lfs_file_seek(&lfs, &file, 0, LFS_SEEK_CUR) => size; lfs_file_seek(&lfs, &file[0], 0, LFS_SEEK_CUR) => size;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Large file seek ---" echo "--- Large file seek ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "hello/kitty042", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], "hello/kitty042", LFS_O_RDONLY) => 0;
lfs_soff_t pos; lfs_soff_t pos;
lfs_size_t size = strlen("kittycatcat"); size = strlen("kittycatcat");
for (int i = 0; i < $MEDIUMSIZE; i++) { for (int i = 0; i < $MEDIUMSIZE; i++) {
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
pos = lfs_file_tell(&lfs, &file); pos = lfs_file_tell(&lfs, &file[0]);
} }
pos >= 0 => 1; pos >= 0 => 1;
lfs_file_seek(&lfs, &file, pos, LFS_SEEK_SET) => pos; lfs_file_seek(&lfs, &file[0], pos, LFS_SEEK_SET) => pos;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
lfs_file_rewind(&lfs, &file) => 0; lfs_file_rewind(&lfs, &file[0]) => 0;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
lfs_file_seek(&lfs, &file, 0, LFS_SEEK_CUR) => size; lfs_file_seek(&lfs, &file[0], 0, LFS_SEEK_CUR) => size;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
lfs_file_seek(&lfs, &file, size, LFS_SEEK_CUR) => 3*size; lfs_file_seek(&lfs, &file[0], size, LFS_SEEK_CUR) => 3*size;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
lfs_file_seek(&lfs, &file, pos, LFS_SEEK_SET) => pos; lfs_file_seek(&lfs, &file[0], pos, LFS_SEEK_SET) => pos;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
lfs_file_seek(&lfs, &file, -size, LFS_SEEK_CUR) => pos; lfs_file_seek(&lfs, &file[0], -size, LFS_SEEK_CUR) => pos;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
lfs_file_seek(&lfs, &file, -size, LFS_SEEK_END) >= 0 => 1; lfs_file_seek(&lfs, &file[0], -size, LFS_SEEK_END) >= 0 => 1;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
size = lfs_file_size(&lfs, &file); size = lfs_file_size(&lfs, &file[0]);
lfs_file_seek(&lfs, &file, 0, LFS_SEEK_CUR) => size; lfs_file_seek(&lfs, &file[0], 0, LFS_SEEK_CUR) => size;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Simple file seek and write ---" echo "--- Simple file seek and write ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "hello/kitty042", LFS_O_RDWR) => 0; lfs_file_open(&lfs, &file[0], "hello/kitty042", LFS_O_RDWR) => 0;
lfs_soff_t pos; lfs_soff_t pos;
lfs_size_t size = strlen("kittycatcat"); size = strlen("kittycatcat");
for (int i = 0; i < $SMALLSIZE; i++) { for (int i = 0; i < $SMALLSIZE; i++) {
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
pos = lfs_file_tell(&lfs, &file); pos = lfs_file_tell(&lfs, &file[0]);
} }
pos >= 0 => 1; pos >= 0 => 1;
memcpy(buffer, "doggodogdog", size); memcpy(buffer, "doggodogdog", size);
lfs_file_seek(&lfs, &file, pos, LFS_SEEK_SET) => pos; lfs_file_seek(&lfs, &file[0], pos, LFS_SEEK_SET) => pos;
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
lfs_file_seek(&lfs, &file, pos, LFS_SEEK_SET) => pos; lfs_file_seek(&lfs, &file[0], pos, LFS_SEEK_SET) => pos;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "doggodogdog", size) => 0; memcmp(buffer, "doggodogdog", size) => 0;
lfs_file_rewind(&lfs, &file) => 0; lfs_file_rewind(&lfs, &file[0]) => 0;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
lfs_file_seek(&lfs, &file, pos, LFS_SEEK_SET) => pos; lfs_file_seek(&lfs, &file[0], pos, LFS_SEEK_SET) => pos;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "doggodogdog", size) => 0; memcmp(buffer, "doggodogdog", size) => 0;
lfs_file_seek(&lfs, &file, -size, LFS_SEEK_END) >= 0 => 1; lfs_file_seek(&lfs, &file[0], -size, LFS_SEEK_END) >= 0 => 1;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
size = lfs_file_size(&lfs, &file); size = lfs_file_size(&lfs, &file[0]);
lfs_file_seek(&lfs, &file, 0, LFS_SEEK_CUR) => size; lfs_file_seek(&lfs, &file[0], 0, LFS_SEEK_CUR) => size;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Large file seek and write ---" echo "--- Large file seek and write ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "hello/kitty042", LFS_O_RDWR) => 0; lfs_file_open(&lfs, &file[0], "hello/kitty042", LFS_O_RDWR) => 0;
lfs_soff_t pos; lfs_soff_t pos;
lfs_size_t size = strlen("kittycatcat"); size = strlen("kittycatcat");
for (int i = 0; i < $MEDIUMSIZE; i++) { for (int i = 0; i < $MEDIUMSIZE; i++) {
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
if (i != $SMALLSIZE) { if (i != $SMALLSIZE) {
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
} }
pos = lfs_file_tell(&lfs, &file); pos = lfs_file_tell(&lfs, &file[0]);
} }
pos >= 0 => 1; pos >= 0 => 1;
memcpy(buffer, "doggodogdog", size); memcpy(buffer, "doggodogdog", size);
lfs_file_seek(&lfs, &file, pos, LFS_SEEK_SET) => pos; lfs_file_seek(&lfs, &file[0], pos, LFS_SEEK_SET) => pos;
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
lfs_file_seek(&lfs, &file, pos, LFS_SEEK_SET) => pos; lfs_file_seek(&lfs, &file[0], pos, LFS_SEEK_SET) => pos;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "doggodogdog", size) => 0; memcmp(buffer, "doggodogdog", size) => 0;
lfs_file_rewind(&lfs, &file) => 0; lfs_file_rewind(&lfs, &file[0]) => 0;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
lfs_file_seek(&lfs, &file, pos, LFS_SEEK_SET) => pos; lfs_file_seek(&lfs, &file[0], pos, LFS_SEEK_SET) => pos;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "doggodogdog", size) => 0; memcmp(buffer, "doggodogdog", size) => 0;
lfs_file_seek(&lfs, &file, -size, LFS_SEEK_END) >= 0 => 1; lfs_file_seek(&lfs, &file[0], -size, LFS_SEEK_END) >= 0 => 1;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
size = lfs_file_size(&lfs, &file); size = lfs_file_size(&lfs, &file[0]);
lfs_file_seek(&lfs, &file, 0, LFS_SEEK_CUR) => size; lfs_file_seek(&lfs, &file[0], 0, LFS_SEEK_CUR) => size;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Boundary seek and write ---" echo "--- Boundary seek and write ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "hello/kitty042", LFS_O_RDWR) => 0; lfs_file_open(&lfs, &file[0], "hello/kitty042", LFS_O_RDWR) => 0;
lfs_size_t size = strlen("hedgehoghog"); size = strlen("hedgehoghog");
const lfs_soff_t offsets[] = {512, 1020, 513, 1021, 511, 1019}; const lfs_soff_t offsets[] = {512, 1020, 513, 1021, 511, 1019};
for (unsigned i = 0; i < sizeof(offsets) / sizeof(offsets[0]); i++) { for (unsigned i = 0; i < sizeof(offsets) / sizeof(offsets[0]); i++) {
lfs_soff_t off = offsets[i]; lfs_soff_t off = offsets[i];
memcpy(buffer, "hedgehoghog", size); memcpy(buffer, "hedgehoghog", size);
lfs_file_seek(&lfs, &file, off, LFS_SEEK_SET) => off; lfs_file_seek(&lfs, &file[0], off, LFS_SEEK_SET) => off;
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
lfs_file_seek(&lfs, &file, off, LFS_SEEK_SET) => off; lfs_file_seek(&lfs, &file[0], off, LFS_SEEK_SET) => off;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "hedgehoghog", size) => 0; memcmp(buffer, "hedgehoghog", size) => 0;
lfs_file_seek(&lfs, &file, 0, LFS_SEEK_SET) => 0; lfs_file_seek(&lfs, &file[0], 0, LFS_SEEK_SET) => 0;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "kittycatcat", size) => 0; memcmp(buffer, "kittycatcat", size) => 0;
lfs_file_sync(&lfs, &file) => 0; lfs_file_sync(&lfs, &file[0]) => 0;
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Out-of-bounds seek ---" echo "--- Out-of-bounds seek ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "hello/kitty042", LFS_O_RDWR) => 0; lfs_file_open(&lfs, &file[0], "hello/kitty042", LFS_O_RDWR) => 0;
lfs_size_t size = strlen("kittycatcat"); size = strlen("kittycatcat");
lfs_file_size(&lfs, &file) => $LARGESIZE*size; lfs_file_size(&lfs, &file[0]) => $LARGESIZE*size;
lfs_file_seek(&lfs, &file, ($LARGESIZE+$SMALLSIZE)*size, lfs_file_seek(&lfs, &file[0], ($LARGESIZE+$SMALLSIZE)*size,
LFS_SEEK_SET) => ($LARGESIZE+$SMALLSIZE)*size; LFS_SEEK_SET) => ($LARGESIZE+$SMALLSIZE)*size;
lfs_file_read(&lfs, &file, buffer, size) => 0; lfs_file_read(&lfs, &file[0], buffer, size) => 0;
memcpy(buffer, "porcupineee", size); memcpy(buffer, "porcupineee", size);
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
lfs_file_seek(&lfs, &file, ($LARGESIZE+$SMALLSIZE)*size, lfs_file_seek(&lfs, &file[0], ($LARGESIZE+$SMALLSIZE)*size,
LFS_SEEK_SET) => ($LARGESIZE+$SMALLSIZE)*size; LFS_SEEK_SET) => ($LARGESIZE+$SMALLSIZE)*size;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "porcupineee", size) => 0; memcmp(buffer, "porcupineee", size) => 0;
lfs_file_seek(&lfs, &file, $LARGESIZE*size, lfs_file_seek(&lfs, &file[0], $LARGESIZE*size,
LFS_SEEK_SET) => $LARGESIZE*size; LFS_SEEK_SET) => $LARGESIZE*size;
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "\0\0\0\0\0\0\0\0\0\0\0", size) => 0; memcmp(buffer, "\0\0\0\0\0\0\0\0\0\0\0", size) => 0;
lfs_file_seek(&lfs, &file, -(($LARGESIZE+$SMALLSIZE)*size), lfs_file_seek(&lfs, &file[0], -(($LARGESIZE+$SMALLSIZE)*size),
LFS_SEEK_CUR) => LFS_ERR_INVAL; LFS_SEEK_CUR) => LFS_ERR_INVAL;
lfs_file_tell(&lfs, &file) => ($LARGESIZE+1)*size; lfs_file_tell(&lfs, &file[0]) => ($LARGESIZE+1)*size;
lfs_file_seek(&lfs, &file, -(($LARGESIZE+2*$SMALLSIZE)*size), lfs_file_seek(&lfs, &file[0], -(($LARGESIZE+2*$SMALLSIZE)*size),
LFS_SEEK_END) => LFS_ERR_INVAL; LFS_SEEK_END) => LFS_ERR_INVAL;
lfs_file_tell(&lfs, &file) => ($LARGESIZE+1)*size; lfs_file_tell(&lfs, &file[0]) => ($LARGESIZE+1)*size;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Inline write and seek ---" echo "--- Results ---"
for SIZE in $SMALLSIZE $MEDIUMSIZE $LARGESIZE tests/stats.py
do
scripts/test.py << TEST
lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "hello/tinykitty$SIZE",
LFS_O_RDWR | LFS_O_CREAT) => 0;
int j = 0;
int k = 0;
memcpy(buffer, "abcdefghijklmnopqrstuvwxyz", 26);
for (unsigned i = 0; i < $SIZE; i++) {
lfs_file_write(&lfs, &file, &buffer[j++ % 26], 1) => 1;
lfs_file_tell(&lfs, &file) => i+1;
lfs_file_size(&lfs, &file) => i+1;
}
lfs_file_seek(&lfs, &file, 0, LFS_SEEK_SET) => 0;
lfs_file_tell(&lfs, &file) => 0;
lfs_file_size(&lfs, &file) => $SIZE;
for (unsigned i = 0; i < $SIZE; i++) {
uint8_t c;
lfs_file_read(&lfs, &file, &c, 1) => 1;
c => buffer[k++ % 26];
}
lfs_file_sync(&lfs, &file) => 0;
lfs_file_tell(&lfs, &file) => $SIZE;
lfs_file_size(&lfs, &file) => $SIZE;
lfs_file_seek(&lfs, &file, 0, LFS_SEEK_SET) => 0;
for (unsigned i = 0; i < $SIZE; i++) {
lfs_file_write(&lfs, &file, &buffer[j++ % 26], 1) => 1;
lfs_file_tell(&lfs, &file) => i+1;
lfs_file_size(&lfs, &file) => $SIZE;
lfs_file_sync(&lfs, &file) => 0;
lfs_file_tell(&lfs, &file) => i+1;
lfs_file_size(&lfs, &file) => $SIZE;
if (i < $SIZE-2) {
uint8_t c[3];
lfs_file_seek(&lfs, &file, -1, LFS_SEEK_CUR) => i;
lfs_file_read(&lfs, &file, &c, 3) => 3;
lfs_file_tell(&lfs, &file) => i+3;
lfs_file_size(&lfs, &file) => $SIZE;
lfs_file_seek(&lfs, &file, i+1, LFS_SEEK_SET) => i+1;
lfs_file_tell(&lfs, &file) => i+1;
lfs_file_size(&lfs, &file) => $SIZE;
}
}
lfs_file_seek(&lfs, &file, 0, LFS_SEEK_SET) => 0;
lfs_file_tell(&lfs, &file) => 0;
lfs_file_size(&lfs, &file) => $SIZE;
for (unsigned i = 0; i < $SIZE; i++) {
uint8_t c;
lfs_file_read(&lfs, &file, &c, 1) => 1;
c => buffer[k++ % 26];
}
lfs_file_sync(&lfs, &file) => 0;
lfs_file_tell(&lfs, &file) => $SIZE;
lfs_file_size(&lfs, &file) => $SIZE;
lfs_file_close(&lfs, &file) => 0;
lfs_unmount(&lfs) => 0;
TEST
done
scripts/results.py

View File

@@ -1,210 +1,156 @@
#!/bin/bash #!/bin/bash
set -eu set -eu
export TEST_FILE=$0
trap 'export TEST_LINE=$LINENO' DEBUG
echo "=== Truncate tests ==="
SMALLSIZE=32 SMALLSIZE=32
MEDIUMSIZE=2048 MEDIUMSIZE=2048
LARGESIZE=8192 LARGESIZE=8192
echo "=== Truncate tests ==="
rm -rf blocks rm -rf blocks
scripts/test.py << TEST tests/test.py << TEST
lfs_format(&lfs, &cfg) => 0; lfs_format(&lfs, &cfg) => 0;
TEST TEST
echo "--- Simple truncate ---" echo "--- Simple truncate ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "baldynoop", lfs_file_open(&lfs, &file[0], "baldynoop",
LFS_O_WRONLY | LFS_O_CREAT) => 0; LFS_O_WRONLY | LFS_O_CREAT) => 0;
strcpy((char*)buffer, "hair"); strcpy((char*)buffer, "hair");
lfs_size_t size = strlen((char*)buffer); size = strlen((char*)buffer);
for (lfs_off_t j = 0; j < $LARGESIZE; j += size) { for (lfs_off_t j = 0; j < $LARGESIZE; j += size) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_size(&lfs, &file) => $LARGESIZE; lfs_file_size(&lfs, &file[0]) => $LARGESIZE;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "baldynoop", LFS_O_RDWR) => 0; lfs_file_open(&lfs, &file[0], "baldynoop", LFS_O_RDWR) => 0;
lfs_file_size(&lfs, &file) => $LARGESIZE; lfs_file_size(&lfs, &file[0]) => $LARGESIZE;
lfs_file_truncate(&lfs, &file, $MEDIUMSIZE) => 0; lfs_file_truncate(&lfs, &file[0], $MEDIUMSIZE) => 0;
lfs_file_size(&lfs, &file) => $MEDIUMSIZE; lfs_file_size(&lfs, &file[0]) => $MEDIUMSIZE;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "baldynoop", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], "baldynoop", LFS_O_RDONLY) => 0;
lfs_file_size(&lfs, &file) => $MEDIUMSIZE; lfs_file_size(&lfs, &file[0]) => $MEDIUMSIZE;
lfs_size_t size = strlen("hair"); size = strlen("hair");
for (lfs_off_t j = 0; j < $MEDIUMSIZE; j += size) { for (lfs_off_t j = 0; j < $MEDIUMSIZE; j += size) {
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "hair", size) => 0; memcmp(buffer, "hair", size) => 0;
} }
lfs_file_read(&lfs, &file, buffer, size) => 0; lfs_file_read(&lfs, &file[0], buffer, size) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Truncate and read ---" echo "--- Truncate and read ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "baldyread", lfs_file_open(&lfs, &file[0], "baldyread",
LFS_O_WRONLY | LFS_O_CREAT) => 0; LFS_O_WRONLY | LFS_O_CREAT) => 0;
strcpy((char*)buffer, "hair"); strcpy((char*)buffer, "hair");
lfs_size_t size = strlen((char*)buffer); size = strlen((char*)buffer);
for (lfs_off_t j = 0; j < $LARGESIZE; j += size) { for (lfs_off_t j = 0; j < $LARGESIZE; j += size) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_size(&lfs, &file) => $LARGESIZE; lfs_file_size(&lfs, &file[0]) => $LARGESIZE;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "baldyread", LFS_O_RDWR) => 0; lfs_file_open(&lfs, &file[0], "baldyread", LFS_O_RDWR) => 0;
lfs_file_size(&lfs, &file) => $LARGESIZE; lfs_file_size(&lfs, &file[0]) => $LARGESIZE;
lfs_file_truncate(&lfs, &file, $MEDIUMSIZE) => 0; lfs_file_truncate(&lfs, &file[0], $MEDIUMSIZE) => 0;
lfs_file_size(&lfs, &file) => $MEDIUMSIZE; lfs_file_size(&lfs, &file[0]) => $MEDIUMSIZE;
lfs_size_t size = strlen("hair"); size = strlen("hair");
for (lfs_off_t j = 0; j < $MEDIUMSIZE; j += size) { for (lfs_off_t j = 0; j < $MEDIUMSIZE; j += size) {
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "hair", size) => 0; memcmp(buffer, "hair", size) => 0;
} }
lfs_file_read(&lfs, &file, buffer, size) => 0; lfs_file_read(&lfs, &file[0], buffer, size) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "baldyread", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], "baldyread", LFS_O_RDONLY) => 0;
lfs_file_size(&lfs, &file) => $MEDIUMSIZE; lfs_file_size(&lfs, &file[0]) => $MEDIUMSIZE;
lfs_size_t size = strlen("hair"); size = strlen("hair");
for (lfs_off_t j = 0; j < $MEDIUMSIZE; j += size) { for (lfs_off_t j = 0; j < $MEDIUMSIZE; j += size) {
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "hair", size) => 0; memcmp(buffer, "hair", size) => 0;
} }
lfs_file_read(&lfs, &file, buffer, size) => 0; lfs_file_read(&lfs, &file[0], buffer, size) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0;
TEST
echo "--- Write, truncate, and read ---"
scripts/test.py << TEST
lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "sequence",
LFS_O_RDWR | LFS_O_CREAT | LFS_O_TRUNC) => 0;
lfs_size_t size = lfs.cfg->cache_size;
lfs_size_t qsize = size / 4;
uint8_t *wb = buffer;
uint8_t *rb = buffer + size;
for (lfs_off_t j = 0; j < size; ++j) {
wb[j] = j;
}
/* Spread sequence over size */
lfs_file_write(&lfs, &file, wb, size) => size;
lfs_file_size(&lfs, &file) => size;
lfs_file_tell(&lfs, &file) => size;
lfs_file_seek(&lfs, &file, 0, LFS_SEEK_SET) => 0;
lfs_file_tell(&lfs, &file) => 0;
/* Chop off the last quarter */
lfs_size_t trunc = size - qsize;
lfs_file_truncate(&lfs, &file, trunc) => 0;
lfs_file_tell(&lfs, &file) => 0;
lfs_file_size(&lfs, &file) => trunc;
/* Read should produce first 3/4 */
lfs_file_read(&lfs, &file, rb, size) => trunc;
memcmp(rb, wb, trunc) => 0;
/* Move to 1/4 */
lfs_file_size(&lfs, &file) => trunc;
lfs_file_seek(&lfs, &file, qsize, LFS_SEEK_SET) => qsize;
lfs_file_tell(&lfs, &file) => qsize;
/* Chop to 1/2 */
trunc -= qsize;
lfs_file_truncate(&lfs, &file, trunc) => 0;
lfs_file_tell(&lfs, &file) => qsize;
lfs_file_size(&lfs, &file) => trunc;
/* Read should produce second quarter */
lfs_file_read(&lfs, &file, rb, size) => trunc - qsize;
memcmp(rb, wb + qsize, trunc - qsize) => 0;
lfs_file_close(&lfs, &file) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
echo "--- Truncate and write ---" echo "--- Truncate and write ---"
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "baldywrite", lfs_file_open(&lfs, &file[0], "baldywrite",
LFS_O_WRONLY | LFS_O_CREAT) => 0; LFS_O_WRONLY | LFS_O_CREAT) => 0;
strcpy((char*)buffer, "hair"); strcpy((char*)buffer, "hair");
lfs_size_t size = strlen((char*)buffer); size = strlen((char*)buffer);
for (lfs_off_t j = 0; j < $LARGESIZE; j += size) { for (lfs_off_t j = 0; j < $LARGESIZE; j += size) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_size(&lfs, &file) => $LARGESIZE; lfs_file_size(&lfs, &file[0]) => $LARGESIZE;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "baldywrite", LFS_O_RDWR) => 0; lfs_file_open(&lfs, &file[0], "baldywrite", LFS_O_RDWR) => 0;
lfs_file_size(&lfs, &file) => $LARGESIZE; lfs_file_size(&lfs, &file[0]) => $LARGESIZE;
lfs_file_truncate(&lfs, &file, $MEDIUMSIZE) => 0; lfs_file_truncate(&lfs, &file[0], $MEDIUMSIZE) => 0;
lfs_file_size(&lfs, &file) => $MEDIUMSIZE; lfs_file_size(&lfs, &file[0]) => $MEDIUMSIZE;
strcpy((char*)buffer, "bald"); strcpy((char*)buffer, "bald");
lfs_size_t size = strlen((char*)buffer); size = strlen((char*)buffer);
for (lfs_off_t j = 0; j < $MEDIUMSIZE; j += size) { for (lfs_off_t j = 0; j < $MEDIUMSIZE; j += size) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_size(&lfs, &file) => $MEDIUMSIZE; lfs_file_size(&lfs, &file[0]) => $MEDIUMSIZE;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
lfs_file_open(&lfs, &file, "baldywrite", LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], "baldywrite", LFS_O_RDONLY) => 0;
lfs_file_size(&lfs, &file) => $MEDIUMSIZE; lfs_file_size(&lfs, &file[0]) => $MEDIUMSIZE;
lfs_size_t size = strlen("bald"); size = strlen("bald");
for (lfs_off_t j = 0; j < $MEDIUMSIZE; j += size) { for (lfs_off_t j = 0; j < $MEDIUMSIZE; j += size) {
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "bald", size) => 0; memcmp(buffer, "bald", size) => 0;
} }
lfs_file_read(&lfs, &file, buffer, size) => 0; lfs_file_read(&lfs, &file[0], buffer, size) => 0;
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
@@ -214,7 +160,7 @@ STARTSIZES="$1"
STARTSEEKS="$2" STARTSEEKS="$2"
HOTSIZES="$3" HOTSIZES="$3"
COLDSIZES="$4" COLDSIZES="$4"
scripts/test.py << TEST tests/test.py << TEST
static const lfs_off_t startsizes[] = {$STARTSIZES}; static const lfs_off_t startsizes[] = {$STARTSIZES};
static const lfs_off_t startseeks[] = {$STARTSEEKS}; static const lfs_off_t startseeks[] = {$STARTSEEKS};
static const lfs_off_t hotsizes[] = {$HOTSIZES}; static const lfs_off_t hotsizes[] = {$HOTSIZES};
@@ -222,31 +168,31 @@ scripts/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
for (unsigned i = 0; i < sizeof(startsizes)/sizeof(startsizes[0]); i++) { for (unsigned i = 0; i < sizeof(startsizes)/sizeof(startsizes[0]); i++) {
sprintf(path, "hairyhead%d", i); sprintf((char*)buffer, "hairyhead%d", i);
lfs_file_open(&lfs, &file, path, lfs_file_open(&lfs, &file[0], (const char*)buffer,
LFS_O_WRONLY | LFS_O_CREAT | LFS_O_TRUNC) => 0; LFS_O_WRONLY | LFS_O_CREAT | LFS_O_TRUNC) => 0;
strcpy((char*)buffer, "hair"); strcpy((char*)buffer, "hair");
lfs_size_t size = strlen((char*)buffer); size = strlen((char*)buffer);
for (lfs_off_t j = 0; j < startsizes[i]; j += size) { for (lfs_off_t j = 0; j < startsizes[i]; j += size) {
lfs_file_write(&lfs, &file, buffer, size) => size; lfs_file_write(&lfs, &file[0], buffer, size) => size;
} }
lfs_file_size(&lfs, &file) => startsizes[i]; lfs_file_size(&lfs, &file[0]) => startsizes[i];
if (startseeks[i] != startsizes[i]) { if (startseeks[i] != startsizes[i]) {
lfs_file_seek(&lfs, &file, lfs_file_seek(&lfs, &file[0],
startseeks[i], LFS_SEEK_SET) => startseeks[i]; startseeks[i], LFS_SEEK_SET) => startseeks[i];
} }
lfs_file_truncate(&lfs, &file, hotsizes[i]) => 0; lfs_file_truncate(&lfs, &file[0], hotsizes[i]) => 0;
lfs_file_size(&lfs, &file) => hotsizes[i]; lfs_file_size(&lfs, &file[0]) => hotsizes[i];
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
} }
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
static const lfs_off_t startsizes[] = {$STARTSIZES}; static const lfs_off_t startsizes[] = {$STARTSIZES};
static const lfs_off_t hotsizes[] = {$HOTSIZES}; static const lfs_off_t hotsizes[] = {$HOTSIZES};
static const lfs_off_t coldsizes[] = {$COLDSIZES}; static const lfs_off_t coldsizes[] = {$COLDSIZES};
@@ -254,31 +200,31 @@ scripts/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
for (unsigned i = 0; i < sizeof(startsizes)/sizeof(startsizes[0]); i++) { for (unsigned i = 0; i < sizeof(startsizes)/sizeof(startsizes[0]); i++) {
sprintf(path, "hairyhead%d", i); sprintf((char*)buffer, "hairyhead%d", i);
lfs_file_open(&lfs, &file, path, LFS_O_RDWR) => 0; lfs_file_open(&lfs, &file[0], (const char*)buffer, LFS_O_RDWR) => 0;
lfs_file_size(&lfs, &file) => hotsizes[i]; lfs_file_size(&lfs, &file[0]) => hotsizes[i];
lfs_size_t size = strlen("hair"); size = strlen("hair");
lfs_off_t j = 0; lfs_off_t j = 0;
for (; j < startsizes[i] && j < hotsizes[i]; j += size) { for (; j < startsizes[i] && j < hotsizes[i]; j += size) {
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "hair", size) => 0; memcmp(buffer, "hair", size) => 0;
} }
for (; j < hotsizes[i]; j += size) { for (; j < hotsizes[i]; j += size) {
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "\0\0\0\0", size) => 0; memcmp(buffer, "\0\0\0\0", size) => 0;
} }
lfs_file_truncate(&lfs, &file, coldsizes[i]) => 0; lfs_file_truncate(&lfs, &file[0], coldsizes[i]) => 0;
lfs_file_size(&lfs, &file) => coldsizes[i]; lfs_file_size(&lfs, &file[0]) => coldsizes[i];
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
} }
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
TEST TEST
scripts/test.py << TEST tests/test.py << TEST
static const lfs_off_t startsizes[] = {$STARTSIZES}; static const lfs_off_t startsizes[] = {$STARTSIZES};
static const lfs_off_t hotsizes[] = {$HOTSIZES}; static const lfs_off_t hotsizes[] = {$HOTSIZES};
static const lfs_off_t coldsizes[] = {$COLDSIZES}; static const lfs_off_t coldsizes[] = {$COLDSIZES};
@@ -286,24 +232,24 @@ scripts/test.py << TEST
lfs_mount(&lfs, &cfg) => 0; lfs_mount(&lfs, &cfg) => 0;
for (unsigned i = 0; i < sizeof(startsizes)/sizeof(startsizes[0]); i++) { for (unsigned i = 0; i < sizeof(startsizes)/sizeof(startsizes[0]); i++) {
sprintf(path, "hairyhead%d", i); sprintf((char*)buffer, "hairyhead%d", i);
lfs_file_open(&lfs, &file, path, LFS_O_RDONLY) => 0; lfs_file_open(&lfs, &file[0], (const char*)buffer, LFS_O_RDONLY) => 0;
lfs_file_size(&lfs, &file) => coldsizes[i]; lfs_file_size(&lfs, &file[0]) => coldsizes[i];
lfs_size_t size = strlen("hair"); size = strlen("hair");
lfs_off_t j = 0; lfs_off_t j = 0;
for (; j < startsizes[i] && j < hotsizes[i] && j < coldsizes[i]; for (; j < startsizes[i] && j < hotsizes[i] && j < coldsizes[i];
j += size) { j += size) {
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "hair", size) => 0; memcmp(buffer, "hair", size) => 0;
} }
for (; j < coldsizes[i]; j += size) { for (; j < coldsizes[i]; j += size) {
lfs_file_read(&lfs, &file, buffer, size) => size; lfs_file_read(&lfs, &file[0], buffer, size) => size;
memcmp(buffer, "\0\0\0\0", size) => 0; memcmp(buffer, "\0\0\0\0", size) => 0;
} }
lfs_file_close(&lfs, &file) => 0; lfs_file_close(&lfs, &file[0]) => 0;
} }
lfs_unmount(&lfs) => 0; lfs_unmount(&lfs) => 0;
@@ -352,4 +298,5 @@ truncate_test \
"2*$LARGESIZE, 2*$LARGESIZE, 2*$LARGESIZE, 2*$LARGESIZE, 2*$LARGESIZE" \ "2*$LARGESIZE, 2*$LARGESIZE, 2*$LARGESIZE, 2*$LARGESIZE, 2*$LARGESIZE" \
"2*$LARGESIZE, 2*$LARGESIZE, 2*$LARGESIZE, 2*$LARGESIZE, 2*$LARGESIZE" "2*$LARGESIZE, 2*$LARGESIZE, 2*$LARGESIZE, 2*$LARGESIZE, 2*$LARGESIZE"
scripts/results.py echo "--- Results ---"
tests/stats.py