zoukankan      html  css  js  c++  java
  • 课程学习总结报告

    要求:

    请您根据本课程所学内容总结梳理出一个精简的Linux系统概念模型,最大程度统摄整顿本课程及相关的知识信息,模型应该是逻辑上可以运转的、自洽的,并举例某一两个具体例子(比如读写文件、分配内存、使用I/O驱动某个硬件等)纳入模型中验证模型。

    谈谈您对课程的心得体会,改进建议等。

    根据课程顺序,把学习内容主要分为以下几个大块:

    一. 系统调用和堆栈框架

    · 为了屏蔽硬件操作的细节,增强系统的安全性,增强用户程序的可移植性,Linux操纵系统划分了用户态和内核态,对应的内存空间被划分成用户空间和内核空间。内核态的权限高于用户态,即内核态下,cs:ip可以指向任意位置,而用户态下,cs:ip的活动范围只能是自己的空间。为了使用户调用操作系统底层服务,如中断,时钟,异常等,需要采取一种机制,就是系统调用。

    从软件的角度看,通过int 0x80指令或者syscall指令可以触发系统调用。首先,当linux进入内核态时,先保存此时的上下文环境,如果是硬件中断触发的系统调用,保存的是中断上下文,如果是用户程序触发的系统调用,保存用户进程上下文。所谓的上下文是内核保存的,用于系统调用返回的参数信息然后,通过系统调用号,找到对应的系统调用处理函数的首地址,建立函数堆栈,修改cs:ip的值并执行处理函数。处理函数执行完毕后,根据保存的上下文信息恢复现场返回用户态。

    · 堆栈是C语言程序运行时必须的一个记录调用路径和参数的空间, 在这个堆栈上保存了函数调用框架, 传递的参数, 保存的返回地址, 函数内部 的局部变量等等参数。一个函数调用动作是通过call指令来完成的。

    一个完成的函数调用过程大致可以用下图表示:即call target,进入target,退出target。

    二. 进程管理

    概念:进程是Linux进行资源分配和调度的基本单位,进程也被看做是程序的一次执行过程,当持久化在磁盘上的二进制代码被载入内存时,Linux操作系统为其分配了用户栈和内核栈,同时使用task_struct这种数据结构对进程进行描述,task_struct是Linux操作系统感知进程存在的数据结构,具体描述了进程号,进程状态,进程的调度策略和调度信息,进程打开文件表,进程链表,父子进程的关系等信息。Linux根据这个数据结构找到进程对应的用户栈和内核栈,并根据cs,ip,ss,sp,ebp等寄存器信息,执行这个进程。

    状态切换

    上下文切换:期间涉及到prev进程上下文的保存,以及next进程上下文的加载,如图所示:

    具体的还牵扯到了进程的内核态和用户态堆栈。

    进程调度:有了进程的概念,Linux就可以执行磁盘中持久化的二进制代码了。为了提高cpu利用率,提高计算机的并发性,引入了进程的调度这个概念,这相当于Linux虚拟化了多个“平行空间”,每个进程都有自己独立的用户栈和内核栈,Linux内核根据调度策略,在一定的时机对进程进行调度。

    进程调度时机包括:时间片用完,中断返回,进程状态发生变化,系统调用返回等。

    至于调度策略,Linux系统采用优先级调度的策略,又分成实时进程和非实时进程,实时进程指需要及时处理的进程,优先级范围是0~99100~139是非实进程的优先级范围。实时进程的优先级高于非实时进程。同一优先级对列按FIFO或者RR(时间片轮转)进行调度。

    三. 中断

    中断最初⽤于避免CPU轮询I/O设备,就绪状态发⽣时让I/O设备主动通过中断信号通知CPU,大大提⾼了CPU在输⼊输出上的⼯作效率,这就是硬件中断(外部中断)。后来随着中断适⽤范围扩⼤,比如解决机器运⾏过程出现的异常情况以及系统调⽤的实现等,这就产⽣了软件中断(内部中断),也称为异常,软件中断⼜分为故障(fault)和陷阱(trap)。

    简而言之,在没有中断机制之前,计算机只能⼀个程序⼀个程序地执⾏,也就是批处理,而无法多个程序并发⼯作。有了中断机制,CPU帮我们做了⼀件事情,就是当⼀个中断信号发⽣时,CPU把当前正在执⾏的进程X的CS:RIP寄存器和RSP寄存器等都压栈到了⼀个叫内核堆栈的地⽅,然后把CS:RIP指向⼀个中断处理程序的入口,做保存现场的⼯作,然后去执⾏其他进程⽐如Y,等重新回来时再恢复现场,即恢复CS:RIP寄存器和RSP寄存器等到CPU上继续执⾏原进程X。显然中断机制在计算机系统中发挥着关键作⽤。

    经过上述的硬件级处理过后, 内核态的堆栈会发生变化, 但是由用户态进入中断和由内核态进入中断又不太一样,由上图的特权级是否变化即可看出,具体在堆栈中则有以下区别:

    可以看到内核态进入中断,需要额外保存用户态的上下文信息,以便从内核态变成用户态时继续执行。

    四. 文件管理

    Linux支持多种文件系统,包括ext2、ext3、vfat等等。

    Linux采用虚拟文件系统VFS来达到支持多种文件系统格式的目标。VFS为各类文件系统提供一个统一的操作界面和编程接口。向上提供统一的编程接口,向下对各种文件系统进行兼容。

    文件系统的结构包括在磁盘上的结构和在内存中的结构。磁盘上包括引导控制块、盘控制块、目录结构、FCB。在内存中包括:

    • 系统打开文件表:包含每个已打开文件的FCB的副本,以及其他信息。
    • 进程打开文件表:包含一个指向系统打开文件表相应项的指针,以及其他信息。

    file结构一方面可从f_dentry链接到目录项模块以及inode模块,获取所有和文件相关的信息,另一方面链接file_operations子模块,其中包含所有可以使用的系统调用函数,从而最终完成对文件的操作。

    五. 具体例子

    以用户读一个文件为例,

    当用户点击打开文件时,会调用库函数中的read()函数,而在这个函数中会触发软中断指令,CPU陷入到内核态,进程堆栈也会切换到相应的内核态堆栈。

    接着,进入异常处理的硬件级流程,在这个过程中,CPU在栈中保存eflags、cs、和eip的内容,随后进入异常处理的软件级流程,在这个过程中, CPU会进一步保存上下文.。

    与这个过程相对应的是:CPU读取idtr寄存器指向的IDT表中的第128项,此时可以得到0x80中断门,通过这个中断门CPU可以得到中断处理例程。

    接着, 中断处理例程会到系统调用表中找到read()函数相对应的VFS虚拟文件系统中的系统调用sys_read()。

    到达VFS层次后,sys_read()会根据fd在进程打开文件表中找到相应的系统打开文件表(File数据结构),然后执行系统打开文件表中的file operations中具体的操作。

    文件打开之后,将pt_regs数据结构中描述的寄存器以及cs:eip寄存器恢复, 此时进程又重新恢复到了用户态, 并沿着read()函数的下一条语句继续执行。

    六. 总结与建议

    总的来说,这门课真的是干货满满,两位老师深入Linux内核代码的耐心讲解,在现在的大环境下真的很难得,也确实让我学到了不少东西,真正了解到了Linux底层的一些运行流程与原理,

    相较于平时自己的摸索,这种课程真的给我带来了很大的帮助。

    建议的话,一些内核代码部分的讲解,逻辑的梳理,只是听老师用嘴说,可能不是很容易理解,如果能有形象的展示,也许会更助于理解。

    最后,希望这门课可以一直继续开下去,帮助更多学弟学妹们。

    谢谢二位老师的辛苦付出,祝老师们身体健康!

     

  • 相关阅读:
    ruilei.cnblogs 访问量突破20万
    VSTS2008 Load Test Agent
    失落的星球 Lost Planet 秘籍
    C#去除特殊字符串
    Linq Coding Part Nine(IEnumerable、IQueryable、Set)
    Web Services Software Factory tutorial (1 of 5)
    迅雷新闻快讯区JS代码剖析
    Interfaces Topic
    前台如何调用后台事件
    [关注]个税起征点8000元什么时候到来?
  • 原文地址:https://www.cnblogs.com/seanloveslife/p/13268158.html
Copyright © 2011-2022 走看看