I'm finally caught up with the ast-* posts from the last 3 weeks
the posix_spawn thread inspired a new iffe C code test feature
that allows the tests to annotate reasons for test failure
(besides the test not compiling at all, which can be a valid test too)
NOTE("reason text");
can be called (preferably once per failure) and "reason text" will appear
in the iffe --verbose (-v) output on stderr
the new version of iffe will be posted later on Monday
here is the annotated posix_spawn test
--
tst lib_posix_spawn unistd.h stdlib.h spawn.h -Dfork=______fork note{
posix_spawn exists and it works and its worth using }end status{
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/wait.h>
#include <spawn.h>
#include <signal.h>
#include <fcntl.h>
#include <string.h>
/* if it uses fork() why bother? */
#undef fork
pid_t fork _ARG_((void)) { NOTE("uses fork()"); return -1; }
pid_t _fork _ARG_((void)) { NOTE("uses _fork()"); return -1; }
pid_t __fork _ARG_((void)) { NOTE("uses __fork()"); return -1; }
int
main(argc, argv)
int argc;
char** argv;
{
char* s;
pid_t pid;
posix_spawnattr_t attr;
int n;
int status;
char* cmd[3];
char tmp[1024];
if (argv[1])
_exit(signal(SIGHUP, SIG_DFL) != SIG_IGN);
signal(SIGHUP, SIG_IGN);
if (posix_spawnattr_init(&attr))
{
NOTE("posix_spawnattr_init() FAILED");
_exit(0);
}
if (posix_spawnattr_setpgroup(&attr, 0))
{
NOTE("posix_spawnattr_setpgroup() FAILED");
_exit(0);
}
if (posix_spawnattr_setflags(&attr, POSIX_SPAWN_SETPGROUP))
{
NOTE("posix_spawnattr_setflags() FAILED");
_exit(0);
}
/* first try an a.out and verify that SIGHUP is ignored */
cmd[0] = argv[0];
cmd[1] = "test";
cmd[2] = 0;
if (posix_spawn(&pid, cmd[0], 0, &attr, cmd, 0))
{
NOTE("posix_spawn() FAILED");
_exit(0);
}
status = 1;
if (wait(&status) < 0)
{
NOTE("wait() FAILED");
_exit(0);
}
if (status != 0)
{
NOTE("SIGHUP ignored in parent not ignored in child");
_exit(0);
}
/* must return exec-type errors or its useless to us *unless*
there is no [v]fork() */
n = strlen(cmd[0]);
if (n >= (sizeof(tmp) - 3))
{
NOTE("test executable path too long");
_exit(0);
}
strcpy(tmp, cmd[0]);
tmp[n] = '.';
tmp[n+1] = 's';
tmp[n+2] = 'h';
tmp[n+3] = 0;
if ((n = open(tmp, O_CREAT|O_WRONLY, S_IRWXU|S_IRWXG|S_IRWXO))
< 0 ||
chmod(tmp, S_IRWXU|S_IRWXG|S_IRWXO) < 0 ||
write(n, "exit 99\n", 8) != 8 ||
close(n) < 0)
{
NOTE("test script create FAILED");
_exit(0);
}
cmd[0] = tmp;
n = 0; /* 0 means reject */
pid = -1;
if (posix_spawn(&pid, cmd[0], 0, &attr, cmd, 0))
n = 2; /* ENOEXEC produces posix_spawn() error => BEST
*/
else if (pid == -1)
NOTE("ENOEXEC returns pid == -1");
else if (wait(&status) != pid)
NOTE("ENOEXEC produces no child process");
else if (!WIFEXITED(status))
NOTE("ENOEXEC produces signal exit");
else
{
status = WEXITSTATUS(status);
if (status == 127)
n = 1; /* ENOEXEC produces exit status 127 =>
GOOD */
else if (status == 99)
NOTE("ENOEXEC invokes sh");
else if (status == 0)
NOTE("ENOEXEC reports no error");
}
_exit(n);
}
}end
--
linux fails with "ENOEXEC invokes sh"
this means an executable file with invalid binary magic (errno => ENOEXEC) will
be passed to "sh" to see if it can handle it -- this tactic is wrong in a
number of ways
its not documented
its not posix
what "sh" does it call
if its not $SHELL then can it be overridden
and finally, for ast purposes, and specifically ksh, it would foul the shell
script
logic where if "exec() fails with ENONEXC => its a shell script", and worse,
shell
scripts passed to posix_spawn() could be hijacked by a completely different sh
implementation
we see these results on the ast build farm
yes
no
no <spawn.h> and no posix_spawn() -- reasonable
ENOEXEC invokes sh ... no
linux
SIGHUP ignored in parent not ignored in child ... no
one sol10.sun4 machine -- others ok -- don't know why yet
On Thu, 5 Jul 2012 19:46:35 +0200 Irek Szczesniak wrote:
> On Wed, Jul 4, 2012 at 8:34 PM, Irek Szczesniak <[email protected]> wrote:
> > On Wed, Jul 4, 2012 at 7:32 PM, ÏÌØÇÁ ËÒÙÖÁÎÏ×ÓËÁÑ
> > <[email protected]> wrote:
> >> Michael or any other Linux guru, can you look why ksh (2012-06-28, the
> >> non doomsday release) no longer uses posix_spawn?
> >> I am getting this line when I build ksh on Fedora:
> >> iffe: test: posix_spawn exists and it works and its worth using ... no
> >>
> >> This doesn't sound right, IMO ksh should prefer (and benefit) from
> >> using posix_spawn()
> >
> > This is interesting. I thought both Linux and Solaris use
> > posix_spawn() to avoid the much more expensive vfork()/exec().
_______________________________________________
ast-developers mailing list
[email protected]
https://mailman.research.att.com/mailman/listinfo/ast-developers