这周的作业同样分为两部分,第一部分的学习MOOC第四节[扒开系统调用的三层皮],并结合实验楼的实验四深入学习。第二部分阅读学习教材「Linux内核设计与实现 (Linux Kernel Development)」第教材第7,8章。

首先从第一部分开始,系统调用的三层皮分别是xyz(API) system_call(中断向量对应的中断服务程序) sys_xyz(服务程序)。为了更深入的了解三层“皮”,我们做了如下的实验。

1.获取系统时间



2.代码完成后我们进行编译并运行



3.C语言代码嵌入汇编代码格式如下

    '''

    _asm_(
汇编语句模板:
输出部分:
输入部分:
破坏描述部分);
即格式为asm("statements":output_...); '''

4.接下来直接用例子来说明



对于里面出现的双%,第一个%代表转译。

5.用实际例子来看懂输出结果



#实验的结果应该是0和1,但在实际操作过程中遇到了编译错误,问题尚未解决,后期会会跟进问题进行处理。

后期跟紧:已正确输出:

缺少代码:movl %%eax,%1;\n\t



6.用汇编方式触发系统调用获取当前时间

代码中d是16进制的13,使用eax传递系统调用号,这里time是13



7.编译并运行上述代码



学习这段代码,我们可以清楚的知道用户态向内核态做了什么,它传递了一个系统调用号,参数NUll就是给ebx传递了一个空参。

实验中,我们首先了解了用户态,内核态,已经了解了系统调用的三层“皮”。学习代码中,我们知道了用户态和内核态传递参数的方式,以及他们之间的联系。接下来就是对课本章节的阅读情况,在第七章,我们了解了内核为处理中断而提供的中断处理程序机制,但中断处理程序本身也有局限,局限包括:

1)中断处理程序以异步方式执行,并且它右可能会打断其他重要代码的执行。

2)如果当前有一个中断处理程序正在执行,最好的情况,同级的其他中断会北屏蔽,最坏的情况,当前处理机上所有的其他中断会被屏蔽。

3)由于中断处理程序往往需要对硬件进行操作,所以他们通常有很高的时限要求。

4)中断处理程序不能在进程上下文中运行,所以他们不能阻塞。

中断和下半部

中断机制就是在硬件需要的时候向内核发出信号。中断本质上是一种由硬件向处理器发出的特殊的电信号,不考虑与处理器的时钟同步。不同的设备对应不同的中断,所以每个中断都通过一个唯一的数字标,称为中断请求(IRQ)线。

异常称为同步中断,是由处理器本身产生的中断;异步中断由其他硬件产生的。

中断处理程序

内核执行的用来响应中断的函数叫中断处理程序或者中断服务例程,是设备驱动程序的一部分。每个中断都有相应的中断处理程序,它要负责通知硬件设备中断已被接收。

驱动程序通过request_irq()注册中断处理程序并激活给定的中断线:

int request_irq(unsigned int irq, irq_handler_t handler, unsigned long flags, const char *name, void *dev)

irq表示要分配的中断号;handler指针指向处理该中断的中断处理程序;flags有几个重要的标志,IRQF_DISABLED表示处理该中断处理程序本身旗舰,禁止所有其他中断,IRQF_SAMPLE_RANDOM表示该设备中断对内核熵池有贡献,IRQF_TIMER是为系统定时器的中断处理准备,IRQF_SHARED表明可在多个中断处理程序之间共享中断线;name是与终端相关的设备的ASCⅡ文本表示;dev用于共享中断线,提供唯一标志信息以便从共享中断线的多个中断处理程序中删除指定那个。若函数返回0则表示成功,返回-EBUSY表示中断线已经在使用。

卸载驱动程序要注销相应的中断处理程序,并释放中断线,要调用函数:

void free_irq(unsigned int irq, void *dev)

对于共享的中断处理程序:

•request_irq()的参数flags必须设置IRQF_SHARED标志;

•对每个注册的中断处理程序,dev参数必须唯一;

•中断处理程序必须能区分它的设备是否真的产生了中断。

内核收到中断后,会依次调用该中断线上注册的每一个处理程序,因此处理程序必须知道它是否应该为这个中断负责,与它相关的设备没有产生中断,那处理程序就必须立刻退出。

中断控制

中断控制的原因归根结底是需要提供同步。通过禁止中断确保某个中断处理程序不会抢占当前代码或内核。锁提供保护机制,防止来自其他处理器的并发访问;禁止中断提供保护机制,防止来自其他处理程序的并发访问。

