Annotation of 42BSD/lib/libc/gen/getwd.c, revision 1.1.1.1

1.1       root        1: /*     @(#)getwd.c     4.8     (Berkeley)      3/2/83  */
                      2: 
                      3: /*
                      4:  * getwd() returns the pathname of the current working directory. On error
                      5:  * an error message is copied to pathname and null pointer is returned.
                      6:  */
                      7: #include <sys/param.h>
                      8: #include <sys/stat.h>
                      9: #include <sys/dir.h>
                     10: 
                     11: #define CURDIR         "."
                     12: #define GETWDERR(s)    strcpy(pathname, (s));
                     13: #define PARENTDIR      ".."
                     14: #define PATHSEP                "/"
                     15: #define ROOTDIR                "/"
                     16: 
                     17: char *strcpy();
                     18: static int pathsize;                   /* pathname length */
                     19: 
                     20: char *
                     21: getwd(pathname)
                     22:        char *pathname;
                     23: {
                     24:        char pathbuf[MAXPATHLEN];               /* temporary pathname buffer */
                     25:        char *pnptr = &pathbuf[(sizeof pathbuf)-1]; /* pathname pointer */
                     26:        char *prepend();                /* prepend dirname to pathname */
                     27:        dev_t rdev;                     /* root device number */
                     28:        DIR *dirp;                      /* directory stream */
                     29:        ino_t rino;                     /* root inode number */
                     30:        struct direct *dir;             /* directory entry struct */
                     31:        struct stat d ,dd;              /* file status struct */
                     32: 
                     33:        pathsize = 0;
                     34:        *pnptr = '\0';
                     35:        stat(ROOTDIR, &d);
                     36:        rdev = d.st_dev;
                     37:        rino = d.st_ino;
                     38:        for (;;) {
                     39:                stat(CURDIR, &d);
                     40:                if (d.st_ino == rino && d.st_dev == rdev)
                     41:                        break;          /* reached root directory */
                     42:                if ((dirp = opendir(PARENTDIR)) == NULL) {
                     43:                        GETWDERR("getwd: can't open ..");
                     44:                        goto fail;
                     45:                }
                     46:                if (chdir(PARENTDIR) < 0) {
                     47:                        GETWDERR("getwd: can't chdir to ..");
                     48:                        goto fail;
                     49:                }
                     50:                fstat(dirp->dd_fd, &dd);
                     51:                if (d.st_dev == dd.st_dev) {
                     52:                        if (d.st_ino == dd.st_ino) {
                     53:                                /* reached root directory */
                     54:                                closedir(dirp);
                     55:                                break;
                     56:                        }
                     57:                        do {
                     58:                                if ((dir = readdir(dirp)) == NULL) {
                     59:                                        closedir(dirp);
                     60:                                        GETWDERR("getwd: read error in ..");
                     61:                                        goto fail;
                     62:                                }
                     63:                        } while (dir->d_ino != d.st_ino);
                     64:                } else
                     65:                        do {
                     66:                                if((dir = readdir(dirp)) == NULL) {
                     67:                                        closedir(dirp);
                     68:                                        GETWDERR("getwd: read error in ..");
                     69:                                        goto fail;
                     70:                                }
                     71:                                stat(dir->d_name, &dd);
                     72:                        } while(dd.st_ino != d.st_ino || dd.st_dev != d.st_dev);
                     73:                closedir(dirp);
                     74:                pnptr = prepend(PATHSEP, prepend(dir->d_name, pnptr));
                     75:        }
                     76:        if (*pnptr == '\0')             /* current dir == root dir */
                     77:                strcpy(pathname, ROOTDIR);
                     78:        else {
                     79:                strcpy(pathname, pnptr);
                     80:                if (chdir(pnptr) < 0) {
                     81:                        GETWDERR("getwd: can't change back to .");
                     82:                        return (NULL);
                     83:                }
                     84:        }
                     85:        return (pathname);
                     86: 
                     87: fail:
                     88:        chdir(prepend(CURDIR, pnptr));
                     89:        return (NULL);
                     90: }
                     91: 
                     92: /*
                     93:  * prepend() tacks a directory name onto the front of a pathname.
                     94:  */
                     95: static char *
                     96: prepend(dirname, pathname)
                     97:        register char *dirname;
                     98:        register char *pathname;
                     99: {
                    100:        register int i;                 /* directory name size counter */
                    101: 
                    102:        for (i = 0; *dirname != '\0'; i++, dirname++)
                    103:                continue;
                    104:        if ((pathsize += i) < MAXPATHLEN)
                    105:                while (i-- > 0)
                    106:                        *--pathname = *--dirname;
                    107:        return (pathname);
                    108: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.