diff --git a/Makefile b/Makefile index b5c1d8e..520bc0c 100644 --- a/Makefile +++ b/Makefile @@ -1,4 +1,4 @@ -SOURCES := src/main.c src/util/calloc.c src/util/string.c src/util/hash.c src/lexer/lexer.c src/builtins/builtins.c src/util/memset.c +SOURCES := src/main.c src/exec.c src/util/calloc.c src/util/string.c src/util/hash.c src/lexer/lexer.c src/builtins/builtins.c src/util/memset.c CFLAGS := -g -Oz -nostdlib LDFLAGS := diff --git a/src/exec.c b/src/exec.c new file mode 100644 index 0000000..b9a67b5 --- /dev/null +++ b/src/exec.c @@ -0,0 +1,122 @@ +#include "builtins/builtins.h" +#include "lexer/lexer.h" +#include "system/system.h" + +static int do_exec(msh_lexer *lexer, char *cmd, char **args, int *n, + int *exec_status) { + char full_path[4096]; + char is_first_arg = 0, exec_success = 0; + unsigned short i = 0, j = 0, counter = 0; + + args[*n] = 0; + + /* Do nothing on blank commands */ + if (*cmd == '\0') { + exec_success = 1; + } + /* Check if the command is a built-in */ + else if (msh_try_builtin(cmd, args)) { + exec_success = 1; + } + /* If the command is a folder, cd to it */ + else if (msh_path_is_directory(cmd)) { + msh_builtin_cd(cmd); + exec_success = 1; + } + /* If the command is a file, first try and execute it. */ + else if (msh_path_exists(cmd)) { + msh_system_execute(cmd, args); + exec_success = 1; + } else { + /* loop through all the path entries and check if the file exists in them. + */ + i = 0, *n = 0, j = 0; + while (j <= lexer->path_count) { + full_path[*n] = lexer->path[j]; + *n += 1; + if (lexer->path[j] == '\0') { + full_path[*n - 1] = msh_path_seperator; + for (i = 0; cmd[i] != 0; i++) { + full_path[i + *n] = cmd[i]; + } + *n += i; + full_path[*n] = '\0'; + *n += 1; + + if (msh_path_exists(full_path)) { + msh_system_execute(full_path, args); + exec_success = 1; + break; + } + + counter++; + if (counter > 2) { + break; + } + *n = 0; + } else { + counter = 0; + } + j++; + } + } + if (!exec_success) { + msh_print_strings("msh: ", cmd, ": command not found\n\r", 0); + } + /* flush out args */ + for (i = 0; i < 512; i++) { + if (args[i] == 0) { + break; + } + args[i] = 0; + } + + return 0; +} + +int msh_execute(msh_lexer *lexer) { + msh_lexer_item_list *list = lexer->item_list_head; + char *cmd = list->item->str; + SIZE_TYPE cmd_size; + int i = 0, n = 0, exec_status = 0; + SIZE_TYPE args_size = 0; + char *args[512]; + + while (list != 0) { + if (!list->item) { + break; + } + switch (list->item->type) { + case MSH_LEXER_ITEM_TYPE_UNKNOWN: + break; + case MSH_LEXER_ITEM_TYPE_WORD: + if (cmd == 0 && *list->item->str != '\0') { + cmd = list->item->str; + } else { + args[n++] = list->item->str; + } + break; + case MSH_LEXER_ITEM_TYPE_COMMENT: + break; + case MSH_LEXER_ITEM_TYPE_OP_OR: + break; + case MSH_LEXER_ITEM_TYPE_OP_AND: + do_exec(lexer, cmd, args, &n, &exec_status); + n = 0; + cmd = 0; + break; + case MSH_LEXER_ITEM_TYPE_OP_PIPE: + break; + case MSH_LEXER_ITEM_TYPE_OP_CONTROL: + break; + case MSH_LEXER_ITEM_TYPE_OP_SEMICOLON: + break; + } + list = list->next; + } + do_exec(lexer, cmd, args, &n, &exec_status); + + msh_lexer_flush(lexer); + + return 0; +}; diff --git a/src/lexer/lexer.c b/src/lexer/lexer.c index 4d38abb..ee42c4c 100644 --- a/src/lexer/lexer.c +++ b/src/lexer/lexer.c @@ -29,9 +29,7 @@ */ #include "lexer.h" -#include "../builtins/builtins.h" #include "../system/system.h" -#include msh_lexer msh_lexer_new() { msh_lexer l = {0}; @@ -148,125 +146,6 @@ lexer_cancel: return; } -static int do_exec(msh_lexer *lexer, char *cmd, char **args, int *n, - int *exec_status) { - char full_path[PATH_MAX]; - char is_first_arg = 0, exec_success = 0; - unsigned short i = 0, j = 0, counter = 0; - - args[*n] = 0; - - /* Do nothing on blank commands */ - if (*cmd == '\0') { - exec_success = 1; - } - /* Check if the command is a built-in */ - else if (msh_try_builtin(cmd, args)) { - exec_success = 1; - } - /* If the command is a folder, cd to it */ - else if (msh_path_is_directory(cmd)) { - msh_builtin_cd(cmd); - exec_success = 1; - } - /* If the command is a file, first try and execute it. */ - else if (msh_path_exists(cmd)) { - msh_execute(cmd, args); - exec_success = 1; - } else { - /* loop through all the path entries and check if the file exists in them. - */ - i = 0, *n = 0, j = 0; - while (j <= lexer->path_count) { - full_path[*n] = lexer->path[j]; - *n += 1; - if (lexer->path[j] == '\0') { - full_path[*n - 1] = msh_path_seperator; - for (i = 0; cmd[i] != 0; i++) { - full_path[i + *n] = cmd[i]; - } - *n += i; - full_path[*n] = '\0'; - *n += 1; - - if (msh_path_exists(full_path)) { - msh_execute(full_path, args); - exec_success = 1; - break; - } - - counter++; - if (counter > 2) { - break; - } - *n = 0; - } else { - counter = 0; - } - j++; - } - } - if (!exec_success) { - msh_print_strings("msh: ", cmd, ": command not found\n\r", 0); - } - /* flush out args */ - for (i = 0; i < 512; i++) { - if (args[i] == 0) { - break; - } - args[i] = 0; - } - - return 0; -} - -int msh_lexer_execute(msh_lexer *lexer) { - msh_lexer_item_list *list = lexer->item_list_head; - char *cmd = list->item->str; - SIZE_TYPE cmd_size; - int i = 0, n = 0, exec_status = 0; - SIZE_TYPE args_size = 0; - char *args[512]; - - while (list != 0) { - if (!list->item) { - break; - } - switch (list->item->type) { - case MSH_LEXER_ITEM_TYPE_UNKNOWN: - break; - case MSH_LEXER_ITEM_TYPE_WORD: - if (cmd == 0 && *list->item->str != '\0') { - cmd = list->item->str; - } else { - args[n++] = list->item->str; - } - break; - case MSH_LEXER_ITEM_TYPE_COMMENT: - break; - case MSH_LEXER_ITEM_TYPE_OP_OR: - break; - case MSH_LEXER_ITEM_TYPE_OP_AND: - do_exec(lexer, cmd, args, &n, &exec_status); - n = 0; - cmd = 0; - break; - case MSH_LEXER_ITEM_TYPE_OP_PIPE: - break; - case MSH_LEXER_ITEM_TYPE_OP_CONTROL: - break; - case MSH_LEXER_ITEM_TYPE_OP_SEMICOLON: - break; - } - list = list->next; - } - do_exec(lexer, cmd, args, &n, &exec_status); - - msh_lexer_flush(lexer); - - return 0; -}; - void msh_lexer_flush(msh_lexer *lexer) { msh_lexer_item_list *list = lexer->item_list_head; while (list->item != 0) { diff --git a/src/lexer/lexer.h b/src/lexer/lexer.h index d8f82eb..232028b 100644 --- a/src/lexer/lexer.h +++ b/src/lexer/lexer.h @@ -68,7 +68,7 @@ void msh_lexer_push_item(msh_lexer *lexer, msh_lexer_item_type type, char *buf, void msh_lexer_flush(msh_lexer *lexer); -int msh_lexer_execute(msh_lexer *lexer); +int msh_execute(msh_lexer *lexer); void msh_lexer_free(msh_lexer *lexer); diff --git a/src/main.c b/src/main.c index d39cda9..ee38242 100644 --- a/src/main.c +++ b/src/main.c @@ -86,7 +86,7 @@ static void loop_func(int action) { if (*ctx.buf != '\0') { int ret; msh_lexer_parse(&ctx.lexer, ctx.buf, ctx.sz + 1); - ret = msh_lexer_execute(&ctx.lexer); + ret = msh_execute(&ctx.lexer); itoa(ret, ctx.result_str, 10); } diff --git a/src/system/linux/linux.c b/src/system/linux/linux.c index 99107af..9528f99 100644 --- a/src/system/linux/linux.c +++ b/src/system/linux/linux.c @@ -173,7 +173,7 @@ void msh_move_cursor(signed int offset) { void msh_write(char *st, SIZE_TYPE size) { SYSCALL(write, 1, st, size); } -int msh_execute(char *cmd, char **args) { +int msh_system_execute(char *cmd, char **args) { SIZE_TYPE fork; if (*cmd == '\0') { diff --git a/src/system/system.h b/src/system/system.h index 2908e4c..24f188a 100644 --- a/src/system/system.h +++ b/src/system/system.h @@ -145,7 +145,7 @@ typedef struct msh_process_t { * Non-zero return values are the exit status. -1 implies the command was not * found. */ -int msh_execute(char *cmd, char **args); +int msh_system_execute(char *cmd, char **args); /* Get an environment variable with the given key.