首页 > 系统 > Linux > 正文

Linux getcwd()的实现

2024-06-28 13:26:23
字体:
来源:转载
供稿:网友
linux getcwd()的实现

通过getcwd()可以获取当前工作目录。

1 #include <unistd.h>2 3 char *getcwd(char *cwdbuf, size_t size);

成功调用返回指向cwdbuf的指针,失败返回NULL。

getcwd()的实现是《Linux/Unix系统编程手册》的练习18.5,题目如下:

实现一个功能与getcwd()相当的函数。提示:要获取当前工作目录的名称,可调用opendir()和readdir()来遍历其父目录(..)中的各个条目,查找其中与当前工作目录具有相同i-node编号及设备号的一项。如此这般,沿着目录树层层拾级而上(chdir(..))并进行扫描,就能构建出完整的目录路径。当前目录与当前工作目录相同时,就结束遍历。无论调用该函数成功与否,都应将调用者遣回其起始目录(使用open()和fchdir()能方便地实现这一功能)

1、通过stat获取文件信息,根据文件信息中的i-node编号和设备号来找到正确的目录

2、运用opendir()、readdir()来获取目录的信息,目录不能通过read()来获取信息。

PS:tlpi_hdr.h头文件为《Linux/Unix系统编程手册》的头文件,可以去作者的网站下载,其中的errExit()为错误处理函数。。。。

  1 /*  2  * =====================================================================================  3  *  4  *       Filename:  18.5.c  5  *  6  *    Description:    7  *  8  *        Version:  1.0  9  *        Created:  2014年05月11日 14时04分35秒 10  *       Revision:  none 11  *       Compiler:  gcc 12  * 13  *         Author:  alan (), alan19920626@Gmail.com 14  *   Organization:   15  * 16  * ===================================================================================== 17  */ 18  19 #include <sys/stat.h> 20 #include <fcntl.h> 21 #include <dirent.h> 22 #include <sys/types.h> 23 #include "tlpi_hdr.h" 24  25 #define BUF_MAX 4096 26  27 extern int errno;  28  29 char *Getcwd(char *cwdbuf, size_t size){ 30     char path[BUF_MAX], cwd[BUF_MAX]; 31     DIR *dirp; 32     struct dirent *dp; 33     struct stat sb, sb_d, sb_1; 34     dev_t dev; 35     ino_t ino; 36  37     while(1){ 38         //获取当前目录的文件信息 39         if(stat(".", &sb) == -1) 40             errExit("stat"); 41         dev = sb.st_dev; 42         ino = sb.st_ino; 43  44         //获取父目录的对应的目录流和父目录的文件信息 45         if((dirp = opendir("..")) == NULL) 46             errExit("opendir"); 47         if(stat("..", &sb_1) == -1) 48             errExit("stat"); 49  50         //判断当前目录是否与父目录相同 51         if(sb_1.st_dev == dev && sb_1.st_ino == ino) 52             break; 53  54         errno = 0; 55          56         //在父目录对应的目录流读取条目 57         while((dp = readdir(dirp)) != NULL){ 58             snPRintf(path, BUF_MAX, "../%s", dp->d_name); 59  60             if(stat(path, &sb_d) == -1) 61                 errExit("stat"); 62  63             //得到当前目录对应的条目并将目录逐渐完善 64             if(dev == sb_d.st_dev && ino == sb_d.st_ino){ 65                 memset(cwd, 0, sizeof(cwd)); 66                 if(strcat(cwd, "/") == NULL) 67                     errExit("strcat"); 68                 if(strcat(cwd, dp->d_name) == NULL) 69                     errExit("strcat"); 70                 if(strcat(cwd, cwdbuf) == NULL) 71                     errExit("strcat"); 72  73                 if(strncpy(cwdbuf, cwd, BUF_MAX) == NULL) 74                     errExit("strncpy"); 75                 break; 76             } 77              78         } 79  80         if(dp == NULL && errno != 0) 81             errExit("readdir"); 82  83         closedir(dirp); 84         chdir("..");      //改变当前目录 85     } 86  87     return cwdbuf; 88 } 89  90 int main(int argc, char *argv[]){ 91     char buf[BUF_MAX]; 92     char t_buf[BUF_MAX]; 93     char *p; 94     int fd; 95  96     if((fd = open(".", O_RDONLY)) == -1) 97         errExit("open"); 98  99     if(argc != 1)100         usageErr("%s", argv[0]);101 102     p = Getcwd(buf, BUF_MAX);103     if(p == NULL)104         errExit("My getcwd");105     printf("My getcwd: %s/n", p);106     fchdir(fd);    //遣回最初的目录107 108     p = getcwd(t_buf, BUF_MAX);109     if(p == NULL)110         errExit("getcwd");111     printf("getcwd: %s/n", p);112 113     exit(EXIT_SUCCESS);114 }

测试结果:

lancelot@debian:~/Code/tlpi$ pwd/home/lancelot/Code/tlpilancelot@debian:~/Code/tlpi$ ./18.5 My getcwd: /home/lancelot/Code/tlpigetcwd: /home/lancelot/Code/tlpi

吐槽&收获:本来打算慢慢通过写学习记录,但是觉得学习很多只是通过把一些重点写出来和一些习题,所以打算放一放,有空再写。重点什么的还要慢慢总结。先把一些习题做了,顺便结合之前学得系统调用和库函数做一些实际的东西先。。。。。。一个下午做这么一条题。。。真心弱菜,不过做出来真得很开心。。。。。还有慢慢长路要走!!!继续努力!!!


发表评论 共有条评论
用户名: 密码:
验证码: 匿名发表