diff options
-rw-r--r-- | src/filesystem.c | 78 |
1 files changed, 28 insertions, 50 deletions
diff --git a/src/filesystem.c b/src/filesystem.c index cac2805..3fe95ab 100644 --- a/src/filesystem.c +++ b/src/filesystem.c | |||
@@ -127,14 +127,19 @@ _fs_update_file_index(u16 index) { | |||
127 | } | 127 | } |
128 | 128 | ||
129 | typedef enum { | 129 | typedef enum { |
130 | FS_OPEN_READ, | 130 | FS_OPEN_READ = (1 << 0), |
131 | FS_OPEN_WRITE, | 131 | FS_OPEN_WRITE = (1 << 1), |
132 | FS_OPEN_APPEND, | 132 | FS_OPEN_APPEND = (1 << 2), |
133 | } OpenMode; | 133 | } OpenMode; |
134 | 134 | ||
135 | typedef struct File { | 135 | typedef struct File { |
136 | // File index offset. | ||
136 | u8 index; | 137 | u8 index; |
138 | // The offset within the file. Must always be valid, and so the File struct | ||
139 | // shouldn't be manaully modified unless we are sure we know what we are | ||
140 | // doing. | ||
137 | u16 offset; | 141 | u16 offset; |
142 | // The mode of this file (read/write/append). | ||
138 | OpenMode mode; | 143 | OpenMode mode; |
139 | } File; | 144 | } File; |
140 | 145 | ||
@@ -148,7 +153,8 @@ fs_open_file(char *name, OpenMode mode) { | |||
148 | } | 153 | } |
149 | } | 154 | } |
150 | 155 | ||
151 | if (mode == FS_OPEN_READ) { | 156 | // If read only. |
157 | if ((mode & (FS_OPEN_WRITE | FS_OPEN_APPEND)) == 0) { | ||
152 | return (File){FS_NULL, 0, mode}; | 158 | return (File){FS_NULL, 0, mode}; |
153 | } | 159 | } |
154 | 160 | ||
@@ -202,8 +208,6 @@ _fs_init_new_block(void) { | |||
202 | return FS_NULL; | 208 | return FS_NULL; |
203 | } | 209 | } |
204 | 210 | ||
205 | #include "text.h" | ||
206 | |||
207 | // Recursively free blocks starting at blk_id. To improve performance, the | 211 | // Recursively free blocks starting at blk_id. To improve performance, the |
208 | // filesystem header is updated in memory but not written to disk. It is | 212 | // filesystem header is updated in memory but not written to disk. It is |
209 | // responsability of the caller to perform the filesystem update. | 213 | // responsability of the caller to perform the filesystem update. |
@@ -236,7 +240,8 @@ _fs_free_blocks(u8 blk_id) { | |||
236 | 240 | ||
237 | // Write to block as a new file. | 241 | // Write to block as a new file. |
238 | void | 242 | void |
239 | _fs_write_to_block(u8 *src, u16 n_bytes, u16 blk_offset, u8 blk_id, u8 prev_blk) { | 243 | _fs_write_to_block(u8 *src, u16 n_bytes, u16 blk_offset, |
244 | u8 blk_id, u8 prev_blk, bool append) { | ||
240 | // Read initial block. | 245 | // Read initial block. |
241 | FileBlock block; | 246 | FileBlock block; |
242 | u16 block_pos = FILE_DATA_START + FILE_BLOCK_SIZE * blk_id; | 247 | u16 block_pos = FILE_DATA_START + FILE_BLOCK_SIZE * blk_id; |
@@ -253,7 +258,7 @@ _fs_write_to_block(u8 *src, u16 n_bytes, u16 blk_offset, u8 blk_id, u8 prev_blk) | |||
253 | block.next_block = _fs_init_new_block(); | 258 | block.next_block = _fs_init_new_block(); |
254 | } | 259 | } |
255 | _fs_write_to_block(src + block_capacity, n_bytes - block_capacity, 0, | 260 | _fs_write_to_block(src + block_capacity, n_bytes - block_capacity, 0, |
256 | block.next_block, blk_id); | 261 | block.next_block, blk_id, append); |
257 | } else if (block.next_block != FS_NULL){ | 262 | } else if (block.next_block != FS_NULL){ |
258 | // Recursively free unused blocks. | 263 | // Recursively free unused blocks. |
259 | _fs_free_blocks(block.next_block); | 264 | _fs_free_blocks(block.next_block); |
@@ -269,52 +274,27 @@ _fs_write_to_block(u8 *src, u16 n_bytes, u16 blk_offset, u8 blk_id, u8 prev_blk) | |||
269 | _fs_write(&block, block_pos, sizeof(FileBlock)); | 274 | _fs_write(&block, block_pos, sizeof(FileBlock)); |
270 | } | 275 | } |
271 | 276 | ||
272 | // void | 277 | int |
273 | // _fs_append_to_block(u8 *src, u16 n_bytes, u8 blk_id, u8 prev_block) { | 278 | fs_seek(File *file, int offset) { |
274 | // // Read initial block. | 279 | u16 file_size = fs_file_size(file); |
275 | // FileBlock block; | 280 | u16 new_offset = MAX((int)file->offset + offset, 0); |
276 | // size_t block_pos = FILE_DATA_START + FILE_BLOCK_SIZE * blk_id; | 281 | if (new_offset >= file_size) { |
277 | // _fs_read(&block, block_pos, sizeof(FileBlock)); | 282 | return -1; |
278 | // u16 block_capacity = (FILE_BLOCK_SIZE - sizeof(FileBlock)) - block.size; | 283 | } |
279 | 284 | file->offset = new_offset; | |
280 | // // Write capacity. | 285 | return 0; |
281 | // u16 block_bytes = MIN(block_capacity, n_bytes); | 286 | } |
282 | // _fs_write(src, block_pos + sizeof(FileBlock), block_bytes); | ||
283 | |||
284 | // // txt_printf("cap: %d\n", block_capacity); | ||
285 | // // txt_printf("bytes: %d\n", n_bytes); | ||
286 | // // txt_printf("id: %d\n", blk_id); | ||
287 | // if (n_bytes > block_capacity) { | ||
288 | // if (block.next_block == FS_NULL) { | ||
289 | // // Find new available block and initialize it. | ||
290 | // block.next_block = _fs_init_new_block(); | ||
291 | // // TODO: Don't forget to set the block_prev of the next block as | ||
292 | // // this one. | ||
293 | // } | ||
294 | // _fs_write_to_block( | ||
295 | // src + block_capacity, | ||
296 | // n_bytes - block_capacity, | ||
297 | // block.next_block, | ||
298 | // blk_id); | ||
299 | // } | ||
300 | |||
301 | // // Update block header. | ||
302 | // if (prev_block != FS_NULL) { | ||
303 | // block.prev_block = prev_bloc7f8k; | ||
304 | // } | ||
305 | // block.size += block_bytes; | ||
306 | // _fs_write(&block, block_pos, sizeof(FileBlock)); | ||
307 | // } | ||
308 | 287 | ||
309 | u16 | 288 | u16 |
310 | fs_write(u8 *src, u16 n_bytes, File *file) { | 289 | fs_write(u8 *src, u16 n_bytes, File *file) { |
311 | if (file->mode != FS_OPEN_WRITE && file->mode != FS_OPEN_APPEND) { | 290 | if ((file->mode & (FS_OPEN_WRITE | FS_OPEN_APPEND)) == 0) { |
312 | return 0; | 291 | return 0; |
313 | } | 292 | } |
314 | 293 | ||
315 | FileIndex *file_idx = &filesystem.files[file->index]; | 294 | FileIndex *file_idx = &filesystem.files[file->index]; |
316 | 295 | ||
317 | u8 blk_id = FS_NULL; | 296 | u8 blk_id = FS_NULL; |
297 | u8 blk_prev = FS_NULL; | ||
318 | u16 offset = file->offset; | 298 | u16 offset = file->offset; |
319 | if (file_idx->first_block == FS_NULL) { | 299 | if (file_idx->first_block == FS_NULL) { |
320 | // Check how many blocks will this write requires and if we have enough | 300 | // Check how many blocks will this write requires and if we have enough |
@@ -352,6 +332,7 @@ fs_write(u8 *src, u16 n_bytes, File *file) { | |||
352 | u16 block_pos = FILE_DATA_START + FILE_BLOCK_SIZE * blk_id; | 332 | u16 block_pos = FILE_DATA_START + FILE_BLOCK_SIZE * blk_id; |
353 | _fs_read(&block, block_pos, sizeof(FileBlock)); | 333 | _fs_read(&block, block_pos, sizeof(FileBlock)); |
354 | blk_id = block.next_block; | 334 | blk_id = block.next_block; |
335 | blk_prev = block.prev_block; | ||
355 | if (blk_id == FS_NULL) { | 336 | if (blk_id == FS_NULL) { |
356 | return 0; | 337 | return 0; |
357 | } | 338 | } |
@@ -361,11 +342,8 @@ fs_write(u8 *src, u16 n_bytes, File *file) { | |||
361 | } | 342 | } |
362 | 343 | ||
363 | // Write to block. | 344 | // Write to block. |
364 | if (file->mode == FS_OPEN_WRITE) { | 345 | _fs_write_to_block(src, n_bytes, offset, blk_id, blk_prev, |
365 | _fs_write_to_block(src, n_bytes, offset, blk_id, FS_NULL); | 346 | file->mode == FS_OPEN_APPEND); |
366 | } else { | ||
367 | // TODO: Append... | ||
368 | } | ||
369 | 347 | ||
370 | return n_bytes; | 348 | return n_bytes; |
371 | } | 349 | } |