LinuxSir.cn,穿越时空的Linuxsir!

 找回密码
 注册
搜索
热搜: shell linux mysql
查看: 2184|回复: 15

stat函数的奇怪问题

[复制链接]
发表于 2004-8-29 23:40:55 | 显示全部楼层 |阅读模式
我按照精华贴里的教程一步步学c编程,看到“文件”一篇时,有这样一个例子:
#include<stdio.h>
#include<fcntl.h>
#include<sys/stat.h>
#include<sys/types.h>
#include<sys/errno.h>
#include<dirent.h>
#include<unistd.h>

static int get_file_size_time(const char *filename)
{
        struct stat statbuf;

        if(stat(filename,&statbuf)==-1)
        {
                printf("Get stat on %s Error:%s\n",filename,strerror(errno));
                return(-1);
        }

        if(S_ISDIR(statbuf.st_mode)) return(1);
        if(S_ISREG(statbuf.st_mode))
        printf("%s size:%ld bytes\tmodified at %s",filename,statbuf.st_size,ctime(&statbuf.st_mtime));

        return(0);
}

int main(int argc,char **argv)
{
        DIR *dirp;
        struct dirent *direntp;
        int stats;

        if(argc!=2)
        {
                printf("Usage:%s filename\n\a",argv[0]);
                exit(1);
        }

        if(((stats=get_file_size_time(argv[1]))==0)||(stats==-1)) exit(1);

        if((dirp=opendir(argv[1]))==NULL)
        {
                printf("Open Directory %s Error:%s\n",argv[1],strerror(errno));
                exit(1);
        }

        while((direntp=readdir(dirp))!=NULL)
        {
               
                get_file_size_time(direntp->d_name); //A           

        }
        closedir(dirp);
       
        exit(1);
}

这个程序有一个参数.如果这个参数是一个文件名,我们输出这个文件的大小和最后修改的时间,如果是一个目录我们输出这个目录下所有文件的大小和修改时间.
当我运行程序并输入一个目录名时,它总是显示no such file or directory.
但是如果我把A行住掉,换成:
                struct stat statbuf;
                stat(direntp->d_name,&statbuf);
                printf("%s size:%ld bytes\tmodified at %s",direntp->d_name,statbuf.st_size,ctime(&statbuf.st_mtime));

也就是把get_file_size_time函数里的一部分拿出来,这样的话就正常了,我百思不得其解,为什么之前向get_file_size_time函数传参数的时候就会出错呢?请各位大虾指教阿!!
发表于 2004-8-30 03:57:48 | 显示全部楼层
 楼主| 发表于 2004-8-30 10:58:41 | 显示全部楼层

  1. #include<stdio.h>
  2. #include<fcntl.h>
  3. #include<sys/stat.h>
  4. #include<sys/types.h>
  5. #include<sys/errno.h>
  6. #include<dirent.h>
  7. #include<unistd.h>

  8. static int get_file_size_time(const char *filename)
  9. {
  10. struct stat statbuf;

  11. if(stat(filename,&statbuf)==-1)
  12. {
  13. printf("Get stat on %s Errors\n",filename,strerror(errno));
  14. return(-1);
  15. }

  16. if(S_ISDIR(statbuf.st_mode)) return(1);
  17. if(S_ISREG(statbuf.st_mode))
  18. printf("%s sizeld bytes\tmodified at %s",filename,statbuf.st_size,ctime(&statbuf.st_mtime));

  19. return(0);
  20. }

  21. int main(int argc,char **argv)
  22. {
  23. DIR *dirp;
  24. struct dirent *direntp;
  25. int stats;

  26. if(argc!=2)
  27. {
  28. printf("Usages filename\n\a",argv[0]);
  29. exit(1);
  30. }

  31. if(((stats=get_file_size_time(argv[1]))==0)||(stats==-1)) exit(1);

  32. if((dirp=opendir(argv[1]))==NULL)
  33. {
  34. printf("Open Directory %s Errors\n",argv[1],strerror(errno));
  35. exit(1);
  36. }

  37. while((direntp=readdir(dirp))!=NULL)
  38. {

  39. get_file_size_time(direntp->d_name); //A

  40. }
  41. closedir(dirp);

  42. exit(1);
  43. }
复制代码

楼上的是要我把代码重贴一遍吗?
 楼主| 发表于 2004-8-30 16:24:40 | 显示全部楼层
我感觉问题是direntp->d_name没有包含路径,所以stat函数执行失败,有没有什么办法让返回的文件名也含有绝对路径呢?
发表于 2004-8-30 19:55:59 | 显示全部楼层
是不是用户没有权限访问该目录,linux下随时注意权限。
 楼主| 发表于 2004-9-1 10:39:19 | 显示全部楼层
应该不是,
程序是在user下编译链接的,我运行的时候输入main temp
temp是user下创立的一个目录,里面有两个文件file1和file2,也都是属于user用户。
 楼主| 发表于 2004-9-1 10:41:30 | 显示全部楼层
如果我把A行住掉,换成:

  1. struct stat statbuf;
  2. stat(direntp->d_name,&statbuf);
  3. printf("%s sizeld bytes\tmodified at %s",direntp-d_name,statbuf.st_size,ctime(&statbuf.st_mtime));
复制代码

也还是不行,stat的返回值仍为-1
让程序读入文件可以,读入目录就不行
发表于 2004-9-1 12:00:00 | 显示全部楼层
呵呵,看看你传到get_file_size_time里面的那个direntp->d_name,当你查询目录时,那个保存的是相对你要查询的目录的相对路径,但是程序运行时候的路径不是那个,当然会找不到了。例如你在/root/下面运行程序(可执行文件假定名叫stat)stat /tmp,这个时候tmp下面有个目录a,那么direntp->d_name保存的是a,可是现在是在/root/下执行的,程序就会相对于/root/去找a,也就是找/root/a,这个情况很少会被满足吧,于是当然就会说找不到了。改也很容易,把*argv[1]和direntp->d_name合起来传给get_file_size_time就行了。不过这个时候记得先看*argv[1]最后是不是\,不是的话要加上,否则还是会错的。
 楼主| 发表于 2004-9-2 18:25:27 | 显示全部楼层
多谢指教!
不过我还是不清楚该怎么把*argv[1]和direntp->d_name合起来传给get_file_size_time,
直接写get_file_size_time(argv[1]\direntp->d_name);
会报"\"错误
发表于 2004-9-2 20:01:46 | 显示全部楼层
strcat或者sprintf
您需要登录后才可以回帖 登录 | 注册

本版积分规则

快速回复 返回顶部 返回列表