mirror of
https://codeberg.org/la-chouette/minishell.git
synced 2025-12-06 07:28:09 +01:00
Norm: Removed most comments.
This commit is contained in:
parent
a7f09137ee
commit
8b43fd2411
59 changed files with 114 additions and 1113 deletions
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* buffer.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <marvin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2024/12/12 12:39:58 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/09 17:26:24 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:44:10 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -39,12 +39,6 @@ void ft_buffer_free(t_buffer *buffer)
|
|||
free(buffer);
|
||||
}
|
||||
|
||||
/*
|
||||
** grows the buffer such that the new capacity is 1.5 times the old.
|
||||
**
|
||||
** in case of error, free all memory and return null.
|
||||
** else return buffer.
|
||||
*/
|
||||
t_buffer *ft_buffer_grow(t_buffer *buffer)
|
||||
{
|
||||
char *newbuffer;
|
||||
|
|
@ -81,15 +75,6 @@ t_buffer *ft_buffer_pushchar(t_buffer *buffer, char c)
|
|||
return (buffer);
|
||||
}
|
||||
|
||||
/*
|
||||
** push buf to the end of buffer, growing buffer if needed.
|
||||
**
|
||||
** also adds an additional null byte to terminate the buffer.
|
||||
**
|
||||
** the number of bytes to copy to buffer is n.
|
||||
** returns buffer.
|
||||
** in case of error, all memory is freed and null is returned.
|
||||
*/
|
||||
t_buffer *ft_buffer_push_buf(t_buffer *buffer, char *buf, size_t n)
|
||||
{
|
||||
if (buffer == NULL)
|
||||
|
|
|
|||
|
|
@ -3,22 +3,16 @@
|
|||
/* ::: :::::::: */
|
||||
/* buffer_charptr.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/10 18:45:49 by kcolin #+# #+# */
|
||||
/* Updated: 2025/03/10 18:46:35 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:43:47 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
#include "buffer.h"
|
||||
#include <stdlib.h>
|
||||
|
||||
/*
|
||||
** Free this buffer, but return a pointer to the internal string, which is not
|
||||
** freed.
|
||||
**
|
||||
** If buffer is null, return null.
|
||||
*/
|
||||
char *ft_buffer_to_charptr(t_buffer *buffer)
|
||||
{
|
||||
char *out;
|
||||
|
|
|
|||
13
src/env/env.c
vendored
13
src/env/env.c
vendored
|
|
@ -3,19 +3,16 @@
|
|||
/* ::: :::::::: */
|
||||
/* env.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/19 13:59:20 by kcolin #+# #+# */
|
||||
/* Updated: 2025/02/19 14:42:35 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:39:37 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
#include "env.h"
|
||||
#include <stdlib.h>
|
||||
|
||||
/*
|
||||
** Free the given env node.
|
||||
*/
|
||||
void env_destroy_node(t_env *env)
|
||||
{
|
||||
if (!env)
|
||||
|
|
@ -25,9 +22,6 @@ void env_destroy_node(t_env *env)
|
|||
free(env);
|
||||
}
|
||||
|
||||
/*
|
||||
** Free the given env linked list.
|
||||
*/
|
||||
void env_destroy(t_env *env)
|
||||
{
|
||||
t_env *next;
|
||||
|
|
@ -42,9 +36,6 @@ void env_destroy(t_env *env)
|
|||
}
|
||||
}
|
||||
|
||||
/*
|
||||
** Get the number of mappings in the givne env linked list
|
||||
*/
|
||||
size_t env_get_size(t_env *env)
|
||||
{
|
||||
size_t nb_elem;
|
||||
|
|
|
|||
22
src/env/env_convert.c
vendored
22
src/env/env_convert.c
vendored
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* env_convert.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/19 14:39:57 by kcolin #+# #+# */
|
||||
/* Updated: 2025/02/19 16:41:08 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:44:33 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -15,13 +15,6 @@
|
|||
#include "envp.h"
|
||||
#include "libft.h"
|
||||
|
||||
/*
|
||||
** Create an envp structure from the given env linked list.
|
||||
**
|
||||
** The linked list is not destroyed.
|
||||
**
|
||||
** in case of allocation error, all memory is freed and NULL is returned.
|
||||
*/
|
||||
char **envp_from_env(t_env *env)
|
||||
{
|
||||
char **new_envp;
|
||||
|
|
@ -48,17 +41,6 @@ char **envp_from_env(t_env *env)
|
|||
return (new_envp);
|
||||
}
|
||||
|
||||
/*
|
||||
** read an envp structure, and create a t_env linked list containing the same
|
||||
** information.
|
||||
**
|
||||
** the envp structure is not freed.
|
||||
**
|
||||
** in case of error, all memory is freed and null is returned.
|
||||
**
|
||||
** no checks additional checks than those of envp_get_key and envp_get_val are
|
||||
** performed
|
||||
*/
|
||||
t_env *env_from_envp(char **envp)
|
||||
{
|
||||
t_env *env;
|
||||
|
|
|
|||
61
src/env/env_manip.c
vendored
61
src/env/env_manip.c
vendored
|
|
@ -6,7 +6,7 @@
|
|||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/19 17:55:24 by kcolin #+# #+# */
|
||||
/* Updated: 2025/03/21 18:49:56 by jguelen ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:45:01 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -16,11 +16,6 @@
|
|||
#include "libft.h"
|
||||
#include "../ft_errno.h"
|
||||
|
||||
/*
|
||||
** Get the value corresponding to a given key in the given environment structure
|
||||
**
|
||||
** If not found, return null
|
||||
*/
|
||||
char *env_get_val(t_env *env, char *key)
|
||||
{
|
||||
t_env *node;
|
||||
|
|
@ -31,17 +26,6 @@ char *env_get_val(t_env *env, char *key)
|
|||
return (NULL);
|
||||
}
|
||||
|
||||
/*
|
||||
** Remove the first env node of the given linked list where the key matches the
|
||||
** given key.
|
||||
**
|
||||
** In any given env linked list, there should only be one entry for a given key.
|
||||
**
|
||||
** If the linked list is empty or the pointer is NULL, nothing is done.
|
||||
**
|
||||
** If the linked list does not contain an element matching the given key,
|
||||
** nothing is done.
|
||||
*/
|
||||
void env_rm_entry(t_env **env, char *key)
|
||||
{
|
||||
t_env *current;
|
||||
|
|
@ -70,9 +54,6 @@ void env_rm_entry(t_env **env, char *key)
|
|||
}
|
||||
}
|
||||
|
||||
/*
|
||||
** Add the given element to the end of the given linked list.
|
||||
*/
|
||||
static void env_add_back(t_env **env, t_env *new)
|
||||
{
|
||||
t_env *last;
|
||||
|
|
@ -88,37 +69,6 @@ static void env_add_back(t_env **env, t_env *new)
|
|||
last->next = new;
|
||||
}
|
||||
|
||||
/*
|
||||
** In the given env linked list, if an element with the given key exist, set its
|
||||
** value to the one provided. If no such element exist, create a new one with
|
||||
** the provided value.
|
||||
**
|
||||
** The provided key and value must be allocated. In case of error, they will be
|
||||
** freed. In case a node matching the given key is found the provided key value
|
||||
** is freed.
|
||||
**
|
||||
** If key or value is null, both key and value are freed and NULL is returned.
|
||||
** ft_errno is set to FT_EINVAL. We therefore allow for a value to be NULL.
|
||||
**
|
||||
** If key is an empty string, key and value are freed, ft_errno is set to
|
||||
** FT_EBADID, and NULL is returned.
|
||||
**
|
||||
** If there is a failure allocating a new node, NULL is returned and ft_errno is
|
||||
** set to FT_EERRNO (malloc would have set it to ENOMEM).
|
||||
**
|
||||
** Returns a pointer to the first element in the linked list, or NULL on error.
|
||||
**
|
||||
** Warning: does not check for validity of a key beyond what is described above.
|
||||
**
|
||||
** Implementation notes: free2 always returns NULL
|
||||
**
|
||||
** Note: once you pass a key to this function, if you pass it a second time, it
|
||||
** will cause bad behaviour.
|
||||
**
|
||||
** Once you passed key and/or value to this function, env is the owner of these
|
||||
** values and is responsible for freeing them. Do not pass multiple times the
|
||||
** same pointers to this function!
|
||||
*/
|
||||
t_env *env_set_entry(t_env **env, char *key, char *value)
|
||||
{
|
||||
t_env *node;
|
||||
|
|
@ -146,15 +96,6 @@ t_env *env_set_entry(t_env **env, char *key, char *value)
|
|||
return (*env);
|
||||
}
|
||||
|
||||
/*
|
||||
** Find and return a pointer to the node in the given env linked list where the
|
||||
** key matches the given key.
|
||||
**
|
||||
** If the node is not found, return NULL.
|
||||
**
|
||||
** Note that this is a pointer to the middle of the linked list, the node is not
|
||||
** copied.
|
||||
*/
|
||||
t_env *env_find_node_bykey(t_env *env, char *key)
|
||||
{
|
||||
while (env)
|
||||
|
|
|
|||
31
src/env/envp.c
vendored
31
src/env/envp.c
vendored
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* envp.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/19 13:35:44 by kcolin #+# #+# */
|
||||
/* Updated: 2025/02/19 13:43:19 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:40:06 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -14,18 +14,6 @@
|
|||
#include "libft.h"
|
||||
#include <stddef.h>
|
||||
|
||||
/*
|
||||
** Get the key part of a line of envp
|
||||
**
|
||||
** given that line is of the form key=value, return a string containing key,
|
||||
** which is allocated and must be freed.
|
||||
**
|
||||
** if line is null or is empty, return NULL
|
||||
**
|
||||
** if line contains no '=', return an copy of line
|
||||
**
|
||||
** if allocation fail, return NULL
|
||||
*/
|
||||
char *envp_get_key(char *line)
|
||||
{
|
||||
char *key;
|
||||
|
|
@ -44,18 +32,6 @@ char *envp_get_key(char *line)
|
|||
return (key);
|
||||
}
|
||||
|
||||
/*
|
||||
** Get the value part of a line of envp
|
||||
**
|
||||
** given that line is of the form key=value, return a string containing value,
|
||||
** which is allocated and must be freed.
|
||||
**
|
||||
** if line is null or is empty, return NULL
|
||||
**
|
||||
** if line contains no '=', return an empty string
|
||||
**
|
||||
** if allocation fail, return NULL
|
||||
*/
|
||||
char *envp_get_val(char *line)
|
||||
{
|
||||
char *val_pointer;
|
||||
|
|
@ -69,9 +45,6 @@ char *envp_get_val(char *line)
|
|||
return (ft_strdup(val_pointer));
|
||||
}
|
||||
|
||||
/*
|
||||
** Free all memory related to a given envp structure
|
||||
*/
|
||||
void envp_destroy(char **envp)
|
||||
{
|
||||
int i;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* connec_pipe_cmd_execute.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/04/11 12:01:29 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/30 11:49:59 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:46:28 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -38,8 +38,8 @@ static void fork_failure(t_minishell *app, int pipefd[2])
|
|||
}
|
||||
|
||||
/*
|
||||
** return the pid returned by fork. values greater than 0 indicate parentprocess
|
||||
*/
|
||||
** return the pid returned by fork.
|
||||
*/
|
||||
static int exec_pid1(t_minishell *app, int pipefd[2], t_cmd *cmd)
|
||||
{
|
||||
int pid1;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* here_doc.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/07 11:42:29 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/29 16:56:08 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:47:33 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -22,19 +22,6 @@
|
|||
char *expand_line(char *line, t_minishell *app);
|
||||
void failed_to_open_tmp_file(void);
|
||||
|
||||
/*
|
||||
** Read from infd into some file until a line that is exactly equal to the
|
||||
** marker is read.
|
||||
**
|
||||
** Then unlink the file, and return a filedescriptor to it, seeked to the start.
|
||||
**
|
||||
** If the marker is not quoted, perform variable expansion on each line. If app
|
||||
** is NULL, no variable expansions are performed.
|
||||
**
|
||||
** If NULL is given as argument, or marker->word is null, or infd is negative,
|
||||
** or getting a random filename fails, or we are unable to create the file, or
|
||||
** the file already exists, or any other error occurs, return NULL.
|
||||
*/
|
||||
char *here_doc(t_worddesc *marker, int infd, t_minishell *app)
|
||||
{
|
||||
int outfd;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* here_doc_utils.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/04/17 11:50:08 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/29 16:39:22 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:47:12 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -16,13 +16,6 @@
|
|||
#include "here_doc.h"
|
||||
#include "../../sig/sig.h"
|
||||
|
||||
/*
|
||||
** - check that arguments are not invalid
|
||||
** - create a random filename
|
||||
** - create the file
|
||||
**
|
||||
** do these operations, with error checking
|
||||
*/
|
||||
int setup_here_doc(t_worddesc *marker, int infd, char **filename)
|
||||
{
|
||||
int outfd;
|
||||
|
|
@ -38,9 +31,6 @@ int setup_here_doc(t_worddesc *marker, int infd, char **filename)
|
|||
return (outfd);
|
||||
}
|
||||
|
||||
/*
|
||||
** output line to outfd, get the next line from infd, and return it
|
||||
*/
|
||||
char *output_line_and_next(int infd, int outfd, char *line)
|
||||
{
|
||||
ft_dprintf(outfd, "%s", line);
|
||||
|
|
@ -49,9 +39,6 @@ char *output_line_and_next(int infd, int outfd, char *line)
|
|||
return (line);
|
||||
}
|
||||
|
||||
/*
|
||||
** closes outfd, reset correct sig mode handling
|
||||
*/
|
||||
char *finalize(int outfd, char *filename)
|
||||
{
|
||||
close(outfd);
|
||||
|
|
@ -70,11 +57,6 @@ int interupted(int outfd, char *filename)
|
|||
return (-1);
|
||||
}
|
||||
|
||||
/*
|
||||
** check if line corresponds to marker
|
||||
**
|
||||
** if true is returned, line has been freed
|
||||
*/
|
||||
bool is_marker(char *line, t_worddesc *marker)
|
||||
{
|
||||
char *cleanline;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* random_filename.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/11 13:29:32 by kcolin #+# #+# */
|
||||
/* Updated: 2025/03/11 13:30:33 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:48:11 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -17,17 +17,6 @@
|
|||
#include <unistd.h>
|
||||
#include "libft.h"
|
||||
|
||||
/*
|
||||
** Genereate a random filename for use by here_doc
|
||||
**
|
||||
** The filename will be of the form
|
||||
** /tmp/minishell_here_doc_XXXXXXXXXXX
|
||||
** where each X is a random alphanumerical char
|
||||
**
|
||||
** Random bytes are generated by reading from /dev/urandom
|
||||
**
|
||||
** Return NULL and sets ft_errno on error
|
||||
*/
|
||||
char *here_doc_random_filename(void)
|
||||
{
|
||||
int randomfd;
|
||||
|
|
|
|||
|
|
@ -3,20 +3,15 @@
|
|||
/* ::: :::::::: */
|
||||
/* strip_newline.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/11 13:31:22 by kcolin #+# #+# */
|
||||
/* Updated: 2025/03/11 13:31:31 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:48:08 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
#include "libft.h"
|
||||
|
||||
/*
|
||||
** create a new string without the terminating newline of the given string.
|
||||
**
|
||||
** If the given string has no terminating newline, create a copy of the input
|
||||
*/
|
||||
char *strip_newline(char *str)
|
||||
{
|
||||
size_t last_char_idx;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* simple_cmd_execute.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/27 16:21:56 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/30 15:08:01 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:49:22 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -49,9 +49,6 @@ static void command_not_found(t_simple_cmd *cmd, t_minishell *app)
|
|||
app->last_return_value = 127;
|
||||
}
|
||||
|
||||
/*
|
||||
** Do all the post-processing steps relating to a command.
|
||||
*/
|
||||
static t_simple_cmd *post_process_command(t_simple_cmd *cmd, t_minishell *app)
|
||||
{
|
||||
simple_cmd_post_process_debug(cmd, app);
|
||||
|
|
|
|||
|
|
@ -6,7 +6,7 @@
|
|||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/21 12:40:46 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/24 16:49:17 by jguelen ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:09:45 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -15,13 +15,6 @@
|
|||
#include <stdio.h>
|
||||
#include <unistd.h>
|
||||
|
||||
/*
|
||||
** get or set ft_errno
|
||||
**
|
||||
** if errno is FT_EGET, return ft_errno and do not set it
|
||||
**
|
||||
** else set ft_errno to errno, and return the previous value of ft_errno
|
||||
*/
|
||||
t_errno ft_errno(t_errno errno)
|
||||
{
|
||||
static t_errno ft_errno = FT_ESUCCESS;
|
||||
|
|
@ -36,9 +29,6 @@ t_errno ft_errno(t_errno errno)
|
|||
return (ft_errno);
|
||||
}
|
||||
|
||||
/*
|
||||
** get the current value of ft_errno
|
||||
*/
|
||||
t_errno ft_errno_get(void)
|
||||
{
|
||||
return (ft_errno(FT_EGET));
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* get_command.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/19 18:03:11 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/29 15:04:59 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:10:04 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -20,9 +20,6 @@
|
|||
#include "libft.h"
|
||||
#include "get_command.h"
|
||||
|
||||
/*
|
||||
** remove one '\n' from the end of the string, if it exists
|
||||
*/
|
||||
static char *strip_newline(char *str)
|
||||
{
|
||||
size_t last_char_idx;
|
||||
|
|
@ -54,14 +51,6 @@ static char *handle_special_command(char *line, t_minishell *app)
|
|||
return (line);
|
||||
}
|
||||
|
||||
/*
|
||||
** get a command line using readline.
|
||||
**
|
||||
** returned buffer must be freed by caller.
|
||||
** will add command to history if appropriate.
|
||||
**
|
||||
** Also handles special commands, which are not further processed.
|
||||
*/
|
||||
char *get_command(t_minishell *app)
|
||||
{
|
||||
char *line;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* minishell.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/05/02 11:53:53 by kcolin #+# #+# */
|
||||
/* Updated: 2025/05/02 12:07:42 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:10:24 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -27,9 +27,6 @@
|
|||
#include "sig/sig_handlers.h"
|
||||
#include "parser/cmd/cmd_debug.h"
|
||||
|
||||
/*
|
||||
** execute command
|
||||
*/
|
||||
static t_subprocess execute_command(t_cmd *cmd, t_minishell *app)
|
||||
{
|
||||
int retvalue;
|
||||
|
|
@ -50,24 +47,6 @@ static void debug_command(t_cmd *cmd, t_minishell *app)
|
|||
cmd_root_debug(cmd);
|
||||
}
|
||||
|
||||
/*
|
||||
** Do all the post-processing steps relating to a simple command.
|
||||
*/
|
||||
/* static t_simple_cmd
|
||||
* *post_process_command(t_simple_cmd *cmd, t_minishell *app) */
|
||||
/* { */
|
||||
/* if (simple_cmd_expand_vars(cmd, app) == NULL) */
|
||||
/* return (simple_cmd_destroy(cmd), NULL); */
|
||||
/* if (simple_cmd_fieldsplit(cmd) == NULL) */
|
||||
/* return (simple_cmd_destroy(cmd), NULL); */
|
||||
/* if (simple_cmd_expand_wildcards(cmd) == NULL) */
|
||||
/* return (simple_cmd_destroy(cmd), NULL); */
|
||||
/* return (cmd); */
|
||||
/* } */
|
||||
|
||||
/*
|
||||
** Initialize main app structure
|
||||
*/
|
||||
static void app_init(t_minishell *app, char **envp)
|
||||
{
|
||||
ft_bzero(app, sizeof(t_minishell));
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* minishell.h :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/04/09 14:02:47 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/30 11:28:11 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:11:18 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -56,7 +56,6 @@ typedef struct s_redirect
|
|||
int open_flags;
|
||||
int c_flags; // flags for third arg of open (case O_CREAT).
|
||||
t_redirectee redirectee; // fd or filename where to redirect source.
|
||||
// used between var expansion and fieldsplit
|
||||
char *unexpanded_filename;
|
||||
char *here_doc_eof; // The here-document limiter if relevant.
|
||||
} t_redirect;
|
||||
|
|
@ -74,13 +73,7 @@ typedef enum e_cmd_type
|
|||
typedef struct s_cmd
|
||||
{
|
||||
t_cmd_type type;
|
||||
/*
|
||||
** flags will probably be useless to us for now.
|
||||
*/
|
||||
int flags;
|
||||
/*
|
||||
** Line number the command starts on -> will probably be unused.
|
||||
*/
|
||||
int line;
|
||||
union u_value
|
||||
{
|
||||
|
|
@ -98,10 +91,6 @@ typedef enum e_connector
|
|||
FT_OR,
|
||||
} t_connector;
|
||||
|
||||
/*
|
||||
** This exists to represent pipelines and AND or OR lists.
|
||||
** does include left associativity.
|
||||
*/
|
||||
typedef struct s_connec_cmd
|
||||
{
|
||||
t_cmd *first;
|
||||
|
|
@ -109,12 +98,6 @@ typedef struct s_connec_cmd
|
|||
t_connector connector;
|
||||
} t_connec_cmd;
|
||||
|
||||
/*
|
||||
** We do not deal with { list; } grouping. This is therefore roughly
|
||||
** equivalent to a subshell_com structure in bash. And therefore we
|
||||
** define this only since it will still be a grouping regarding redirections
|
||||
** AND require a subshell every time in the case of minishell.
|
||||
*/
|
||||
typedef struct s_group_cmd
|
||||
{
|
||||
t_cmd *cmd;
|
||||
|
|
@ -123,7 +106,7 @@ typedef struct s_group_cmd
|
|||
|
||||
typedef struct s_simple_cmd
|
||||
{
|
||||
int line; //Probably unused.
|
||||
int line;
|
||||
t_wordlist *words; //argv in list form
|
||||
t_redirect *redirections; //redirections to perform
|
||||
} t_simple_cmd;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* cmds_parse.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/04/16 13:11:33 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/16 13:12:15 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:49:54 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -17,9 +17,6 @@
|
|||
#include "cmd_destroy.h"
|
||||
#include "../connec_cmd/connec_reorient_subtree.h"
|
||||
|
||||
/*
|
||||
** Parse list of commands or pipeline.
|
||||
*/
|
||||
t_cmd *minishell_cmds_parse(t_minishell *app, t_wordlist **tokens)
|
||||
{
|
||||
t_cmd *subtree;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* cmd_parsing.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/31 10:28:28 by jguelen #+# #+# */
|
||||
/* Updated: 2025/04/25 13:17:56 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:00:27 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -50,9 +50,6 @@ static t_cmd *expecting_quote_error(t_minishell *app)
|
|||
return (NULL);
|
||||
}
|
||||
|
||||
/*
|
||||
** TODO check if we need to differentiate the cause of a NULL return.
|
||||
*/
|
||||
t_cmd *minishell_parse(t_minishell *app, char *command_line)
|
||||
{
|
||||
t_cmd *root_cmd;
|
||||
|
|
|
|||
|
|
@ -3,23 +3,16 @@
|
|||
/* ::: :::::::: */
|
||||
/* identifier.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/19 14:43:57 by kcolin #+# #+# */
|
||||
/* Updated: 2025/02/19 14:47:00 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:50:55 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
#include "identifier.h"
|
||||
#include "libft.h"
|
||||
|
||||
/*
|
||||
** Return true if id is a valid bash identifier, false otherwise.
|
||||
**
|
||||
** A valid identifier starts with one of a-zA-Z_
|
||||
** It can contain any char a-zA-Z0-9_
|
||||
** It must contain at least one char
|
||||
*/
|
||||
bool is_identifier(char *id)
|
||||
{
|
||||
if (id == NULL || id[0] == '\0')
|
||||
|
|
|
|||
|
|
@ -3,23 +3,15 @@
|
|||
/* ::: :::::::: */
|
||||
/* metacharacter.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <marvin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/06 15:23:31 by kcolin #+# #+# */
|
||||
/* Updated: 2025/02/11 19:04:03 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:51:07 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
#include "metacharacter.h"
|
||||
|
||||
// FIXME: use ft_strchr
|
||||
/*
|
||||
** return true if the character is a metacharacter
|
||||
**
|
||||
** Bash reference manual: A character that, when unquoted, separates words. A
|
||||
** metacharacter is a space, tab, newline, or one of the following characters:
|
||||
** ‘|’, ‘&’, ‘(’, ‘)’, ‘<’, or ‘>’.
|
||||
*/
|
||||
bool is_metacharacter(char c)
|
||||
{
|
||||
if (c == ' ' || c == '\t' || c == '\n' || c == '|' || c == '&'
|
||||
|
|
|
|||
|
|
@ -3,25 +3,16 @@
|
|||
/* ::: :::::::: */
|
||||
/* operator_combo.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/17 16:30:54 by kcolin #+# #+# */
|
||||
/* Updated: 2025/02/17 16:34:34 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:51:16 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "libft.h"
|
||||
|
||||
/*
|
||||
** return true if c can be used as the next character for an operator in start
|
||||
**
|
||||
** recognized operators are:
|
||||
** ||
|
||||
** >>
|
||||
** <<
|
||||
** &&
|
||||
*/
|
||||
bool is_operator_combo(char *start, char c)
|
||||
{
|
||||
if (ft_strlen(start) != 1)
|
||||
|
|
|
|||
|
|
@ -3,19 +3,16 @@
|
|||
/* ::: :::::::: */
|
||||
/* operator_start.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/17 16:21:03 by kcolin #+# #+# */
|
||||
/* Updated: 2025/02/18 17:53:13 by jguelen ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:51:23 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
#include "libft.h"
|
||||
#include <stdbool.h>
|
||||
|
||||
/*
|
||||
** Is the character the start of an operator?
|
||||
*/
|
||||
bool is_operator_start(char c)
|
||||
{
|
||||
if (ft_strchr("<>|&()", c) != NULL)
|
||||
|
|
|
|||
|
|
@ -3,19 +3,16 @@
|
|||
/* ::: :::::::: */
|
||||
/* pipe.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/21 15:04:48 by kcolin #+# #+# */
|
||||
/* Updated: 2025/02/21 15:06:00 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:51:30 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
#include "pipe.h"
|
||||
#include "libft.h"
|
||||
|
||||
/*
|
||||
** return true if the given worddesc is a pipe operator "|"
|
||||
*/
|
||||
bool is_pipe(t_worddesc *word)
|
||||
{
|
||||
if (ft_strcmp("|", word->word) == 0)
|
||||
|
|
|
|||
|
|
@ -3,18 +3,15 @@
|
|||
/* ::: :::::::: */
|
||||
/* quote.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/20 13:21:08 by kcolin #+# #+# */
|
||||
/* Updated: 2025/02/20 13:22:12 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:51:44 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
#include "quote.h"
|
||||
|
||||
/*
|
||||
** return true if c is either ' or "
|
||||
*/
|
||||
bool is_quote(char c)
|
||||
{
|
||||
if (c == '\'' || c == '"')
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* redirect_from_words.h :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/04/14 17:31:23 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/14 17:32:12 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:52:22 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
|
|||
|
|
@ -6,7 +6,7 @@
|
|||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/20 17:36:20 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/28 16:43:53 by jguelen ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:53:03 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -44,9 +44,6 @@ static t_redirect *redirection_remove_quotes(t_redirect *in_list)
|
|||
return (out_list);
|
||||
}
|
||||
|
||||
/*
|
||||
** do quote removal on all words of this simple cmd
|
||||
*/
|
||||
t_simple_cmd *simple_cmd_remove_quotes(t_simple_cmd *cmd)
|
||||
{
|
||||
t_wordlist *new;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* remove_quotes.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/04/15 12:00/08 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/15 12:00:08 by kcolin ### ########.fr */
|
||||
/* Created: 2025/04/15 12:00:08 by kcolin #+# #+# */
|
||||
/* Updated: 2025/05/02 12:53:14 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -22,16 +22,6 @@ static bool is_ignore_mark(char c)
|
|||
return (false);
|
||||
}
|
||||
|
||||
/*
|
||||
** use the marker in the given worddesc to create a new worddesc by removing
|
||||
** unquoted quotes.
|
||||
**
|
||||
** The new worddesc will have the marker set to NULL.
|
||||
**
|
||||
** If word is null return null.
|
||||
**
|
||||
** In case of allocation failure, return null
|
||||
*/
|
||||
t_worddesc *remove_quotes(t_worddesc *word)
|
||||
{
|
||||
t_worddesc *output;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* simple_cmd.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/21 12:30:07 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/29 13:09:43 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:53:31 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -16,11 +16,6 @@
|
|||
#include "../redirect/redirect_debug.h"
|
||||
#include "../cmd/cmd_destroy.h"
|
||||
|
||||
/*
|
||||
** parse a wordlist and yield a simple command.
|
||||
**
|
||||
** takes ownership of words
|
||||
*/
|
||||
t_simple_cmd *simple_cmd_from_wordlist(t_wordlist *words)
|
||||
{
|
||||
t_simple_cmd *cmd;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* worddesc.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/13 17:20:36 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/18 09:20:14 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:54:18 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -14,17 +14,6 @@
|
|||
#include "libft.h"
|
||||
#include <stdlib.h>
|
||||
|
||||
/*
|
||||
** allocate a new worddesc with given flags, marker, and word.
|
||||
**
|
||||
** mark_string is initialized as a string of the same length as word, but filled
|
||||
** with spaces
|
||||
**
|
||||
** return null in case of error, or if word is null
|
||||
**
|
||||
** In case of allocation error, word is freed, as well as any memory allocated
|
||||
** in this function
|
||||
*/
|
||||
t_worddesc *worddesc_create(char *word, char flags, char *marker,
|
||||
t_token_type type)
|
||||
{
|
||||
|
|
@ -42,9 +31,6 @@ t_worddesc *worddesc_create(char *word, char flags, char *marker,
|
|||
return (retvalue);
|
||||
}
|
||||
|
||||
/*
|
||||
** free all memory associated with this worddesc
|
||||
*/
|
||||
void worddesc_destroy(t_worddesc *worddesc)
|
||||
{
|
||||
if (worddesc == NULL)
|
||||
|
|
@ -54,9 +40,6 @@ void worddesc_destroy(t_worddesc *worddesc)
|
|||
free(worddesc);
|
||||
}
|
||||
|
||||
// copy the given worddesc, including all internal data
|
||||
//
|
||||
// return null on error
|
||||
t_worddesc *worddesc_copy(t_worddesc *worddesc)
|
||||
{
|
||||
t_worddesc *out;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* worddesc.h :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/04/15 12:00:08 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/17 14:30:48 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:54:56 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -49,27 +49,8 @@ typedef enum e_token_type
|
|||
*/
|
||||
typedef struct s_worddesc
|
||||
{
|
||||
/*
|
||||
** The word itself
|
||||
*/
|
||||
char *word;
|
||||
/*
|
||||
** flags for this word
|
||||
**s_worddesc
|
||||
** See above for flag definitions
|
||||
*/
|
||||
char flags;
|
||||
/*
|
||||
** a character mask for word to designate the status
|
||||
** of its characters and wether or not they are subject to modifications
|
||||
**
|
||||
** Possible flags are ''', '"', '$', '&', ' '
|
||||
**
|
||||
** ' ' the default, no flag, no meaning
|
||||
** ''' corresponding character is single-quoted
|
||||
** '"' corresponding character is double-quoted
|
||||
** '$' corresponding character is a result of $var expansion
|
||||
*/
|
||||
char *marker;
|
||||
t_token_type token_type;
|
||||
} t_worddesc;
|
||||
|
|
|
|||
|
|
@ -6,7 +6,7 @@
|
|||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/13 17:07:01 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/07 17:40:30 by jguelen ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:57:29 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -15,12 +15,6 @@
|
|||
#include "unistd.h"
|
||||
#include <stdlib.h>
|
||||
|
||||
/*
|
||||
** create a new wordlist element, with next set to null and word set to the
|
||||
** passed worddesc.
|
||||
**
|
||||
** in case of error, return null
|
||||
*/
|
||||
t_wordlist *wordlist_create(t_worddesc *word)
|
||||
{
|
||||
t_wordlist *retvalue;
|
||||
|
|
@ -33,9 +27,6 @@ t_wordlist *wordlist_create(t_worddesc *word)
|
|||
return (retvalue);
|
||||
}
|
||||
|
||||
/*
|
||||
** free all memory associated with this wordlist.
|
||||
*/
|
||||
void wordlist_destroy(t_wordlist *wordlist)
|
||||
{
|
||||
t_wordlist *prev;
|
||||
|
|
@ -49,11 +40,6 @@ void wordlist_destroy(t_wordlist *wordlist)
|
|||
}
|
||||
}
|
||||
|
||||
/*
|
||||
** get the worddesc at position idx in the given wordlist.
|
||||
**
|
||||
** return null if out of range or wordlist is null
|
||||
*/
|
||||
t_worddesc *wordlist_get(t_wordlist *wordlist, int idx)
|
||||
{
|
||||
if (wordlist == NULL || idx < 0)
|
||||
|
|
@ -68,16 +54,6 @@ t_worddesc *wordlist_get(t_wordlist *wordlist, int idx)
|
|||
return (wordlist->word);
|
||||
}
|
||||
|
||||
/*
|
||||
** push the given worddesc to the end of the given wordlist.
|
||||
**
|
||||
** if wordlist is null, create a new wordlist.
|
||||
**
|
||||
** returns a pointer to the first element in the wordlist.
|
||||
**
|
||||
** if malloc failure is encountered, all memory for this wordlist is freed, and
|
||||
** null is returned.
|
||||
*/
|
||||
t_wordlist *wordlist_push(t_wordlist *wordlist, t_worddesc *worddesc)
|
||||
{
|
||||
t_wordlist *start;
|
||||
|
|
@ -93,11 +69,6 @@ t_wordlist *wordlist_push(t_wordlist *wordlist, t_worddesc *worddesc)
|
|||
return (start);
|
||||
}
|
||||
|
||||
/*
|
||||
** remove and return the first element in the given wordlist
|
||||
**
|
||||
** If wordlist is empty, return null.
|
||||
*/
|
||||
t_worddesc *wordlist_pop(t_wordlist **wordlist)
|
||||
{
|
||||
t_wordlist *first;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* wordlist.h :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/04/09 15:40:23 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/16 15:10:29 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:58:06 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -15,22 +15,9 @@
|
|||
|
||||
# include "../worddesc/worddesc.h"
|
||||
|
||||
/*
|
||||
** Linked-list of WORDS
|
||||
**
|
||||
** cf. section 3.2.4 of https://aosabook.org/en/v1/bash.html
|
||||
**
|
||||
** we are copying how bash does it.
|
||||
*/
|
||||
typedef struct s_wordlist
|
||||
{
|
||||
/*
|
||||
** pointer to the next element in the list
|
||||
*/
|
||||
struct s_wordlist *next;
|
||||
/*
|
||||
** pointer to the word at this position in the list
|
||||
*/
|
||||
struct s_worddesc *word;
|
||||
} t_wordlist;
|
||||
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* wordlist_copy.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/04 12:07:53 by kcolin #+# #+# */
|
||||
/* Updated: 2025/03/10 15:05:51 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:55:06 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -14,9 +14,6 @@
|
|||
#include "libft.h"
|
||||
#include <stdlib.h>
|
||||
|
||||
// Make a copy of the given wordlist, copying all internal data as well.
|
||||
//
|
||||
// Return null in case of error.
|
||||
t_wordlist *wordlist_copy(const t_wordlist *wordlist)
|
||||
{
|
||||
t_wordlist *outlist;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* wordlist_debug.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/24 18:20:00 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/29 13:05:20 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:55:13 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -14,9 +14,6 @@
|
|||
#include "libft.h"
|
||||
#include "../../treedrawing.h"
|
||||
|
||||
/*
|
||||
** Debug-print a wordlist
|
||||
*/
|
||||
void wordlist_debug(t_wordlist *wordlist, t_buffer *leader, bool is_last)
|
||||
{
|
||||
indent(leader, is_last);
|
||||
|
|
|
|||
|
|
@ -3,21 +3,16 @@
|
|||
/* ::: :::::::: */
|
||||
/* wordlist_idx.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/09 15:14:27 by kcolin #+# #+# */
|
||||
/* Updated: 2025/03/10 16:08:43 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:55:27 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
#include "wordlist.h"
|
||||
#include <stdlib.h>
|
||||
|
||||
/*
|
||||
** Remove the element at the given index from the wordlist and return it.
|
||||
**
|
||||
** return null if out of range or wordlist is null
|
||||
*/
|
||||
t_worddesc *wordlist_pop_idx(t_wordlist **wordlist, int idx)
|
||||
{
|
||||
t_wordlist *iter;
|
||||
|
|
@ -47,9 +42,6 @@ t_worddesc *wordlist_pop_idx(t_wordlist **wordlist, int idx)
|
|||
return (free(temp), out);
|
||||
}
|
||||
|
||||
/*
|
||||
** Remove the element at the given index from the wordlist and destroy it.
|
||||
*/
|
||||
void wordlist_destroy_idx(t_wordlist **wordlist, int idx)
|
||||
{
|
||||
worddesc_destroy(wordlist_pop_idx(wordlist, idx));
|
||||
|
|
|
|||
|
|
@ -6,7 +6,7 @@
|
|||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/08 17:29:05 by jguelen #+# #+# */
|
||||
/* Updated: 2025/03/20 09:41:04 by jguelen ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:55:53 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -21,15 +21,6 @@ static void ft_swap_wordlist_contents(t_wordlist *list1, t_wordlist *list2)
|
|||
list2->word = tmp_word;
|
||||
}
|
||||
|
||||
/*
|
||||
** The pivot is selected as in classic variations to be the last element of the
|
||||
** list initially.
|
||||
** The partitionning makes it so in the end all elements smaller than the pivot,
|
||||
** which in this case will be determined by a simple order of growing ascii
|
||||
** value on the word->word component of the wordlist, are on the left of the
|
||||
** pivot value and all elements greater on the right.
|
||||
** @RETURN the index at wich the pivot is now to be found.
|
||||
*/
|
||||
static int wordlist_quicksort_partition(t_wordlist *list, int start, int end)
|
||||
{
|
||||
int i;
|
||||
|
|
@ -58,11 +49,6 @@ static int wordlist_quicksort_partition(t_wordlist *list, int start, int end)
|
|||
return (i);
|
||||
}
|
||||
|
||||
/*
|
||||
** Returns the wordlist list sorted in ascending ascii order.
|
||||
** Proceeds by directly swapping the inside contents and not by rewiring the
|
||||
** nodes themselves.
|
||||
*/
|
||||
t_wordlist *wordlist_quicksort(t_wordlist *list, int start, int end)
|
||||
{
|
||||
int pivot;
|
||||
|
|
@ -75,9 +61,6 @@ t_wordlist *wordlist_quicksort(t_wordlist *list, int start, int end)
|
|||
return (list);
|
||||
}
|
||||
|
||||
/*
|
||||
** Is intended as a shortcut for practical use as a full list sort.
|
||||
*/
|
||||
t_wordlist *wordlist_quicksort_full(t_wordlist *list)
|
||||
{
|
||||
return (wordlist_quicksort(list, 0, wordlist_size(list) - 1));
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* wordlist_utils.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/10 09:51:34 by jguelen #+# #+# */
|
||||
/* Updated: 2025/04/30 14:52:32 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:56:55 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -16,11 +16,6 @@
|
|||
#include "../../../libft/libft.h"
|
||||
#include "../../ft_errno.h"
|
||||
|
||||
/*
|
||||
** Creates a new wordlist composed of only one element. Its next field is NULL
|
||||
** and its word field is a copy of the worddesc passed as a parameter.
|
||||
** Returns NULL in case of error.
|
||||
*/
|
||||
t_wordlist *wordlist_independant_create(t_worddesc *word)
|
||||
{
|
||||
t_wordlist *new;
|
||||
|
|
@ -43,10 +38,6 @@ t_wordlist *wordlist_independant_create(t_worddesc *word)
|
|||
return (new);
|
||||
}
|
||||
|
||||
/*
|
||||
** Returns the number of words present in the wordlist given as parameter.
|
||||
** NOTE: Assumes list not to be circular.
|
||||
*/
|
||||
int wordlist_size(t_wordlist *wordlist)
|
||||
{
|
||||
int size;
|
||||
|
|
@ -69,10 +60,6 @@ t_wordlist *wordlist_last(t_wordlist *list)
|
|||
return (list);
|
||||
}
|
||||
|
||||
/*
|
||||
** Returns the node at index idx in list or NULL if idx is out
|
||||
** of bounds.
|
||||
*/
|
||||
t_wordlist *wordlist_get_elem(t_wordlist *list, int idx)
|
||||
{
|
||||
if (list == NULL || idx < 0)
|
||||
|
|
|
|||
|
|
@ -3,38 +3,26 @@
|
|||
/* ::: :::::::: */
|
||||
/* rule_utils.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/20 12:01:57 by kcolin #+# #+# */
|
||||
/* Updated: 2025/02/20 13:18:22 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:58:26 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
#include "rule_utils.h"
|
||||
#include "../matchers/operator_combo.h"
|
||||
|
||||
/*
|
||||
** return true if we are in an unquoted operator state
|
||||
*/
|
||||
bool unquoted_operator(t_token_build *builder)
|
||||
{
|
||||
return (unquoted(builder) && builder->currently_in_operator);
|
||||
}
|
||||
|
||||
/*
|
||||
** return true if we are in an unquoted state
|
||||
*/
|
||||
bool unquoted(t_token_build *builder)
|
||||
{
|
||||
return (builder->quote == '\0');
|
||||
}
|
||||
|
||||
/*
|
||||
** return true if the current char combines with the current token to form an
|
||||
** operator.
|
||||
**
|
||||
** If current token is null, return false
|
||||
*/
|
||||
bool operator_combo(t_token_build *builder, char *original)
|
||||
{
|
||||
if (builder->cur_token == NULL)
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* tokenizing_1_5.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/19 13:20:01 by jguelen #+# #+# */
|
||||
/* Updated: 2025/02/24 14:51:09 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:12:36 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -19,10 +19,6 @@
|
|||
** https://pubs.opengroup.org/onlinepubs/9699919799/utilities/V3_chap02.html
|
||||
*/
|
||||
|
||||
/*
|
||||
** 1. If the end of input is recognized, the current token (if any) shall be
|
||||
** delimited.
|
||||
*/
|
||||
bool rule_eof(t_token_build *builder, char *original)
|
||||
{
|
||||
if (original[builder->idx] == '\0')
|
||||
|
|
@ -33,11 +29,6 @@ bool rule_eof(t_token_build *builder, char *original)
|
|||
return (false);
|
||||
}
|
||||
|
||||
/*
|
||||
** 2. If the previous character was used as part of an operator and the current
|
||||
** character is not quoted and can be used with the previous characters to form
|
||||
** an operator, it shall be used as part of that (operator) token.
|
||||
*/
|
||||
bool rule_combine_operator(t_token_build *builder, char *original)
|
||||
{
|
||||
if (unquoted_operator(builder) && operator_combo(builder, original))
|
||||
|
|
@ -49,11 +40,6 @@ bool rule_combine_operator(t_token_build *builder, char *original)
|
|||
return (false);
|
||||
}
|
||||
|
||||
/*
|
||||
** 3. If the previous character was used as part of an operator and the current
|
||||
** character cannot be used with the previous characters to form an operator,
|
||||
** the operator containing the previous character shall be delimited.
|
||||
*/
|
||||
bool rule_operator_end(t_token_build *builder, char *original)
|
||||
{
|
||||
if (unquoted_operator(builder) && !operator_combo(builder, original))
|
||||
|
|
@ -64,15 +50,6 @@ bool rule_operator_end(t_token_build *builder, char *original)
|
|||
return (false);
|
||||
}
|
||||
|
||||
/*
|
||||
** 4. If the current character is single-quote, or double-quote and it is not
|
||||
** quoted, it shall affect quoting for subsequent characters up to the end of
|
||||
** the quoted text. The rules for quoting are as described in Quoting . The
|
||||
** result token shall contain exactly the characters that appear in the input,
|
||||
** unmodified, including any embedded or enclosing quotes or substitution
|
||||
** operators, between the <quotation-mark> and the end of the quoted text. The
|
||||
** token shall not be delimited by the end of the quoted field.
|
||||
*/
|
||||
bool rule_quote(t_token_build *builder, char *original)
|
||||
{
|
||||
if (is_quote(original[builder->idx]))
|
||||
|
|
@ -87,22 +64,6 @@ bool rule_quote(t_token_build *builder, char *original)
|
|||
return (false);
|
||||
}
|
||||
|
||||
/*
|
||||
** 5. If the current character is an unquoted '$' or '`', the shell shall
|
||||
** identify the start of any candidates for parameter expansion (Parameter
|
||||
** Expansion), command substitution (Command Substitution), or arithmetic
|
||||
** expansion (Arithmetic Expansion) from their introductory unquoted character
|
||||
** sequences: '$' or "${", "$(" or '`', and "$((", respectively. The shell shall
|
||||
** read sufficient input to determine the end of the unit to be expanded (as
|
||||
** explained in the cited sections). While processing the characters, if
|
||||
** instances of expansions or quoting are found nested within the substitution,
|
||||
** the shell shall recursively process them in the manner specified for the
|
||||
** construct that is found. The characters found from the beginning of the
|
||||
** substitution to its end, allowing for any recursion necessary to recognize
|
||||
** embedded constructs, shall be included unmodified in the result token,
|
||||
** including any embedded or enclosing substitution operators or quotes. The
|
||||
** token shall not be delimited by the end of the substitution.
|
||||
*/
|
||||
bool rule_var_substitution(t_token_build *builder, char *original)
|
||||
{
|
||||
if (original[builder->idx] == '$' && builder->quote != '\'')
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* tokenizing_6_10.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: jguelen <marvin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/19 13:21:18 by jguelen #+# #+# */
|
||||
/* Updated: 2025/02/20 13:14:21 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 12:59:55 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -14,18 +14,11 @@
|
|||
#include "rule_utils.h"
|
||||
#include "../matchers/operator_start.h"
|
||||
#include "../matchers/blank.h"
|
||||
|
||||
/*
|
||||
** cf. Token Recognition section at
|
||||
** https://pubs.opengroup.org/onlinepubs/9699919799/utilities/V3_chap02.html
|
||||
*/
|
||||
|
||||
/*
|
||||
** 6. If the current character is not quoted and can be used as the first
|
||||
** character of a new operator, the current token (if any) shall be delimited.
|
||||
** The current character shall be used as the beginning of the next (operator)
|
||||
** token.
|
||||
*/
|
||||
bool rule_new_operator(t_token_build *builder, char *original)
|
||||
{
|
||||
if (unquoted(builder) && is_operator_start(original[builder->idx]))
|
||||
|
|
@ -37,10 +30,6 @@ bool rule_new_operator(t_token_build *builder, char *original)
|
|||
return (false);
|
||||
}
|
||||
|
||||
/*
|
||||
** 7. If the current character is an unquoted <blank>, any token containing the
|
||||
** previous character is delimited and the current character shall be discarded.
|
||||
*/
|
||||
bool rule_delimit_blank(t_token_build *builder, char *original)
|
||||
{
|
||||
if (unquoted(builder) && is_blank(original[builder->idx]))
|
||||
|
|
@ -52,10 +41,6 @@ bool rule_delimit_blank(t_token_build *builder, char *original)
|
|||
return (false);
|
||||
}
|
||||
|
||||
/*
|
||||
** 8. If the previous character was part of a word, the current character shall
|
||||
** be appended to that word.
|
||||
*/
|
||||
bool rule_combine_word(t_token_build *builder, char *original)
|
||||
{
|
||||
if (builder->currently_in_word)
|
||||
|
|
@ -67,9 +52,6 @@ bool rule_combine_word(t_token_build *builder, char *original)
|
|||
return (false);
|
||||
}
|
||||
|
||||
/*
|
||||
** 10. The current character is used as the start of a new word.
|
||||
*/
|
||||
bool rule_new_word(t_token_build *builder, char *original)
|
||||
{
|
||||
new_word(builder, original[builder->idx]);
|
||||
|
|
|
|||
|
|
@ -6,7 +6,7 @@
|
|||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/21 12:29:36 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/24 16:48:19 by jguelen ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:00:12 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -22,16 +22,6 @@ static void set_quote_error(char quote)
|
|||
ft_errno(FT_EUNCLOSED_SMPL_QUOTE);
|
||||
}
|
||||
|
||||
/*
|
||||
** split a string into words, respecting quotes etc.
|
||||
**
|
||||
** cf. Token Recognition section at
|
||||
** https://pubs.opengroup.org/onlinepubs/9699919799/utilities/V3_chap02.html
|
||||
**
|
||||
** words are separated with <blanks>, which are defined here
|
||||
** https://pubs.opengroup.org/onlinepubs/9699919799/
|
||||
** section 7.3.1 LC_CTYPE
|
||||
*/
|
||||
t_wordlist *minishell_wordsplit(char *original)
|
||||
{
|
||||
t_token_build token_build;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* expand_wildcard.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/04/03 19:28:28 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/30 15:09:59 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:00:43 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -65,9 +65,6 @@ static t_redirect *redirect_expand_wildcards(t_redirect *in_list)
|
|||
return (out_list);
|
||||
}
|
||||
|
||||
/*
|
||||
** returns null on error
|
||||
*/
|
||||
static t_wordlist *wordlist_expand_wildcards(t_wordlist *inlist)
|
||||
{
|
||||
t_wordlist *outlist;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* sig.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/05/02 12:16:37 by kcolin #+# #+# */
|
||||
/* Updated: 2025/05/02 12:18:17 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:01:42 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -14,19 +14,8 @@
|
|||
#include "signal.h"
|
||||
#include "sig_handlers.h"
|
||||
|
||||
/*
|
||||
** g_signum exists to store the value of a signal if relevant for later
|
||||
** processing.
|
||||
** NOTE: g_signum starts at 0 and should be set back to 0 after the information
|
||||
** it stores has been properly processed.
|
||||
*/
|
||||
int g_signum = 0;
|
||||
|
||||
/*
|
||||
** Catches SIGINT and SIGQUIT.
|
||||
** Set to ignore SIGQUIT and catch SIGINT to set g_signum for
|
||||
** further processing when in interactive mode.
|
||||
*/
|
||||
int set_interactive_mode_sig_handling(void)
|
||||
{
|
||||
struct sigaction sig_act;
|
||||
|
|
@ -44,11 +33,6 @@ int set_interactive_mode_sig_handling(void)
|
|||
return (0);
|
||||
}
|
||||
|
||||
/*
|
||||
** Set to ignore SIGINT and SIGQUIT signals if they are generated through
|
||||
** a call to kill when the program is currently executing commands.
|
||||
** Otherwise set g_signum to the number corresponding to the caught signal.
|
||||
*/
|
||||
int set_exec_mode_sig_handling(void)
|
||||
{
|
||||
struct sigaction sig_act;
|
||||
|
|
@ -66,11 +50,6 @@ int set_exec_mode_sig_handling(void)
|
|||
return (0);
|
||||
}
|
||||
|
||||
/*
|
||||
** Set to ignore SIGINT and SIGQUIT signals if they are generated through
|
||||
** a call to kill when the program is currently executing commands.
|
||||
** Otherwise set g_signum to the number corresponding to the caught signal.
|
||||
*/
|
||||
int set_here_doc_mode_sig_handling(void)
|
||||
{
|
||||
struct sigaction sig_act;
|
||||
|
|
|
|||
|
|
@ -3,20 +3,16 @@
|
|||
/* ::: :::::::: */
|
||||
/* sig.h :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/19 18:21:55 by jguelen #+# #+# */
|
||||
/* Updated: 2025/05/02 11:53:24 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:01:49 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
#ifndef SIG_H
|
||||
# define SIG_H
|
||||
|
||||
/*
|
||||
** Needed to have the definitions relative to sigaction and siginfo
|
||||
** correctly taken into account.
|
||||
*/
|
||||
# define _POSIX_C_SOURCE 200809L
|
||||
|
||||
# include "libft.h"
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* sig_handlers.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/04/17 12:01:39 by kcolin #+# #+# */
|
||||
/* Updated: 2025/05/02 12:20:24 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:01:15 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -17,9 +17,6 @@
|
|||
#include "sig.h"
|
||||
#include "libft.h"
|
||||
|
||||
/*
|
||||
** redisplay prompt
|
||||
*/
|
||||
void sig_interactive(int signum)
|
||||
{
|
||||
if (signum == SIGINT)
|
||||
|
|
@ -41,9 +38,6 @@ int get_sig_retvalue(void)
|
|||
return (retvalue);
|
||||
}
|
||||
|
||||
/*
|
||||
** Stores the value of the caught signal in g_signum for later processing.
|
||||
*/
|
||||
void sig_cmd(int signum, siginfo_t *siginfo, void *context)
|
||||
{
|
||||
(void)context;
|
||||
|
|
|
|||
|
|
@ -3,19 +3,15 @@
|
|||
/* ::: :::::::: */
|
||||
/* path_split.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: jguelen <marvin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/14 10:07:47 by jguelen #+# #+# */
|
||||
/* Updated: 2025/03/14 12:54:49 by jguelen ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:02:15 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
#include "path_split.h"
|
||||
|
||||
/*
|
||||
** We do not ignore empty words here. The word count is therefore the number of
|
||||
** times the separator appears + 1 or 0 if the string s is NULL.
|
||||
*/
|
||||
static size_t paths_count(const char *s, const char sep)
|
||||
{
|
||||
size_t count;
|
||||
|
|
@ -46,13 +42,6 @@ void path_split_destroy(char **split)
|
|||
free(split);
|
||||
}
|
||||
|
||||
/*
|
||||
** Copies and returns in a malloc-allocated string the first "word" of *s.
|
||||
** the first word is defined here as the longest substring of *s starting at
|
||||
** the beginning of *s and not including any c character.
|
||||
** During this process it moves *s past the next c character.
|
||||
** NOTE: '\0' should never be considered a valid separator.
|
||||
*/
|
||||
static char *ft_dup_firstword(char **s, const char c)
|
||||
{
|
||||
char *first_word;
|
||||
|
|
@ -68,19 +57,6 @@ static char *ft_dup_firstword(char **s, const char c)
|
|||
return (first_word);
|
||||
}
|
||||
|
||||
/*
|
||||
** A modified version of a common word-split but that does not ignore NULL
|
||||
** entries i.e. if PATH is of the form
|
||||
** PATH=/usr/bin:::/bin
|
||||
** the result will be {"/usr/bin", "", "", "/bin", NULL}
|
||||
** where all elements except the terminating NULL has been malloc-allocated to
|
||||
** ensure an ease of both treatment and end-detection.
|
||||
** The parameter separator is maintained even if in our specific case it is
|
||||
** expected to simply be ':'.
|
||||
** @Retun Returns a NULL-terminated array when each entry correspond to a
|
||||
** the longest substring possible between separator characters or end of string
|
||||
** in the normal case. Returns NULL in case of an allocation error.
|
||||
*/
|
||||
char **path_split(char const *s, const char separator)
|
||||
{
|
||||
char **split;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* path_split.h :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: jguelen <marvin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/14 10:11:29 by jguelen #+# #+# */
|
||||
/* Updated: 2025/03/14 12:20:27 by jguelen ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:02:30 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -16,16 +16,6 @@
|
|||
# include <stdlib.h>
|
||||
# include "libft.h"
|
||||
|
||||
/*
|
||||
** A modified version of a common word-split but that does not ignore NULL
|
||||
** entries i.e. if PATH is of the form
|
||||
** PATH=/usr/bin:::/bin
|
||||
** the resul will be {"/usr/bin", "", "", "/bin", NULL}
|
||||
** where all elements except the terminating NULL has been malloc-allocated to
|
||||
** ensure an ease of both treatment and end-detection.
|
||||
** The parameter separator is maintained even if in our specific case it is
|
||||
** expected to simply be ':'.
|
||||
*/
|
||||
char **path_split(const char *s, char separator);
|
||||
void path_split_destroy(char **split);
|
||||
|
||||
|
|
|
|||
|
|
@ -6,19 +6,12 @@
|
|||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/02/25 13:02:59 by jguelen #+# #+# */
|
||||
/* Updated: 2025/03/14 09:55:09 by jguelen ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:02:37 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
#include "replace_substr.h"
|
||||
|
||||
/*
|
||||
** @RETURN Returns a new C-compliant malloc-allocated string corresponding to
|
||||
** text where the substring starting in text at index index_start and ending
|
||||
** at index_end is replaced in totality by the C-compliant string replacement
|
||||
** excluding its NULL-byte.
|
||||
** Returns NULL if an allocation error occurred.
|
||||
*/
|
||||
char *replace_in_str(const char *text, size_t index_start, size_t index_end,
|
||||
const char *replacement)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* simple_filename_exp.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/02 13:40:10 by jguelen #+# #+# */
|
||||
/* Updated: 2025/04/24 17:58:39 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:03:26 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -18,13 +18,6 @@
|
|||
#include <stdbool.h>
|
||||
#include <sys/stat.h>
|
||||
|
||||
/*
|
||||
** Returns a malloc-allocated string representing the full path to
|
||||
** the command or executable corresponding to name or NULL in case of
|
||||
** failure and sets ft_errno in accordance.
|
||||
** NOTE: if name contains a '/' character then name is considered to
|
||||
** be an absolute path.
|
||||
*/
|
||||
char *get_cmdpath(const char *name, t_minishell *app)
|
||||
{
|
||||
char *cmd_path;
|
||||
|
|
|
|||
|
|
@ -6,7 +6,7 @@
|
|||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/18 18:40:14 by jguelen #+# #+# */
|
||||
/* Updated: 2025/03/19 16:34:10 by jguelen ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:03:20 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -19,10 +19,6 @@
|
|||
#include <stdlib.h>
|
||||
#include <sys/stat.h>
|
||||
|
||||
/*
|
||||
** Returns a malloc-allocated string corresponding to
|
||||
** "path_dir/name"
|
||||
*/
|
||||
char *alloc_path(char *path_dir, char *name)
|
||||
{
|
||||
char *path;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* simple_filename_exp_utils_utils.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/04/24 17:56:47 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/25 15:42:20 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:03:10 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -16,13 +16,6 @@
|
|||
#include "subst.h"
|
||||
#include "path_split.h"
|
||||
|
||||
/*
|
||||
** The return value of this function is always safe to destroy with
|
||||
** path_split_destroy.
|
||||
** Returns a NULL-terminated array containing each possible path contained
|
||||
** in the PATH environnement variable.
|
||||
** Returns NULL in case of an allocation error.
|
||||
*/
|
||||
char **get_paths_array(t_env *env)
|
||||
{
|
||||
char **path_array;
|
||||
|
|
@ -42,20 +35,6 @@ char **get_paths_array(t_env *env)
|
|||
return (path_array);
|
||||
}
|
||||
|
||||
/*
|
||||
** Utility function that attempts to find a regular executable file for which
|
||||
** the execution rights are granted. It disregards non-regular files and so in
|
||||
** particular directories (note that using stat allows us to follow symlinks to
|
||||
** their target if encountered). If a file is found here for which the execution
|
||||
** permission is not granted and no elligible file was found before its path is
|
||||
** stored inside oldpath so that in case no file is found to be executable it
|
||||
** is the value stored in oldpath that will be used resulting in a Permission
|
||||
** denied error. oldpath is to store the first occurrence of a regular file
|
||||
** corresponding to the filepath but not executable.
|
||||
**
|
||||
** We disregard all stat(2) failures, since bash does the same and treats them
|
||||
** all to mean that the file does not exist.
|
||||
*/
|
||||
static char *select_path(char *filepath, char **oldpath, char **path,
|
||||
struct stat *fstat)
|
||||
{
|
||||
|
|
@ -77,19 +56,6 @@ static char *select_path(char *filepath, char **oldpath, char **path,
|
|||
return (NULL);
|
||||
}
|
||||
|
||||
/*
|
||||
** This function exists to implement the bash behaviour specific to where
|
||||
** the PATH variable has been set with a non-empty value.
|
||||
** It checks the working directory if there is a void inside PATH and tries to
|
||||
** find the executable command inside the path entry itself otherwise
|
||||
** disregarding directories and selecting the first entry that both exists and
|
||||
** is executable. If no such entry exists but one or more regular file(s)
|
||||
** exist(s) with the correct name in one of the entries (it therefore lacks the
|
||||
** execution permission) this function will return the first found.
|
||||
** Returns NULL if an error occurred or nothing corresponds to filename
|
||||
** in PATH. ft_errno is set in the course of this function to help distinguish
|
||||
** the nature of the case.
|
||||
*/
|
||||
static char *deal_with_filled_path(char *filename, char **path,
|
||||
struct stat *fstat)
|
||||
{
|
||||
|
|
@ -127,19 +93,6 @@ static char *filter_dir(struct stat fstat, char *filepath)
|
|||
return (free(filepath), NULL);
|
||||
}
|
||||
|
||||
/*
|
||||
** This function searches the environment to resolve a full path for an
|
||||
** executable file corresponding to filename. It deals with two types of bash
|
||||
** behaviours: a PATH unset or corresponding to an empty value and a PATH set
|
||||
** and with a non-empty value.
|
||||
** In the first case it searches the current working directory for the file
|
||||
** coorresponding to filename. If no regular file is found it returns NULL and
|
||||
** distinguishes the case where a directory was found corresponding to filename
|
||||
** by setting ft_errno to FT_ISDIR.
|
||||
** The second case is dealt with using deal_with_filled_path (see the function
|
||||
** itself for details).
|
||||
** Returns NULL on error or if nothing is found.
|
||||
*/
|
||||
char *filepath_from_env(char *filename, t_minishell *app)
|
||||
{
|
||||
char *filepath;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* variable_subst.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/19 17:28:29 by kcolin #+# #+# */
|
||||
/* Updated: 2025/04/18 09:22:10 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:05:15 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -16,35 +16,6 @@
|
|||
#include "replace_substr.h"
|
||||
#include "../env/env_manip.h"
|
||||
|
||||
/*
|
||||
** @Param
|
||||
** word: the worddesc to be modified
|
||||
** i: the index at which the $ marking the start of expansion is located
|
||||
** id_len: the length of the string that constitutes a valid bash
|
||||
** identifier
|
||||
** rep: a malloc-allocated string previously calculated to correspond to
|
||||
** the actual value to set as the expansion
|
||||
** This function exists to actually modify the worddesc word by modifying the
|
||||
** word proper inside but also keep the marker string coherent with these
|
||||
** modifications so that further steps can act properly with the type of
|
||||
** expansion and properly field split (word split in the manual) the result or
|
||||
** not. To this end if an expansion occurs outside quotes every character
|
||||
** resulting from it is marked simply with a '$' character and is subject to
|
||||
** future field splitting. If however, the expansion occurs within double quotes
|
||||
** it is not to be subjected to field splitting in the future and every
|
||||
** character resulting from such an expansion is marked with a '&'.
|
||||
**
|
||||
** cf. https://www.gnu.org/software/bash/manual/bash.html#Quoting
|
||||
** section 3.5.7
|
||||
** The shell scans the results of parameter expansion, command substitution, and
|
||||
** arithmetic expansion that did not occur within double quotes for word
|
||||
** splitting.
|
||||
**
|
||||
** NOTE: It frees the malloc-allocated string rep.
|
||||
**
|
||||
** @RETURN In case of allocation error returns NULL, oterwise returns word
|
||||
** itself.
|
||||
*/
|
||||
static t_worddesc *word_update(t_worddesc *word, size_t i, size_t id_len,
|
||||
char *rep)
|
||||
{
|
||||
|
|
@ -71,11 +42,6 @@ static t_worddesc *word_update(t_worddesc *word, size_t i, size_t id_len,
|
|||
return (word);
|
||||
}
|
||||
|
||||
/*
|
||||
** Calculates the string corresponding to the value of the variable to be
|
||||
** expanded in the word proper and returns it.
|
||||
** The string returned is always malloc-allocated or NULL.
|
||||
*/
|
||||
static char *calculate_replacement(t_worddesc *word, t_minishell *app, size_t i,
|
||||
size_t *id_len)
|
||||
{
|
||||
|
|
@ -106,22 +72,6 @@ static char *calculate_replacement(t_worddesc *word, t_minishell *app, size_t i,
|
|||
return (free(id), rep);
|
||||
}
|
||||
|
||||
/*
|
||||
** @Param word should NOT be NULL.
|
||||
** Replace the word field of the t_worddesc pointer word with a new string
|
||||
** corresponding to the replacement of the '$' followed by a valid bash
|
||||
** identifier with the corresponding value if present in env, the return value
|
||||
** of the last foreground executed pipeline in the case of $? or nothing if
|
||||
** the corresponding identifier does not have an entry in env.
|
||||
** Similarly if the character following the '$' is neither '_' or
|
||||
** alphanumerical the dollar is removed except for the appearance of a '\0'
|
||||
** signaling the end of the word.
|
||||
** Returns NULL and sets errno in case of error, or the worddesc pointer word
|
||||
** itself if everything went normally.
|
||||
**
|
||||
** returns NULL and does not touch errno if this word should be deleted (because
|
||||
** of the expansion of an unquoted empty variable).
|
||||
*/
|
||||
t_worddesc *word_var_expansion(t_worddesc *word, t_minishell *app)
|
||||
{
|
||||
size_t i;
|
||||
|
|
@ -149,15 +99,6 @@ t_worddesc *word_var_expansion(t_worddesc *word, t_minishell *app)
|
|||
return (word);
|
||||
}
|
||||
|
||||
/*
|
||||
** Returns the t_wordlist passed as a parameter where the words have been
|
||||
** modified to contain strings that represent the result of parameter expansion
|
||||
** where the introductory '$' character was not single quoted.
|
||||
** We DO NOT take the '\' character into account as an escape character here
|
||||
** under any circumstance per subject requirement.
|
||||
**
|
||||
** In case of error, all of list is freed.
|
||||
*/
|
||||
t_wordlist *wordlist_var_expansion(t_wordlist *list, t_minishell *app)
|
||||
{
|
||||
t_wordlist *in_list;
|
||||
|
|
|
|||
|
|
@ -6,7 +6,7 @@
|
|||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/06 13:03:41 by kcolin #+# #+# */
|
||||
/* Updated: 2025/03/19 09:03:31 by jguelen ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:03:56 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -16,11 +16,6 @@
|
|||
#include "../env/env.h"
|
||||
#include "../../libft/libft.h"
|
||||
|
||||
/*
|
||||
** Returns a C-compliant malloc-allocated string of length len and composed
|
||||
** only of the character c except for the terminating NULL-byte or NULL in
|
||||
** case of an allocation error.
|
||||
*/
|
||||
char *construct_repeting_char_string(char c, size_t len)
|
||||
{
|
||||
char *new;
|
||||
|
|
@ -32,24 +27,11 @@ char *construct_repeting_char_string(char c, size_t len)
|
|||
return (new);
|
||||
}
|
||||
|
||||
/*
|
||||
** @RETURN Returns a malloc-allocated string representing the return value of
|
||||
** the last foreground executed pipeline.
|
||||
*/
|
||||
char *expand_question_mark(t_minishell *app)
|
||||
{
|
||||
return (ft_itoa(app->last_return_value));
|
||||
}
|
||||
|
||||
/*
|
||||
** Returns the longest possible substring present in str starting at the
|
||||
** beginning that follows the definition of a valid bash identifier.
|
||||
** NOTE(reminder): a valid bash identifier (name) is a non-empty string
|
||||
** starting with a '_' or an alphabetic character and composed only of '_'s or
|
||||
** alphanumerical characters.
|
||||
** The returned string is malloc-allocated.
|
||||
** In case of an allocation error, NULL is returned.
|
||||
*/
|
||||
char *ft_get_longest_identifier(char *str)
|
||||
{
|
||||
char *key;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* wildcard_exp.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/20 15:01:38 by jguelen #+# #+# */
|
||||
/* Updated: 2025/04/30 14:53:30 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:08:40 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -14,17 +14,12 @@
|
|||
#include "../ft_errno.h"
|
||||
#include "subst.h"
|
||||
#include "replace_substr.h"
|
||||
/******************************************************************************/
|
||||
/* */
|
||||
/* NOTE: The use of errno and the setting of it was OKed by Alexandru */
|
||||
/* */
|
||||
/******************************************************************************/
|
||||
|
||||
/******************************************************************************/
|
||||
/* */
|
||||
/* NOTE: The use of errno and the setting of it was OKed by Alexandru in this */
|
||||
/* context. */
|
||||
/* */
|
||||
/******************************************************************************/
|
||||
/*
|
||||
** Returns a directory stream corresponding to the current directory.
|
||||
**
|
||||
*/
|
||||
static DIR *open_current_dir(void)
|
||||
{
|
||||
char *cur_dir_path;
|
||||
|
|
@ -51,13 +46,6 @@ static DIR *open_current_dir(void)
|
|||
return (dir);
|
||||
}
|
||||
|
||||
/*
|
||||
** Adds filename to the end of the wordlist *list by creating a worddesc whose
|
||||
** word is filename and marker makes filename be considered fully single
|
||||
** quoted.
|
||||
** NOTE: In case of error, this function destroys *list in a similar fashion
|
||||
** as worddesc_create destroys its first parameter in case of failure.
|
||||
*/
|
||||
t_wordlist *add_file_to_list(t_wordlist **list, char *filename)
|
||||
{
|
||||
t_worddesc *file_desc;
|
||||
|
|
@ -81,20 +69,6 @@ t_wordlist *add_file_to_list(t_wordlist **list, char *filename)
|
|||
return (*list);
|
||||
}
|
||||
|
||||
/*
|
||||
** A function designed to present all possible * or ? filename expansions
|
||||
** for the current directory. (? is not asked by the subject).
|
||||
** Does not take into account any other wildcard and does only search the
|
||||
** current working directory.
|
||||
** @PARAM A C compliant character string representing a pattern for a filename.
|
||||
** @RETURN Returns a wordlist for which each entry corresponds to a filename
|
||||
** that matches pattern->word if any file matches in the current directory.
|
||||
** Otherwise return file_pattern itself if nothing matches the perceived
|
||||
** pattern. This list should be alphabetically sorted.
|
||||
** Can return NULL only in case of error.
|
||||
** NOTE: this function never becomes the owner of file_pattern to maintain
|
||||
** coherency of use.
|
||||
*/
|
||||
static t_wordlist *expand_star_core(t_worddesc *file_pattern)
|
||||
{
|
||||
struct dirent *new;
|
||||
|
|
@ -120,17 +94,6 @@ static t_wordlist *expand_star_core(t_worddesc *file_pattern)
|
|||
return (wordlist_quicksort_full(file_wordlist));
|
||||
}
|
||||
|
||||
/*
|
||||
** Returns 1 if and only if filename is recognized by pattern, 0
|
||||
** otherwise or -1 in case of error.
|
||||
** Takes only into account the * wildcard or ?, those characters
|
||||
** NOTE: for a pattern to accept '.' as the first character of a filename
|
||||
** it must be explicitly matched (only for the first character though).
|
||||
** Similarly, '/' is never to be matched except if given explicitly as per
|
||||
** bash requirement. This is a note in case of future expansion as in our case
|
||||
** here we do not have to deal with that since we concern ourselves only with
|
||||
** the current working directory.
|
||||
*/
|
||||
char fits_pattern(char *str, t_worddesc *pattern)
|
||||
{
|
||||
char **pattern_check;
|
||||
|
|
|
|||
|
|
@ -3,19 +3,16 @@
|
|||
/* ::: :::::::: */
|
||||
/* wildcard_exp_utils.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/21 13:46/14 by kcolin #+# #+# */
|
||||
/* Updated: 2025/03/24 13:51:30 by jguelen ### ########.fr */
|
||||
/* Created: 2025/03/21 13:46:14 by kcolin #+# #+# */
|
||||
/* Updated: 2025/05/02 13:06:22 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
#include "subst.h"
|
||||
#include <stdbool.h>
|
||||
|
||||
/*
|
||||
** Cleanly disposes of a pattern checker two dimensionnal array.
|
||||
*/
|
||||
void destroy_pattern_check(char **pattern_check, size_t len)
|
||||
{
|
||||
size_t i;
|
||||
|
|
@ -29,17 +26,6 @@ void destroy_pattern_check(char **pattern_check, size_t len)
|
|||
free(pattern_check);
|
||||
}
|
||||
|
||||
/*
|
||||
** Returns 1 if the currently examined characters in str and pattern can match
|
||||
** allowing to preserve the validity of previous matches one "character" behind
|
||||
** in both strings.
|
||||
** i.e. serves to detect when the currently examined character of str in index i
|
||||
** and the current character of pattern match exactly or the character in
|
||||
** pattern under scrutiny is an unquoted '?'. There is one exception to wit
|
||||
** the character '.' can only be matched exactly if it is the first character of
|
||||
** both str and pattern and explicitly given. That is in this case ? cannot
|
||||
** match it even if it can under all other circumstance.
|
||||
*/
|
||||
static int same_character_or_one_char_wild(char *str, t_worddesc *pattern,
|
||||
size_t i, size_t j)
|
||||
{
|
||||
|
|
@ -50,9 +36,6 @@ static int same_character_or_one_char_wild(char *str, t_worddesc *pattern,
|
|||
&& pattern->marker[j - 1] != '&'));
|
||||
}
|
||||
|
||||
/*
|
||||
** Condition to know if the wildcard '*' can catch something.
|
||||
*/
|
||||
static int at_star_in_pattern(char *str, t_worddesc *pattern,
|
||||
size_t i, size_t j)
|
||||
{
|
||||
|
|
@ -64,10 +47,6 @@ static int at_star_in_pattern(char *str, t_worddesc *pattern,
|
|||
&& pattern->marker[j - 1] != '&');
|
||||
}
|
||||
|
||||
/*
|
||||
** Sets true where the pattern would match an empty string (the most basic
|
||||
** prefix of str).
|
||||
*/
|
||||
static void init_pattern_checker(t_worddesc *pattern, char **checker)
|
||||
{
|
||||
size_t i;
|
||||
|
|
@ -84,48 +63,6 @@ static void init_pattern_checker(t_worddesc *pattern, char **checker)
|
|||
}
|
||||
}
|
||||
|
||||
/*
|
||||
** Fills the table which contains in its most low and right cell 0 if
|
||||
** str does not match the pattern and 1 otherwise.
|
||||
** This construction is only done for the current diectory so no special
|
||||
** treatment is to be considered for '/' characters which otherwise have
|
||||
** to be matched explicitely. We do however consider the case where the '.'
|
||||
** character cannot be matched except explicitely when in first position
|
||||
** in str.
|
||||
** This function has the goal of building an array of prefix recognition
|
||||
** where each and every cell i,j in the array corresponds to the matching of the
|
||||
** prefix str[0 .. i - 1] with pattern[0 .. j - 1].
|
||||
** the array has the form:
|
||||
** empty string will be noted ε.
|
||||
** pattern | | p[0] | . . . | p[pattern_len - 1]
|
||||
** _s_\_(p)_|___________________|__________|_______|____________________
|
||||
** i \ j | 0 | 1 | . . . | pattern_len
|
||||
** _____\___|___________________|__________|_______|____________________
|
||||
** 0 | ε == ε | | | pattern == ε
|
||||
** _________|___________________|__________|_______|____________________
|
||||
** 1 | str[0..0] == ε |str[0..0] | |
|
||||
** | |== p[0..0]| | pattern == p[0..0]
|
||||
** _________|___________________|__________|_______|____________________
|
||||
** . | | | |
|
||||
** . | | | |
|
||||
** . | | | |
|
||||
** _________|___________________|__________|_______|____________________
|
||||
** str len|| str == ε | str == | |
|
||||
** [len - 1]| | p[0..0] | | pattern == str
|
||||
**
|
||||
** There are several ways to preserve a match while going forward either in str,
|
||||
** in pattern or both: either you are matching corresponding characters or a '?'
|
||||
** wildcard in pattern with str or you are considering a '*' wildcard in
|
||||
** pattern. In those cases you can inherit from a match previously reached.
|
||||
** Otherwise, no match can be found.
|
||||
** When considering two characters that are identical (or '?' in pattern) you
|
||||
** will match exactly if amd only if you matched one character before in both
|
||||
** strings.
|
||||
** In the case of the consideration of the '*' wildcard in pattern, since it
|
||||
** matches both ε and any arbitrary string, you will match if before seeing the
|
||||
** '*' in pattern you already matched (case ε i.e. checker[i-1][j]) or if you
|
||||
** englobe the character currently considered in str (checker[i][j - 1]).
|
||||
*/
|
||||
void build_pattern_checks(char *str, t_worddesc *pattern,
|
||||
char **checker)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -6,7 +6,7 @@
|
|||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/15 15:09:56 by jguelen #+# #+# */
|
||||
/* Updated: 2025/04/30 14:04:57 by jguelen ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:06:44 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -14,10 +14,6 @@
|
|||
#include "subst.h"
|
||||
#include "replace_substr.h"
|
||||
|
||||
/*
|
||||
** Removes unquoted quotes and from file_pattern->word and keeps
|
||||
** file_pattern->marker congruent.
|
||||
*/
|
||||
void clean_pattern(t_worddesc *file_pattern)
|
||||
{
|
||||
int i;
|
||||
|
|
@ -42,13 +38,6 @@ void clean_pattern(t_worddesc *file_pattern)
|
|||
}
|
||||
}
|
||||
|
||||
/*
|
||||
** Checks if a worddesc is to be considered a pattern as bash would in a
|
||||
** reduced capacity, to wit if it contains at least one unquoted '?' or '*'
|
||||
** character.
|
||||
** Returns 1 if the worddesc pointed to by desc is to be considered a pattern,
|
||||
** 0 otherwise.
|
||||
*/
|
||||
int ispattern(t_worddesc *desc)
|
||||
{
|
||||
size_t i;
|
||||
|
|
|
|||
|
|
@ -3,10 +3,10 @@
|
|||
/* ::: :::::::: */
|
||||
/* treedrawing.h :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: kcolin <kcolin@42.fr> +#+ +:+ +#+ */
|
||||
/* By: jguelen <jguelen@student.42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/18 12:24:25 by kcolin #+# #+# */
|
||||
/* Updated: 2025/03/19 13:50:37 by kcolin ### ########.fr */
|
||||
/* Updated: 2025/05/02 13:11:33 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
|
|
@ -21,11 +21,6 @@
|
|||
# define VERTICAL " │ "
|
||||
# define SPACE " "
|
||||
|
||||
/* # define CROSS " |- " */
|
||||
/* # define CORNER " \\- " */
|
||||
/* # define VERTICAL " | " */
|
||||
/* # define SPACE " " */
|
||||
|
||||
void indent(t_buffer *indent, bool is_last);
|
||||
void dedent(t_buffer *indent, bool is_last);
|
||||
|
||||
|
|
|
|||
|
|
@ -1,103 +0,0 @@
|
|||
/* ************************************************************************** */
|
||||
/* */
|
||||
/* ::: :::::::: */
|
||||
/* word_search.c :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: jguelen <marvin@42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/02 14:27:58 by jguelen #+# #+# */
|
||||
/* Updated: 2025/03/02 18:12:00 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
#include "word_search.h"
|
||||
|
||||
/*
|
||||
** @PARAM needle_len must be the length of the string needle.
|
||||
** Calculates the Knuth-Morris-Pratt array for the word needle to then determine
|
||||
** what shifts to make later for the searching window of the searching of needle
|
||||
** in a text in the future.
|
||||
** Returns the KMP array for needle or NULL if an allocation error occurs or
|
||||
** needle is either NULL or needle_len is 0.
|
||||
*/
|
||||
static int *create_kmp_array(char *needle, size_t needle_len)
|
||||
{
|
||||
int *kmp;
|
||||
size_t i;
|
||||
int j;
|
||||
|
||||
if (!needle || !needle_len)
|
||||
return (NULL);
|
||||
i = 0;
|
||||
j = -1;
|
||||
kmp = malloc((needle_len + 1) * sizeof(int));
|
||||
if (!kmp)
|
||||
return (NULL);
|
||||
kmp[0] = -1;
|
||||
while (i < needle_len)
|
||||
{
|
||||
while (j > -1 && needle[i] != needle[j])
|
||||
j = kmp[j];
|
||||
i++;
|
||||
j++;
|
||||
if (needle[i] == needle[j])
|
||||
kmp[i] = kmp[j];
|
||||
else
|
||||
kmp[i] = j;
|
||||
}
|
||||
return (kmp);
|
||||
}
|
||||
|
||||
/*
|
||||
** @Param Should only be provided with arguments that are neither NULL or empty
|
||||
** Could be extended to report all occurrences of needle in haystack
|
||||
** but for now only reports the first.
|
||||
** (cf http://monge.univ-mlv.fr/~lecroq/string/node8.html#SECTION0080)
|
||||
*/
|
||||
ssize_t word_search_kmp(char *haystack, char *needle)
|
||||
{
|
||||
int i;
|
||||
int j;
|
||||
int *kmp;
|
||||
int needle_len;
|
||||
int haystack_len;
|
||||
|
||||
needle_len = ft_strlen(needle);
|
||||
kmp = create_kmp_array(needle, needle_len);
|
||||
if (!kmp)
|
||||
return (-2);
|
||||
i = 0;
|
||||
j = 0;
|
||||
haystack_len = ft_strlen(haystack);
|
||||
while (j < haystack_len)
|
||||
{
|
||||
while (i > -1 && needle[i] != haystack[j])
|
||||
i = kmp[i];
|
||||
j++;
|
||||
if (++i >= needle_len)
|
||||
return (free(kmp), j - i);
|
||||
}
|
||||
free(kmp);
|
||||
return (-1);
|
||||
}
|
||||
|
||||
/*
|
||||
** Should not be given NULL or empty arguments.
|
||||
*/
|
||||
ssize_t word_search_brute(char *haystack, char *needle)
|
||||
{
|
||||
ssize_t i;
|
||||
ssize_t needle_len;
|
||||
ssize_t haystack_len;
|
||||
|
||||
needle_len = ft_strlen(needle);
|
||||
haystack_len = ft_strlen(haystack);
|
||||
i = 0;
|
||||
while (i <= (haystack_len - needle_len))
|
||||
{
|
||||
if (ft_memcmp(haystack + i, needle, needle_len) == 0)
|
||||
return (i);
|
||||
i++;
|
||||
}
|
||||
return (-1);
|
||||
}
|
||||
|
|
@ -1,69 +0,0 @@
|
|||
/* ************************************************************************** */
|
||||
/* */
|
||||
/* ::: :::::::: */
|
||||
/* word_search.h :+: :+: :+: */
|
||||
/* +:+ +:+ +:+ */
|
||||
/* By: jguelen <marvin@42.fr> +#+ +:+ +#+ */
|
||||
/* +#+#+#+#+#+ +#+ */
|
||||
/* Created: 2025/03/02 14:10:36 by jguelen #+# #+# */
|
||||
/* Updated: 2025/03/02 17:56:02 by jguelen ### ########.fr */
|
||||
/* */
|
||||
/* ************************************************************************** */
|
||||
|
||||
#ifndef WORD_SEARCH_H
|
||||
# define WORD_SEARCH_H
|
||||
|
||||
# include <stdlib.h>
|
||||
# include "libft.h"
|
||||
|
||||
/*
|
||||
** An implementation of the Knuth, Morris and Pratt algorithm for exact word
|
||||
** searching in a text.
|
||||
** cf. http://monge.univ-mlv.fr/~lecroq/string/node8.html#SECTION0080
|
||||
**
|
||||
** The design of the Knuth-Morris-Pratt algorithm follows a tight analysis of
|
||||
** the Morris and Pratt algorithm. Let us look more closely at the Morris-Pratt
|
||||
** algorithm. It is possible to improve the length of the shifts.
|
||||
**
|
||||
** Consider an attempt at a left position j, that is when the the window is
|
||||
** positioned on the text factor y[j .. j + m - 1]. Assume that the first
|
||||
** mismatch occurs between x[i] and y[i+j] with 0 < i < m. Then,
|
||||
** x[0 .. i - 1] = y[j .. i + j - 1] = u and a = x[i] != y[i + j] = b.
|
||||
**
|
||||
** When shifting, it is reasonable to expect that a prefix v of the pattern
|
||||
** matches some suffix of the portion u of the text. Moreover, if we want to
|
||||
** avoid another immediate mismatch, the character following the prefix v in the
|
||||
** pattern must be different from a. The longest such prefix v is called the
|
||||
** tagged border of u (it occurs at both ends of u followed by different
|
||||
** characters in x).
|
||||
**
|
||||
** This introduces the notation: let kmpNext[i] be the length of the longest
|
||||
** border of x[0 .. i - 1] followed by a character c different from x[i] and -1
|
||||
** if no such tagged border exits, for 0 < i leq m. Then, after a shift, the
|
||||
** comparisons can resume between characters x[kmpNext[i]] and y[i+j] without
|
||||
** missing any occurrence of x in y, and avoiding a backtrack on the text
|
||||
** (see figure 7.1). The value of kmpNext[0] is set to -1.
|
||||
** The table kmpNext can be computed in O(m) space and time before the searching
|
||||
** phase, applying the same searching algorithm to the pattern itself, as if
|
||||
** x = y.
|
||||
**
|
||||
** The searching phase can be performed in O(m + n) time. The Knuth-Morris-Pratt
|
||||
** algorithm performs at most 2 * n - 1 text character comparisons during the
|
||||
** searching phase. The delay (maximal number of comparisons for a single text
|
||||
** character) is bounded by log_Phi(m) where Phi is the golden ratio.
|
||||
*/
|
||||
|
||||
/*
|
||||
** Uses the Knuth-Morris-Pratt algorithm.
|
||||
** Returns the index where an occurrence of needle was found in haystack, or
|
||||
** -1 if no such occurrence was found and -2 in case of allocation error.
|
||||
*/
|
||||
ssize_t word_search_kmp(char *haystack, char *needle);
|
||||
/*
|
||||
** The simple, familiar brute force searching algorithm of a word in a text.
|
||||
** Returns the index where an occurrence of needle is found in haystack, or
|
||||
** -1 if no such occurrence exists.
|
||||
*/
|
||||
ssize_t word_search_brute(char *haystack, char *needle);
|
||||
|
||||
#endif
|
||||
Loading…
Add table
Add a link
Reference in a new issue