On 5 September 2012 01:28, Irek Szczesniak <iszczesn...@gmail.com> wrote: > On Tue, Sep 4, 2012 at 11:57 PM, Roland Mainz <roland.ma...@nrubsig.org> > wrote: >> Hi! >> >> ---- >> >> [Just some follow-up to the recent discussion] >> Question is: Why do we want a per-thread cwd ? Is it useful ? >> >> AFAIK the arguments are: >> * Pro: >> - Moving the cwd from global to a pre-thead makes it easier to >> implement thread support for existing applications >> <any more arguments ?> >> * Contra: >> - The per-thread cwd is locked on the current thread. Moving objects >> relying on this per-thread cwd to another thread (e.g. job "borrowing" >> or forwarding) is not possible unless we alter that's thread cwd >> (which means we have the same kind+class of problems we tried to solve >> when we tried to get rid of the global cwd) >> - The per-thread cwd is only known to libast... any other API will not >> be aware of this (Glenn: Can this we resolved by compiling existing >> libraries against the libast headers ?) >> >> Finally: Wouldn't it be a better solution to drop the notion of a >> global or per-thread cwd _COMPLETELY_ and let the applications and >> APIs themselves handle this... with as many dirfd's they want ? The >> idea would be that all APIs which currently rely on global resources >> like { cwd, umask, environ } get this information passed as arguments >> instead of relying on the global versions (we already see this >> movement in POSIX with the introduction of the |*at()|-APIs in XPG7 or >> newer additions like >> |posix_spawnattr_setfchdir()|/|posix_spawnattr_setenviron()|/|fexecve()| >> etc. ...) ? > > Roland, your analysis is wrong. > > A global cwd or per thread cwd is a resource which has to be shared > between objects. The problem is that they have to *share* it > implicitly. > All problems listed in this list or known to me so far have their root > in the unprotected, implicit sharing, and the results of unintended > changes, i.e. one object does a change which other objects are not > aware of. Multithreading and the concurrency of access is cited very > often, but it's only a specialized symptom of the more general problem > of implicit sharing. > > So the question is: Does a per thread cwd solve the problem of > unprotected and implicit sharing of the cwd? The answer is a clear NO, > not even with IMO or IMHO. > It's just an idiotic attempt to bump legacy apis to the age of > threads, but without solving the right problem or even try to ask the > right question. > A per thread cwd does at least not solve the problem that objects > share this cwd implicitly and can still interact in unintended ways. > > The right solution is: Stop the implicit sharing, and start explicit > sharing, or do not share at all. > > For an api this means: Stop using the global cwd, and start passing a > fd to the base directory you'd like to work in as an argument. For > example glob() needs to be extended to add a gl_dirfd field to pass > the base dir fd, a void *(*gl_fdopendir) (__const char *); to provide > a pointer to fdopendir() (opendir() will operate on strings and a not > directory fd). After that change glob() can operate completely > independent of the global cwd, and even nested calls of glob() within > glob() no longer pose a problem. > > You also have to start thinking about apis as *objects* (and not > threads or processes) and that these objects have to work relative to > a base directory. For example a glob_t is a object, Shell_t is an > object, a relative path is an object, and so on. They all work > relative to a base directory fd, implicitly or explicitly. > Our goal should be to make it always explicitly - the notation of a > global cwd or per thread cwd is just in the way of that (correct) > view.
There's little to say here: I fully agree with you. There's nothing wrong with a global cwd in a small, simple, single threaded application, but as soon as you have a complex application which uses a diverse set of shared libraries in many different layers (not only threads!) the global or thread cwd gets into the way. And if you _are_ the shared library (like libast is one) providing APIs then relying on a global or thread cwd is pretty much a dumb idea. History proved that. Lionel _______________________________________________ ast-developers mailing list ast-developers@research.att.com https://mailman.research.att.com/mailman/listinfo/ast-developers