stat函数与lstat函数的区别

概述

最近在深入学习Unix/Linux系统编程,发现stat与lstat函数的参数一样,所以决定研究下,发现二者的区别.

int stat(const char *pathname, struct stat *statbuf);
int lstat(const char *pathname, struct stat *statbuf);

论证

写一个测试文件test.c,用ls -l命令查看详细情况.

haha@hello:~/my-code$ ls -l test.c 
-rw-r--r-- 1 haha haha 528528 Jul  1 09:47 test.c

然后创建一个软链接

ln -s ~/my-code/test.c test.soft

注:软链接相当于Windows系统的快捷方式,创建软链接的时候最好用绝对路径.

然后查看test.c和test.soft

haha@hello:~/my-code$ ls -l test.c test.soft
-rw-r--r-- 1 haha haha 528528 Jul  1 09:47 test.c
lrwxrwxrwx 1 haha haha     25 Jul  1 09:55 test.soft -> /home/haha/my-code/test.c

分别写两个程序去发现stat和lstat函数的不同.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
// a file named stat.c

#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>

int main(int argc, char *argv[])
{
if(argc < 2){
fprintf(stderr,"Usage: %s filename\n",argv[1]);
exit(1);
}
struct stat info;
int ret = stat(argv[1], &info);
if(ret == -1){
perror("stat");
exit(1);
}

// get file size
int size = (int)info.st_size;
printf("file size = %d\n",size);
return 0;
}

然后编译并运行:

haha@hello:~/my-code$ gcc -g -o stat stat.c
haha@hello:~/my-code$ ./stat test.c
file size = 528528
haha@hello:~/my-code$ ./stat test.soft
file size = 528528

从上面输出可以看出软链接test.soft和原文件test.c大小相等,都是528528字节.

然后新建一个lstat.c文件

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>

int main(int argc, char *argv[])
{
if(argc < 2){
fprintf(stderr,"Usage: %s filename\n",argv[1]);
exit(1);
}
struct stat info;
int ret = lstat(argv[1], &info); // only the point that different from stat.c
if(ret == -1){
perror("stat");
exit(1);
}

// get file size
int size = (int)info.st_size;
printf("file size = %d\n",size);
return 0;
}

然后编译并运行:

haha@hello:~/my-code$ gcc -g -o lstat lstat.c
haha@hello:~/my-code$ ./lstat test.c
file size = 528528
haha@hello:~/my-code$ ./lstat test.soft
file size = 25

从上面输出可以看出软链接test.soft和原文件test.c大小不相等.

所以不同点在于用两个程序查看test.c的软链接文件大小不想等,lstat只是计算软链接的大小,而stat是计算软链接映射的原文件大小.

结论

stat函数一般称作穿透(追踪)函数,当然是相对于软链接来说的.
lstat函数一般般称作不穿透(追踪)函数,也是相对于软链接来说的.