diff --git a/3-ShellPart1/dsh_cli.c b/3-ShellPart1/dsh_cli.c new file mode 100644 index 0000000000000000000000000000000000000000..0e5d710c8ee75e7e3caf2877d19ff0ea184c688d --- /dev/null +++ b/3-ShellPart1/dsh_cli.c @@ -0,0 +1,168 @@ +#include <stdio.h> +#include <stdlib.h> +#include <string.h> + +#include "dshlib.h" + +/* + * Implement your main function by building a loop that prompts the + * user for input. Use the SH_PROMPT constant from dshlib.h and then + * use fgets to accept user input. Since we want fgets to also handle + * end of file so we can run this headless for testing we need to check + * the return code of fgets. I have provided an example below of how + * to do this assuming you are storing user input inside of the cmd_buff + * variable. + * + * while(1){ + * printf("%s", SH_PROMPT); + * if (fgets(cmd_buff, ARG_MAX, stdin) == NULL){ + * printf("\n"); + * break; + * } + * //remove the trailing \n from cmd_buff + * cmd_buff[strcspn(cmd_buff,"\n")] = '\0'; + * + * //IMPLEMENT THE REST OF THE REQUIREMENTS + * } + * + * Also, use the constants in the dshlib.h in this code. + * SH_CMD_MAX maximum buffer size for user input + * EXIT_CMD constant that terminates the dsh program + * SH_PROMPT the shell prompt + * OK the command was parsed properly + * WARN_NO_CMDS the user command was empty + * ERR_TOO_MANY_COMMANDS too many pipes used + * + * Expected output: + * + * CMD_OK_HEADER if the command parses properly. You will + * follow this by the command details + * + * CMD_WARN_NO_CMD if the user entered a blank command + * CMD_ERR_PIPE_LIMIT if the user entered too many commands using + * the pipe feature, e.g., cmd1 | cmd2 | ... | + * + * See the provided test cases for output expectations. + */ + + +// ASCII art for the dragon command (extra credit) +static const char* DRAGON_ASCII = "\ + @%%%% \n\ + %%%%%% \n\ + %%%%%% \n\ + % %%%%%%% @ \n\ + %%%%%%%%%% %%%%%%% \n\ + %%%%%%% %%%%@ %%%%%%%%%%%%@ %%%%%% @%%%% \n\ + %%%%%%%%%%%%%%%%%%%%%% %%%%%%%%%%%%%%%%%%%%%%%%%%%% \n\ + %%%%%%%%%%%%%%%%%%%%%%%%%% %%%%%%%%%%%% %%%%%%%%%%%%%%% \n\ + %%%%%%%%%%%%%%%%%%%%%%%%%%%%% %%%%%%%%%%%%%%%%%%% %%% \n\ + %%%%%%%%%%%%%%%%%%%%%%%%%%%%@ @%%%%%%%%%%%%%%%%%% %% \n\ + %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% %%%%%%%%%%%%%%%%%%%%%% \n\ + %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \n\ + %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%@%%%%%%@ \n\ + %%%%%%%%@ %%%%%%%%%%%%%%%% %%%%%%%%%%%%%%%%%%%%%%%%%% %% \n\ + %%%%%%%%%%%%% %%@%%%%%%%%%%%% %%%%%%%%%%% %%%%%%%%%%%% @% \n\ + %%%%%%%%%% %%% %%%%%%%%%%%%%% %%%%%%%%%%%%%%%%%%%%%%%% \n\ + %%%%%%%%% % %%%%%%%%%%%%% %%%%%%%%%%%%@%%%%%%%%%%% \n\ +%%%%%%%%%@ % %%%%%%%%%%%%% @%%%%%%%%%%%%%%%%%%%%%%%%% \n\ +%%%%%%%%@ %%@%%%%%%%%%%%% @%%%%%%%%%%%%%%%%%%%%%%%%%%%% \n\ +%%%%%%%@ %%%%%%%%%%%%%%% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \n\ +%%%%%%%%%% %%%%%%%%%%%%%%% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% %%%% \n\ +%%%%%%%%%@ @%%%%%%%%%%%%%% %%%%%%%%%%%%@ %%%% %%%%%%%%%%%%%%%%% %%%%%%%%\n\ +%%%%%%%%%% %%%%%%%%%%%%%%%%% %%%%%%%%%%%%% %%%%%%%%%%%%%%%%%% %%%%%%%%%\n\ +%%%%%%%%%@%%@ %%%%%%%%%%%%%%%%@ %%%%%%%%%%%%%% %%%%%%%%%%%%%%%%%%%%%%%% %%\n\ + %%%%%%%%%% % %%%%%%%%%%%%%%@ %%%%%%%%%%%%%% %%%%%%%%%%%%%%%%%%%%%%%%%% %%\n\ + %%%%%%%%%%%% @ %%%%%%%%%%%%%%%%%% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% %%% \n\ + %%%%%%%%%%%%% %% % %@ %%%%%%%%%%%%%%%%%% %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% %%% \n\ + %%%%%%%%%%%%%%%%%% %%%%%%%%%%%%%%%%%%%%%% @%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% %%%%%%% \n\ + %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% %%%%%%%%%%%%%%%%%%%%%%%%%%%% %%% \n\ + @%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% %%%%%%%%%%%%%%%%%%%%%%%%% \n\ + %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% %%%%%%%%%%%%%%%%%%% %%%%%%% \n\ + %%%%%%%%%%%%%%%%%%%%%%%%%% %%%%%%%%%%%%%%% @%%%%%%%%% \n\ + %%%%%%%%%%%%%%%%%%%% @%@% @%%%%%%%%%%%%%%%%%% %%% \n\ + %%%%%%%%%%%%%%% %%%%%%%%%% %%%%%%%%%%%%%%% % \n\ + %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% %%%%%%%%%%%%%% \n\ + %%%%%%%%%%%%%%%%%%%%%%%%%% %%%% %%% %%%%%%%%%% %%%@ \n\ + %%%%%%%%%%%%%%%%%%% %%%%%% %% %%%%%%%%%%%%%@ \n\ + %%%%%%%@ \n"; + +// Helper function to print command list +static void print_command_list(command_list_t *clist) { + printf(CMD_OK_HEADER, clist->num); + for (int i = 0; i < clist->num; i++) { + printf("<%d> %s", i + 1, clist->commands[i].exe); + if (strlen(clist->commands[i].args) > 0) { + printf(" [%s]", clist->commands[i].args); + } + printf("\n"); + } +} + +#include <stdio.h> +#include <stdlib.h> +#include <string.h> + +int main() { + // Allocate memory for storing user input commands + char *cmd_buff = malloc(SH_CMD_MAX * sizeof(char)); + command_list_t clist; // Structure to hold parsed commands + + // Check if memory allocation was successful + if (!cmd_buff) { + fprintf(stderr, "Error: Unable to allocate memory for command buffer\n"); + return EXIT_FAILURE; + } + + while (1) { + printf("%s", SH_PROMPT); // Display shell prompt + + // Read input from the user + if (fgets(cmd_buff, ARG_MAX, stdin) == NULL) { + printf("\n"); // Handle EOF or input error gracefully + break; + } + + // Remove trailing newline character from input + cmd_buff[strcspn(cmd_buff, "\n")] = '\0'; + + // Check if user wants to exit the shell + if (strcmp(cmd_buff, EXIT_CMD) == 0) { + free(cmd_buff); // Free allocated memory before exiting + return EXIT_SUCCESS; + } + + // Easter egg: Display ASCII art if the user types "dragon" + if (strcmp(cmd_buff, "dragon") == 0) { + printf("%s", DRAGON_ASCII); + continue; // Skip further command processing + } + + // Parse the input and build a command list + int rc = build_cmd_list(cmd_buff, &clist); + + // Process the parsed command based on the return status + switch (rc) { + case OK: + print_command_list(&clist); // Print parsed commands + break; + case WARN_NO_CMDS: + printf(CMD_WARN_NO_CMD); // Warning if no valid commands were found + break; + case ERR_TOO_MANY_COMMANDS: + printf(CMD_ERR_PIPE_LIMIT, CMD_MAX); // Error if too many commands are entered + break; + default: + fprintf(stderr, "Error: Command processing failed\n"); // Handle unknown errors + break; + } + } + + free(cmd_buff); // Ensure memory is freed before program termination + return EXIT_FAILURE; +} + + + free(cmd_buff); + return EXIT_SUCCESS; +} \ No newline at end of file