apue对应源码和环境配置参考这两篇文章:
https://www.jianshu.com/p/dd734b0e8cb9
https://blog.csdn.net/qq_29116917/article/details/103786194
不过进入home目录以后,每次运行命令都要加sudo前缀,解决的办法是:
1.sudo passwd 重置root密码 //因为ubuntu的root默认是随机密码
2. su root 以root身份运行终端
第一章
登录名:一般在/etc/passwd里面
关于dirent,文件夹包括/usr/include/dirent.h和/usr/include/x86_64-linux-gnu/bits/dirent.h
可以通过 getpid来获得进程的id
进程控制有三种主要的函数: fork exec(有7种变体)和waitpid
who 显示当前用户
pwd 显示当前目录全路径名
ctrl + D 默认文件结束符,用来结束输入
线程也有线程id,不过线程id只在其所属的进程中起作用
< 作为重定向输入,比如 ./a.out < inputfile 就是把inputfile作为输入,执行a.out
> 这个重定向输出,不讲了(有点奇怪,重定向和管道的区别是啥,可以和管道一起使用,比如 program1 < inputfile | prog2 | prog3 > outputfile )
error的两种输出方式:
perror
stderror
用户标识
用户id, 一个整数,root用户的值为0
组id,用来给用户分组,同组的用户可以共享资源,比如文件
组文件通常是/etc/group
可以通过getuid和getgid来获得用户id,以及组id
库函数和系统调用区别
malloc是库函数,系统调用是sbrk,系统调用在内核态,库函数在用户态
库函数比较复杂,系统调用功能比较简单
awk的用法, 2.5.4
3.2 文件描述符
变化范围为0~OPEN_MAX-1,OPEN_MAX为允许打开的最大文件数,比如20个
3.3 open和openat
oflag由 O_RDONLY, O_EXEC等值进行或运算得到, 看到了61页,3种可能性
函数 open ,openat
两者比较大的区别就是,open只以绝对路径打开文件,而openat可以以相对路径打开文件
函数create
creat和open的区别就是,creat只能写文件,open可读可写
off_t lseek(int fd, off_t offset, int whence), 为打开的文件显式设置偏移量。
whence有三种可能SEEK_SET(0 绝对偏移量),SEEK_CUR(1 相当于当前位置的偏移量), SEEK_END(相对文件尾端的偏移量)
针对下面的文件,通过 gcc编译以后得到a.out文件
#include "apue.h"
int main(void)
{
if(lseek(STDIN_FILENO, 0, SEEK_CUR) == -1)
printf("cannot seek\n");
else
printf("seek OK\n");
exit(0);
}
然后执行命令,这个命令分为两部分,./ 代表执行命令,a.out代表执行文件
./a.out
结果如下:
seek OK,是指可以读到文件,因为/etc/passwd就是一个文件,
cannot seek,是指读不到,因为a.out没有接收到文件输入,或者文件不存在
看到空洞文件,就没看了,不想看
3.7 函数read
read(int fd, void* buf, unsigned nbytes) 返回读到的字节数
3.8 函数wirte
read(int fd, void* buf, unsigned nbytes) 返回已写的字节数
3.9 I/O 的效率
没啥好说的,就是测试了不同size的缓冲区,I/O效率咋样
3.10 文件共享
文件的结构图如下,不过需要的是,linux没有将数据结构分为i节点和v节点,而是采用了一个与文件系统相关的i节点,和一个与文件系统无关的i节点
具体信息,可以参考xv6的简单操作系统,进程表项中有一个file数组:
struct proc {
struct spinlock lock;
// p->lock must be held when using these:
enum procstate state; // Process state
struct proc *parent; // Parent process
void *chan; // If non-zero, sleeping on chan
int killed; // If non-zero, have been killed
int xstate; // Exit status to be returned to parent's wait
int pid; // Process ID
// these are private to the process, so p->lock need not be held.
uint64 kstack; // Virtual address of kernel stack
uint64 sz; // Size of process memory (bytes)
pagetable_t pagetable; // User page table
struct trapframe *trapframe; // data page for trampoline.S
struct context context; // swtch() here to run process
struct file *ofile[NOFILE]; // Open files 文件数组
struct inode *cwd; // Current directory
char name[16]; // Process name (debugging)
void (*handler)();
int spend;
int interval;
struct trapframe *trapframeSave;
int waitReturn;
};
file对应的结构如下:
struct file {
enum { FD_NONE, FD_PIPE, FD_INODE, FD_DEVICE } type;
int ref; // reference count
char readable;
char writable;
struct pipe *pipe; // FD_PIPE
struct inode *ip; // FD_INODE and FD_DEVICE
uint off; // FD_INODE
short major; // FD_DEVICE
};
#define major(dev) ((dev) >> 16 & 0xFFFF)
#define minor(dev) ((dev) & 0xFFFF)
#define mkdev(m,n) ((uint)((m)<<16| (n)))
// in-memory copy of an inode
struct inode {
uint dev; // Device number
uint inum; // Inode number
int ref; // Reference count
struct sleeplock lock; // protects everything below here
int valid; // inode has been read from disk?
short type; // copy of disk inode
short major;
short minor;
short nlink;
uint size;
uint addrs[NDIRECT+1];
};
3.11 原子操作
不看了
太无聊了 靠,,,,,!~!!!!!!
194