12346Seric /* 2*6635Ssam * SCCSID(@(#)curdir.c 4.4); 3*6635Ssam */ 4*6635Ssam #include <sys/param.h> 5*6635Ssam #include <sys/stat.h> 6*6635Ssam #include <sys/dir.h> 72346Seric 8*6635Ssam #define dot "." 9*6635Ssam #define dotdot ".." 102346Seric 11*6635Ssam static char *name; 122346Seric 13*6635Ssam static int off = -1; 14*6635Ssam static struct stat d, dd; 15*6635Ssam static struct direct *dir; 16*6635Ssam static DIR *dirp; 17*6635Ssam static int cat(), prexit(); 182346Seric 19*6635Ssam char * 20*6635Ssam curdir(np) 21*6635Ssam char *np; 22*6635Ssam { 23*6635Ssam int rdev, rino; 242346Seric 25*6635Ssam *np++ = '/'; 26*6635Ssam name = np; 27*6635Ssam stat("/", &d); 28*6635Ssam rdev = d.st_dev; 29*6635Ssam rino = d.st_ino; 30*6635Ssam for (;;) { 31*6635Ssam stat(dot, &d); 32*6635Ssam if (d.st_ino==rino && d.st_dev==rdev) 33*6635Ssam goto done; 34*6635Ssam if ((dirp = opendir(dotdot)) == 0) 35*6635Ssam prexit("curdir: cannot open ..\n"); 36*6635Ssam fstat(dirp->dd_fd, &dd); 37*6635Ssam chdir(dotdot); 38*6635Ssam if(d.st_dev == dd.st_dev) { 39*6635Ssam if(d.st_ino == dd.st_ino) 40*6635Ssam goto done; 41*6635Ssam do 42*6635Ssam if ((dir = readdir(dirp)) == 0) 43*6635Ssam prexit("curdir: read error in ..\n"); 44*6635Ssam while (dir->d_ino != d.st_ino); 45*6635Ssam } else 46*6635Ssam do { 47*6635Ssam if ((dir = readdir(dirp)) == 0) 48*6635Ssam prexit("curdir: read error in ..\n"); 49*6635Ssam stat(dir->d_name, &dd); 50*6635Ssam } while(dd.st_ino != d.st_ino || dd.st_dev != d.st_dev); 51*6635Ssam closedir(dirp); 52*6635Ssam cat(); 53*6635Ssam } 54*6635Ssam done: 55*6635Ssam name--; 56*6635Ssam if (chdir(name) < 0) { 57*6635Ssam write(2, name, strlen(name)); 58*6635Ssam prexit(": can't change back\n"); 59*6635Ssam } 60*6635Ssam return (0); 61*6635Ssam } 622346Seric 63*6635Ssam static 64*6635Ssam cat() 652346Seric { 66*6635Ssam register i, j; 672346Seric 68*6635Ssam i = dir->d_namlen; 69*6635Ssam if ((off+i+2) > 1024-1) 70*6635Ssam return; 71*6635Ssam for(j=off+1; j>=0; --j) 72*6635Ssam name[j+i+1] = name[j]; 73*6635Ssam if (off >= 0) 74*6635Ssam name[i] = '/'; 75*6635Ssam off += i+1; 76*6635Ssam name[off] = 0; 77*6635Ssam for(--i; i>=0; --i) 78*6635Ssam name[i] = dir->d_name[i]; 792346Seric } 802346Seric 81*6635Ssam static 82*6635Ssam prexit(cp) 83*6635Ssam char *cp; 842346Seric { 85*6635Ssam write(2, cp, strlen(cp)); 86*6635Ssam exit(1); 872346Seric } 88