Re: Environment of expansions and visibility of side-effect assignments

2017-07-27 Thread Casper . Dik


>On Solaris, vfork() is 3x faster than fork(),

This depends very much on application.

In Solaris, vfork() is more or less O(1) where fork() is a O(n)
where "n" is the size of the address space: each r/w page which isn't 
shared needs to be marked "read-only" so the first modification clones the 
page to a writable copy.

With shared library and the dynamic linker, there is very little that you 
can do between vfork() to exec/_exit in the child.

The current Solaris implementation of posix_spawn() does use vfork() and 
it is known that its use is safe.  For others this is less so.

Ok, vfork() isn't completely O(1): it needs to halt all the other 
threads executing in the same address space, basically it stops to world

Casper



Re: Environment of expansions and visibility of side-effect assignments

2017-07-27 Thread Joerg Schilling
Jilles Tjoelker  wrote:

> > >From my metering, I know that on Solaris vfork() is 3x faster than fork()
> > even tough the fork() implementation in SunOS uses CopyOnWrite since 1988.
>
> > As a result, I typically see aprox. 30% better performance with a 
> > "configure" 
> > run when vfork() is used.
>
> That difference is a bit higher than I saw in "real" benchmarks on
> FreeBSD, but the differences I saw were still significant, both on PC
> and embedded hardware. I think using vfork() somehow is definitely
> interesting for a scripting shell.

It would be of interest to me what actual difference between a fork() and a 
vfork() call you see on FreeBSD.

On Solaris, vfork() is 3x faster than fork(), but on Linux both are of the same 
speed as Linux only implements the "pitfalls" from vfork() but not the 
advantages that mean:

the address space description of the child is not a copy of the address 
space description from the parent, but the child rather borrows the 
address space description from the parent.

Linux implements vfork() like fork() but with shared memory. Linux fork() 
implementation is based on the concept from SunOS-4.0 from 1988, where the 
child uses a copy-on-write MMU setup. So fork() is faster than it has been on 
UNIX before SunOS-4.0, but Linux vfork() does not benefit from possible 
advantages.

I use a benchmark based on the configure script that I publish with the 
schilytools.

My tests are run from "bosh" with "set -o time" in effect and a shell specific 
test is run as:

shell=SUT-shell
CONFIG_SHELL=$shell $shell ./configure

ksh93 - compiled the way it is on OpenSolaris - is the fastest shell I know.
ksh93 1.5x faster than bash.

BTW: my memory was wrong, bosh is only 10% faster than it's predecessor the 
OpenSolaris Bourne Shell. This however varies between CPU types and with newer 
CPU types, the difference is bigger.

> I think this was deliberate so that side effects from ${foo?} and
> ${foo=bar} affect the outer shell environment instead of just the single
> command.
>
> > You would need:
> > 
> > expredir();
> > forkshell();
> > if (child) {
> > redirect();
> > exec();
> > } else {
> > repair_mods_from_the_child();
> > }
>
> > if you use vfork.
>
> This looks icky because opening a redirection may block (for example if
> the file is a fifo), which leads to the vforked child sticking around in
> its strange state for longer than expected.

> If this approach is used for background simple commands, it is
> definitely broken because the redirection opens should execute in
> parallel with the rest of the script. Things like
>   mkfifo f; something >f & exec 3 would deadlock.

bosh uses vfork() only for the simple cases and never for the cases where the 
shell syntax explicitely mentions a fork.

Jörg

-- 
 EMail:jo...@schily.net(home) Jörg Schilling D-13353 Berlin
joerg.schill...@fokus.fraunhofer.de (work) Blog: http://schily.blogspot.com/
 URL: http://cdrecord.org/private/ http://sf.net/projects/schilytools/files/'