1[[case]] # simple formatting test
2code = '''
3    lfs_format(&lfs, &cfg) => 0;
4'''
5
6[[case]] # mount/unmount
7code = '''
8    lfs_format(&lfs, &cfg) => 0;
9    lfs_mount(&lfs, &cfg) => 0;
10    lfs_unmount(&lfs) => 0;
11'''
12
13[[case]] # reentrant format
14reentrant = true
15code = '''
16    err = lfs_mount(&lfs, &cfg);
17    if (err) {
18        lfs_format(&lfs, &cfg) => 0;
19        lfs_mount(&lfs, &cfg) => 0;
20    }
21    lfs_unmount(&lfs) => 0;
22'''
23
24[[case]] # invalid mount
25code = '''
26    lfs_mount(&lfs, &cfg) => LFS_ERR_CORRUPT;
27'''
28
29[[case]] # expanding superblock
30define.LFS_BLOCK_CYCLES = [32, 33, 1]
31define.N = [10, 100, 1000]
32code = '''
33    lfs_format(&lfs, &cfg) => 0;
34    lfs_mount(&lfs, &cfg) => 0;
35    for (int i = 0; i < N; i++) {
36        lfs_file_open(&lfs, &file, "dummy",
37                LFS_O_WRONLY | LFS_O_CREAT | LFS_O_EXCL) => 0;
38        lfs_file_close(&lfs, &file) => 0;
39        lfs_stat(&lfs, "dummy", &info) => 0;
40        assert(strcmp(info.name, "dummy") == 0);
41        assert(info.type == LFS_TYPE_REG);
42        lfs_remove(&lfs, "dummy") => 0;
43    }
44    lfs_unmount(&lfs) => 0;
45
46    // one last check after power-cycle
47    lfs_mount(&lfs, &cfg) => 0;
48    lfs_file_open(&lfs, &file, "dummy",
49            LFS_O_WRONLY | LFS_O_CREAT | LFS_O_EXCL) => 0;
50    lfs_file_close(&lfs, &file) => 0;
51    lfs_stat(&lfs, "dummy", &info) => 0;
52    assert(strcmp(info.name, "dummy") == 0);
53    assert(info.type == LFS_TYPE_REG);
54    lfs_unmount(&lfs) => 0;
55'''
56
57[[case]] # expanding superblock with power cycle
58define.LFS_BLOCK_CYCLES = [32, 33, 1]
59define.N = [10, 100, 1000]
60code = '''
61    lfs_format(&lfs, &cfg) => 0;
62    for (int i = 0; i < N; i++) {
63        lfs_mount(&lfs, &cfg) => 0;
64        // remove lingering dummy?
65        err = lfs_stat(&lfs, "dummy", &info);
66        assert(err == 0 || (err == LFS_ERR_NOENT && i == 0));
67        if (!err) {
68            assert(strcmp(info.name, "dummy") == 0);
69            assert(info.type == LFS_TYPE_REG);
70            lfs_remove(&lfs, "dummy") => 0;
71        }
72
73        lfs_file_open(&lfs, &file, "dummy",
74                LFS_O_WRONLY | LFS_O_CREAT | LFS_O_EXCL) => 0;
75        lfs_file_close(&lfs, &file) => 0;
76        lfs_stat(&lfs, "dummy", &info) => 0;
77        assert(strcmp(info.name, "dummy") == 0);
78        assert(info.type == LFS_TYPE_REG);
79        lfs_unmount(&lfs) => 0;
80    }
81
82    // one last check after power-cycle
83    lfs_mount(&lfs, &cfg) => 0;
84    lfs_stat(&lfs, "dummy", &info) => 0;
85    assert(strcmp(info.name, "dummy") == 0);
86    assert(info.type == LFS_TYPE_REG);
87    lfs_unmount(&lfs) => 0;
88'''
89
90[[case]] # reentrant expanding superblock
91define.LFS_BLOCK_CYCLES = [2, 1]
92define.N = 24
93reentrant = true
94code = '''
95    err = lfs_mount(&lfs, &cfg);
96    if (err) {
97        lfs_format(&lfs, &cfg) => 0;
98        lfs_mount(&lfs, &cfg) => 0;
99    }
100
101    for (int i = 0; i < N; i++) {
102        // remove lingering dummy?
103        err = lfs_stat(&lfs, "dummy", &info);
104        assert(err == 0 || (err == LFS_ERR_NOENT && i == 0));
105        if (!err) {
106            assert(strcmp(info.name, "dummy") == 0);
107            assert(info.type == LFS_TYPE_REG);
108            lfs_remove(&lfs, "dummy") => 0;
109        }
110
111        lfs_file_open(&lfs, &file, "dummy",
112                LFS_O_WRONLY | LFS_O_CREAT | LFS_O_EXCL) => 0;
113        lfs_file_close(&lfs, &file) => 0;
114        lfs_stat(&lfs, "dummy", &info) => 0;
115        assert(strcmp(info.name, "dummy") == 0);
116        assert(info.type == LFS_TYPE_REG);
117    }
118
119    lfs_unmount(&lfs) => 0;
120
121    // one last check after power-cycle
122    lfs_mount(&lfs, &cfg) => 0;
123    lfs_stat(&lfs, "dummy", &info) => 0;
124    assert(strcmp(info.name, "dummy") == 0);
125    assert(info.type == LFS_TYPE_REG);
126    lfs_unmount(&lfs) => 0;
127'''
128