/* ************************************************************************** */ /* */ /* ::: :::::::: */ /* main.c :+: :+: :+: */ /* +:+ +:+ +:+ */ /* By: lperrey +#+ +:+ +#+ */ /* +#+#+#+#+#+ +#+ */ /* Created: 2021/10/04 05:59:26 by lperrey #+# #+# */ /* Updated: 2021/10/19 21:16:21 by hulamy ### ########.fr */ /* */ /* ************************************************************************** */ #include "minishell.h" void print_tab(char **array); typedef struct s_pipe { int nb_pipes; int **pipes_fd; char **input_split; } t_pipe; typedef struct s_cmd { char **argv; // t_pid pid; int pid; void *builtin; int fd_in; int fd_out; } t_cmd; int count_pipes(char *input) { int i; int nb; i = -1; nb = 0; while (input[++i]) if (input[i] == '|') nb++; return (nb); } int **create_pipes(int nb) { int **pipes_fd; int i; if (!nb) return (NULL); pipes_fd = calloc(nb, sizeof(int *)); i = 0; while(i < nb) { pipes_fd[i] = calloc(2, sizeof(int)); pipe(pipes_fd[i]); //printf("%i - %i\n", pipes_fd[i][0],pipes_fd[i][1]); i++; } return (pipes_fd); } char **split_pipes(char *input) { char **split; int i; split = ft_split(input, '|'); i = -1; while (split[++i]) split[i] = ft_strtrim(split[i], " "); // print_tab(split); return (split); } t_pipe *fill_pipes(char *input) { t_pipe *pipes; pipes = calloc(1, sizeof(t_pipe)); pipes->nb_pipes = count_pipes(input); pipes->pipes_fd = create_pipes(pipes->nb_pipes); pipes->input_split = split_pipes(input); return (pipes); } int redirection(char **input) { int i; i = 0; while ((*input)[i] != '\0' && (*input)[i] != '>') i++; if ((*input)[i] == '>') { *input = ft_substr(*input, 0, i); return (open("file.txt", O_WRONLY | O_TRUNC)); } return (0); } // pipe[0] read end // pipe[1] write end void execute_cmd(t_all *c, t_pipe *pipes) { pid_t pid; pid_t wpid; int status; int i; status = 0; i = 0; while (i <= pipes->nb_pipes) { pid = fork(); if (pid == 0) // child { if (pipes->nb_pipes) { if (i == 0) dup2(pipes->pipes_fd[0][1], STDOUT_FILENO); if (i == 1) dup2(pipes->pipes_fd[0][0], STDIN_FILENO); close(pipes->pipes_fd[0][0]); close(pipes->pipes_fd[0][1]); } if (!ft_strncmp(pipes->input_split[i], "sleep ", 6)) execve("/bin/sleep", ft_split(pipes->input_split[i], ' '), c->envp); if (!ft_strncmp(pipes->input_split[i], "ls ", 3)) execve("/bin/ls", ft_split(pipes->input_split[i], ' '), c->envp); if (!ft_strncmp(pipes->input_split[i], "cat ", 4)) execve("/bin/cat", ft_split(pipes->input_split[i], ' '), c->envp); if (!ft_strncmp(pipes->input_split[i], "wc ", 3)) execve("/usr/bin/wc", ft_split(pipes->input_split[i], ' '), c->envp); if (!ft_strncmp(pipes->input_split[i], "sort ", 5)) execve("/usr/bin/sort", ft_split(pipes->input_split[i], ' '), c->envp); } if (pid > 0) // parent { if (pipes->nb_pipes) { close(pipes->pipes_fd[0][0]); close(pipes->pipes_fd[0][1]); } } i++; } while ((wpid = wait(&status)) > 0); } void **cmd_path(char **argv, char **envp) { int i; char **path; char *cmd; i = 0; while (envp[i] && ft_strncmp(envp[i], "PATH=", 5)) i++; path = ft_split(envp[i] + 5, ':'); // 5 = lentgh of "PATH=" i = -1; while (*path && i != 0) { cmd = ft_strjoin(path[0], "/"); cmd = ft_strjoin(cmd, argv[0]); i = access(cmd, X_OK); path++; } argv[0] = cmd; return (NULL); } int handle_fd(char **input, int i, int fdin, int *fd_in, int *fd_out) { int *pipes_fd; int next_in; char *tmp; //printf("cmd:%i", i); *fd_in = fdin; *fd_out = 1; next_in = 0; if (input[i + 1]) { pipes_fd = calloc(2, sizeof(int)); pipe(pipes_fd); *fd_out = pipes_fd[1]; next_in = pipes_fd[0]; //printf(" - pipes:[%i][%i]", pipes_fd[0], pipes_fd[1]); } tmp = ft_strchr(input[i], '>'); if (tmp) { tmp[0] = '\0'; tmp = ft_strtrim(tmp + 2, " "); // +2 for "> " *fd_out = open(tmp, O_WRONLY | O_TRUNC); next_in = *fd_out; //printf(" - file:[%i]", *fd_out); } //printf(" - final_fd:[%i][%i]\n", *fd_in, *fd_out); return (next_in); } //t_list *parser(char *input) void parser(char *input, char **envp) { t_list *cmd; t_cmd *element; char **input_split; int i; int tmp_fd; input_split = ft_split(input, '|'); tmp_fd = 0; i = 0; while (input_split[i]) { element = calloc(1, sizeof(t_cmd)); tmp_fd = handle_fd(input_split, i, tmp_fd, &(element->fd_in), &(element->fd_out)); element->argv = ft_split(input_split[i], ' '); element->builtin = cmd_path(element->argv, envp); cmd = ft_lstnew(element); i++; } } void shell_loop(t_all *c) { char *line_input; // t_list *cmd; // t_pipe *pipes; // int nb_pipes; // int **pipes_fd; // char **split; line_input = NULL; while (1) { if (line_input) free(line_input); line_input = readline(c->prompt); if (line_input && *line_input) { // cmd = parser(line_input); parser(line_input, c->envp); // exec_cmd(c, cmd); // pipes = fill_pipes(line_input); // execute_cmd(c, pipes); // if (!ft_strncmp(line_input, "env", 4)) // temp placeholder // builtin_env(0, NULL, c); // else if (!ft_strncmp(line_input, "exit", 5)) // temp placeholder // builtin_exit(0, NULL, c); // else if (!ft_strncmp(line_input, "pipe ", 5)) // temp temp temp // else if (!ft_strncmp(line_input, "pipe ", 5)) // temp temp temp // pipes_hugo(line_input, c); // else // printf("echo: %s\n", line_input); } } } void wip_test() { char term_desc[2048]; char *term_type; int term_width; int term_height; int ret; term_type = getenv("TERM"); if (term_type == 0) ft_putstr_fd("Specify a terminal type with `setenv TERM '.\n", 2); ret = tgetent(term_desc, term_type); if (ret < 0) ft_putstr_fd("Could not access the termcap data base.\n", 2); if (ret == 0) ft_putstr_fd("Terminal type `%s' is not defined.\n", 2); term_height = tgetnum ("li"); term_width = tgetnum ("co"); /* Extract information that termcap functions use. */ /* temp = tgetstr ("pc", BUFFADDR); PC = temp ? *temp : 0; BC = tgetstr ("le", BUFFADDR); UP = tgetstr ("up", BUFFADDR); */ } int main(int argc, char *argv[], char *envp[]) { t_all c; (void)argc; (void)argv; if (!init(&c, envp)) exit(EXIT_FAILURE); shell_loop(&c); return (0); }