下半部和退后执行的工作

鉴于中断处理程序运行速度和完成工作量之间的矛盾,把中断处理分为两部分:上半部和下半部。

中断处理程序是上半部,接收到中断就立马执行,只做严格的限时工作;能被允许稍后完成的工作会推迟到下半部,在合适的时机,下半部会被开中断执行。

下半部的任务是执行与中断处理密切相关但中断处理本身不执行的工作。一般情况,需要放在上半部的工作:

•对时间非常敏感;

•和硬件相关;

•要保证不被其他中断打断。

下半部实现机制有BH、任务队列、软终端、tasklet和工作队列。其中BH和任务队列已经去除。软中断在编译期间就进行静态注册,tasklet可以通过代码进行动态注册。

软中断由softirq_action结构表示,定义在<linux/interrupt.h>中。最多可能有32个软中断。中断处理程序返回前会标记软中断,注册的软中断必须在被标记后才会执行,称作触发软中断。而软中断都要在do_softirq()中执行。

tasklet是利用软中断实现的一种下半部机制,由tasklet_struct结构表示:

struct tasklet_struct{

struct tasklet_struct next;//链表中下一个tasklet

unsigned long state; //tasklet的状态

atomic_t count; //引用计数器

void (
func)(unsigned long);//tasklet处理函数

unsigned long data; //给tasklet处理函数的参数

}

工作队列子系统是一个用于创建内核线程的接口,通过它创建的进程负责执行有内核其他部分排到队列里的任务,这些内核线程称作工作者线程。缺省的工作者线程叫event/n,n是处理器编号,每个处理器一个线程。工作者线程用workqueue_struct结构表示:


struct workqueue_struct{
struct cpu_workqueue_struct cpu_wq[NR_CPUS];
struct list_head list;
const char *name;
int sinqlethread;
int freezeable;
int rt;
}

该结构内是一个由cpu_workqueue_struct结构组成的数组:


struct cpu_workqueue_struct{
spinlock_t lock;//锁保护这种结构
struct list_head worklist;//工作列表
wait_queue_head_t more_work;
struct work_struct *current_struct;
struct workqueue_struct *wq;//关联工作队列结构
task)t *thread;//关联线程
}

所有工作者线程都是用普通的内核线程实现的,都要执行worker_thread()函数。工作用work_struct结构体表示:


struct work_struct{
atomic_long_t data;
struct list_head entry;
work_func_t func;
}

对于现在常用的三种下半部接口,软中断和tasklet都是在中断上下文中,而工作队列是进程上下文;软中断没有顺序执行保障,tasklet同类型不能同时执行,工作队列也没有顺序执行保障,和进程上下文一样被调度。

所以,整个中断处理流程就被分为了两个部分,或叫两半。第一部分是中断处理程序,内核通过对它的异步执行完成对硬件中断的即时响应。第二部分的任务就是执行与中断处理密切相关但中断处理程序本身不执行的工作。第八章涵盖了用于延迟Linux内核工作的三种机制:软中断、tasklet和工作队列。

