# HG changeset patch # User Paul Boddie # Date 1575223799 -3600 # Node ID 224029b28695eda4fcc899edfed262ec079d1744 # Parent 9e6aae29b3ad3adcc719a1ea187b23de3af96366 Updated the virtual filesystem server to work with the other components. diff -r 9e6aae29b3ad -r 224029b28695 server/src/Makefile --- a/server/src/Makefile Mon Jul 22 17:36:37 2019 +0200 +++ b/server/src/Makefile Sun Dec 01 19:09:59 2019 +0100 @@ -6,6 +6,6 @@ SRC_CC = main.cc fspath.cc -REQUIRES_LIBS = libstdc++ l4re_c l4re_c-util libipc libfsclient libfsserver +REQUIRES_LIBS = libstdc++ l4re_c libipc libfsclient libfsserver include $(L4DIR)/mk/prog.mk diff -r 9e6aae29b3ad -r 224029b28695 server/src/main.cc --- a/server/src/main.cc Mon Jul 22 17:36:37 2019 +0200 +++ b/server/src/main.cc Sun Dec 01 19:09:59 2019 +0100 @@ -19,12 +19,8 @@ * Boston, MA 02110-1301, USA */ -#include - -#include #include #include -#include #include #include @@ -34,11 +30,17 @@ #include #include -#include -#include -#include +#include #include "fspath.h" +/* Exposure of the resource. */ + +#include + +/* Implemented interfaces. */ + +#include + /* Mountpoint-to-server mapping. */ @@ -49,165 +51,161 @@ -/* Virtual filesystem server. */ +/* Virtual filesystem resource. */ -class Vfs_server : public OpeningServer +class Vfs_resource : public UserFilesystemResource { private: MountTable _servers; public: - explicit Vfs_server() - : OpeningServer() + explicit Vfs_resource() + : UserFilesystemResource() { } - void dispatch(ipc_message_t *msg) + + + /* Obtain an object as a filesystem reference. */ + + long getfs_object(fs_object_t *fsobj, l4_cap_idx_t *fs) { - switch (l4_msgtag_label(msg->tag)) - { - case Fs_op_mount: - mount(msg); - break; + file_descriptor_t desc; + long err; + + /* Obtain a suitable descriptor. */ + + err = init_desc(&desc, fsobj); + + if (err) + return err; + + /* Return a reference to any directly-accessed object. */ + + char *path = fsdesc_get_name(fsobj); - case Fs_op_open: - open(msg); - break; + if ((path != NULL) && !strlen(path)) + { + *fs = desc.server; + return L4_EOK; + } + + /* Find the path within the selected filesystem. */ + + /* Propagate the message to the identified filesystem. + The L4_MSGTAG_PROPAGATE flag is not supported by Fiasco.OC, so this + object has to act as intermediary. */ - case Fs_op_getfs: - getfs(msg); - break; + err = fs_getfs(&desc); + + if (err) + return err; + + /* Free the capabilities and buffer from this task. */ - default: - ipc_message_send_error(msg, -L4_EBADPROTO); - break; - } + fsdesc_deallocate_object(fsobj); + + /* Export and eventually free the server reference from this task. */ + + *fs = discard_cap(desc.ref); + + return L4_EOK; } - void getfs(ipc_message_t *msg) + /* Mount a filesystem at a particular location. */ + + long mount_object(fs_object_t *fsobj, l4_cap_idx_t fs) { - _open(Fs_op_getfs, msg); + /* Obtain the object's path. */ + + char *path = fsdesc_get_name(fsobj); + + if (path == NULL) + return -L4_EINVAL; + + /* Mount the supplied capability. */ + + mount_at_path(fs, path); + + /* Free the capability and buffer from this task. */ + + fsdesc_deallocate_buffer(fsobj); + + return L4_EOK; } - void open(ipc_message_t *msg) - { - _open(Fs_op_open, msg); - } + /* Open a filesystem object. */ - void _open(int op, ipc_message_t *msg) + long open_object(fs_object_t *fsobj, int flags, size_t *size, l4_cap_idx_t *file) { file_descriptor_t desc; - int flags; long err; - /* Obtain the flags. */ + /* Obtain a suitable descriptor. */ + + err = init_desc(&desc, fsobj); + + if (err) + return err; + + /* Find the path within the selected filesystem. */ - flags = ipc_message_get_word(msg, 0); + /* Propagate the message to the identified filesystem. + The L4_MSGTAG_PROPAGATE flag is not supported by Fiasco.OC, so this + object has to act as intermediary. */ - /* Obtain the dataspace and IRQ object. */ + err = fs_open(&desc, flags); + + if (err) + return err; + + /* Free the capabilities and buffer from this task. */ - err = fsdesc_import_object(msg, 0, &desc.obj); - if (err) - { - ipc_message_send_error(msg, -L4_EIO); - return; - } + fsdesc_deallocate_object(fsobj); + + /* Export and eventually free the server reference from this task. */ + + *size = desc.obj.size; + *file = discard_cap(desc.ref); + + return L4_EOK; + } + + + + /* Non-exported methods. */ + + /* Initialise a descriptor for accessing a mounted filesystem. */ + + long init_desc(file_descriptor_t *desc, fs_object_t *obj) + { + /* Copy the object details into the descriptor. */ + + desc->obj = *obj; /* Match the path to a mountpoint. */ - char *path = fsdesc_get_name(&desc.obj); + char *path = fsdesc_get_name(&desc->obj); if (path == NULL) - { - ipc_message_send_error(msg, -L4_EINVAL); - return; - } + return -L4_EINVAL; MountTableIterator entry = find_mountpoint(path); if (entry == _servers.end()) - { - ipc_message_send_error(msg, -L4_ENOENT); - return; - } + return -L4_ENOENT; /* Rewrite the path for the selected filesystem. */ rewrite_path(path, entry->first); - /* Find the path within the selected filesystem. */ - - /* Propagate the message to the identified filesystem. - NOTE: The L4_MSGTAG_PROPAGATE flag is not supported by Fiasco.OC, so this - NOTE: object has to act as intermediary. */ - - desc.server = entry->second; - - err = fs_ipc_open(&desc, flags, op); - if (err) - { - ipc_message_send_error(msg, -L4_EIO); - return; - } - - /* Free the capabilities and buffer from this task. */ - - fsdesc_deallocate_object(&desc.obj); - - /* Return the file size. */ - - ipc_message_add_word(msg, desc.obj.size); - - /* Export and eventually free the server reference from this task. */ - - ipc_message_propagate_item(msg, desc.ref); - } - - void mount(ipc_message_t *msg) - { - fs_object_t fsobj; - l4_cap_idx_t server; - long err; - - /* Obtain the filesystem capability. */ + /* Use the filesystem as the target of any query. */ - err = ipc_message_import_capability(msg, 0, &server); - if (err) - { - ipc_message_send_error(msg, -L4_EIO); - return; - } - - /* Obtain the dataspace. */ - - err = fsdesc_import_dataspace(msg, 1, &fsobj); - if (err) - { - ipc_message_send_error(msg, -L4_EIO); - return; - } - - /* Obtain the object's path. */ + desc->server = entry->second; - char *path = fsdesc_get_name(&fsobj); - - if (path == NULL) - { - ipc_message_send_error(msg, -L4_EINVAL); - return; - } - - /* Mount the supplied capability. */ - - mount_at_path(server, path); - - /* Free the capability and buffer from this task. */ - - fsdesc_deallocate_buffer(&fsobj); + return L4_EOK; } - /* Non-exported methods. */ - void mount_at_path(l4_cap_idx_t server, const char *path) { /* NOTE: Should terminate with path separator if absent. @@ -278,9 +276,10 @@ /* Initialise and register a new server object. */ - Vfs_server server_obj; + Vfs_resource resource; + UserFilesystemServer server(&resource); - if (server_obj.bind("export")) + if (server.bind("export")) { printf("Could not bind thread.\n"); return 1; @@ -318,13 +317,14 @@ /* Terminate the path and register the mountpoint. */ *sep = '\0'; - server_obj.mount_at_path(fscap, buffer); + resource.mount_at_path(fscap, buffer); } fclose(fp); /* Enter the IPC server loop. */ - server_obj.loop(); + printf("Starting vfs resource...\n"); + server.start(); return 0; }