umka/umka_shell.c

144 lines
3.6 KiB
C
Raw Normal View History

2020-01-27 23:54:57 +01:00
/*
2022-06-27 19:36:56 +02:00
SPDX-License-Identifier: GPL-2.0-or-later
2020-01-27 23:54:57 +01:00
2022-06-27 19:36:56 +02:00
UMKa - User-Mode KolibriOS developer tools
umka_shell - the shell
2020-01-27 23:54:57 +01:00
Copyright (C) 2017-2023 Ivan Baravy <dunkaist@gmail.com>
2022-06-27 19:36:56 +02:00
Copyright (C) 2021 Magomed Kostoev <mkostoevr@yandex.ru>
2020-01-27 23:54:57 +01:00
*/
#include <errno.h>
#include <fcntl.h>
2018-05-14 09:54:05 +02:00
#include <inttypes.h>
#include <limits.h>
#include <stdio.h>
#include <stdlib.h>
2017-11-02 21:41:11 +01:00
#include <string.h>
2022-06-13 23:46:48 +02:00
#include <unistd.h>
#include "shell.h"
#include "umkaio.h"
2019-10-09 01:35:47 +02:00
#include "trace.h"
#include "optparse/optparse.h"
2022-05-30 00:08:15 +02:00
#define HIST_FILE_BASENAME ".umka_shell.history"
struct umka_shell_ctx {
struct umka_ctx *umka;
struct umka_io *io;
struct shell_ctx *shell;
};
2022-05-30 00:08:15 +02:00
char history_filename[PATH_MAX];
struct umka_shell_ctx *
umka_shell_init(int reproducible, FILE *fin) {
struct umka_shell_ctx *ctx = malloc(sizeof(struct umka_shell_ctx));
ctx->umka = umka_init(UMKA_RUNNING_NEVER);
ctx->io = io_init(&ctx->umka->running);
ctx->shell = shell_init(reproducible, history_filename, ctx->umka, ctx->io,
fin);
return ctx;
}
void build_history_filename(void) {
2022-05-30 00:08:15 +02:00
const char *dir_name;
if (!(dir_name = getenv("HOME"))) {
dir_name = ".";
}
sprintf(history_filename, "%s/%s", dir_name, HIST_FILE_BASENAME);
}
/*
2022-05-30 19:47:49 +02:00
uint8_t mem0[64*1024*1024];
uint8_t mem1[128*1024*1024];
uint8_t mem2[256*1024*1024];
*/
2022-05-30 19:47:49 +02:00
int
main(int argc, char **argv) {
2022-05-29 17:17:00 +02:00
(void)argc;
const char *usage = \
2022-05-29 17:17:00 +02:00
"usage: umka_shell [-i infile] [-o outfile] [-r] [-c] [-h]\n"
" -i infile file with commands\n"
" -o outfile file for logs\n"
" -r reproducible logs (without pointers and datetime)\n"
2024-03-02 15:28:47 +01:00
" -c covfile collect coverage to the file\n";
char covfile[64];
2022-05-29 17:17:00 +02:00
const char *infile = NULL, *outfile = NULL;
FILE *fin = stdin;
FILE *fout = stdout;
2022-05-30 00:08:15 +02:00
build_history_filename();
/*
2022-05-30 19:47:49 +02:00
kos_boot.memmap_block_cnt = 3;
kos_boot.memmap_blocks[0] = (e820entry_t){(uintptr_t)mem0, 64*1024*1024, 1};
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};
*/
2024-03-02 15:28:47 +01:00
int coverage = 0;
int reproducible = 0;
2022-05-29 17:17:00 +02:00
struct optparse options;
optparse_init(&options, argv);
int opt;
2024-03-02 15:28:47 +01:00
while ((opt = optparse(&options, "i:o:rc:")) != -1) {
2022-05-29 17:17:00 +02:00
switch (opt) {
case 'i':
infile = options.optarg;
break;
case 'o':
outfile = options.optarg;
break;
case 'r':
reproducible = 1;
2022-05-29 17:17:00 +02:00
break;
case 'c':
coverage = 1;
2024-03-02 15:28:47 +01:00
sprintf(covfile, "%s.%i", options.optarg, getpid());
2022-05-29 17:17:00 +02:00
break;
case 'h':
fputs(usage, stderr);
exit(0);
default:
fprintf(stderr, "bad option: %c\n", opt);
fputs(usage, stderr);
exit(1);
}
}
if (infile) {
fin = fopen(infile, "r");
if (!fin) {
fprintf(stderr, "[!] can't open file for reading: %s\n", infile);
exit(1);
}
2022-05-29 17:17:00 +02:00
}
if (outfile) {
fout = freopen(outfile, "w", stdout);
if (!fout) {
fprintf(stderr, "[!] can't open file for writing: %s\n", outfile);
exit(1);
}
2022-05-29 17:17:00 +02:00
}
struct umka_shell_ctx *ctx = umka_shell_init(reproducible, fin);
if (coverage)
2024-03-02 15:28:47 +01:00
trace_enable();
run_test(ctx->shell);
2022-06-13 23:46:48 +02:00
if (coverage) {
2024-03-02 15:28:47 +01:00
trace_disable();
FILE *f = fopen(covfile, "w");
2022-06-13 23:46:48 +02:00
fwrite(coverage_table,
COVERAGE_TABLE_SIZE * sizeof(struct coverage_branch), 1, f);
fclose(f);
}
return 0;
}