2017-2018-1 20155302 《信息安全系统设计基础》第6周学习总结
2017-2018-1 20155302 《信息安全系统设计基础》第6周学习总结
第八章教材学习内容总结
异常的类别:中断,陷阱,故障,中止
中断:中断是异步发生的,是来自处理器外部的I/O设备的信号的结果.硬件中断的异常处理程序通常称为中断处理程序
陷阱的系统调用
陷阱是有意的异常,是执行一条指令的结果.陷阱最重要的用途是在用户程序和内核之间提供一个像过程一样的接口,叫做系统调用
请求服务:读文件(read),创建一个新的进程(fork),加载一个新的程序(execve),终止当前进程(exit)
进程
进程提供给程序的关键抽象:
一个独立的逻辑控制流,它提供一个假象,好象程序独占的使用处理器
一个私有的地址空间,它提供一个假象,好象程序独占的使用存储器系统
(1)逻辑控制流
如果想用调试器单步执行程序我们会看到一系列的程序计数器(PC)的值,这些值唯一的对应于包含在程序的可执行目标文件中的指令,或是包含在运行时动态链接到程序的共享对象中的指令
这个PC值得序列叫做逻辑控制流,简称逻辑流
(2)并发流
一个逻辑流的执行在时间上与另一个流重叠:并发流.并发的运行
多个流并发的执行的一般现象称为并发
一个进程和其他进程轮流运行的概念称为多任务
一个进程执行他的控制流的一部分的每一时间段叫作时间片
多任务也叫做时间分片
并行流是并发流的一个真子集,如果两个流并发的运行在不同的处理器核或者计算机上,那么我们称他们为并行流(并行的运行,并行的执行)
(3)私有地址空间
n位地址的机器:地址空间是2^n个可能地址的集合
一个进程为每个程序提供他自己的私有地址空间
私有:和这个空间中某个地址相关联的那个存储器字节是不能被其他进程读或写的
(4)用户模式和内核模式
运行应用程序代码的进程初始时是在用户模式中的。进程从用户模式变为内核模式的唯一方法是通过异常。
linux提供了/proc文件系统,它允许用户模式进程访问内核数据结构的内容。
(5)上下文切换
上下文切换:操作系统内核使用叫上下文切换的异常控制流来实现多任务。
上下文切换:a)保存当前进程的上下文;b)恢复某个先前被抢占的进程被保存的上下文; c)将控制传递给这个新恢复的进程
调度:内核中的调度器实现调度。
当内核代表用户执行上下文切换时,可能会发生上下文切换。如果系统调用发生阻塞,那么内核可以让当前进程休眠,切换到另一个进程,如read系统调用,或者sleep会显示地请求让调用进程休眠。一般,即使系统调用没有阻塞,内核亦可以决定上下文切换,而不是将控制返回给调用进程。
中断也可能引起上下文切换。如,定时器中断。
回收子进程
回收:当一个进程终止时,内核并不立即把它从系统中清除。相反,进程被保持在一种已终止的状态中,直到被它的父进程回收。
僵死进程:一个终止了但是还未被回收的进程称为僵死进程。
回收子进程的两种方法:1,内核的init进程 2,父进程waitpid函数
1)如果父进程没有回收它的僵死子进程就终止了,那么内核就会安排init进城来回收它们。init进程的PID为1,并且是在系统初始化时创建的。
2)一个进程可以通过调用waitpid函数来等待它的子进程终止或停止。
waitpid函数有点复杂,默认地(当options=0时),waitpid挂起调用进程的执行,知道它的等待集合中的一个子进程终止。
1.判定等待集合的成员
2.修改默认行为
3.检查已回收子进程的退出状态
4.错误条件
5.wait函数
6.使用waitpid的示例
信号
一种更高层次的软件形式的异常,称为unix信号,它允许进程中断其他进程。
低层的硬件异常是由内核异常处理程序处理的,正常情况下,对用户进程而言是不可见的。信号提供了一种机制,通知用户进程发生了这些异常。
信号处理问题
- 当一个程序要捕获多个信号时,一些细微的问题就产生了。
(1)待处理信号被阻塞。Unix信号处理程序通常会阻塞当前处理程序正在处理的类型的待处理信号。
(2)待处理信号不会排队等待。任意类型至多只有一个待处理信号。因此,如果有两个类型为K的信号传送到一个目的进程,而由于目的进程当前正在执行信号K的处理程序,所以信号K时阻塞的,那么第二和信号就简单地被简单的丢弃,他不会排队等待。
(3)系统调用可以被中断。像read、wait和accept这样的系统调用潜在地会阻塞进程一段较长的时间,称为慢速系统调用。在某些系统中,当处理程序捕获到一个信号时,被中断的慢速系统调用在信号处理程序返回时不再继续,而是立即返回给用户一个错误的条件,并将errno设置为EINTR。
- 不可以用信号来对其他进程中发生的事件计较。
可移植的信号处理
Signal包装函数设置的信号处理程序的信号处理语义:
(1)只有这个处理程序当前正在处理的那种类型的信号被阻塞
(2)和所有信号实现一样,信号不会排队等候
(3)只要有可能,被中断的系统调用会自动重启。
(4)一旦设置了信号处理程序,它就会一直保持,知道signal带着handler参数为SIG_IGN或者SIG_DFL被调用。
操作进程的工具
Linux系统提供了大量的监控和操作进程的有用工具:
- STRACE:打印一个正在运行的程序和它的子进程调用的每个系统调用的轨迹。对于好奇的的工具。用-StatiC编译你的程序,能传到一个更干净的、不带学生而言,这是一个令人着迷有大量与共享库相关的输出的轨迹。
- PS:列出当前系统中的进程(包括僵死进程)
- TOP:打印出关于当前进程资源使用的信息。
- PMAP:显示进程的存储器映射。proc:一个虚拟文件系统,以ASCII文本格式输出大量内核数数据结构的内容,用户程序可 cat 2 / proc / load avg” , 观察在Linux系统上的平均负载。
第十章 教材学习内容总结
1.打开和关闭文件
(1)进程是通过调用open函数来打开一个已存在的文件或者创建一个新文件的
include <sys/types.h>
include <sys/stat.h>
include <fcntl.h>
include <unistd.h>
(2)创建一个新文件,文件的拥有者有读写权限,而所有其他的用户都有读权限
umask(DEF_UMASK);
fg=Open("foo.txt",O_CREAT|O_TRUNC|O_WEONLY,DEF_MODE);
(3)通过调用close函数关闭一个打开的文件
int close(int fd);//返回值成功为0,出错为-1
2.读和写文件
(1)应用程序是通过分别调用read和write函数来执行输入和输出的
(2)read函数从描述符为fd的当前文件位置拷贝最多n个字节到存储器位置buf,返回值-1表示一个错误。而返回值0表示EOF。否则,返回值表示的是实际传送的字节数量
(3)write函数从存储器位置buf拷贝至多n个字节到描述符fd的当前文件位置
(4)通过调用lseek函数,应用程序能够显示地修改当前文件的位置
(5)在某些情况下,read和write传送的字节比应用程序要求的要少,这些不足值不表示有错误
①读时遇到EOF。假设我们读一个文件,该文件从当前文件位置开始只含有20多个字节,而我们以50个字节的片进行读取。这样一来,下一个read返回的不足值为20,此后的read将通过返回不足值0来发出EOF信号。
②从终端读文本行。如果打开文件是与终端相关联的(如键盘和显示器),那么每个read函数将以此传送一个文本行,返回的不足值等于文本行的大小。
③读和写网络套接字。如果打开的文件对应于网络套接字,那么内部缓冲约束和较长的网络延迟会引起read和write返回不足值。对Unix管道调用read和write时,也有可能出现不足值,这种进程间的通信机制不在我们讨论的范围之内。
实际上,除了EOF,在读磁盘文件时,将不会遇到不足值,而且在写磁盘文件时,也不会遇到不足值。如果想创建简装的诸如web服务器这样的网络应用,就必须通过反复调用read和write处理不足值,直到所有需要的字节都传送完毕。
3.读取文件元数据
(1)应用程序能够通过调用stat和fstat函数,检索到关于文件的信息(元数据)
(2)文件类型
①普通文件:二进制或文本数据,宏指令:S_ISREG()
②目录文件:包含其他文件的信息,宏指令:S_ISDIR()
③套接字:通过网络和其他进程通信的文件,宏指令:S_ISSOCK()
4.I/0重定向
(1)Unix外壳提供了I/O重定向操作符,允许用户将磁盘文件和标准输入输出联系起来
(2)重定向使用dup2函数
5.共享文件
* 内核用三个相关的数据结构来表示打开的文件
a.描述符表。表项是由进程打开的文件描述符来索引的。每个打开的描述符表项指向文件表中的一个表项。
b.文件表。每个文件表的表项组成包括由当前的文件位置、引用计数以及一个指向v-node表中对应表项的指针。关闭一个描述符会减少相应的文件表表项中的应用计数。内核不会删除这个文件表表项,直到它的引用计数为零。
c.v-node表。所有的进程共享这张v-node表,每个表项包含stat结构中的大多数信息,包括st_mode和st_size成员。
-
描述符1和4通过不同的打开文件表表项来引用两个不同的文件。
-
多个描述符也可以通过不同的文件表表项来应用同一个文件。
-
调用fork()之后
子进程有一个父进程描述符表的副本。父子进程共享相同的打开文件表集合,因此共享相同的文件位置。一个很重要的结果就是,在内核删除相应文件表表项之前,父子进程必须都关闭了他们的描述符。
教材学习中的问题和解决过程
问:仔细阅读课本第10章后遇到一个问题就是我该使用哪些i/o函数??
答:
- 尽量只使用标准I/O,而不要涉及低级的Unix I/O函数
- 建议在网络套接字上不要使用标准I/O函数来进行输入和输出。而要使用健壮的RIO函数。
- 标准I/O流,从某种意义上来说是全双工的,因为程序能够在同一个流上执行输入和输出。
代码调试中的问题和解决过程
fork()函数会第一次调用,返回两次,一次在父进程,一次在子进程。
返回值用来明确是在父进程还是在子进程中执行。
调用一次,返回两次。
但如果多个Fork函数存在时该如何执行呢?
代码托管
https://gitee.com/bestiisjava2017/yxc20155302/tree/master/src/信息安全系统设计基础20155302
其他(感悟、思考等,可选)
本章内容较多,且读起来叫枯燥,理解起来较为费力,代码部分更加明显。
学习进度条
代码行数(新增积) | 博客量(新增积) | 学习时间(新增积) | 重要成长 | |
---|---|---|---|---|
目标 | 5000行 | 30篇 | 400小时 | |
第一周 | 0/0 | 2/2 | 20/20 | |
第二周 | 0/0 | 2/4 | 18/38 | |
第三周 | 80/80 | 3/7 | 22/60 | |
第四周 | 180/260 | 2/9 | 30/90 | |
第五周 | 218/478 | 2/11 | 20/110 |
-
计划学习时间:XX小时
-
实际学习时间:XX小时
-
改进情况:
(有空多看看现代软件工程 课件
软件工程师能力自我评价表)