ra8-firmware 0.1.0
Bare-metal firmware for the Renesas RA8 family (RA8D2 / RA8P1)
Loading...
Searching...
No Matches
ra8_io_vfs.c
Go to the documentation of this file.
1
17
18#include "ra8_io_vfs.h"
19
20#include <stdint.h>
21
22#include "ra8_attributes.h"
23#include "ra8_check.h"
24#include "ra8_err.h"
25#include "ra8_fs.h"
26#include "ra8_io_fsfmt.h"
27#include "ra8_io_vfs_internal.h"
28
30static const char* const s_tag = "ra8_io_vfs";
31
35 void* file_ctx;
36 uint8_t mount_index;
37 bool in_use;
38};
39
44
45RA8_PRIV bool priv_ra8_io_vfs_streq(const char* a, const char* b)
46{
47 for (uint32_t i = 0U; i < (uint32_t)k_ra8_io_vfs_name_max; ++i) {
48 if (a[i] != b[i]) {
49 return false;
50 }
51 if (a[i] == '\0') {
52 return true;
53 }
54 }
55 return true;
56}
57
73static bool internal_name_ok(const char* name)
74{
75 uint32_t i = 0U;
76 for (i = 0U; i < (uint32_t)k_ra8_io_vfs_name_max; ++i) {
77 const char c = name[i];
78 if (c == '\0') {
79 break;
80 }
81 if (c == ':') {
82 return false;
83 }
84 if (c == '/') {
85 return false;
86 }
87 }
88 if (i == 0U) {
89 return false;
90 }
91 return i < (uint32_t)k_ra8_io_vfs_name_max;
92}
93
108static void internal_copy_name(char* dst, const char* src)
109{
110 uint32_t i = 0U;
111 for (i = 0U; i < (uint32_t)k_ra8_io_vfs_name_max - 1U; ++i) {
112 dst[i] = src[i];
113 if (src[i] == '\0') {
114 return;
115 }
116 }
117 dst[i] = '\0';
118}
119
120RA8_PRIV vfs_slot_t* priv_ra8_io_vfs_find(const char* name, uint8_t* out_index)
121{
122 for (uint32_t i = 0U; i < (uint32_t)k_ra8_io_vfs_max_mounts; ++i) {
123 if (!s_table[i].in_use) {
124 continue;
125 }
126 if (priv_ra8_io_vfs_streq(s_table[i].name, name)) {
127 if (out_index != nullptr) {
128 *out_index = (uint8_t)i;
129 }
130 return &s_table[i];
131 }
132 }
133 return nullptr;
134}
135
151{
152 for (uint32_t i = 0U; i < (uint32_t)k_ra8_io_vfs_max_mounts; ++i) {
153 if (!s_table[i].in_use) {
154 return &s_table[i];
155 }
156 }
157 return nullptr;
158}
159
160RA8_PRIV ra8_err_t priv_ra8_io_vfs_split(const char* path, char* out_name, const char** out_sub)
161{
162 uint32_t i = 0U;
163 for (i = 0U; i < (uint32_t)k_ra8_io_vfs_name_max; ++i) {
164 const char c = path[i];
165 if (c == '\0') {
167 }
168 if (c == ':') {
169 break;
170 }
171 out_name[i] = c;
172 }
173 if (i >= (uint32_t)k_ra8_io_vfs_name_max) {
175 }
176 out_name[i] = '\0';
177 *out_sub = &path[i + 1U];
178 return k_ra8_ok;
179}
180
182 vfs_slot_t** out_slot,
183 uint8_t* out_index,
184 const char** out_sub)
185{
186 char name[(uint32_t)k_ra8_io_vfs_name_max];
187 const ra8_err_t e = priv_ra8_io_vfs_split(path, name, out_sub);
188 if (e != k_ra8_ok) {
189 return e;
190 }
191 vfs_slot_t* slot = priv_ra8_io_vfs_find(name, out_index);
192 if (slot == nullptr) {
193 return k_ra8_err_not_found;
194 }
195 *out_slot = slot;
196 return k_ra8_ok;
197}
198
214static bool internal_is_native(const ra8_io_fsfmt_t* format)
215{
216 const ra8_io_fsfmt_t* native = nullptr;
218 if (format == native) {
219 return true;
220 }
222 return format == native;
223}
224
243 const char* name,
244 const ra8_io_fsfmt_t* format,
245 void* mount_ctx,
246 bool owned)
247{
248 internal_copy_name(slot->name, name);
249 slot->format = format;
250 slot->mount_ctx = mount_ctx;
251 slot->owned = owned;
252 slot->native = internal_is_native(format);
253 slot->in_use = true;
254}
255
272{
273 if (mode == k_ra8_fs_mode_read) {
274 return true;
275 }
276 if (mode == k_ra8_fs_mode_write) {
277 return true;
278 }
279 return mode == k_ra8_fs_mode_append;
280}
281
300{
301 if (!internal_mode_valid(mode)) {
303 }
304 if (mode == k_ra8_fs_mode_read) {
305 return k_ra8_ok;
306 }
307 if (format->caps.read_only) {
309 }
310 if (!format->caps.supports_streaming_write) {
312 }
313 if (format->ops->write == nullptr) {
315 }
316 return k_ra8_ok;
317}
318
334{
335 for (uint32_t i = 0U; i < (uint32_t)k_ra8_io_vfs_max_files; ++i) {
336 if (!s_files[i].in_use) {
337 return &s_files[i];
338 }
339 }
340 return nullptr;
341}
342
359{
360 if (file == nullptr) {
361 return false;
362 }
363 for (uint32_t i = 0U; i < (uint32_t)k_ra8_io_vfs_max_files; ++i) {
364 if (file == &s_files[i]) {
365 return file->in_use;
366 }
367 }
368 return false;
369}
370
388{
390 if (slot->in_use && slot->owned) {
391 e = slot->format->ops->unmount(slot->mount_ctx);
392 }
393 *slot = (vfs_slot_t){};
394 return e;
395}
396
402
404{
405 ra8_err_t first_error = k_ra8_ok;
406 for (uint32_t i = 0U; i < (uint32_t)k_ra8_io_vfs_max_files; ++i) {
407 s_files[i] = (ra8_io_vfs_file_t){};
408 }
409 for (uint32_t i = 0U; i < (uint32_t)k_ra8_io_vfs_max_mounts; ++i) {
411 if (first_error == k_ra8_ok) {
412 first_error = e;
413 }
414 }
415 return first_error;
416}
417
419{
420 RA8_CHECK_NULL_PTR(name, s_tag, "name must not be nullptr");
421 RA8_CHECK_NULL_PTR(mount, s_tag, "mount must not be nullptr");
422 if (!internal_name_ok(name)) {
424 }
425 if (priv_ra8_io_vfs_find(name, nullptr) != nullptr) {
426 return k_ra8_err_exists;
427 }
429 if (slot == nullptr) {
430 return k_ra8_err_no_mem;
431 }
432 const ra8_io_fsfmt_t* format = nullptr;
433 RA8_RETURN_ON_ERROR(ra8_io_fsfmt_get_builtin(mount->type, &format), s_tag, "native type");
434 internal_store_mount(slot, name, format, mount, false);
435 return k_ra8_ok;
436}
437
458 const ra8_io_fsfmt_t** out_format,
459 void** out_mount_ctx)
460{
461 RA8_RETURN_ON_ERROR(ra8_io_fsfmt_probe(backend, out_format), s_tag, "probe format");
462 RA8_RETURN_ON_ERROR((*out_format)->ops->mount(backend, out_mount_ctx), s_tag, "mount format");
463 return k_ra8_ok;
464}
465
466ra8_err_t ra8_io_vfs_mount_auto(const char* name, const ra8_fs_backend_t* backend)
467{
468 RA8_CHECK_NULL_PTR(name, s_tag, "name must not be nullptr");
469 RA8_CHECK_NULL_PTR(backend, s_tag, "backend must not be nullptr");
470 if (!internal_name_ok(name)) {
472 }
473 if (priv_ra8_io_vfs_find(name, nullptr) != nullptr) {
474 return k_ra8_err_exists;
475 }
477 if (slot == nullptr) {
478 return k_ra8_err_no_mem;
479 }
480 const ra8_io_fsfmt_t* format = nullptr;
481 void* mount_ctx = nullptr;
482 const ra8_err_t probed = internal_vfs_probe_and_mount(backend, &format, &mount_ctx);
483 if (probed != k_ra8_ok) {
484 return probed;
485 }
486 internal_store_mount(slot, name, format, mount_ctx, true);
487 return k_ra8_ok;
488}
489
491{
492 RA8_CHECK_NULL_PTR(name, s_tag, "name must not be nullptr");
493 uint8_t index = 0U;
494 vfs_slot_t* slot = priv_ra8_io_vfs_find(name, &index);
495 if (slot == nullptr) {
496 return k_ra8_err_not_found;
497 }
498 for (uint32_t i = 0U; i < (uint32_t)k_ra8_io_vfs_max_files; ++i) {
499 if (s_files[i].in_use) {
500 if (s_files[i].mount_index == index) {
501 return k_ra8_err_busy;
502 }
503 }
504 }
506 if (slot->owned) {
507 e = slot->format->ops->unmount(slot->mount_ctx);
508 }
509 *slot = (vfs_slot_t){};
510 return e;
511}
512
535 ra8_fs_mode_t mode,
536 vfs_slot_t** out_slot,
537 const char** out_sub)
538{
539 RA8_RETURN_ON_ERROR(priv_ra8_io_vfs_resolve(path, out_slot, nullptr, out_sub), s_tag, "resolve");
540 if (!(*out_slot)->native) {
542 }
543 RA8_RETURN_ON_ERROR(internal_can_open((*out_slot)->format, mode), s_tag, "open capability");
544 return k_ra8_ok;
545}
546
547ra8_err_t ra8_io_vfs_open(const char* path, ra8_fs_mode_t mode, ra8_fs_file_t** out_file)
548{
549 RA8_CHECK_NULL_PTR(path, s_tag, "path must not be nullptr");
550 RA8_CHECK_NULL_PTR(out_file, s_tag, "out_file must not be nullptr");
551 vfs_slot_t* slot = nullptr;
552 const char* sub = nullptr;
553 const ra8_err_t resolved = internal_vfs_open_resolve(path, mode, &slot, &sub);
554 if (resolved != k_ra8_ok) {
555 return resolved;
556 }
557 void* file_ctx = nullptr;
558 RA8_RETURN_ON_ERROR(slot->format->ops->open(slot->mount_ctx, sub, mode, &file_ctx),
559 s_tag,
560 "open");
561 *out_file = (ra8_fs_file_t*)file_ctx;
562 return k_ra8_ok;
563}
564
586 ra8_fs_mode_t mode,
587 vfs_slot_t** out_slot,
588 uint8_t* out_index,
589 const char** out_sub)
590{
591 RA8_RETURN_ON_ERROR(priv_ra8_io_vfs_resolve(path, out_slot, out_index, out_sub),
592 s_tag,
593 "resolve");
594 RA8_RETURN_ON_ERROR(internal_can_open((*out_slot)->format, mode), s_tag, "open capability");
595 return k_ra8_ok;
596}
597
599{
600 RA8_CHECK_NULL_PTR(path, s_tag, "path must not be nullptr");
601 RA8_CHECK_NULL_PTR(out_file, s_tag, "out_file must not be nullptr");
602 vfs_slot_t* slot = nullptr;
603 uint8_t index = 0U;
604 const char* sub = nullptr;
605 const ra8_err_t resolved = internal_vfs_file_open_resolve(path, mode, &slot, &index, &sub);
606 if (resolved != k_ra8_ok) {
607 return resolved;
608 }
610 if (file == nullptr) {
611 return k_ra8_err_no_mem;
612 }
613 void* file_ctx = nullptr;
614 RA8_RETURN_ON_ERROR(slot->format->ops->open(slot->mount_ctx, sub, mode, &file_ctx),
615 s_tag,
616 "open");
617 file->format = slot->format;
618 file->file_ctx = file_ctx;
619 file->mount_index = index;
620 file->in_use = true;
621 *out_file = file;
622 return k_ra8_ok;
623}
624
626{
627 RA8_CHECK_NULL_PTR(file, s_tag, "file must not be nullptr");
628 if (!internal_file_valid(file)) {
630 }
631 const ra8_err_t e = file->format->ops->close(file->file_ctx);
632 *file = (ra8_io_vfs_file_t){};
633 return e;
634}
635
637ra8_io_vfs_file_read(ra8_io_vfs_file_t* file, void* buf, uint32_t bytes, uint32_t* out_read)
638{
639 RA8_CHECK_NULL_PTR(file, s_tag, "file must not be nullptr");
640 RA8_CHECK_NULL_PTR(buf, s_tag, "buf must not be nullptr");
641 RA8_CHECK_NULL_PTR(out_read, s_tag, "out_read must not be nullptr");
642 if (!internal_file_valid(file)) {
644 }
645 return file->format->ops->read(file->file_ctx, buf, bytes, out_read);
646}
647
648ra8_err_t ra8_io_vfs_file_write(ra8_io_vfs_file_t* file, const void* buf, uint32_t bytes)
649{
650 RA8_CHECK_NULL_PTR(file, s_tag, "file must not be nullptr");
651 RA8_CHECK_NULL_PTR(buf, s_tag, "buf must not be nullptr");
652 if (!internal_file_valid(file)) {
654 }
655 if (file->format->caps.read_only) {
657 }
658 if (!file->format->caps.supports_streaming_write) {
660 }
661 if (file->format->ops->write == nullptr) {
663 }
664 return file->format->ops->write(file->file_ctx, buf, bytes);
665}
666
668{
669 RA8_CHECK_NULL_PTR(file, s_tag, "file must not be nullptr");
670 if (!internal_file_valid(file)) {
672 }
673 return file->format->ops->seek(file->file_ctx, offset_bytes);
674}
675
676ra8_err_t ra8_io_vfs_file_tell(const ra8_io_vfs_file_t* file, uint64_t* out_offset)
677{
678 RA8_CHECK_NULL_PTR(file, s_tag, "file must not be nullptr");
679 RA8_CHECK_NULL_PTR(out_offset, s_tag, "out_offset must not be nullptr");
680 if (!internal_file_valid(file)) {
682 }
683 return file->format->ops->tell(file->file_ctx, out_offset);
684}
685
686ra8_err_t ra8_io_vfs_file_size(const ra8_io_vfs_file_t* file, uint64_t* out_bytes)
687{
688 RA8_CHECK_NULL_PTR(file, s_tag, "file must not be nullptr");
689 RA8_CHECK_NULL_PTR(out_bytes, s_tag, "out_bytes must not be nullptr");
690 if (!internal_file_valid(file)) {
692 }
693 return file->format->ops->size(file->file_ctx, out_bytes);
694}
695
697{
698 RA8_CHECK_NULL_PTR(file, s_tag, "file must not be nullptr");
699 if (!internal_file_valid(file)) {
701 }
702 if (!file->format->caps.supports_sync) {
704 }
705 if (file->format->ops->sync == nullptr) {
707 }
708 return file->format->ops->sync(file->file_ctx);
709}
710
712{
713 RA8_CHECK_NULL_PTR(name, s_tag, "name must not be nullptr");
714 RA8_CHECK_NULL_PTR(out, s_tag, "out must not be nullptr");
715 vfs_slot_t* slot = priv_ra8_io_vfs_find(name, nullptr);
716 if (slot == nullptr) {
717 return k_ra8_err_not_found;
718 }
719 *out = slot->format->caps;
720 return k_ra8_ok;
721}
722
724{
725 RA8_CHECK_NULL_PTR(name, s_tag, "name must not be nullptr");
726 RA8_CHECK_NULL_PTR(out, s_tag, "out must not be nullptr");
727 vfs_slot_t* slot = priv_ra8_io_vfs_find(name, nullptr);
728 if (slot == nullptr) {
729 return k_ra8_err_not_found;
730 }
731 if (!slot->format->caps.supports_free_space) {
733 }
734 if (slot->format->ops->free_space == nullptr) {
736 }
737 return slot->format->ops->free_space(slot->mount_ctx, out);
738}
static const char * s_tag
Logging / check tag.
Definition ra8_app.c:17
Annotation-attribute framework macros for ra8-firmware.
#define RA8_PRIV
Module-private helper: shared across TUs but only inside one library.
#define RA8_TEST_HELPER
Mark a symbol as externally-linked but only callable from tests.
#define RA8_INTERNAL
Marker that a function is intended to be static (file-local).
Validation and Error-Checking Macros for ra8-firmware.
#define RA8_RETURN_ON_ERROR(err, tag, message)
Early return on error, propagating the code upward.
Definition ra8_check.h:184
#define RA8_CHECK_NULL_PTR(ptr, tag, message)
Reject nullptr pointer, returning k_ra8_err_null_ptr.
Definition ra8_check.h:243
Error Code Definitions for ra8-firmware.
@ k_ra8_err_not_supported
Requested feature not compiled in, not wired, or not supported by this MCU variant.
Definition ra8_err.h:180
@ k_ra8_err_no_mem
Static buffer exhausted (no dynamic memory on this project).
Definition ra8_err.h:142
@ k_ra8_err_busy
Resource busy – blocking operation cannot proceed.
Definition ra8_err.h:195
@ k_ra8_err_invalid_arg
Invalid function argument.
Definition ra8_err.h:152
@ k_ra8_err_exists
Item already exists – cannot create again.
Definition ra8_err.h:216
@ k_ra8_err_invalid_state
Module in wrong state for requested operation.
Definition ra8_err.h:161
@ k_ra8_ok
Success – operation completed with all postconditions satisfied.
Definition ra8_err.h:119
@ k_ra8_err_not_found
Requested item not found (lookup / search missed).
Definition ra8_err.h:173
ra8_err_codes_t ra8_err_t
Canonical error-return type used by every ra8-firmware API.
Definition ra8_err.h:546
Minimal FAT12/FAT16/FAT32 filesystem adapter (read + write).
static ra8_fs_file_t s_files[k_ra8_fs_max_files]
File handle table – max k_ra8_fs_max_files open at once.
@ k_ra8_fs_type_exfat
exFAT (read + streaming write + format).
@ k_ra8_fs_type_fat16
4085 <= count_of_clusters < 65525.
ra8_fs_mode_t
File-open modes accepted by ra8_fs_open().
@ k_ra8_fs_mode_append
Open at EOF for writing.
@ k_ra8_fs_mode_read
Read-only, must exist.
@ k_ra8_fs_mode_write
Truncate (or create) for writing.
ra8_io pluggable filesystem-format registry (probe + capabilities).
ra8_err_t ra8_io_fsfmt_probe(const ra8_fs_backend_t *backend, const ra8_io_fsfmt_t **out)
Detect the format of a volume by probing registered formats in order.
ra8_err_t ra8_io_fsfmt_get_builtin(ra8_fs_type_t type, const ra8_io_fsfmt_t **out)
Return the built-in descriptor serving one native ra8_fs type.
ra8_err_t priv_ra8_io_vfs_resolve(const char *path, vfs_slot_t **out_slot, uint8_t *out_index, const char **out_sub)
Resolve "name:sub" to a mount slot and sub-path.
Definition ra8_io_vfs.c:181
static void internal_store_mount(vfs_slot_t *slot, const char *name, const ra8_io_fsfmt_t *format, void *mount_ctx, bool owned)
Populate a previously selected free mount slot.
Definition ra8_io_vfs.c:242
static ra8_err_t internal_vfs_init_slot(vfs_slot_t *slot)
Reset one mount slot for global reinit, unmounting it first if owned.
Definition ra8_io_vfs.c:387
ra8_err_t ra8_io_vfs_mount(const char *name, ra8_fs_mount_t *mount)
Register a mounted volume under a name.
Definition ra8_io_vfs.c:418
ra8_err_t ra8_io_vfs_free_space(const char *name, ra8_fs_space_t *out)
Query free and total bytes through a mounted format's ops.
Definition ra8_io_vfs.c:723
ra8_err_t ra8_io_vfs_init_slot_test(vfs_slot_t *slot)
Implementation of ra8_io_vfs_init_slot_test().
Definition ra8_io_vfs.c:398
ra8_err_t ra8_io_vfs_open(const char *path, ra8_fs_mode_t mode, ra8_fs_file_t **out_file)
Open a file by "name:/path".
Definition ra8_io_vfs.c:547
ra8_err_t ra8_io_vfs_file_close(ra8_io_vfs_file_t *file)
Close and always release one format-neutral stream facade.
Definition ra8_io_vfs.c:625
ra8_err_t priv_ra8_io_vfs_split(const char *path, char *out_name, const char **out_sub)
Split "name:sub" into a bounded name and sub-path pointer.
Definition ra8_io_vfs.c:160
static bool internal_is_native(const ra8_io_fsfmt_t *format)
Test whether a descriptor is one of the native ra8_fs built-ins.
Definition ra8_io_vfs.c:214
bool priv_ra8_io_vfs_streq(const char *a, const char *b)
Compare two mount names within the fixed bound.
Definition ra8_io_vfs.c:45
ra8_err_t ra8_io_vfs_file_size(const ra8_io_vfs_file_t *file, uint64_t *out_bytes)
Report a format-neutral stream's size.
Definition ra8_io_vfs.c:686
static ra8_err_t internal_vfs_open_resolve(const char *path, ra8_fs_mode_t mode, vfs_slot_t **out_slot, const char **out_sub)
Resolve a raw-open path and require the target format be native.
Definition ra8_io_vfs.c:534
ra8_err_t ra8_io_vfs_get_caps(const char *name, ra8_io_fsfmt_caps_t *out)
Copy the truthful capabilities of a named mounted format.
Definition ra8_io_vfs.c:711
static bool internal_name_ok(const char *name)
Validate a non-empty bounded mount name with no path separators.
Definition ra8_io_vfs.c:73
ra8_err_t ra8_io_vfs_file_sync(ra8_io_vfs_file_t *file)
Explicitly sync a stream, or return not-supported when unavailable.
Definition ra8_io_vfs.c:696
ra8_err_t ra8_io_vfs_mount_auto(const char *name, const ra8_fs_backend_t *backend)
Probe and mount a block backend through the registered format ops.
Definition ra8_io_vfs.c:466
static void internal_copy_name(char *dst, const char *src)
Copy one already-validated mount name into a fixed slot.
Definition ra8_io_vfs.c:108
ra8_err_t ra8_io_vfs_file_open(const char *path, ra8_fs_mode_t mode, ra8_io_vfs_file_t **out_file)
Open a format-neutral stream through a mounted format's ops.
Definition ra8_io_vfs.c:598
static ra8_io_vfs_file_t * internal_free_file(void)
Find one free generic-file facade.
Definition ra8_io_vfs.c:333
static ra8_err_t internal_vfs_file_open_resolve(const char *path, ra8_fs_mode_t mode, vfs_slot_t **out_slot, uint8_t *out_index, const char **out_sub)
Resolve a facade-open path and require the format support mode.
Definition ra8_io_vfs.c:585
ra8_err_t ra8_io_vfs_unmount(const char *name)
Remove a named mount from the table.
Definition ra8_io_vfs.c:490
ra8_err_t ra8_io_vfs_file_read(ra8_io_vfs_file_t *file, void *buf, uint32_t bytes, uint32_t *out_read)
Read bytes through a format-neutral stream.
Definition ra8_io_vfs.c:637
static vfs_slot_t * internal_free_mount(void)
Find one free mount slot.
Definition ra8_io_vfs.c:150
static bool internal_file_valid(const ra8_io_vfs_file_t *file)
Verify a facade is currently owned by the fixed file table.
Definition ra8_io_vfs.c:358
static bool internal_mode_valid(ra8_fs_mode_t mode)
Test whether a value is one of the three public stream modes.
Definition ra8_io_vfs.c:271
ra8_err_t ra8_io_vfs_file_seek(ra8_io_vfs_file_t *file, uint64_t offset_bytes)
Seek a format-neutral stream.
Definition ra8_io_vfs.c:667
static ra8_err_t internal_vfs_probe_and_mount(const ra8_fs_backend_t *backend, const ra8_io_fsfmt_t **out_format, void **out_mount_ctx)
Probe a backend's format and mount it through that format, guarded.
Definition ra8_io_vfs.c:457
ra8_err_t ra8_io_vfs_file_tell(const ra8_io_vfs_file_t *file, uint64_t *out_offset)
Report a format-neutral stream's current offset.
Definition ra8_io_vfs.c:676
static vfs_slot_t s_table[(uint32_t) k_ra8_io_vfs_max_mounts]
Fixed mount table.
Definition ra8_io_vfs.c:41
ra8_err_t ra8_io_vfs_init(void)
Reset the VFS mount table to empty.
Definition ra8_io_vfs.c:403
static ra8_err_t internal_can_open(const ra8_io_fsfmt_t *format, ra8_fs_mode_t mode)
Capability-gate a requested open mode.
Definition ra8_io_vfs.c:299
ra8_err_t ra8_io_vfs_file_write(ra8_io_vfs_file_t *file, const void *buf, uint32_t bytes)
Write bytes, or return not-supported when capability-gated.
Definition ra8_io_vfs.c:648
vfs_slot_t * priv_ra8_io_vfs_find(const char *name, uint8_t *out_index)
Find an occupied mount slot by name and optionally report its index.
Definition ra8_io_vfs.c:120
ra8_io virtual filesystem – mount many volumes, address them by name.
@ k_ra8_io_vfs_max_mounts
Concurrent named mounts.
Definition ra8_io_vfs.h:56
@ k_ra8_io_vfs_max_files
Concurrent generic streams.
Definition ra8_io_vfs.h:57
@ k_ra8_io_vfs_name_max
Mount name length incl NUL.
Definition ra8_io_vfs.h:58
Module-private mount-slot layout and path resolvers for the ra8_io VFS.
Block-device interface that ra8_fs runs on top of.
Open-file state.
Cached parse of one mounted FAT volume.
ra8_fs_type_t type
FAT12 / FAT16 / FAT32.
A mounted volume's capacity, free space, and cluster geometry.
Definition ra8_fs_meta.h:84
What a filesystem format supports.
One registered filesystem format.
Opaque, statically-pooled format-neutral file stream.
Publicly opaque stream facade, drawn from s_files.
Definition ra8_io_vfs.c:33
uint8_t mount_index
Owning mount slot.
Definition ra8_io_vfs.c:36
const ra8_io_fsfmt_t * format
Format owning file_ctx.
Definition ra8_io_vfs.c:34
void * file_ctx
Format-private open-file state.
Definition ra8_io_vfs.c:35
bool in_use
Facade is occupied.
Definition ra8_io_vfs.c:37
One fixed named-mount slot.
void * mount_ctx
Format-private mounted context.
const ra8_io_fsfmt_t * format
Selected format descriptor.
bool in_use
Slot is occupied.
bool native
Context is a native ra8_fs mount.
bool owned
VFS must invoke format unmount.
char name[(uint32_t) k_ra8_io_vfs_name_max]
NUL-terminated mount name.