这次回顾第10章习题。

电子书地址:

http://eol.bnuz.edu.cn/meol/common/script/preview/download_preview.jsp?fileid=2169600&resid=242120&lid=28605

参考资料:

https://dreamanddead.github.io/CSAPP-3e-Solutions/chapter10/

10.6

#include "csapp.h"

int main()
{
    int fd1,fd2;
    
    fd1 = Open("foo.txt",O_RDONLY, 0);
    fd2 = Open("bar.txt", O_RDONLY, 0);
    Close(fd2);
    fd2 = Open("baz.txt", O_RDONLY, 0);
    printf("fd2 = %d\n", fd2);
    exit(0);
}

输出结果为:

fd2 = 4

测试:

gcc -o 10.6 10.6.c -lpthread

$ ./10.6
fd2 = 4

10.7

代码:

/* $begin cpfile */
#include "csapp.h"

int main(int argc, char **argv) 
{
    int n;
    rio_t rio;
    char buf[MAXLINE];

    Rio_readinitb(&rio, STDIN_FILENO);
    // 5 for test
    while((n = Rio_readnb(&rio, buf, 5)) != 0) {
        Rio_writen(STDOUT_FILENO, buf, n);
    }

    exit(0);
}
/* $end cpfile */

验证:

gcc -o 10.7 10.7.c -lpthread

$ ./10.7
abcdefge
abcde
fge

10.8

代码:

/* $begin statcheck */
#include "csapp.h"

int main (int argc, char **argv) 
{
    struct stat stat;
    char *type, *readok;

    /* $end statcheck */
    if (argc != 2) {
        fprintf(stderr, "usage: %s <filename>\n", argv[0]);
        exit(0);
    }

    // get fd
    int fd;
    sscanf(argv[1], "%d", &fd);
    /* $begin statcheck */
    Fstat(fd, &stat);
    if (S_ISREG(stat.st_mode))     /* Determine file type */
	type = "regular";
    else if (S_ISDIR(stat.st_mode))
	type = "directory";
    else 
	type = "other";
    if ((stat.st_mode & S_IRUSR)) /* Check read access */
	readok = "yes";
    else
	readok = "no";

    printf("type: %s, read: %s\n", type, readok);
    exit(0);
}
/* $end statcheck */

验证:

gcc -o 10.8 10.8.c -lpthread

$ ./10.8 0
type: other, read: yes
$ ./10.8 1
type: other, read: yes
$ ./10.8 2
type: other, read: yes
$ ./10.8 3
Fstat error: Bad file descriptor

10.9

参考资料:

https://dreamanddead.github.io/CSAPP-3e-Solutions/chapter10/10.9/

需要将文件描述符3重定向到标准输入0即可:

if (Fork() == 0) {/*child */
	/* What code is the shell executing right here? */
    dup2(0, 3);
	Execve("fstatcheck",argv, envp);
}

10.10

代码:

/* $begin cpfile */
#include "csapp.h"

int main(int argc, char **argv) 
{
    int n;
    rio_t rio;
    char buf[MAXLINE];
    if (argc == 2) {
        int l = strlen(argv[1]);
        Rio_writen(STDOUT_FILENO, argv[1], l);
    }

    Rio_readinitb(&rio, STDIN_FILENO);
    while((n = Rio_readlineb(&rio, buf, MAXLINE)) != 0) {
        Rio_writen(STDOUT_FILENO, buf, n);
    }

    exit(0);
}
/* $end cpfile */

验证:

gcc -o 10.10 10.10.c -lpthread