diff --git a/linux/io.c b/linux/io.c index db067c3..0fa67a9 100644 --- a/linux/io.c +++ b/linux/io.c @@ -27,22 +27,24 @@ io_init(int change_task) { } void -io_close(void *userdata) { - struct umka_io *io = (struct umka_io*)userdata; +io_close(void *arg) { + struct umka_io *io = arg; free(io); } ssize_t -io_read(int fd, void *buf, size_t count, int change_task) { - (void)change_task; +io_read(int fd, void *buf, size_t count, void *arg) { + struct umka_io *io = arg; + (void)io; ssize_t res; res = read(fd, buf, count); return res; } ssize_t -io_write(int fd, const void *buf, size_t count, int change_task) { - (void)change_task; +io_write(int fd, const void *buf, size_t count, void *arg) { + struct umka_io *io = arg; + (void)io; ssize_t res; res = write(fd, buf, count); return res; diff --git a/linux/io.h b/linux/io.h index f773bd2..ddac37d 100644 --- a/linux/io.h +++ b/linux/io.h @@ -12,10 +12,19 @@ #include -ssize_t -io_read(int fd, void *buf, size_t count, int change_task); +#define IO_DONT_CHANGE_TASK 0 +#define IO_CHANGE_TASK 1 + +void * +io_init(int change_task); + +void +io_close(void *arg); ssize_t -io_write(int fd, const void *buf, size_t count, int change_task); +io_read(int fd, void *buf, size_t count, void *arg); + +ssize_t +io_write(int fd, const void *buf, size_t count, void *arg); #endif // IO_H_INCLUDED diff --git a/shell.c b/shell.c index 3ac3a51..cccc792 100644 --- a/shell.c +++ b/shell.c @@ -321,9 +321,9 @@ get_last_dir(const char *path) { } static void -prompt() { +prompt(struct shell_ctx *ctx) { if (cur_dir_changed) { - if (umka_initialized) { + if (ctx->umka && ctx->umka->initialized) { COVERAGE_ON(); umka_sys_get_cwd(cur_dir, PATH_MAX); COVERAGE_OFF(); @@ -406,7 +406,6 @@ cmd_send_scancode(struct shell_ctx *ctx, int argc, char **argv) { static void cmd_umka_init(struct shell_ctx *ctx, int argc, char **argv) { - (void)ctx; const char *usage = \ "usage: umka_init \n" " number or string: 1=shell, 2=fuse, 3=os"; @@ -428,8 +427,12 @@ cmd_umka_init(struct shell_ctx *ctx, int argc, char **argv) { } COVERAGE_ON(); - umka_init(tool); + ctx->umka = umka_init(tool); COVERAGE_OFF(); + + if (!ctx->umka) { + printf("![shell] can't init umka\n"); + } } static void @@ -631,7 +634,7 @@ cmd_disk_add(struct shell_ctx *ctx, int argc, char **argv) { } struct vdisk *umka_disk = vdisk_init(file_name, adjust_cache_size, - cache_size, umka_tool == UMKA_OS); + cache_size, ctx->io); if (umka_disk) { COVERAGE_ON(); disk_t *disk = disk_add(&umka_disk->diskfunc, disk_name, umka_disk, 0); @@ -3875,7 +3878,7 @@ run_test(struct shell_ctx *ctx) { char *line; while((line = bestline(prompt_line))) { if (!is_tty) { - prompt(); + prompt(ctx); printf("%s\n", line); } if (!strcmp(line, "X") || !strcmp(line, "q")) { @@ -3907,3 +3910,23 @@ run_test(struct shell_ctx *ctx) { return NULL; } + +struct shell_ctx * +shell_init(int reproducible, const char *hist_file, struct umka_io *io) { + struct shell_ctx *ctx = malloc(sizeof(struct shell_ctx)); + ctx->umka = NULL; + ctx->io = io; + ctx->reproducible = reproducible; + ctx->hist_file = hist_file; + ctx->var = NULL; + return ctx; +} + +void +shell_close(struct shell_ctx *ctx) { + struct shell_var *next; + for (struct shell_var *var = ctx->var; var; var = next) { + next = var->next; + free(var); + } +} diff --git a/shell.h b/shell.h index 224e8fc..b2304a0 100644 --- a/shell.h +++ b/shell.h @@ -4,13 +4,15 @@ UMKa - User-Mode KolibriOS developer tools umka_shell - the shell - Copyright (C) 2020-2022 Ivan Baravy + Copyright (C) 2020-2023 Ivan Baravy */ #ifndef SHELL_H_INCLUDED #define SHELL_H_INCLUDED #include +#include "umka.h" +#include "io.h" enum shell_var_type { SHELL_VAR_SINT, @@ -18,6 +20,9 @@ enum shell_var_type { SHELL_VAR_POINTER, }; +#define SHELL_LOG_NONREPRODUCIBLE 0 +#define SHELL_LOG_REPRODUCIBLE 1 + #define SHELL_VAR_NAME_LEN 16 struct shell_var { @@ -28,11 +33,20 @@ struct shell_var { }; struct shell_ctx { + struct umka_ctx *umka; + struct umka_io *io; int reproducible; const char *hist_file; struct shell_var *var; }; -void *run_test(struct shell_ctx *ctx); +struct shell_ctx * +shell_init(int reproducible, const char *hist_file, struct umka_io *io); + +void +shell_close(struct shell_ctx *shell); + +void * +run_test(struct shell_ctx *ctx); #endif // SHELL_H_INCLUDED diff --git a/umka.asm b/umka.asm index c338a02..fb5dbf8 100644 --- a/umka.asm +++ b/umka.asm @@ -2,7 +2,7 @@ ; ; UMKa - User-Mode KolibriOS developer tools ; -; Copyright (C) 2017-2022 Ivan Baravy +; Copyright (C) 2017-2023 Ivan Baravy ; Copyright (C) 2021 Magomed Kostoev if HOST eq windows @@ -113,7 +113,8 @@ pubsym coverage_end pubsym sha3_256_oneshot, 'hash_oneshot' pubsym kos_time_to_epoch -pubsym umka_init +pubsym umka_init, 4 +pubsym umka_close, 4 pubsym current_process, 'kos_current_process' pubsym current_slot, 'kos_current_slot' @@ -555,12 +556,28 @@ proc kos_eth_input c uses ebx esi edi ebp, buffer_ptr ret endp -proc umka_init c uses ebx esi edi ebp, _tool - mov eax, [_tool] - mov [umka_tool], eax - mov [umka_initialized], 1 - call umka._.check_alignment +struct umka_ctx + tool dd ? + initialized dd ? +ends +proc umka_init c uses ebx esi edi ebp, _tool + call umka._.check_alignment + stdcall kos_init + stdcall kernel_alloc, sizeof.umka_ctx + mov ecx, [_tool] + mov [umka_tool], ecx + mov [eax+umka_ctx.tool], ecx + mov [eax+umka_ctx.initialized], 1 + ret +endp + +proc umka_close c, _ctx + xor eax, eax + ret +endp + +proc kos_init uses ebx esi edi ebp mov edi, endofcode mov ecx, uglobals_size xor eax, eax @@ -1047,10 +1064,8 @@ else if HOST eq linux else error "Your OS is not supported" end if -pubsym umka_tool + umka_tool dd ? -pubsym umka_initialized -umka_initialized dd 0 fpu_owner dd ? uglobal diff --git a/umka.h b/umka.h index 60af83b..e56a155 100644 --- a/umka.h +++ b/umka.h @@ -3,7 +3,7 @@ UMKa - User-Mode KolibriOS developer tools - Copyright (C) 2017-2022 Ivan Baravy + Copyright (C) 2017-2023 Ivan Baravy Copyright (C) 2021 Magomed Kostoev */ @@ -28,6 +28,15 @@ typedef void siginfo_t; #define STDCALL __attribute__((__stdcall__)) +struct umka_ctx { + uint32_t tool; + uint32_t initialized; +}; + +#define UMKA_DEFAULT_DISPLAY_BPP 32 +#define UMKA_DEFAULT_DISPLAY_WIDTH 400 +#define UMKA_DEFAULT_DISPLAY_HEIGHT 300 + #define KEYBOARD_MODE_ASCII 0 #define KEYBOARD_MODE_SCANCODES 1 @@ -532,9 +541,12 @@ umka_osloop() { void irq0(int signo, siginfo_t *info, void *context); -void +struct umka_ctx * umka_init(int tool); +void +umka_close(struct umka_ctx *ctx); + void i40(void); @@ -1049,8 +1061,6 @@ _Static_assert(sizeof(appdata_t) == 256, "must be 0x100 bytes long"); extern appdata_t *kos_scheduler_current[NR_SCHED_QUEUES]; -extern uint32_t umka_tool; -extern uint32_t umka_initialized; extern uint8_t kos_redraw_background; extern size_t kos_task_count; extern wdata_t kos_window_data[]; diff --git a/umka_fuse.c b/umka_fuse.c index 02078b9..5005a95 100644 --- a/umka_fuse.c +++ b/umka_fuse.c @@ -4,7 +4,7 @@ UMKa - User-Mode KolibriOS developer tools umka_fuse - FUSE <-> KolibriOS FS calls converter - Copyright (C) 2017-2021 Ivan Baravy + Copyright (C) 2017-2023 Ivan Baravy */ #define FUSE_USE_VERSION 31 @@ -22,14 +22,32 @@ #include #include #include +#include "io.h" #include "vdisk.h" #include "umka.h" -#define UMKA_DEFAULT_DISPLAY_WIDTH 400 -#define UMKA_DEFAULT_DISPLAY_HEIGHT 300 - #define DIRENTS_TO_READ 100 +struct umka_fuse_ctx { + struct umka_ctx *umka; + struct umka_io *io; +}; + +static struct umka_fuse_ctx * +umka_fuse_init() { + struct umka_fuse_ctx *ctx = malloc(sizeof(struct umka_fuse_ctx)); + ctx->umka = NULL; + ctx->io = io_init(IO_DONT_CHANGE_TASK); + return ctx; +} + +static void +umka_fuse_close(struct umka_fuse_ctx *ctx) { + umka_close(ctx->umka); + io_close(ctx->io); + free(ctx); +} + static void bdfe_to_stat(bdfe_t *kf, struct stat *st) { // if (kf->attr & KF_FOLDER) { @@ -47,14 +65,19 @@ bdfe_to_stat(bdfe_t *kf, struct stat *st) { } static void * -umka_fuse_init(struct fuse_conn_info *conn, struct fuse_config *cfg) { +fs_init(struct fuse_conn_info *conn, struct fuse_config *cfg) { (void) conn; cfg->kernel_cache = 1; return NULL; } +static void +fs_destroy(void *private_data) { + struct umka_fuse_ctx *ctx = private_data; + umka_fuse_close(ctx); +} static int -umka_getattr(const char *path, struct stat *stbuf, struct fuse_file_info *fi) { +fs_getattr(const char *path, struct stat *stbuf, struct fuse_file_info *fi) { (void) fi; int res = 0; @@ -76,7 +99,7 @@ umka_getattr(const char *path, struct stat *stbuf, struct fuse_file_info *fi) { } static int -umka_readdir(const char *path, void *buf, fuse_fill_dir_t filler, off_t offset, +fs_readdir(const char *path, void *buf, fuse_fill_dir_t filler, off_t offset, struct fuse_file_info *fi, enum fuse_readdir_flags flags) { (void) offset; // TODO (void) fi; @@ -106,7 +129,7 @@ umka_readdir(const char *path, void *buf, fuse_fill_dir_t filler, off_t offset, } static int -umka_open(const char *path, struct fuse_file_info *fi) { +fs_open(const char *path, struct fuse_file_info *fi) { // if (strcmp(path+1, "blah") != 0) // return -ENOENT; (void) path; @@ -118,7 +141,7 @@ umka_open(const char *path, struct fuse_file_info *fi) { } static int -umka_read(const char *path, char *buf, size_t size, off_t offset, +fs_read(const char *path, char *buf, size_t size, off_t offset, struct fuse_file_info *fi) { (void) fi; @@ -130,29 +153,30 @@ umka_read(const char *path, char *buf, size_t size, off_t offset, } static struct fuse_operations umka_oper = { - .init = umka_fuse_init, - .getattr = umka_getattr, - .readdir = umka_readdir, - .open = umka_open, - .read = umka_read, + .init = fs_init, + .destroy = fs_destroy, + .getattr = fs_getattr, + .readdir = fs_readdir, + .open = fs_open, + .read = fs_read, }; int main(int argc, char *argv[]) { - umka_tool = UMKA_FUSE; if (argc != 3) { printf("usage: umka_fuse dir img\n"); exit(1); } - kos_boot.bpp = 32; + kos_boot.bpp = UMKA_DEFAULT_DISPLAY_BPP; kos_boot.x_res = UMKA_DEFAULT_DISPLAY_WIDTH; kos_boot.y_res = UMKA_DEFAULT_DISPLAY_HEIGHT; - kos_boot.pitch = UMKA_DEFAULT_DISPLAY_WIDTH*4; // 32bpp + kos_boot.pitch = UMKA_DEFAULT_DISPLAY_WIDTH * UMKA_DEFAULT_DISPLAY_BPP / 8; + + struct umka_fuse_ctx *ctx = umka_fuse_init(); - umka_init(UMKA_FUSE); struct vdisk *umka_disk = vdisk_init(argv[2], 1, 0u, 0); disk_t *disk = disk_add(&umka_disk->diskfunc, "hd0", umka_disk, 0); disk_media_changed(disk, 1); - return fuse_main(argc-1, argv, &umka_oper, NULL); + return fuse_main(argc-1, argv, &umka_oper, ctx); } diff --git a/umka_os.c b/umka_os.c index 5f6e090..62e4c6d 100644 --- a/umka_os.c +++ b/umka_os.c @@ -4,7 +4,7 @@ UMKa - User-Mode KolibriOS developer tools umka_os - kind of KolibriOS rump kernel - Copyright (C) 2018-2022 Ivan Baravy + Copyright (C) 2018-2023 Ivan Baravy */ #include @@ -30,14 +30,28 @@ #include "trace.h" #include "vnet.h" -#define HIST_FILE_BASENAME ".umka_shell.history" -#define UMKA_DEFAULT_DISPLAY_WIDTH 400 -#define UMKA_DEFAULT_DISPLAY_HEIGHT 300 +#define HIST_FILE_BASENAME ".umka_os.history" #define THREAD_STACK_SIZE 0x100000 +struct umka_os_ctx { + struct umka_ctx *umka; + struct umka_io *io; + struct shell_ctx *shell; +}; + char history_filename[PATH_MAX]; +struct umka_os_ctx * +umka_os_init() { + struct umka_os_ctx *ctx = malloc(sizeof(struct umka_os_ctx)); + ctx->umka = NULL; + ctx->io = io_init(IO_DONT_CHANGE_TASK); + ctx->shell = shell_init(SHELL_LOG_NONREPRODUCIBLE, history_filename, + ctx->io); + return ctx; +} + void build_history_filename() { const char *dir_name; if (!(dir_name = getenv("HOME"))) { @@ -137,12 +151,9 @@ main(int argc, char *argv[]) { trace_begin(); } - umka_tool = UMKA_OS; umka_sti(); const char *infile = NULL, *outfile = NULL; - struct shell_ctx ctx = {.reproducible = 0, .hist_file = history_filename, - .var = NULL}; build_history_filename(); struct optparse options; @@ -173,6 +184,8 @@ main(int argc, char *argv[]) { exit(1); } + struct umka_os_ctx *ctx = umka_os_init(); + struct sigaction sa; sa.sa_sigaction = irq0; sigemptyset(&sa.sa_mask); @@ -201,8 +214,8 @@ main(int argc, char *argv[]) { return 1; } - struct app_hdr *app = mmap(KOS_APP_BASE, 16*0x100000, PROT_READ | PROT_WRITE | - PROT_EXEC, MAP_FIXED | MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); + struct app_hdr *app = mmap(KOS_APP_BASE, 16*0x100000, PROT_READ | PROT_WRITE + | PROT_EXEC, MAP_FIXED | MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); if (app == MAP_FAILED) { perror("mmap failed"); exit(1); @@ -210,12 +223,12 @@ main(int argc, char *argv[]) { printf("pid=%d, kos_lfb_base=%p\n", getpid(), (void*)kos_lfb_base); - kos_boot.bpp = 32; + kos_boot.bpp = UMKA_DEFAULT_DISPLAY_BPP; kos_boot.x_res = UMKA_DEFAULT_DISPLAY_WIDTH; kos_boot.y_res = UMKA_DEFAULT_DISPLAY_HEIGHT; - kos_boot.pitch = UMKA_DEFAULT_DISPLAY_WIDTH*4; // 32bpp + kos_boot.pitch = UMKA_DEFAULT_DISPLAY_WIDTH * UMKA_DEFAULT_DISPLAY_BPP / 8; - run_test(&ctx); + run_test(ctx->shell); // umka_stack_init(); // load_app_host("../apps/board_cycle", app); diff --git a/umka_os.us b/umka_os.us index 23d7e11..0ed1c8e 100644 --- a/umka_os.us +++ b/umka_os.us @@ -1,3 +1,3 @@ -umka_init +umka_init umka_os ramdisk_init ../img/kolibri.raw disk_add ../img/xfs_samehash_s05k.raw hd0 -c 0 diff --git a/umka_shell.c b/umka_shell.c index bfd51cf..33a595f 100644 --- a/umka_shell.c +++ b/umka_shell.c @@ -4,7 +4,7 @@ UMKa - User-Mode KolibriOS developer tools umka_shell - the shell - Copyright (C) 2017-2022 Ivan Baravy + Copyright (C) 2017-2023 Ivan Baravy Copyright (C) 2021 Magomed Kostoev */ @@ -16,15 +16,29 @@ #include #include "optparse.h" #include "shell.h" +#include "io.h" #include "umka.h" #include "trace.h" #define HIST_FILE_BASENAME ".umka_shell.history" -#define UMKA_DEFAULT_DISPLAY_WIDTH 400 -#define UMKA_DEFAULT_DISPLAY_HEIGHT 300 + +struct umka_shell_ctx { + struct umka_ctx *umka; + struct umka_io *io; + struct shell_ctx *shell; +}; char history_filename[PATH_MAX]; +struct umka_shell_ctx * +umka_shell_init(int reproducible) { + struct umka_shell_ctx *ctx = malloc(sizeof(struct umka_shell_ctx)); + ctx->umka = NULL; + ctx->io = io_init(IO_DONT_CHANGE_TASK); + ctx->shell = shell_init(reproducible, history_filename, ctx->io); + return ctx; +} + void build_history_filename() { const char *dir_name; if (!(dir_name = getenv("HOME"))) { @@ -42,7 +56,6 @@ uint8_t mem2[256*1024*1024]; int main(int argc, char **argv) { (void)argc; - umka_tool = UMKA_SHELL; const char *usage = \ "usage: umka_shell [-i infile] [-o outfile] [-r] [-c] [-h]\n" " -i infile file with commands\n" @@ -50,8 +63,6 @@ main(int argc, char **argv) { " -r reproducible logs (without pointers and datetime)\n" " -c collect coverage\n"; const char *infile = NULL, *outfile = NULL; - struct shell_ctx ctx = {.reproducible = 0, .hist_file = history_filename, - .var = NULL}; build_history_filename(); /* kos_boot.memmap_block_cnt = 3; @@ -59,10 +70,12 @@ main(int argc, char **argv) { kos_boot.memmap_blocks[1] = (e820entry_t){(uintptr_t)mem1, 128*1024*1024, 1}; kos_boot.memmap_blocks[2] = (e820entry_t){(uintptr_t)mem2, 256*1024*1024, 1}; */ - kos_boot.bpp = 32; + kos_boot.bpp = UMKA_DEFAULT_DISPLAY_BPP; kos_boot.x_res = UMKA_DEFAULT_DISPLAY_WIDTH; kos_boot.y_res = UMKA_DEFAULT_DISPLAY_HEIGHT; - kos_boot.pitch = UMKA_DEFAULT_DISPLAY_WIDTH*4; // 32bpp + kos_boot.pitch = UMKA_DEFAULT_DISPLAY_WIDTH * UMKA_DEFAULT_DISPLAY_BPP / 8; + + int reproducible = 0; struct optparse options; int opt; @@ -77,7 +90,7 @@ main(int argc, char **argv) { outfile = options.optarg; break; case 'r': - ctx.reproducible = 1; + reproducible = 1; break; case 'c': coverage = 1; @@ -100,10 +113,12 @@ main(int argc, char **argv) { exit(1); } + struct umka_shell_ctx *ctx = umka_shell_init(reproducible); + if (coverage) trace_begin(); - run_test(&ctx); + run_test(ctx->shell); if (coverage) { trace_end(); diff --git a/vdisk.c b/vdisk.c index f5a475c..3084e63 100644 --- a/vdisk.c +++ b/vdisk.c @@ -42,7 +42,7 @@ vdisk_adjust_cache_size(void *userdata, size_t suggested_size) { struct vdisk* vdisk_init(const char *fname, int adjust_cache_size, size_t cache_size, - int change_task) { + void *io) { size_t fname_len = strlen(fname); size_t dot_raw_len = strlen(RAW_SUFFIX); size_t dot_qcow2_len = strlen(QCOW2_SUFFIX); @@ -63,6 +63,6 @@ vdisk_init(const char *fname, int adjust_cache_size, size_t cache_size, disk->diskfunc.adjust_cache_size = vdisk_adjust_cache_size; disk->adjust_cache_size = adjust_cache_size; disk->cache_size = cache_size; - disk->change_task = change_task; + disk->io = io; return disk; } diff --git a/vdisk.h b/vdisk.h index 93644b0..b2348a8 100644 --- a/vdisk.h +++ b/vdisk.h @@ -19,11 +19,11 @@ struct vdisk { uint64_t sect_cnt; unsigned cache_size; int adjust_cache_size; - int change_task; + void *io; }; struct vdisk* vdisk_init(const char *fname, int adjust_cache_size, size_t cache_size, - int change_task); + void *io); #endif // VDISK_H_INCLUDED diff --git a/vdisk/raw.c b/vdisk/raw.c index cb2c6a5..368f667 100644 --- a/vdisk/raw.c +++ b/vdisk/raw.c @@ -36,7 +36,7 @@ vdisk_raw_read(void *userdata, void *buffer, off_t startsector, struct vdisk_raw *disk = userdata; lseek(disk->fd, startsector * disk->vdisk.sect_size, SEEK_SET); io_read(disk->fd, buffer, *numsectors * disk->vdisk.sect_size, - disk->vdisk.change_task); + disk->vdisk.io); COVERAGE_ON(); return ERROR_SUCCESS; } @@ -48,7 +48,7 @@ vdisk_raw_write(void *userdata, void *buffer, off_t startsector, struct vdisk_raw *disk = userdata; lseek(disk->fd, startsector * disk->vdisk.sect_size, SEEK_SET); io_write(disk->fd, buffer, *numsectors * disk->vdisk.sect_size, - disk->vdisk.change_task); + disk->vdisk.io); COVERAGE_ON(); return ERROR_SUCCESS; }