diff --git a/caller.c b/caller.c index ecf9841..7a77074 100755 --- a/caller.c +++ b/caller.c @@ -12,6 +12,23 @@ #include "minishell.h" +static void exe(t_datas *datas, t_command *cmd); +static pid_t caller(t_datas *datas, t_command *cmd); + +int is_builtin(char *cmd) +{ + if (!ft_strncmp(cmd, "echo", 5) || + !ft_strncmp(cmd, "pwd", 4) || + !ft_strncmp(cmd, "cd", 3) || + !ft_strncmp(cmd, "export", 7) || + !ft_strncmp(cmd, "unset", 6) || + !ft_strncmp(cmd, "env", 4) || + !ft_strncmp(cmd, "exit", 5)) + return (1); + else + return (0); +} + int builtin_call(t_datas *datas, t_command *cmd) { if (ft_strncmp(cmd->argv[0], "echo", 5) == 0) @@ -32,21 +49,32 @@ int builtin_call(t_datas *datas, t_command *cmd) return (-1); } -int is_builtin(char *cmd) +int piper(t_datas *datas, t_command *cmd) { - if (!ft_strncmp(cmd, "echo", 5) || - !ft_strncmp(cmd, "pwd", 4) || - !ft_strncmp(cmd, "cd", 3) || - !ft_strncmp(cmd, "export", 7) || - !ft_strncmp(cmd, "unset", 6) || - !ft_strncmp(cmd, "env", 4) || - !ft_strncmp(cmd, "exit", 5)) - return (1); - else - return (0); + int pip[2]; + int status; + pid_t pid; + + if (cmd->fd[1] == 0 && cmd->next && cmd->next->fd[0] == 0) + { + pipe(pip); + cmd->fd[1] = pip[1]; + cmd->next->fd[0] = pip[0]; + } + pid = caller(datas, cmd); + if (cmd->fd[1]) + close(cmd->fd[1]); + if (cmd->next) + piper(datas, cmd->next); + waitpid(pid, &status, 0); + if (!cmd->next) + handle_status(datas, status); + if (cmd->fd[0]) + close(cmd->fd[0]); + return (1); } -void exe(t_datas *datas, t_command *cmd) +static void exe(t_datas *datas, t_command *cmd) { char **path_dirs; char *path; @@ -71,7 +99,7 @@ void exe(t_datas *datas, t_command *cmd) } } -pid_t caller(t_datas *datas, t_command *cmd) +static pid_t caller(t_datas *datas, t_command *cmd) { pid_t pid; @@ -90,28 +118,3 @@ pid_t caller(t_datas *datas, t_command *cmd) } return pid; } - -int piper(t_datas *datas, t_command *cmd) -{ - int pip[2]; - int status; - pid_t pid; - - if (cmd->fd[1] == 0 && cmd->next && cmd->next->fd[0] == 0) - { - pipe(pip); - cmd->fd[1] = pip[1]; - cmd->next->fd[0] = pip[0]; - } - pid = caller(datas, cmd); - if (cmd->fd[1]) - close(cmd->fd[1]); - if (cmd->next) - piper(datas, cmd->next); - waitpid(pid, &status, 0); - if (!cmd->next) - handle_status(datas, status); - if (cmd->fd[0]) - close(cmd->fd[0]); - return (1); -} diff --git a/env.c b/env.c index 3ebeecb..40e150e 100755 --- a/env.c +++ b/env.c @@ -12,42 +12,7 @@ #include "minishell.h" -int is_valid_identifier(char *ident) -{ - if (ft_isalpha(ident[0]) || ident[0] == '_') - { - while (*ident) - { - if (!ft_isalpha(*ident) && !ft_isdigit(*ident) && *ident != '_') - return (0); - ident++; - } - return (1); - } - return (0); -} -void clean_env(t_datas *datas) -{ - int i; - int j; - - i = 0; - j = 0; - while (i < 1024) - { - if (!datas->envp[i]) - { - j = 1; - while (!datas->envp[i + j] && (i + j) < 1024) - j++; - if (i + j == 1024) - return ; - datas->envp[i] = datas->envp[i + j]; - datas->envp[i + j] = NULL; - } - i++; - } -} +static void clean_env(t_datas *datas); int ft_unset(t_datas *datas, t_command *cmd) { char **env; @@ -100,6 +65,7 @@ int ft_env(t_datas *datas, t_command *cmd) return (0); } +static int is_valid_identifier(char *ident); int ft_export(t_datas *datas, t_command *cmd) { char **new; @@ -133,3 +99,41 @@ int ft_export(t_datas *datas, t_command *cmd) datas->envp[i] = ft_strdup(cmd->argv[1]); return (1); } + +static void clean_env(t_datas *datas) +{ + int i; + int j; + + i = 0; + j = 0; + while (i < ENVP_MAX_SIZE) + { + if (!datas->envp[i]) + { + j = 1; + while (!datas->envp[i + j] && (i + j) < ENVP_MAX_SIZE) + j++; + if (i + j == ENVP_MAX_SIZE) + return ; + datas->envp[i] = datas->envp[i + j]; + datas->envp[i + j] = NULL; + } + i++; + } +} + +static int is_valid_identifier(char *ident) +{ + if (ft_isalpha(ident[0]) || ident[0] == '_') + { + while (*ident) + { + if (!ft_isalpha(*ident) && !ft_isdigit(*ident) && *ident != '_') + return (0); + ident++; + } + return (1); + } + return (0); +} diff --git a/lexer.c b/lexer.c index 93be36a..c4bd30a 100755 --- a/lexer.c +++ b/lexer.c @@ -12,7 +12,68 @@ #include "minishell.h" -int create_token(t_lexer *lex, char str[]) +static int check_state(t_lexer *lex, char **line); +static int create_token(t_lexer *lex, char str[]); +static int check_register(t_lexer *lex, char **line, char *tmp); + +t_token *lexer(t_datas *datas, char *line) +{ + t_lexer *lex; + t_token *ret; + char *tmp; + int tmp_i; + + lex = ft_calloc(1, sizeof *lex); + lex->state = ROOT_ST; + tmp = ft_calloc(STR_MAX_SIZE, sizeof *tmp); + tmp_i = 0; + while (*line) + { + if (check_state(lex, &line)) + continue; + if (lex->state != S_QUOTE_ST && *line == '$') + tmp_i = replace_var(datas, &line, tmp, tmp_i); + else if (check_register(lex, &line, tmp)) + tmp_i = (ft_bzero(tmp, STR_MAX_SIZE), 0); + else + tmp[tmp_i++] = *(line++); + } + create_token(lex, tmp); + free(tmp); + ret = lex->tokens; + free(lex); + return (ret); +} + +static int check_state(t_lexer *lex, char **line) +{ + t_state new; + + new = OLD_ST; + if (**line == '"') + { + if (lex->state == D_QUOTE_ST) + new = ROOT_ST; + else if (lex->state == ROOT_ST) + new = D_QUOTE_ST; + } + else if (**line == '\'') + { + if (lex->state == S_QUOTE_ST) + new = ROOT_ST; + else if (lex->state == ROOT_ST) + new = S_QUOTE_ST; + } + if (new) + { + (*line)++; + lex->state = new; + return (1); + } + return (0); +} + +static int create_token(t_lexer *lex, char str[]) { t_token *tok; t_token *tmp; @@ -39,28 +100,9 @@ int create_token(t_lexer *lex, char str[]) return (1); } -int set_redir(t_lexer *lex, char **line, char ch) -{ - static t_type type_out[2] = {OUT, ADD}; - static t_type type_in[2] = {IN, HD}; - t_type *type; - - if (ch == '>') - type = type_out; - else - type = type_in; - if (**line == ch && (*line)++) - { - if (**line == ch && (*line)++) - lex->next_type = type[1]; - else - lex->next_type = type[0]; - return (1); - } - return (0); -} +static int set_redir(t_lexer *lex, char **line, char ch); -int check_register(t_lexer *lex, char **line, char *tmp) +static int check_register(t_lexer *lex, char **line, char *tmp) { int spaces; @@ -88,59 +130,23 @@ int check_register(t_lexer *lex, char **line, char *tmp) return (create_token(lex, tmp)); } -int check_state(t_lexer *lex, char **line) +static int set_redir(t_lexer *lex, char **line, char ch) { - t_state new; - - new = OLD_ST; - if (**line == '"') - { - if (lex->state == D_QUOTE_ST) - new = ROOT_ST; - else if (lex->state == ROOT_ST) - new = D_QUOTE_ST; - } - else if (**line == '\'') - { - if (lex->state == S_QUOTE_ST) - new = ROOT_ST; - else if (lex->state == ROOT_ST) - new = S_QUOTE_ST; - } - if (new) - { - (*line)++; - lex->state = new; - return (1); - } - return (0); -} - -t_token *lexer(t_datas *datas, char *line) -{ - t_lexer *lex; - t_token *ret; - char *tmp; - int tmp_i; + static t_type type_out[2] = {OUT, ADD}; + static t_type type_in[2] = {IN, HD}; + t_type *type; - lex = ft_calloc(1, sizeof *lex); - lex->state = ROOT_ST; - tmp = ft_calloc(1024, sizeof *tmp); - tmp_i = 0; - while (*line) + if (ch == '>') + type = type_out; + else + type = type_in; + if (**line == ch && (*line)++) { - if (check_state(lex, &line)) - continue; - if (lex->state != S_QUOTE_ST && *line == '$') - tmp_i = replace_var(datas, &line, tmp, tmp_i); - else if (check_register(lex, &line, tmp)) - tmp_i = (ft_bzero(tmp, 1024), 0); + if (**line == ch && (*line)++) + lex->next_type = type[1]; else - tmp[tmp_i++] = *(line++); + lex->next_type = type[0]; + return (1); } - create_token(lex, tmp); - free(tmp); - ret = lex->tokens; - free(lex); - return (ret); + return (0); } diff --git a/minishell.c b/minishell.c index b16cf5d..6d86adc 100755 --- a/minishell.c +++ b/minishell.c @@ -18,8 +18,7 @@ void termios(int ctl) int tty; tty = ttyslot(); - if (tcgetattr(tty, &termios_p) < 0) - exit ((perror("stdin"), EXIT_FAILURE)); + tcgetattr(tty, &termios_p); if (ctl) { termios_p.c_lflag |= ECHOCTL; @@ -62,7 +61,7 @@ void prompt(t_datas *datas) line = readline("$ "); termios(1); if (line == NULL) - halt(datas, EXIT_FAILURE); + halt(datas, EXIT_SUCCESS); if (is_empty(line)) return ; cmd = parser(datas, lexer(datas, line), NULL); @@ -76,11 +75,10 @@ void prompt(t_datas *datas) int main(int argc, char **argv, char **envp) { - t_datas datas; - int i; + static t_datas datas; + static int i = 0; - i = 0; - datas.envp = ft_calloc(ENVP_LIMIT, sizeof(char *)); + datas.envp = ft_calloc(ENVP_MAX_SIZE, sizeof(char *)); while (*envp) datas.envp[i++] = ft_strdup(*(envp++)); datas.exit_code = 0; diff --git a/minishell.h b/minishell.h index 69fbd94..9cbe68c 100755 --- a/minishell.h +++ b/minishell.h @@ -12,11 +12,9 @@ #ifndef MINISHELL_H # define MINISHELL_H -# define ENVP_LIMIT 1024 -# define PIPE_MAX_SIZE 8192 +# define ENVP_MAX_SIZE 1024 +# define STR_MAX_SIZE 1024 # define PATHS_MAX_SIZE 126 -# define PROMPT_PREFIX 0 -# define DEBUG 0 # include "libft/libft.h" # include @@ -55,10 +53,9 @@ void sigs_handler(int sig_num); void halt(t_datas *datas, int ret_code); // ----------------------------------Utils_2.c -int replace_var(t_datas *datas, char **line, \ - char *tmp, int tmp_i); int file_error(char *cmd, char *file, char *msg); -char *expend_str(t_datas *datas, char *line); +int replace_var(t_datas *datas, char **line, char *tmp, int tmp_i); +char *expend_str(t_datas *datas, char *line); // ----------------------------------Builtins.c int ft_echo(t_command *cmd); @@ -67,16 +64,13 @@ int ft_cd(t_command *cmd); int ft_exit(t_datas *datas, t_command *cmd); // ----------------------------------Env.c -int is_valid_identifier(char *ident); int ft_unset(t_datas *datas, t_command *cmd); int ft_env(t_datas *datas, t_command *cmd); int ft_export(t_datas *datas, t_command *cmd); // ----------------------------------Caller.c -void exe(t_datas *datas, t_command *cmd); -int builtin_call(t_datas *datas, t_command *cmd); int is_builtin(char *cmd); -pid_t caller(t_datas *datas, t_command *cmd); +int builtin_call(t_datas *datas, t_command *cmd); int piper(t_datas *datas, t_command *cmd); // ----------------------------------Parser.c @@ -97,11 +91,7 @@ typedef struct s_token struct s_token *next; } t_token; -size_t count_arguments(t_token *tok); -void update_redir(t_datas *datas, t_command *cmd,\ - t_token *tok); -t_command *parser(t_datas *datas, t_token *tok,\ - t_command *prev); +t_command *parser(t_datas *datas, t_token *tok,t_command *prev); // ----------------------------------Lexer.c typedef enum e_state @@ -121,9 +111,6 @@ typedef struct s_lex int n_elem; } t_lexer; -int create_token(t_lexer *lex, char str[]); -int check_register(t_lexer *lex, char **line, char *tmp); -int check_state(t_lexer *lex, char **line); t_token *lexer(t_datas *datas, char *line); #endif diff --git a/parser.c b/parser.c index 9856118..2fcf880 100755 --- a/parser.c +++ b/parser.c @@ -12,25 +12,32 @@ #include "minishell.h" -int push_heredoc(t_datas *datas, char *str) +static size_t count_arguments(t_token *tok); +static t_token *parse_cmd(t_datas *datas, t_token *tok, t_command *cmd); + +t_command *parser(t_datas *datas, t_token *tok, t_command *prev) { - char *line; - int pip[2]; + t_command *cmd; - pipe(pip); - while(1) + if (!tok) + return (NULL); + cmd = ft_calloc(1, sizeof *cmd); + if (prev) + cmd->prev = prev; + cmd->argv = ft_calloc(count_arguments(tok) + 1, sizeof(char *)); + cmd->argc = 0; + while(tok && tok->type != PIPE) + tok = parse_cmd(datas, tok, cmd); + if (tok) { - line = readline(">"); - if (!ft_strncmp(line, str, ft_strlen(str) + 1)) - break; - ft_putstr_fd(expend_str(datas, line), pip[1]); - write(pip[1], "\n", 1); + cmd->next = parser(datas, tok->next, cmd); + free(tok->value); + free(tok); } - close(pip[1]); - return (pip[0]); + return(cmd); } -size_t count_arguments(t_token *tok) +static size_t count_arguments(t_token *tok) { size_t ret; @@ -44,7 +51,42 @@ size_t count_arguments(t_token *tok) return (ret); } -void update_redir(t_datas *datas, t_command *cmd, t_token *tok) +static void update_redir(t_datas *datas, t_command *cmd, t_token *tok); + +static t_token *parse_cmd(t_datas *datas, t_token *tok, t_command *cmd) +{ + t_token *prev_tok; + + if (tok->type) + update_redir(datas, cmd, tok); + else + cmd->argv[cmd->argc++] = ft_strdup(tok->value); + prev_tok = tok; + tok = tok->next; + free(prev_tok->value); + free(prev_tok); + return (tok); +} + +static int push_heredoc(t_datas *datas, char *str) +{ + char *line; + int pip[2]; + + pipe(pip); + while(1) + { + line = readline(">"); + if (!ft_strncmp(line, str, ft_strlen(str) + 1)) + break; + ft_putstr_fd(expend_str(datas, line), pip[1]); + write(pip[1], "\n", 1); + } + close(pip[1]); + return (pip[0]); +} + +static void update_redir(t_datas *datas, t_command *cmd, t_token *tok) { if (tok->type == OUT) { @@ -71,40 +113,3 @@ void update_redir(t_datas *datas, t_command *cmd, t_token *tok) cmd->fd[0] = push_heredoc(datas, tok->value); } } - -t_token *parse_cmd(t_datas *datas, t_token *tok, t_command *cmd) -{ - t_token *prev_tok; - - if (tok->type) - update_redir(datas, cmd, tok); - else - cmd->argv[cmd->argc++] = ft_strdup(tok->value); - prev_tok = tok; - tok = tok->next; - free(prev_tok->value); - free(prev_tok); - return (tok); -} - -t_command *parser(t_datas *datas, t_token *tok, t_command *prev) -{ - t_command *cmd; - - if (!tok) - return (NULL); - cmd = ft_calloc(1, sizeof(t_command)); - if (prev) - cmd->prev = prev; - cmd->argv = ft_calloc(count_arguments(tok) + 1, sizeof(char *)); - cmd->argc = 0; - while(tok && tok->type != PIPE) - tok = parse_cmd(datas, tok, cmd); - if (tok) - { - cmd->next = parser(datas, tok->next, cmd); - free(tok->value); - free(tok); - } - return(cmd); -} diff --git a/utils_2.c b/utils_2.c index 23472eb..db28e83 100644 --- a/utils_2.c +++ b/utils_2.c @@ -24,32 +24,7 @@ int file_error(char *cmd, char *file, char *msg) return (0); } -char *get_var_value(t_datas *datas, char **line, int name_len) -{ - int i; - char **env; - char *name; - char *value; - - name = ft_substr(*line, 1, name_len - 1); - i = 0; - value = NULL; - while (datas->envp[i] && !value) - { - env = ft_split(datas->envp[i], '='); - if (!ft_strncmp(name, env[0], name_len + 1)) - value = (free(env[0]), env[1]); - else if (++i) - ft_free_split(env); - } - free(name); - if (value) - free(env); - else - value = strdup(""); - return (value); -} - +static char *get_var_value(t_datas *datas, char **line, int name_len); int replace_var(t_datas *datas, char **line, char *tmp, int tmp_i) { int name_len; @@ -83,7 +58,7 @@ char *expend_str(t_datas *datas, char *line) char *tmp; int tmp_i; - tmp = ft_calloc(1024, sizeof *tmp); + tmp = ft_calloc(STR_MAX_SIZE, sizeof *tmp); if (!tmp) free(tmp); tmp_i = 0; @@ -96,3 +71,29 @@ char *expend_str(t_datas *datas, char *line) } return (tmp); } + +static char *get_var_value(t_datas *datas, char **line, int name_len) +{ + int i; + char **env; + char *name; + char *value; + + name = ft_substr(*line, 1, name_len - 1); + i = 0; + value = NULL; + while (datas->envp[i] && !value) + { + env = ft_split(datas->envp[i], '='); + if (!ft_strncmp(name, env[0], name_len + 1)) + value = (free(env[0]), env[1]); + else if (++i) + ft_free_split(env); + } + free(name); + if (value) + free(env); + else + value = strdup(""); + return (value); +}