From 3f79b7bd553a52fca7a098f5195b406ff9970491 Mon Sep 17 00:00:00 2001 From: Nathan Reiner Date: Sun, 15 Jan 2023 01:13:51 +0100 Subject: add list and static library builder --- lib/arg/Makefile | 3 ++ lib/arg/arg.c | 85 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++ lib/arg/arg.h | 9 ++++++ 3 files changed, 97 insertions(+) create mode 100644 lib/arg/Makefile create mode 100644 lib/arg/arg.c create mode 100644 lib/arg/arg.h (limited to 'lib/arg') diff --git a/lib/arg/Makefile b/lib/arg/Makefile new file mode 100644 index 0000000..384f797 --- /dev/null +++ b/lib/arg/Makefile @@ -0,0 +1,3 @@ +unit_test: + gcc test.c arg.c ../io/io.c ../aec/aec.c ../malloc/malloc.c ../avl_tree/avl_tree.c ../cstr/cstr.c ../env/env.c ../sys/start.S -o test -static -nostdlib -fno-stack-protector -Wno-implicit-function-declaration -g + ./test diff --git a/lib/arg/arg.c b/lib/arg/arg.c new file mode 100644 index 0000000..271b535 --- /dev/null +++ b/lib/arg/arg.c @@ -0,0 +1,85 @@ +#include "arg.h" + +#include "../sys/sizes.h" +#include "../cstr/cstr.h" + +#include "../avl_tree/avl_tree.h" +#include "../malloc/malloc.h" +#include "../sys/exit.h" +#include "../io/io.h" +#include "../aec/aec.h" + +typedef struct { + const char *name; + union { + void (*flag_func)(); + void (*arg_func)(const char *); + }; +} arg_func_t; + +avl_tree_t *flags = 0; +avl_tree_t *args = 0; +void (*default_arg)(const char *) = 0; + + +i8 __arg_func_compare(void *a, void *b) { + return cstr_compare(((arg_func_t *)a)->name, ((arg_func_t *)b)->name); +} + + +void arg_parse_arg(int argc, const char **argv) +{ + arg_func_t *func; + arg_func_t q; + for (int i = 1; i < argc; ++i) { + q.name = argv[i]; + if (args && + i < argc - 1 && + argv[i + 1][0] != '-' && + (func = avl_tree_search(args, &q)) != 0) { + func->arg_func(argv[i + 1]); + ++i; + } else if (flags && (func = avl_tree_search(flags, &q)) != 0) { + func->flag_func(); + + } else if (argv[i][0] != '-' && default_arg) { + default_arg(argv[i]); + + } else { + wstdf("%S%Ferror:%S unknown flag '%s'\n", SGR_BOLD, COLOR_RED, SGR_RESET, argv[i]); + exit(-1); + } + } +} + + +void arg_register_arg(const char *flag, void(*func)(const char *)) +{ + if (!args) { + args = new_avl_tree(&__arg_func_compare, 1); + } + + arg_func_t *f = malloc(sizeof(arg_func_t)); + f->name = flag; + f->arg_func = func; + avl_tree_insert(args, f); +} + + +void arg_register_flag(const char *flag, void(*func)(const char *)) +{ + if (!flags) { + flags = new_avl_tree(&__arg_func_compare, 1); + } + + arg_func_t *f = malloc(sizeof(arg_func_t)); + f->name = flag; + f->flag_func = func; + avl_tree_insert(flags, f); +} + + +void arg_register_default(void (*func)(const char *)) +{ + default_arg = func; +} diff --git a/lib/arg/arg.h b/lib/arg/arg.h new file mode 100644 index 0000000..5bffb33 --- /dev/null +++ b/lib/arg/arg.h @@ -0,0 +1,9 @@ +#ifndef ARG_H +#define ARG_H + +void arg_parse_arg(int argc, const char **argv); +void arg_register_flag(const char *flag, void(*func)()); +void arg_register_arg(const char *flag, void(*func)(const char *)); +void arg_register_default(void (*func)(const char *)); + +#endif -- cgit v1.2.3-70-g09d2