我正在为我的求职面试复习一些内容,在这个问题上,它询问了这个程序使用了多少inode,打开文件表条目和文件描述符?你能帮帮我吗?
#include <stdio.h>
#include <unistd.h>
#include <fcntl.h>
int main(int argc, char* argv[]){
char buffer[3] = "ab";
int r = open("new.txt", O_RDONLY);
int r1, r2, pid;
r1 = dup(r);
read(r, buffer, 1);
if((pid=fork())==0) {
r1 = open("new.txt", O_RDONLY);
} else{
waitpid(pid, NULL, 0);
}
read(r1, buffer+1, 1);
printf("%s", buffer);
return 0;
}
答案 0 :(得分:6)
#include <stdio.h>
#include <unistd.h>
#include <fcntl.h>
#include <unistd.h>
int main(int argc, char* argv[]){
char buffer[3] = "ab";
int r = open("new.txt", O_RDONLY);
int r1, r2, pid;
r1 = dup(r);
read(r, buffer, 1);
if((pid=fork())==0) {
r1 = open("new.txt", O_RDONLY);
while (1)
{
sleep(1);
}
} else{
waitpid(pid, NULL, 0);
while (1)
{
sleep(1);
}
}
read(r1, buffer+1, 1);
printf("%s", buffer);
return 0;
}
wutiejun@linux-00343520:~/Temp> gcc -o test main.c
wutiejun@linux-00343520:~/Temp> ./test &
[1] 10404
wutiejun@linux-00343520:~/Temp> ls -l /proc/10404/fd
Total 0
lrwx------ 1 wutiejun users 64 June 9 16:33 0 -> /dev/pts/0
lrwx------ 1 wutiejun users 64 June 9 16:33 1 -> /dev/pts/0
lrwx------ 1 wutiejun users 64 June 9 16:33 2 -> /dev/pts/0
l-wx------ 1 wutiejun users 64 June 9 16:33 3 -> /home/wutiejun/Temp/new.txt
l-wx------ 1 wutiejun users 64 June 9 16:33 4 -> /home/wutiejun/Temp/new.txt
wutiejun@linux-00343520:~/Temp> ps -a
PID TTY TIME CMD
10404 pts/0 00:00:00 test
10405 pts/0 00:00:00 test
10417 pts/0 00:00:00 ps
wutiejun@linux-00343520:~/Temp> ls -l /proc/10405/fd
Total 0
lrwx------ 1 wutiejun users 64 June 9 16:34 0 -> /dev/pts/0
lrwx------ 1 wutiejun users 64 June 9 16:34 1 -> /dev/pts/0
lrwx------ 1 wutiejun users 64 June 9 16:33 2 -> /dev/pts/0
lr-x------ 1 wutiejun users 64 June 9 16:34 3 -> /home/wutiejun/Temp/new.txt
lr-x------ 1 wutiejun users 64 June 9 16:34 4 -> /home/wutiejun/Temp/new.txt
lr-x------ 1 wutiejun users 64 June 9 16:33 5 -> /home/wutiejun/Temp/new.txt
wutiejun@linux-00343520:~/Temp>
因此,您可以计算打开的文件。 我不确定inode数字,我认为这取决于不同的文件系统。
答案 1 :(得分:3)
我们必须在这里做一些假设。
假设1:我们运行的系统中所有文件系统都使用inode(它只是数据结构的名称。几十年来,Inode并未作为流程的抽象公开)。 “inode数量”问题的一个完全有效的答案可能是:0因为我在NFS上运行。如果使用的术语是“vnode”,我会更舒服,因为即使它也是一个特定于系统的术语,它实际上在比“inode”更多的系统中更有意义。
假设2:程序以stdin / stderr / stdout打开并指向相同的文件描述开始。
假设3:stdin&amp; co是来自/ dev
的pty假设4:/ dev是一个普通的目录,就像在经典的unix中一样,而不像linux那样它是一个devfs。此外,pty作为普通文件打开,就像90年代早期一样,而不是通过某种克隆机制。
假设5:“new.txt”存在且可供此过程访问。
假设6:“文件表条目”实际上是指file description。
假设7:程序没有动态链接。这是因为在程序到达main
之前,动态链接器可能已经打开了任意大量的文件。
假设8:libc中的stdio在实际需要之前不会打开各种语言环境和数据库。
假设9:可能失败的事情(fork
,open
,dup
),不会。
假设10:pid_t
适合int
。
让我们看看会发生什么(跳过的行与问题无关)。
int main(int argc, char* argv[]){
此时我们有三个打开的文件描述符。与假设一样,这些文件描述符指向来自文件系统上相同文件的相同文件描述。
得分(描述符,描述,索引节点):3,1,1
int r = open("new.txt", O_RDONLY);
我们成功打开了一个文件。
得分:4,2,2
r1 = dup(r);
我们成功复制了文件描述符。 dup
:d文件描述符指向与原始描述符相同的文件描述。
得分:5,2,2
if((pid=fork())==0) {
Fork复制文件描述符表,但描述符仍然指向相同的描述。
得分:10,2,2
r1 = open("new.txt", O_RDONLY);
这将创建一个新的文件描述,指向与我们已经打开的相同的inode。
得分:11,3,2
} else {
waitpid(pid, NULL, 0);
}
让我们假设子进程已经成功退出,尽管它是以非常不干净的方式进行的(fork
ed孩子应该通过_exit
退出,而不是从main
返回,但我们'这次让它滑动)。子进程关闭所有描述符,这也会导致一个描述被关闭,因为它只有一个引用。
得分:5,2,2
答案:鉴于所有假设,峰值为11个文件描述符,3个文件描述(如果我们坚持使用古老的术语,则为“文件表条目”),2个inode。
备选答案:11,2 + X,1 + Y,其中X是stdin / out / err使用的描述数,Y对于inode数量是相同的。