20169207《Linux内核原理与分析》第六周作业的更多相关文章

  1. 20169212《Linux内核原理与分析》第二周作业

    <Linux内核原理与分析>第二周作业 这一周学习了MOOCLinux内核分析的第一讲,计算机是如何工作的?由于本科对相关知识的不熟悉,所以感觉有的知识理解起来了有一定的难度,不过多查查资 ...

  2. 20169210《Linux内核原理与分析》第二周作业

    <Linux内核原理与分析>第二周作业 本周作业分为两部分:第一部分为观看学习视频并完成实验楼实验一:第二部分为看<Linux内核设计与实现>1.2.18章并安装配置内核. 第 ...

  3. 2018-2019-1 20189221 《Linux内核原理与分析》第九周作业

    2018-2019-1 20189221 <Linux内核原理与分析>第九周作业 实验八 理理解进程调度时机跟踪分析进程调度与进程切换的过程 进程调度 进度调度时机: 1.中断处理过程(包 ...

  4. 2017-2018-1 20179215《Linux内核原理与分析》第二周作业

    20179215<Linux内核原理与分析>第二周作业 这一周主要了解了计算机是如何工作的,包括现在存储程序计算机的工作模型.X86汇编指令包括几种内存地址的寻址方式和push.pop.c ...

  5. 2019-2020-1 20199329《Linux内核原理与分析》第九周作业

    <Linux内核原理与分析>第九周作业 一.本周内容概述: 阐释linux操作系统的整体构架 理解linux系统的一般执行过程和进程调度的时机 理解linux系统的中断和进程上下文切换 二 ...

  6. 2019-2020-1 20199329《Linux内核原理与分析》第二周作业

    <Linux内核原理与分析>第二周作业 一.上周问题总结: 未能及时整理笔记 Linux还需要多用 markdown格式不熟练 发布博客时间超过规定期限 二.本周学习内容: <庖丁解 ...

  7. 2019-2020-1 20209313《Linux内核原理与分析》第二周作业

    2019-2020-1 20209313<Linux内核原理与分析>第二周作业 零.总结 阐明自己对"计算机是如何工作的"理解. 一.myod 步骤 复习c文件处理内容 ...

  8. 2018-2019-1 20189221《Linux内核原理与分析》第一周作业

    Linux内核原理与分析 - 第一周作业 实验1 Linux系统简介 Linux历史 1991 年 10 月,Linus Torvalds想在自己的电脑上运行UNIX,可是 UNIX 的商业版本非常昂 ...

  9. 《Linux内核原理与分析》第一周作业 20189210

    实验一 Linux系统简介 这一节主要学习了Linux的历史,Linux有关的重要人物以及学习Linux的方法,Linux和Windows的区别.其中学到了LInux中的应用程序大都为开源自由的软件, ...

  10. 2018-2019-1 20189221《Linux内核原理与分析》第二周作业

    读书报告 <庖丁解牛Linux内核分析> 第 1 章 计算工作原理 1.1 存储程序计算机工作模型 1.2 x86-32汇编基础 1.3汇编一个简单的C语言程序并分析其汇编指令执行过程 因 ...

随机推荐

  1. shell 脚本编写基础

    在进行Linux测试时编写脚本是必不可少的,Shell脚本的名称可以随便定义,也不要什么后缀名,例如可以写abc,smartzip这类名称,运行时只要键入 ./smartzip就能运行脚本了.. 每行 ...

  2. ef linq 中判断实体中是否包含某集合

    我有一个需求,问题有很多标签,在查询时,需要筛选包含查询标签的一个集合(List<int>),以前的做法是先查询出来符合查询标签条件的标签id的结果集A,再查询问题时,加上判断是否包含该标 ...

  3. python 虚拟环境操作 virtualenv +virtualenvwrapper

    Window 下创建python的虚拟环境 下载工具 pip install virtualenv 创建虚拟环境目录 # 注意此命令创建的虚拟环境目录是在当前目录下 virtualenv testen ...

  4. c# 关于取小数点后值四舍五入精度问题

    ---恢复内容开始--- 最近做一个校验码验证法算法的生成程序,涉及到取小数点后值的问题;对其中遇到的问题做一下总结: 1:ToString()转换时碰到0.9999999999999之类的数据,给自 ...

  5. iOS.Library.Architecture

    在用file查看library的architechture时有以下输出: $ file WebPWebP: Mach-O universal binary with 3 architecturesWe ...

  6. VirtualBox中安装Fedora9及其ARM开发环境配置

    因为要学习Tiny4412开发板的嵌入式编程,需要用到Fedora9系统(和手册对应),我就在VirtualBox虚拟机(此虚拟机安装在Ubuntu12.04上)上安装了Fedora9,下面就讲解一下 ...

  7. LibreOJ #6013. 「网络流 24 题」负载平衡 最小费用最大流 供应平衡问题

    #6013. 「网络流 24 题」负载平衡 内存限制:256 MiB时间限制:1000 ms标准输入输出 题目类型:传统评测方式:文本比较 上传者: 匿名 提交提交记录统计讨论测试数据   题目描述 ...

  8. error C4430: 缺少类型说明符 - 假定为 int。注意: C++ 不支持默认 int 错误的解决方法

    一些函数定义中,在VC6中,如果没有显示的指定返回值类型,编译器将其视为默认整型:但是vs2008/vs2010不支持默认整型,解决这个问题不能修改每个没有显示指示返回值类型的函数地方,可以用排除44 ...

  9. 深入研究 UCenter API For .NET

    康盛旗下产品的搭建 来自http://www.dozer.cc/2011/02/ucenter-api-in-depth-4th/ 1.UCenter 这个当然是最基本的东西,安装起来也很简单,官方就 ...

  10. Spring ApplicationContext(八)事件监听机制

    Spring ApplicationContext(八)事件监听机制 本节则重点关注的是 Spring 的事件监听机制,主要是第 8 步:多播器注册:第 10 步:事件注册. public void ...