[PATCH] Ash support for replace and subsitution

James Simmons jsimmons at infradead.org
Tue Mar 25 14:16:32 PDT 2008


> CONDITIONAL EXPRESSIONS
>        Conditional expressions are used by the [[  compound  command  and  the
>        test  and [ builtin commands to test file attributes and perform string
>        and arithmetic comparisons.  Expressions are formed from the  following
>        unary  or  binary  primaries.   If any file argument to one of the pri-
>        maries is of the form /dev/fd/n, then file descriptor n is checked.  If
>        the  file  argument  to  one  of  the  primaries  is one of /dev/stdin,
>        /dev/stdout, or /dev/stderr, file descriptor 0, 1, or 2,  respectively,
>        is checked.
> 
>        Unless otherwise specified, primaries that operate on files follow sym-
>        bolic links and operate on the target of the link, rather than the link
>        itself.
> 
>        -a file
>               True if file exists.
>        ...
>        arg1 OP arg2
>               OP is one of -eq, -ne, -lt, -le, -gt, or -ge.  These  arithmetic
>               binary  operators return true if arg1 is equal to, not equal to,
>               less than, less than or equal to, greater than, or greater  than
>               or  equal  to arg2, respectively.  Arg1 and arg2 may be positive
>               or negative integers.

Okay. The below script shows the issue. It fails for busybox.

#!bin/sh

a=24
b=47

if [[ "$a" -eq 24 && "$b" -eq 47 ]]
then
	echo "Test succeeds"
else
	echo "test fails"
fi

If you apply this patch it works. Basically ash assumes everything in 
between [[ and ]] is a TWORD instead of a conditional. If it does see the 
&& in between [[ and  ]] ash interpites it as a [[ ]] && instead. It does 
a internal translation of && to -a and || to -o.
 
diff -urwN busybox-1.10.0.orig/shell/ash.c busybox-1.10.0/shell/ash.c
--- busybox-1.10.0.orig/shell/ash.c	2008-03-24 12:40:29.000000000 -0400
+++ busybox-1.10.0/shell/ash.c	2008-03-24 12:57:45.000000000 -0400
@@ -10008,7 +10008,7 @@
 	union node *n = NULL;
 	union node *vars, **vpp;
 	union node **rpp, *redir;
-	int savecheckkwd;
+	int savecheckkwd, flag = 0;
 
 	args = NULL;
 	app = &args;
@@ -10021,11 +10021,24 @@
 	for (;;) {
 		checkkwd = savecheckkwd;
 		switch (readtoken()) {
+		case TAND:
+			wordtext = (char *) "-a";
+		case TOR:
+			if (strcmp(wordtext, "&&"))
+				wordtext = (char *) "-o";
+			if (!flag) {
+				tokpushback++;
+				goto out;
+			}
 		case TWORD:
 			n = stzalloc(sizeof(struct narg));
 			n->type = NARG;
 			/*n->narg.next = NULL; - stzalloc did it */
 			n->narg.text = wordtext;
+			if (!strcmp("[[", wordtext))
+				flag = 1;
+			else if (!strcmp("]]", wordtext))
+				flag = 0;
 			n->narg.backquote = backquotelist;
 			if (savecheckkwd && isassignment(wordtext)) {
 				*vpp = n;


More information about the busybox mailing list