fix(execution): Redir ahah type

This commit is contained in:
Jean 2026-01-29 19:12:58 +01:00
parent a70943e5cc
commit 4315eb5c0d
2 changed files with 162 additions and 145 deletions

View file

@ -16,137 +16,6 @@
#include "../utils/vars/vars.h" #include "../utils/vars/vars.h"
#include "execution.h" #include "execution.h"
static char **list_to_argv(struct list *command_list)
{
size_t len = 0;
struct list *cur = command_list;
while (cur)
{
len++;
cur = cur->next;
}
char **argv = calloc(len + 1, sizeof(char *));
if (!argv)
return NULL;
cur = command_list;
for (size_t i = 0; i < len; i++)
{
argv[i] = (char *)cur->data;
cur = cur->next;
}
argv[len] = NULL;
return argv;
}
static int try_builtin(char **argv, struct hash_map *vars);
int exec_ast_command(struct ast_command *command, struct hash_map *vars)
{
(void)vars;
set_all_redir(command->redirections);
if (!command || !(command->command))
{
return 1;
}
char **argv = list_to_argv(command->command);
if (!argv || !(argv[0]))
{
free(argv);
unset_all_redir();
return 0;
}
int builtin_ret = try_builtin(argv, vars);
if (builtin_ret != -1)
{
free(argv);
unset_all_redir();
return builtin_ret;
}
pid_t pid = fork();
if (pid < 0)
{
perror("fork");
free(argv);
unset_all_redir();
return 1;
}
if (pid == 0)
{
execvp(argv[0], argv);
perror("execvp");
unset_all_redir();
_exit(127);
}
int status = 0;
waitpid(pid, &status, 0);
free(argv);
unset_all_redir();
if (WIFEXITED(status))
{
return WEXITSTATUS(status);
}
return 1;
}
int exec_ast_if(struct ast_if *if_node, struct hash_map *vars)
{
int cond = execution(if_node->condition, vars);
if (cond == 0)
return execution(if_node->then_clause, vars);
else
return execution(if_node->else_clause, vars);
}
int exec_ast_list(struct ast_list *list_node, struct hash_map *vars)
{
struct list *cur = list_node->children;
int ret = 0;
while (cur)
{
struct ast *child = (struct ast *)cur->data;
if (!ast_is_void(child))
ret = execution(child, vars);
cur = cur->next;
}
return ret;
}
int exec_ast_and_or(struct ast_and_or *ao_node, struct hash_map *vars)
{
int left_ret = execution(ao_node->left, vars);
if (ao_node->type == AST_AND_OR_TYPE_AND)
{
if (left_ret == 0)
return execution(ao_node->right, vars);
return left_ret;
}
else
{
if (left_ret != 0)
return execution(ao_node->right, vars);
return left_ret;
}
}
static int get_fd_target(const struct ast_redir *redir)
{
if (redir->io_number != -1)
return redir->io_number;
if (redir->type == AST_REDIR_TYPE_LESS
|| redir->type == AST_REDIR_TYPE_LESSGREAT
|| redir->type == AST_REDIR_TYPE_LESSAND)
return 0;
return 1;
}
static int open_redir_file(const struct ast_redir *redir, int *flags, int *mode) static int open_redir_file(const struct ast_redir *redir, int *flags, int *mode)
{ {
*mode = 0644; *mode = 0644;
@ -169,20 +38,6 @@ static int open_redir_file(const struct ast_redir *redir, int *flags, int *mode)
return -3; // not a file open return -3; // not a file open
} }
static int handle_and_restore_fd(int saved_fd, int fd_target)
{
if (saved_fd != -1)
{
dup2(saved_fd, fd_target);
close(saved_fd);
}
else
{
close(fd_target);
}
return 0;
}
static int set_all_redir(struct list *redir_list) static int set_all_redir(struct list *redir_list)
{ {
while (redir_list) while (redir_list)
@ -248,6 +103,166 @@ static int set_all_redir(struct list *redir_list)
return 0; return 0;
} }
static char **list_to_argv(struct list *command_list)
{
size_t len = 0;
struct list *cur = command_list;
while (cur)
{
len++;
cur = cur->next;
}
char **argv = calloc(len + 1, sizeof(char *));
if (!argv)
return NULL;
cur = command_list;
for (size_t i = 0; i < len; i++)
{
argv[i] = (char *)cur->data;
cur = cur->next;
}
argv[len] = NULL;
return argv;
}
static int try_builtin(char **argv, struct hash_map *vars);
int exec_ast_command(struct ast_command *command, struct hash_map *vars)
{
(void)vars;
set_all_redir(command->redirections ? command->redirections->children
: NULL);
if (!command || !(command->command))
{
return 1;
}
char **argv = list_to_argv(command->command);
if (!argv || !(argv[0]))
{
free(argv);
unset_all_redir(command->redirections ? command->redirections->children
: NULL);
return 0;
}
int builtin_ret = try_builtin(argv, vars);
if (builtin_ret != -1)
{
free(argv);
unset_all_redir(command->redirections ? command->redirections->children
: NULL);
return builtin_ret;
}
pid_t pid = fork();
if (pid < 0)
{
perror("fork");
free(argv);
unset_all_redir(command->redirections ? command->redirections->children
: NULL);
return 1;
}
if (pid == 0)
{
execvp(argv[0], argv);
perror("execvp");
unset_all_redir(command->redirections ? command->redirections->children
: NULL);
_exit(127);
}
int status = 0;
waitpid(pid, &status, 0);
free(argv);
unset_all_redir(command->redirections ? command->redirections->children
: NULL);
if (WIFEXITED(status))
{
return WEXITSTATUS(status);
}
return 1;
}
int exec_ast_if(struct ast_if *if_node, struct hash_map *vars)
{
int cond = execution(if_node->condition, vars);
if (cond == 0)
return execution(if_node->then_clause, vars);
else
return execution(if_node->else_clause, vars);
}
int exec_ast_list(struct ast_list *list_node, struct hash_map *vars)
{
struct list *cur = list_node->children;
int ret = 0;
while (cur)
{
struct ast *child = (struct ast *)cur->data;
if (!ast_is_void(child))
ret = execution(child, vars);
cur = cur->next;
}
return ret;
}
int exec_ast_and_or(struct ast_and_or *ao_node, struct hash_map *vars)
{
int left_ret = execution(ao_node->left, vars);
if (ao_node->type == AST_AND_OR_TYPE_AND)
{
if (left_ret == 0)
return execution(ao_node->right, vars);
return left_ret;
}
else
{
if (left_ret != 0)
return execution(ao_node->right, vars);
return left_ret;
}
}
void unset_all_redir(struct list *redir_list)
{
while (redir_list)
{
struct ast_redir *redir = (struct ast_redir *)redir_list->data;
int target_fd;
if (redir->io_number != -1)
{
target_fd = redir->io_number;
}
else
{
if (redir->type == AST_REDIR_TYPE_LESS
|| redir->type == AST_REDIR_TYPE_LESSGREAT
|| redir->type == AST_REDIR_TYPE_LESSAND)
{
target_fd = 0;
}
else
{
target_fd = 1;
}
}
if (redir->saved_fd != -1)
{
dup2(redir->saved_fd, target_fd);
close(redir->saved_fd);
redir->saved_fd = -1;
}
redir_list = redir_list->next;
}
}
/* /*
int exec_ast_redir(struct ast_redir *redir, struct hash_map *vars) int exec_ast_redir(struct ast_redir *redir, struct hash_map *vars)
{ {

View file

@ -9,4 +9,6 @@ int exec_ast_if(struct ast_if *if_node, struct hash_map *vars);
int exec_ast_list(struct ast_list *list_node, struct hash_map *vars); int exec_ast_list(struct ast_list *list_node, struct hash_map *vars);
int exec_ast_and_or(struct ast_and_or *ao_node, struct hash_map *vars); int exec_ast_and_or(struct ast_and_or *ao_node, struct hash_map *vars);
void unset_all_redir(struct list *redir_list);
#endif // EXECUTION_HELPERS_H #endif // EXECUTION_HELPERS_H