On Mon, May 21, 2012 at 03:44:51PM +0200, Edgar Fu? wrote: > What's the suggested method for breaking out of the emulation directory? > I want <EMULDIR>/opt/tivoli/tsm/client/ba/bin/dsm.opt to be a symlink to > <no-emulation>/usr/pkg/etc/tsm/dsm.opt. > I can achieve this with a considerable amount of ../, but that amount depends > on the value of <EMULDIR>, more precisely, it's expanded value, which happens > to be /usr/pkg/emul/linux32 in the case in question. > I was thinking about a /emul/none -> / symlink.
The string "/../" at the beginning of a path (e.g. in a symlink) is magic and means the real root. > I'm not sure how the behaviour of the emulation sort-of-chroot is defined > to be if it, for example, looks up /usr/local/foo/bar and e.g. a "real" > /usr/local (or /usr/local/foo) exists, but /usr/local/foo > (or /usr/local/foo/bar) doesn't. > Is this documented anywhere? Has it change since 4.0? I am not sure to what extent it's documented. The way it works is that path lookups for which TRYEMULROOT is set are, if absolute paths, tried first against the emulation root and then if that fails against the real root. What's tried is the whole path, not single steps, so the existence of partial paths in the wrong place shouldn't break it. This is not supposed to have changed recently, although I did rework the code and it's not impossible that some corner cases changed. At some point the behavior in connection with directory operations will change slightly(*) but this hasn't happened yet. The TRYEMULROOT mechanism was itself added (to replace a pile of ad hoc hacks) at some point, but I believe that was between 3.0 and 4.0. Now, as for which lookups TRYEMULROOT is applied to... that is not really well defined. It's "most of them". A while back I posted trying to develop a consensus about what the rules should be, but didn't really get any traction. (*) The expected change is that lookups for operating in a directory (e.g. mkdir, rmdir, rename, etc.) will look up the containing directory only using TRYEMULROOT, instead of also looking for the operation target before retrying. This will change the behavior of, for example, unlink("/usr/bin/foo") when /usr/bin/foo exists and /emul/whatever/usr/bin exists, but /emul/whatever/usr/bin/foo does not. It will also prevent mkdir("/usr/bin") from failing if /usr/bin exists and /emul/whatever/usr exists but /emul/whatever/usr/bin does not. There's also been an argument made that directory ops of this type should not have TRYEMULROOT set at all, but as noted above there's no consensus on that yet. -- David A. Holland dholl...@netbsd.org