test_truncate.toml 15 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477
  1. # simple truncate
  2. [cases.test_truncate_simple]
  3. defines.MEDIUMSIZE = [32, 2048]
  4. defines.LARGESIZE = 8192
  5. code = '''
  6. lfs_t lfs;
  7. lfs_format(&lfs, cfg) => 0;
  8. lfs_mount(&lfs, cfg) => 0;
  9. lfs_file_t file;
  10. lfs_file_open(&lfs, &file, "baldynoop",
  11. LFS_O_WRONLY | LFS_O_CREAT) => 0;
  12. uint8_t buffer[1024];
  13. strcpy((char*)buffer, "hair");
  14. size_t size = strlen((char*)buffer);
  15. for (lfs_off_t j = 0; j < LARGESIZE; j += size) {
  16. lfs_file_write(&lfs, &file, buffer, size) => size;
  17. }
  18. lfs_file_size(&lfs, &file) => LARGESIZE;
  19. lfs_file_close(&lfs, &file) => 0;
  20. lfs_unmount(&lfs) => 0;
  21. lfs_mount(&lfs, cfg) => 0;
  22. lfs_file_open(&lfs, &file, "baldynoop", LFS_O_RDWR) => 0;
  23. lfs_file_size(&lfs, &file) => LARGESIZE;
  24. lfs_file_truncate(&lfs, &file, MEDIUMSIZE) => 0;
  25. lfs_file_size(&lfs, &file) => MEDIUMSIZE;
  26. lfs_file_close(&lfs, &file) => 0;
  27. lfs_unmount(&lfs) => 0;
  28. lfs_mount(&lfs, cfg) => 0;
  29. lfs_file_open(&lfs, &file, "baldynoop", LFS_O_RDONLY) => 0;
  30. lfs_file_size(&lfs, &file) => MEDIUMSIZE;
  31. size = strlen("hair");
  32. for (lfs_off_t j = 0; j < MEDIUMSIZE; j += size) {
  33. lfs_file_read(&lfs, &file, buffer, size) => size;
  34. memcmp(buffer, "hair", size) => 0;
  35. }
  36. lfs_file_read(&lfs, &file, buffer, size) => 0;
  37. lfs_file_close(&lfs, &file) => 0;
  38. lfs_unmount(&lfs) => 0;
  39. '''
  40. # truncate and read
  41. [cases.test_truncate_read]
  42. defines.MEDIUMSIZE = [32, 2048]
  43. defines.LARGESIZE = 8192
  44. code = '''
  45. lfs_t lfs;
  46. lfs_format(&lfs, cfg) => 0;
  47. lfs_mount(&lfs, cfg) => 0;
  48. lfs_file_t file;
  49. lfs_file_open(&lfs, &file, "baldyread",
  50. LFS_O_WRONLY | LFS_O_CREAT) => 0;
  51. uint8_t buffer[1024];
  52. strcpy((char*)buffer, "hair");
  53. size_t size = strlen((char*)buffer);
  54. for (lfs_off_t j = 0; j < LARGESIZE; j += size) {
  55. lfs_file_write(&lfs, &file, buffer, size) => size;
  56. }
  57. lfs_file_size(&lfs, &file) => LARGESIZE;
  58. lfs_file_close(&lfs, &file) => 0;
  59. lfs_unmount(&lfs) => 0;
  60. lfs_mount(&lfs, cfg) => 0;
  61. lfs_file_open(&lfs, &file, "baldyread", LFS_O_RDWR) => 0;
  62. lfs_file_size(&lfs, &file) => LARGESIZE;
  63. lfs_file_truncate(&lfs, &file, MEDIUMSIZE) => 0;
  64. lfs_file_size(&lfs, &file) => MEDIUMSIZE;
  65. size = strlen("hair");
  66. for (lfs_off_t j = 0; j < MEDIUMSIZE; j += size) {
  67. lfs_file_read(&lfs, &file, buffer, size) => size;
  68. memcmp(buffer, "hair", size) => 0;
  69. }
  70. lfs_file_read(&lfs, &file, buffer, size) => 0;
  71. lfs_file_close(&lfs, &file) => 0;
  72. lfs_unmount(&lfs) => 0;
  73. lfs_mount(&lfs, cfg) => 0;
  74. lfs_file_open(&lfs, &file, "baldyread", LFS_O_RDONLY) => 0;
  75. lfs_file_size(&lfs, &file) => MEDIUMSIZE;
  76. size = strlen("hair");
  77. for (lfs_off_t j = 0; j < MEDIUMSIZE; j += size) {
  78. lfs_file_read(&lfs, &file, buffer, size) => size;
  79. memcmp(buffer, "hair", size) => 0;
  80. }
  81. lfs_file_read(&lfs, &file, buffer, size) => 0;
  82. lfs_file_close(&lfs, &file) => 0;
  83. lfs_unmount(&lfs) => 0;
  84. '''
  85. # write, truncate, and read
  86. [cases.test_truncate_write_read]
  87. code = '''
  88. lfs_t lfs;
  89. lfs_format(&lfs, cfg) => 0;
  90. lfs_mount(&lfs, cfg) => 0;
  91. lfs_file_t file;
  92. lfs_file_open(&lfs, &file, "sequence",
  93. LFS_O_RDWR | LFS_O_CREAT | LFS_O_TRUNC) => 0;
  94. uint8_t buffer[1024];
  95. size_t size = lfs_min(lfs.cfg->cache_size, sizeof(buffer)/2);
  96. lfs_size_t qsize = size / 4;
  97. uint8_t *wb = buffer;
  98. uint8_t *rb = buffer + size;
  99. for (lfs_off_t j = 0; j < size; ++j) {
  100. wb[j] = j;
  101. }
  102. /* Spread sequence over size */
  103. lfs_file_write(&lfs, &file, wb, size) => size;
  104. lfs_file_size(&lfs, &file) => size;
  105. lfs_file_tell(&lfs, &file) => size;
  106. lfs_file_seek(&lfs, &file, 0, LFS_SEEK_SET) => 0;
  107. lfs_file_tell(&lfs, &file) => 0;
  108. /* Chop off the last quarter */
  109. lfs_size_t trunc = size - qsize;
  110. lfs_file_truncate(&lfs, &file, trunc) => 0;
  111. lfs_file_tell(&lfs, &file) => 0;
  112. lfs_file_size(&lfs, &file) => trunc;
  113. /* Read should produce first 3/4 */
  114. lfs_file_read(&lfs, &file, rb, size) => trunc;
  115. memcmp(rb, wb, trunc) => 0;
  116. /* Move to 1/4 */
  117. lfs_file_size(&lfs, &file) => trunc;
  118. lfs_file_seek(&lfs, &file, qsize, LFS_SEEK_SET) => qsize;
  119. lfs_file_tell(&lfs, &file) => qsize;
  120. /* Chop to 1/2 */
  121. trunc -= qsize;
  122. lfs_file_truncate(&lfs, &file, trunc) => 0;
  123. lfs_file_tell(&lfs, &file) => qsize;
  124. lfs_file_size(&lfs, &file) => trunc;
  125. /* Read should produce second quarter */
  126. lfs_file_read(&lfs, &file, rb, size) => trunc - qsize;
  127. memcmp(rb, wb + qsize, trunc - qsize) => 0;
  128. lfs_file_close(&lfs, &file) => 0;
  129. lfs_unmount(&lfs) => 0;
  130. '''
  131. # truncate and write
  132. [cases.test_truncate_write]
  133. defines.MEDIUMSIZE = [32, 2048]
  134. defines.LARGESIZE = 8192
  135. code = '''
  136. lfs_t lfs;
  137. lfs_format(&lfs, cfg) => 0;
  138. lfs_mount(&lfs, cfg) => 0;
  139. lfs_file_t file;
  140. lfs_file_open(&lfs, &file, "baldywrite",
  141. LFS_O_WRONLY | LFS_O_CREAT) => 0;
  142. uint8_t buffer[1024];
  143. strcpy((char*)buffer, "hair");
  144. size_t size = strlen((char*)buffer);
  145. for (lfs_off_t j = 0; j < LARGESIZE; j += size) {
  146. lfs_file_write(&lfs, &file, buffer, size) => size;
  147. }
  148. lfs_file_size(&lfs, &file) => LARGESIZE;
  149. lfs_file_close(&lfs, &file) => 0;
  150. lfs_unmount(&lfs) => 0;
  151. lfs_mount(&lfs, cfg) => 0;
  152. lfs_file_open(&lfs, &file, "baldywrite", LFS_O_RDWR) => 0;
  153. lfs_file_size(&lfs, &file) => LARGESIZE;
  154. lfs_file_truncate(&lfs, &file, MEDIUMSIZE) => 0;
  155. lfs_file_size(&lfs, &file) => MEDIUMSIZE;
  156. strcpy((char*)buffer, "bald");
  157. size = strlen((char*)buffer);
  158. for (lfs_off_t j = 0; j < MEDIUMSIZE; j += size) {
  159. lfs_file_write(&lfs, &file, buffer, size) => size;
  160. }
  161. lfs_file_size(&lfs, &file) => MEDIUMSIZE;
  162. lfs_file_close(&lfs, &file) => 0;
  163. lfs_unmount(&lfs) => 0;
  164. lfs_mount(&lfs, cfg) => 0;
  165. lfs_file_open(&lfs, &file, "baldywrite", LFS_O_RDONLY) => 0;
  166. lfs_file_size(&lfs, &file) => MEDIUMSIZE;
  167. size = strlen("bald");
  168. for (lfs_off_t j = 0; j < MEDIUMSIZE; j += size) {
  169. lfs_file_read(&lfs, &file, buffer, size) => size;
  170. memcmp(buffer, "bald", size) => 0;
  171. }
  172. lfs_file_read(&lfs, &file, buffer, size) => 0;
  173. lfs_file_close(&lfs, &file) => 0;
  174. lfs_unmount(&lfs) => 0;
  175. '''
  176. # truncate write under powerloss
  177. [cases.test_truncate_reentrant_write]
  178. defines.SMALLSIZE = [4, 512]
  179. defines.MEDIUMSIZE = [32, 1024]
  180. defines.LARGESIZE = 2048
  181. reentrant = true
  182. code = '''
  183. lfs_t lfs;
  184. int err = lfs_mount(&lfs, cfg);
  185. if (err) {
  186. lfs_format(&lfs, cfg) => 0;
  187. lfs_mount(&lfs, cfg) => 0;
  188. }
  189. lfs_file_t file;
  190. err = lfs_file_open(&lfs, &file, "baldy", LFS_O_RDONLY);
  191. assert(!err || err == LFS_ERR_NOENT);
  192. if (!err) {
  193. size_t size = lfs_file_size(&lfs, &file);
  194. assert(size == 0 ||
  195. size == (size_t)LARGESIZE ||
  196. size == (size_t)MEDIUMSIZE ||
  197. size == (size_t)SMALLSIZE);
  198. for (lfs_off_t j = 0; j < size; j += 4) {
  199. uint8_t buffer[1024];
  200. lfs_file_read(&lfs, &file, buffer, 4) => 4;
  201. assert(memcmp(buffer, "hair", 4) == 0 ||
  202. memcmp(buffer, "bald", 4) == 0 ||
  203. memcmp(buffer, "comb", 4) == 0);
  204. }
  205. lfs_file_close(&lfs, &file) => 0;
  206. }
  207. lfs_file_open(&lfs, &file, "baldy",
  208. LFS_O_WRONLY | LFS_O_CREAT | LFS_O_TRUNC) => 0;
  209. lfs_file_size(&lfs, &file) => 0;
  210. uint8_t buffer[1024];
  211. strcpy((char*)buffer, "hair");
  212. size_t size = strlen((char*)buffer);
  213. for (lfs_off_t j = 0; j < LARGESIZE; j += size) {
  214. lfs_file_write(&lfs, &file, buffer, size) => size;
  215. }
  216. lfs_file_size(&lfs, &file) => LARGESIZE;
  217. lfs_file_close(&lfs, &file) => 0;
  218. lfs_file_open(&lfs, &file, "baldy", LFS_O_RDWR) => 0;
  219. lfs_file_size(&lfs, &file) => LARGESIZE;
  220. lfs_file_truncate(&lfs, &file, MEDIUMSIZE) => 0;
  221. lfs_file_size(&lfs, &file) => MEDIUMSIZE;
  222. strcpy((char*)buffer, "bald");
  223. size = strlen((char*)buffer);
  224. for (lfs_off_t j = 0; j < MEDIUMSIZE; j += size) {
  225. lfs_file_write(&lfs, &file, buffer, size) => size;
  226. }
  227. lfs_file_size(&lfs, &file) => MEDIUMSIZE;
  228. lfs_file_close(&lfs, &file) => 0;
  229. lfs_file_open(&lfs, &file, "baldy", LFS_O_RDWR) => 0;
  230. lfs_file_size(&lfs, &file) => MEDIUMSIZE;
  231. lfs_file_truncate(&lfs, &file, SMALLSIZE) => 0;
  232. lfs_file_size(&lfs, &file) => SMALLSIZE;
  233. strcpy((char*)buffer, "comb");
  234. size = strlen((char*)buffer);
  235. for (lfs_off_t j = 0; j < SMALLSIZE; j += size) {
  236. lfs_file_write(&lfs, &file, buffer, size) => size;
  237. }
  238. lfs_file_size(&lfs, &file) => SMALLSIZE;
  239. lfs_file_close(&lfs, &file) => 0;
  240. lfs_unmount(&lfs) => 0;
  241. '''
  242. # more aggressive general truncation tests
  243. [cases.test_truncate_aggressive]
  244. defines.CONFIG = 'range(6)'
  245. defines.SMALLSIZE = 32
  246. defines.MEDIUMSIZE = 2048
  247. defines.LARGESIZE = 8192
  248. code = '''
  249. lfs_t lfs;
  250. #define COUNT 5
  251. const struct {
  252. lfs_off_t startsizes[COUNT];
  253. lfs_off_t startseeks[COUNT];
  254. lfs_off_t hotsizes[COUNT];
  255. lfs_off_t coldsizes[COUNT];
  256. } configs[] = {
  257. // cold shrinking
  258. {{2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE},
  259. {2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE},
  260. {2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE},
  261. { 0, SMALLSIZE, MEDIUMSIZE, LARGESIZE, 2*LARGESIZE}},
  262. // cold expanding
  263. {{2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE},
  264. {2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE},
  265. {2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE},
  266. { 0, SMALLSIZE, MEDIUMSIZE, LARGESIZE, 2*LARGESIZE}},
  267. // warm shrinking truncate
  268. {{2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE},
  269. {2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE},
  270. { 0, SMALLSIZE, MEDIUMSIZE, LARGESIZE, 2*LARGESIZE},
  271. { 0, 0, 0, 0, 0}},
  272. // warm expanding truncate
  273. {{ 0, SMALLSIZE, MEDIUMSIZE, LARGESIZE, 2*LARGESIZE},
  274. { 0, SMALLSIZE, MEDIUMSIZE, LARGESIZE, 2*LARGESIZE},
  275. {2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE},
  276. {2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE}},
  277. // mid-file shrinking truncate
  278. {{2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE},
  279. { LARGESIZE, LARGESIZE, LARGESIZE, LARGESIZE, LARGESIZE},
  280. { 0, SMALLSIZE, MEDIUMSIZE, LARGESIZE, 2*LARGESIZE},
  281. { 0, 0, 0, 0, 0}},
  282. // mid-file expanding truncate
  283. {{ 0, SMALLSIZE, MEDIUMSIZE, LARGESIZE, 2*LARGESIZE},
  284. { 0, 0, SMALLSIZE, MEDIUMSIZE, LARGESIZE},
  285. {2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE},
  286. {2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE, 2*LARGESIZE}},
  287. };
  288. const lfs_off_t *startsizes = configs[CONFIG].startsizes;
  289. const lfs_off_t *startseeks = configs[CONFIG].startseeks;
  290. const lfs_off_t *hotsizes = configs[CONFIG].hotsizes;
  291. const lfs_off_t *coldsizes = configs[CONFIG].coldsizes;
  292. lfs_format(&lfs, cfg) => 0;
  293. lfs_mount(&lfs, cfg) => 0;
  294. for (unsigned i = 0; i < COUNT; i++) {
  295. char path[1024];
  296. sprintf(path, "hairyhead%d", i);
  297. lfs_file_t file;
  298. lfs_file_open(&lfs, &file, path,
  299. LFS_O_WRONLY | LFS_O_CREAT | LFS_O_TRUNC) => 0;
  300. uint8_t buffer[1024];
  301. strcpy((char*)buffer, "hair");
  302. size_t size = strlen((char*)buffer);
  303. for (lfs_off_t j = 0; j < startsizes[i]; j += size) {
  304. lfs_file_write(&lfs, &file, buffer, size) => size;
  305. }
  306. lfs_file_size(&lfs, &file) => startsizes[i];
  307. if (startseeks[i] != startsizes[i]) {
  308. lfs_file_seek(&lfs, &file,
  309. startseeks[i], LFS_SEEK_SET) => startseeks[i];
  310. }
  311. lfs_file_truncate(&lfs, &file, hotsizes[i]) => 0;
  312. lfs_file_size(&lfs, &file) => hotsizes[i];
  313. lfs_file_close(&lfs, &file) => 0;
  314. }
  315. lfs_unmount(&lfs) => 0;
  316. lfs_mount(&lfs, cfg) => 0;
  317. for (unsigned i = 0; i < COUNT; i++) {
  318. char path[1024];
  319. sprintf(path, "hairyhead%d", i);
  320. lfs_file_t file;
  321. lfs_file_open(&lfs, &file, path, LFS_O_RDWR) => 0;
  322. lfs_file_size(&lfs, &file) => hotsizes[i];
  323. size_t size = strlen("hair");
  324. lfs_off_t j = 0;
  325. for (; j < startsizes[i] && j < hotsizes[i]; j += size) {
  326. uint8_t buffer[1024];
  327. lfs_file_read(&lfs, &file, buffer, size) => size;
  328. memcmp(buffer, "hair", size) => 0;
  329. }
  330. for (; j < hotsizes[i]; j += size) {
  331. uint8_t buffer[1024];
  332. lfs_file_read(&lfs, &file, buffer, size) => size;
  333. memcmp(buffer, "\0\0\0\0", size) => 0;
  334. }
  335. lfs_file_truncate(&lfs, &file, coldsizes[i]) => 0;
  336. lfs_file_size(&lfs, &file) => coldsizes[i];
  337. lfs_file_close(&lfs, &file) => 0;
  338. }
  339. lfs_unmount(&lfs) => 0;
  340. lfs_mount(&lfs, cfg) => 0;
  341. for (unsigned i = 0; i < COUNT; i++) {
  342. char path[1024];
  343. sprintf(path, "hairyhead%d", i);
  344. lfs_file_t file;
  345. lfs_file_open(&lfs, &file, path, LFS_O_RDONLY) => 0;
  346. lfs_file_size(&lfs, &file) => coldsizes[i];
  347. size_t size = strlen("hair");
  348. lfs_off_t j = 0;
  349. for (; j < startsizes[i] && j < hotsizes[i] && j < coldsizes[i];
  350. j += size) {
  351. uint8_t buffer[1024];
  352. lfs_file_read(&lfs, &file, buffer, size) => size;
  353. memcmp(buffer, "hair", size) => 0;
  354. }
  355. for (; j < coldsizes[i]; j += size) {
  356. uint8_t buffer[1024];
  357. lfs_file_read(&lfs, &file, buffer, size) => size;
  358. memcmp(buffer, "\0\0\0\0", size) => 0;
  359. }
  360. lfs_file_close(&lfs, &file) => 0;
  361. }
  362. lfs_unmount(&lfs) => 0;
  363. '''
  364. # noop truncate
  365. [cases.test_truncate_nop]
  366. defines.MEDIUMSIZE = [32, 2048]
  367. code = '''
  368. lfs_t lfs;
  369. lfs_format(&lfs, cfg) => 0;
  370. lfs_mount(&lfs, cfg) => 0;
  371. lfs_file_t file;
  372. lfs_file_open(&lfs, &file, "baldynoop",
  373. LFS_O_RDWR | LFS_O_CREAT) => 0;
  374. uint8_t buffer[1024];
  375. strcpy((char*)buffer, "hair");
  376. size_t size = strlen((char*)buffer);
  377. for (lfs_off_t j = 0; j < MEDIUMSIZE; j += size) {
  378. lfs_file_write(&lfs, &file, buffer, size) => size;
  379. // this truncate should do nothing
  380. lfs_file_truncate(&lfs, &file, j+size) => 0;
  381. }
  382. lfs_file_size(&lfs, &file) => MEDIUMSIZE;
  383. lfs_file_seek(&lfs, &file, 0, LFS_SEEK_SET) => 0;
  384. // should do nothing again
  385. lfs_file_truncate(&lfs, &file, MEDIUMSIZE) => 0;
  386. lfs_file_size(&lfs, &file) => MEDIUMSIZE;
  387. for (lfs_off_t j = 0; j < MEDIUMSIZE; j += size) {
  388. lfs_file_read(&lfs, &file, buffer, size) => size;
  389. memcmp(buffer, "hair", size) => 0;
  390. }
  391. lfs_file_read(&lfs, &file, buffer, size) => 0;
  392. lfs_file_close(&lfs, &file) => 0;
  393. lfs_unmount(&lfs) => 0;
  394. // still there after reboot?
  395. lfs_mount(&lfs, cfg) => 0;
  396. lfs_file_open(&lfs, &file, "baldynoop", LFS_O_RDWR) => 0;
  397. lfs_file_size(&lfs, &file) => MEDIUMSIZE;
  398. for (lfs_off_t j = 0; j < MEDIUMSIZE; j += size) {
  399. lfs_file_read(&lfs, &file, buffer, size) => size;
  400. memcmp(buffer, "hair", size) => 0;
  401. }
  402. lfs_file_read(&lfs, &file, buffer, size) => 0;
  403. lfs_file_close(&lfs, &file) => 0;
  404. lfs_unmount(&lfs) => 0;
  405. '''