From 9f2b7d5e6af2504c7db07dde94cecf1cbb67ed7a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Franti=C5=A1ek=20Boh=C3=A1=C4=8Dek?= Date: Mon, 28 Jun 2021 17:19:18 +0200 Subject: [PATCH] feat: add file executing --- file-browser/include/file_open.h | 11 +++++ file-browser/src/file_execute.c | 3 +- file-browser/src/file_open.c | 72 ++++++++++++++++++++++++++++ file-browser/src/local_file_access.c | 21 ++++---- 4 files changed, 97 insertions(+), 10 deletions(-) create mode 100644 file-browser/include/file_open.h create mode 100644 file-browser/src/file_open.c diff --git a/file-browser/include/file_open.h b/file-browser/include/file_open.h new file mode 100644 index 0000000..2fe720d --- /dev/null +++ b/file-browser/include/file_open.h @@ -0,0 +1,11 @@ +#ifndef __FILE_OPEN_H__ +#define __FILE_OPEN_H__ + +#include +#include "file_access.h" +#include "options.h" + +file_operation_error_t file_open(file_t *file, exec_options_t *options, + fileaccess_state_t state); + +#endif // __FILE_OPEN_H__ diff --git a/file-browser/src/file_execute.c b/file-browser/src/file_execute.c index cb4dbea..ed81944 100644 --- a/file-browser/src/file_execute.c +++ b/file-browser/src/file_execute.c @@ -4,6 +4,7 @@ #include #include #include +#include executing_file_error_t executing_file_execute(char *path, char *args) { executing_file_error_t ret; @@ -15,7 +16,7 @@ executing_file_error_t executing_file_execute(char *path, char *args) { } if (pid == 0) { - execl(path, args, (char*)NULL); + execl(path, path, args, (char*)NULL); exit(errno); } diff --git a/file-browser/src/file_open.c b/file-browser/src/file_open.c new file mode 100644 index 0000000..b90eb57 --- /dev/null +++ b/file-browser/src/file_open.c @@ -0,0 +1,72 @@ +#include "file_open.h" +#include "file_access.h" +#include +#include +#include +#include "nonblocking_io.h" +#include "serialize_lock.h" + +static void file_prepare_before_open() { + serialize_unlock(); +} + +static void file_prepare_after_open() { + struct termios old; + file_set_nonblocking(STDIN_FILENO, &old); + + if (serialize_lock(1) <= 0) { + serialize_lock(0); + } +} + +file_operation_error_t file_open(file_t *file, exec_options_t *options, fileaccess_state_t state) { + executing_file_t executing; + if (file->permissions & S_IXUSR) { + // executable + file_prepare_before_open(); + executing_file_or_error_t executing_or_error = fileaccess_file_execute(state, file, ""); + if (executing_or_error.error) { + file_prepare_after_open(); + return executing_or_error.payload.error; + } + + executing = executing_or_error.payload.file; + } else if (options != NULL) { + char mime[256]; + fileaccess_file_get_mimetype(state, file, mime); + + char *program = exec_options_get_program(options, mime); + + if (program == NULL) { + program = exec_options_get_program(options, "text"); + } + + if (program == NULL) { + return FILOPER_SUCCESS; + } + + char local_path[PATH_MAX]; + file_operation_error_t error = fileaccess_file_get_local_path(state, file, local_path); + + if (error != FILOPER_SUCCESS) { + return error; + } + + file_prepare_before_open(); + executing_file_error_t executing_or_error = executing_file_execute(program, local_path); + + if (executing_or_error.error != FILOPER_SUCCESS) { + file_prepare_after_open(); + return executing_or_error.error; + } + + executing = executing_or_error.file; + } else { + return FILOPER_UNKNOWN; + } + + executing_file_wait(&executing); + file_prepare_after_open(); + // TODO: figure out return data? + return FILOPER_SUCCESS; +} diff --git a/file-browser/src/local_file_access.c b/file-browser/src/local_file_access.c index 5d66394..911c20e 100644 --- a/file-browser/src/local_file_access.c +++ b/file-browser/src/local_file_access.c @@ -4,6 +4,7 @@ #include "path.h" #include #include +#include #include #include #include @@ -77,9 +78,11 @@ static file_operation_error_t file_get_information(void *malloced, directory_or_error_t local_fileaccess_directory_list(fileaccess_state_t state, char *path) { directory_or_error_t ret; - char full_path[path_join_memory_size(state.payload.local.path, path)]; + char full_path[PATH_MAX]; path_join((char *)state.payload.local.path, path, full_path); + realpath(full_path, full_path); + DIR *dirptr = opendir(full_path); if (dirptr == NULL) { ret.error = true; @@ -87,9 +90,13 @@ directory_or_error_t local_fileaccess_directory_list(fileaccess_state_t state, return ret; } + char show_path[PATH_MAX]; + realpath(path, show_path); + uint32_t files_count = 0; uint64_t size = directory_get_needed_bytes(path, &files_count, dirptr); - uint64_t files_offset = sizeof(directory_t) + strlen(path) + 1; + + uint64_t files_offset = sizeof(directory_t) + strlen(show_path) + 1; uint64_t names_offset = files_count * sizeof(file_t) + files_offset; directory_t *directory = malloc(size); void *malloced = directory; @@ -103,7 +110,7 @@ directory_or_error_t local_fileaccess_directory_list(fileaccess_state_t state, directory->path = malloced + sizeof(directory_t); directory->files = malloced + files_offset; directory->files_count = 0; - strcpy(directory->path, path); + strcpy(directory->path, show_path); struct dirent * dir; errno = 0; @@ -208,14 +215,10 @@ local_fileaccess_file_get_mime_type(fileaccess_state_t state, file_t *file, const char *data = magic_file(magic, full_path); if (data == NULL) { error = file_operation_error_from_errno(errno); + } else { + strcpy(mime, data); } - uint16_t i = 0; - while (*data != '\0') { - mime[i++] = *data; - } - mime[i] = '\0'; - magic_close(magic); return error; } -- 2.48.1