Browse Source

[enh] handle to not parse chevrons between coted blocks:
- new function which check chevron is on non coted blocks.
- add corresponding unit tests.

Moul 4 years ago
parent
commit
baa05adbe8
3 changed files with 36 additions and 2 deletions
  1. 33 2
      src/redirect.c
  2. 1 0
      src/sh.h
  3. 2 0
      tests.sh

+ 33 - 2
src/redirect.c

@@ -1,7 +1,9 @@
 #include "sh.h"
 
 /*
+** Get chevrons positions
 ** If a chevron is present:
+**  Take closer chevron
 **  Prevent segfault by checking there is something before and after chevron
 **  Parse redirections: split in four parts:
 **  Get position of the first chevron
@@ -15,13 +17,16 @@
 void	parse_redirection(t_e *e, char **str, int i, int len)
 {
 	int		chev;
+	int		chev2;
 	char	**split;
 	int		nchev;
 	int		fd;
 
-	if ((chev = ft_search_pos_char(str[i], '<')) != -1 || \
-		(chev = ft_search_pos_char(str[i], '>')) != -1)
+	chev = check_chev_is_on_non_coted_block(e, len, str[i], '>');
+	chev2 = check_chev_is_on_non_coted_block(e, len, str[i], '<');
+	if (chev != -1 || chev2 != -1)
 	{
+		chev = (chev != -1 && chev < chev2) || chev2 == -1 ? chev : chev2;
 		if (check_before_after_chevron(str[i], chev) == 1)
 		{
 			error_message("", "", "nothing specified before or after chevron");
@@ -40,6 +45,32 @@ void	parse_redirection(t_e *e, char **str, int i, int len)
 		launch_pipe(str[i]);
 }
 
+/*
+** while not found chevron (increment begin position of check):
+** - for every block:
+**  - if chev is inside the block and the block is non-coted
+**   - return chevron position
+** else: return error
+*/
+
+int		check_chev_is_on_non_coted_block(t_e *e, int len, char *str, char c)
+{
+	int		j;
+	int		chev;
+
+	chev = 0;
+	while (ft_search_pos_char(&str[chev + 1], c) != -1)
+	{
+		j = -1;
+		chev += ft_search_pos_char(&str[chev + 1], c) + 1;
+		while (e->b[++j] != NULL)
+			if (e->b[j]->type == 0 && len + chev >= e->b[j]->begin && \
+			len + chev <= e->b[j]->end)
+				return (chev);
+	}
+	return (-1);
+}
+
 /*
 ** Check if there is visible char before and after chevrons
 */

+ 1 - 0
src/sh.h

@@ -34,6 +34,7 @@ int		non_coted_block(t_e *e, char *line, int pos, t_block *blk);
 ** redirect.c
 */
 void	parse_redirection(t_e *e, char **str, int i, int len);
+int		check_chev_is_on_non_coted_block(t_e *e, int len, char *str, char c);
 int		check_before_after_chevron(char *str, int chev);
 char	**parse_and(char *str, char **split, int file_pos);
 void	redirections(t_e *e, char *cmd, char *operator, char *ofd, char *file);

+ 2 - 0
tests.sh

@@ -128,6 +128,8 @@ tests=(
 #"echo \"!\"#$%&\'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_\`abcdefghijklmnopqrstuvwxyz{|}~\""
 # test all ASCII char: check they are used to split str like ';', '>', '<' or '|'
 "echo \"nrsatu;nrtsa\""
+"echo \"rasnt>inausrt\" > toto; cat toto"
+"echo \" nrastiu<rasntiu\" > toto; cat toto"
 "ls ; echo \"nasruit><rnasuti\" > toto ; cat < toto"
 
 ### Back cotes: pipe