X-Git-Url: https://git.whamcloud.com/?a=blobdiff_plain;f=libsysio%2Fsrc%2Fchdir.c;h=3f5c90028b3cbfd3c2f9965fecf58fde682a7298;hb=refs%2Fchanges%2F80%2F5580%2F2;hp=36c4757ac6e7b4d159aef1b166493c27398a104a;hpb=b8292c00324fbe9a25910ce53d03569186ea3e2c;p=fs%2Flustre-release.git diff --git a/libsysio/src/chdir.c b/libsysio/src/chdir.c index 36c4757..3f5c900 100644 --- a/libsysio/src/chdir.c +++ b/libsysio/src/chdir.c @@ -9,7 +9,7 @@ * terms of the GNU Lesser General Public License * (see cit/LGPL or http://www.gnu.org/licenses/lgpl.html) * - * Cplant(TM) Copyright 1998-2003 Sandia Corporation. + * Cplant(TM) Copyright 1998-2006 Sandia Corporation. * Under the terms of Contract DE-AC04-94AL85000, there is a non-exclusive * license for use of this work by or on behalf of the US Government. * Export of this program may require a license from the United States @@ -79,6 +79,10 @@ #include "file.h" #include "sysio-symbols.h" +#ifdef DEFER_INIT_CWD +const char *_sysio_init_cwd = NULL; +#endif + struct pnode *_sysio_cwd = NULL; /* @@ -90,15 +94,17 @@ _sysio_p_chdir(struct pnode *pno) int err; /* - * Revalidate the pnode, and ensure it's a directory + * Revalidate the pnode, and ensure it's an accessable directory */ err = _sysio_p_validate(pno, NULL, NULL); if (err) return err; - if (!(pno->p_base->pb_ino && - S_ISDIR(pno->p_base->pb_ino->i_mode))) + S_ISDIR(pno->p_base->pb_ino->i_stbuf.st_mode))) return -ENOTDIR; + if ((err = _sysio_permitted(pno, X_OK)) != 0) + return err; + /* * Release old if set. */ @@ -154,6 +160,9 @@ _sysio_p_path(struct pnode *pno, char **buf, size_t size) cur = pno; + if (!size && buf && *buf) + return -EINVAL; + /* * Walk up the tree to the root, summing the component name * lengths and counting the vertices. @@ -231,6 +240,19 @@ SYSIO_INTERFACE_NAME(getcwd)(char *buf, size_t size) SYSIO_INTERFACE_DISPLAY_BLOCK; SYSIO_INTERFACE_ENTER; +#ifdef DEFER_INIT_CWD + if (!_sysio_cwd) { + struct pnode *pno; + + /* + * Can no longer defer initialization of the current working + * directory. Force namei to make it happen now. + */ + if (_sysio_namei(NULL, ".", 0, NULL, &pno) != 0) + abort(); + P_RELE(pno); + } +#endif err = _sysio_p_path(_sysio_cwd, &buf, buf ? size : 0); SYSIO_INTERFACE_RETURN(err ? NULL : buf, err); }