On 2013-03-18 05:38, Bernd Petrovitsch wrote:
Hi!
On Mon, 2013-03-18 at 10:09 +0100, Bastian Bittorf wrote:
* Joshua Judson Rosen<[email protected]> [18.03.2013 09:58]:
failure to dot/source a file can still result in an error-message without
making the shell quit. In order to do that, I had to slightly adjust
somebody posted a link to the posix-standard, where explicity is
written, a shell must abort when a '. $file' fails. what is your
usecase? why is a
[ -e "$file" ]&& . "$file"
not ok for you? my usecase was more a "speed" issue, because
The only technical reason against that is the race condition if $file is
deleted after the existence/read check.
Yes. And there's no way to get around the shell aborting in that case.
There's also an issue of compatibility with scripts written for other shells...:
Well, since the standard wants that ....
`luckily', the other popular bourne shells (e.g.: bash, dash/ash, ksh) seem to
all actually behave contrary to POSIX on this matter; portable scripts already
have to do ". $file || exit" if they actually want the POSIX behaviour....
So, even ignoring the unfixable race condition, there's a porting effort
required to make shell scripts work with busybox ash as it is.
Given the other places where busybox favours de facto standards over POSIX
(e.g.: ls reports in 1-kB block rather than 512-byte blocks, command
option-parsing doesn't stop at the first non-option parameter),
doing the same in dotcmd() seems reasonable.
Walter Harms mentioned `$POSIXLY_CORRECT', which is how the GNU programs
handle these `POSIX says one thing but everyone actually does this other thing'
cases; I was somewhat surprised to find that POSIXLY_CORRECT already
occurs some other places in busybox, so maybe Walter's right to suggest that.
Or maybe Mike Frysinger's suggestion to conditionalise the behaviour with
`#if ENABLE_ASH_BASH_COMPAT' is correct. Here's a patch that does both ;)
--
"Don't be afraid to ask (λf.((λx.xx) (λr.f(rr))))."
diff --git a/shell/ash.c b/shell/ash.c
index fbbdb06..af5e55b 100644
--- a/shell/ash.c
+++ b/shell/ash.c
@@ -1218,8 +1218,8 @@ ash_vmsg_and_raise(int cond, const char *msg, va_list ap)
TRACE(("\") pid=%d\n", getpid()));
} else
TRACE(("ash_vmsg_and_raise(%d, NULL) pid=%d\n", cond, getpid()));
- if (msg)
#endif
+ if (msg)
ash_vmsg(msg, ap);
flush_stdout_stderr();
@@ -9542,6 +9542,7 @@ breakcmd(int argc UNUSED_PARAM, char **argv)
enum {
INPUT_PUSH_FILE = 1,
INPUT_NOFILE_OK = 2,
+ INPUT_NOFILE_NONFATAL = 4,
};
static smallint checkkwd;
@@ -9984,7 +9985,16 @@ setinputfile(const char *fname, int flags)
if (fd < 0) {
if (flags & INPUT_NOFILE_OK)
goto out;
- ash_msg_and_raise_error("can't open '%s'", fname);
+
+ ash_msg("can't open '%s'", fname);
+
+#if ENABLE_ASH_BASH_COMPAT
+ if (lookupvar("POSIXLY_CORRECT") == NULL &&
+ (flags & INPUT_NOFILE_NONFATAL))
+ goto out;
+#endif
+
+ ash_msg_and_raise_error(NULL);
}
if (fd < 10) {
fd2 = copyfd(fd, 10);
@@ -12236,8 +12246,9 @@ find_dot_file(char *name)
}
/* not found in the PATH */
- ash_msg_and_raise_error("%s: not found", name);
- /* NOTREACHED */
+ ash_msg("%s: not found", name);
+
+ return NULL;
}
static int FAST_FUNC
@@ -12246,6 +12257,7 @@ dotcmd(int argc, char **argv)
char *fullname;
struct strlist *sp;
volatile struct shparam saveparam;
+ int inputfd;
for (sp = cmdenviron; sp; sp = sp->next)
setvareq(ckstrdup(sp->text), VSTRFIXED | VTEXTFIXED);
@@ -12260,6 +12272,15 @@ dotcmd(int argc, char **argv)
fullname = find_dot_file(argv[1]);
+ if (fullname == NULL)
+ {
+#if ENABLE_ASH_BASH_COMPAT
+ if (lookupvar("POSIXLY_CORRECT") == NULL)
+ return EXIT_FAILURE;
+#endif
+ ash_msg_and_raise_error(NULL);
+ }
+
argv += 2;
argc -= 2;
if (argc) { /* argc > 0, argv[0] != NULL */
@@ -12269,7 +12290,10 @@ dotcmd(int argc, char **argv)
shellparam.p = argv;
};
- setinputfile(fullname, INPUT_PUSH_FILE);
+ inputfd = setinputfile(fullname, INPUT_PUSH_FILE | INPUT_NOFILE_NONFATAL);
+ if (inputfd < 0)
+ return EXIT_FAILURE;
+
commandname = fullname;
cmdloop(0);
popfile();
_______________________________________________
busybox mailing list
[email protected]
http://lists.busybox.net/mailman/listinfo/busybox