On 01/13/2013 04:34:56 AM, Felix Janda wrote:
Sorry for this repeated hair-splitting.
Eh, it happens. :)I'm constantly mucking about in areas I'm brand new to (or haven't got the background for, or last messed with so long ago I've forgotten important things, or while massively distracted and sleep deprived...), so I'm wrong a lot. I just try to fix it when I notice.
On 01/12/13 at 11:33pm, Rob Landley wrote: > On 01/10/2013 02:25:13 PM, Felix Janda wrote: > > On 01/02/13 at 12:41am, Rob Landley wrote:> > > What I did was disable #3 in the case where cwd doesn't exist. So> > the > > > new rule #3 is: > > > > > > 3) If cwd exists and $PWD doesn't point to it, fall back to -P. > > > > Thanks for the clarification. > >> > Your version of 3) depends on whether pwd is builtin or not. Do you> > mean > > something like "If getcwd() fails ..."? > > cwd is what getcwd() returns. $PWD is an environment variable.I wanted to differentiate between the current working directory and itsname.
The kernel has two magic symlinks as part of each process's state: 1) "." which is set by chdir() and returned by getcwd().2) "/" which is set by chroot() and not really returned by anything because it's what other paths are explained relative _to_.
Inside the kernel, each points to a dentry, which is pinned by the reference so you don't have to worry about it going away. (It can be invalidated by deleting the dentry's attached inode, but I believe it's still around as a zombie until the reference count drops to zero. And there's a horrible magic syscall called switch_root that iterates through every process in the system and redirects the "." and "/" links of every process from one of these to another, but that does horrible latency spike locking.)
Each dentry has a ".." link, which is not a process attribute, but a dentry attribute. (Or is it inode? The fact dentries aren't really independent of an underlying inode is half the reason you can't hardlink directories. Anyway, ".." is implemented by following the dentry parent pointer, with the exception that "/" pointing to the current dentry is treated the same as the dentry parent pointer being NULL. Yes, this means that if you go:
mkdir("sub");
chroot("sub");
chdir("../../../../../../../../..");
chroot(".");
You can escape a chroot. Moving the "/" symlink _under_ "." means the
.. test won't hit it, you see. There's no >= test here, just ==.
Anyway, given a dentry the kernel can traverse up to the root (either equal to "/" or where the dentry parent pointer is NULL) to work out the absolute path to this dentry, and since each dentry only has one parent pointer there's only _one_ absolute path to a given dentry.
Does that help?
Doesn't an unliked current working still exist for the processes its the cwd of?
You have a pointer to a zombie dentry, the parent pointer of which is NULL. It's been unlinked from the tree but won't be garbage collected until the reference count falls to zero. I'd guess the corresponding inode has been freed and thus the inode pointer is also NULL (thus freeing up actual disk space, unlike a filehandle to an open _file_), but I'd have to go look at the kernel source to know for sure.
(I was wrong about that 3) depends on whether pwd in builtin or not since child processes inherit cwd.)
Child processes inherit environment variables too, but a child process can't change the parent's attributes. (Ok, it could ptrace it but that's HORRIBLE and we're not doing that. Sorry, reflexive action anytime anyone, including me, says "you can't do X". There's usually a bad way to do it. I have a black belt in bad ways to do things, and a lot of experience in cleaning them up to look presentable. I do the "don't ask questions, post errors" thing to _myself_ all the time.)
> > > > BTW, in the case that one has deleted and recreated one's current> > > > working> > > > directory one could also use "cd ." to get to the new directory.> > >> > > Good to know. (This means the shell is special casing "." as well as> > > "..". I need to read the susv4 shell stuff thoroughly, it's been > > > years...) > >> > The susv4 page special cases "." and ".." a bit, but it seems to me> > only> > in the $CDPATH handling. Ah, I see that you don't care about $CDPATH> > from > > the about page. > > $CDPATH and $PWD are separate. I just read http://landley.net/toybox/about.html:
I read http://pubs.opengroup.org/onlinepubs/9699919799/utilities/cd.html(About the above URL: don't ask me why www.opengroup.org redirects to pubs.opengroup.org but just opengroup.org says the service is discontinued. The safe thing to do is probably just http://pubs.opengroup.org/onlinepubs/9699919799/download/ and use a file:// url on the local disk. That's what I do most of the time, and then have to dig up a public URL when I want to point somebody else at a page...)
> And some things (like $CDPATH support in "cd") await a good explanation> of why to bother with them. and interpreted it as a reluctance to implement $CDPATH support.
I am reluctant to implement $CDPATH support. Having a search path so that when you "cd frog" it finds /usr/ranunculus/diseases/frog is just _weird_. That said, someday an actual user of it might show up and change my mind.
> > Then I think one can leave out step 5 on susv4's page on> > cd, and "cd ." is no more special than "cd dir"; it does a chdir to> > "$PWD/." > > or "$PWD/dir" respectively and then updates $PWD to its canonical > > form. (and > > modifies $OLDPWD also if necessary) > > Um, steps 4 and 8 are the ones that say cd . and .. are special? Step 4 means that $CDPATH shouldn't be taken into account when you do something like "cd ./dir" or "cd ../dir".
$CDPATH is not the same as $PWD. $CDPATH is a _search_path_ for cd. You know how when you run an executable it searches $PATH? Apparently when you cd to a directory it searches $CDPATH. Who knew? I didn't, and I've been using unix variants since the late 80's. (Well, if you count Vax Eunice on my father's work machine which had an amiga software library on it and xmodem. If you count _actual_ unix, more like 1992.)
In Step 8 the usual formal processes of simplifying a path (by
removing "."
dot components and so on) described.
Of course here "." and ".." are treated specially, but this treatment
affects only $PWD, since chdir("/some/dir/.") should do the same as
chdir("/some/dir").
I'm only talking about $PWD.
Step 9 looks like fun...
I have an epic todo list for toysh. "cd" is a shell command, thus part of toysh.
Part of the reason I haven't been dinking at it in small amounts is there's so much context to keeps traight in your head I should probably buckle down and focus on just the shell for a couple months at some point, and right now the same effort completes multiple smaller commands.
That said, I should do the basic cleanup pass (remove toybuf dependency that imposes command line length limitations), add basic environment variable support, start on conditionals (if/while/for)...
But I need to finish the cleanup pass on cp. And finish the losetup/umount/mount chain. And review the pile of commands that are already in but not properly cleaned up. And figure out why current toolchains stopped doing proper dead function elimination (a toybox with just "true" on x86-64 is 15k! That's ridiculous. Admittedly a main() that does nothing but "return 1", built with -s -Os is 6k. That's gcc+glibc for you. But still, that extra 9k is sad. And if you objdump -d a toybox built with gcc 4.2.1 it hasn't got parse_optflags() in it, but one built with ubuntu's current gcc does. Yup, upstream toolchain regression in the ability to eliminiate dead code. The <strike>aristocrats</strike> free software foundation!
Rob _______________________________________________ Toybox mailing list [email protected] http://lists.landley.net/listinfo.cgi/toybox-landley.net
