Linux内核源代码的学习过程转换完成细节
想执行都要经过的地方
--->放入就绪队列---->被调度---->运行switch_to
__switch_to了,这是个函数。这个函数的返回地址就区分了被调度的进程是新创建的进程还是已经运行过的进程了。
watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQvYWdhbmxlbmd6aQ==/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70/gravity/SouthEast" alt="">
unsigned long esi,edi; /
asm volatile("pushfl/n/t" /
"pushl %%ebp/n/t" /
"movl %%esp,%0/n/t" /* save ESP */ /
"movl %5,%%esp/n/t" /* restore ESP */ / //注意这里已经切换到了新的内核栈,故原来的栈中的局部变量所有失效。因而想得到其值就必须想办法保存它们,为了效率。这里将prev保存在寄存器中, 以便善后使用
"movl $1f,%1/n/t" /* save EIP */ / //这里。仅仅要是以前在这里被切换出去的进程都会将标号1作为再回来时的eip
"pushl %6/n/t" /* restore EIP */ / //将新进程的eip压入栈中,由于以下是个jmp,并且jmp到的函数最后有一个return。那么依照return的语义,就能够从栈取出eip加载 eip寄存器了,实际上这个对__switch_to的jmp调用就是一个手动的call调用(须要注意的是,这里return的是下一个进程的eip保存的是本进程的eip留给下次被切换进来的时候像如今这样使用)。非常巧妙
"jmp __switch_to/n" / //__switch_to是个FASTCALL的函数。eax/ebx寄存器传參数
"1:/t" / //标号1的指令,非常easy。可是就是这个简单成全了总体架构的简单 这里为什么不用call
"popl %%ebp/n/t" /
"popfl" /
:"=m" (prev->thread.esp),"=m" (prev->thread.eip), /
"=a" (last),"=S" (esi),"=D" (edi) /
:"m" (next->thread.esp),"m" (next->thread.eip), /
"2" (prev), "d" (next)); /
} while (0)
__switch_to/n"的时候,它的返回地址将不会是标号1:而应该是eip,即在copy_thread中设置的eip中的值:ret_from_fork
ENTRY(ret_from_fork)
pushl %eax
call schedule_tail
GET_THREAD_INFO(%ebp)
popl %eax
jmp syscall_exit
syscall_exit:
...
work_resched:
call schedule
...
当他从ret_from_fork退出时。会从堆栈中弹出原来保存的eip,而ip指向kernel_thread_helper,
至此kernel_thread_helper被调用。他就行执行我们的指定的函数了do_exit().
从内核空间返回到用户空间。
离出来放到一个地方,然后无论是已经有的进程还是新创建的进程都从这个固定的分离出来标号1的地址处取指令不就能够了吗?内核的设计者不可能还没有我聪明,那样的话会浪费取指令的时间和空间的,
ENTRY(ret_from_fork)
pushl %eax //注意刚从switch_to调用的__switch_to中ret回来。正好ret到了ret_from_fork(注意switch_to中jmp 指令前的push),而那个函数返回的就是prev,将其放到了eax中,故这里schedule_tail的參数就是prev,也就是切换出去的进程。
call schedule_tail
GET_THREAD_INFO(%ebp)
popl %eax
jmp syscall_exit
上 面看到ret_from_fork调用的schedule_tail參数是切换出去的进程,而后者立即调用finish_task_switch,这样就 和schedule中的switch_to之后的逻辑对上了,并且參数也没有什么问题,
schedule的局部变量在prev的内核栈中,在切换到新的内核栈后(schedule函数用到了两个内核栈),prev失效。因此才要保存(这里能够理解为从prev传递到兴许可见的地方)的。
Linux内核源代码的学习过程转换完成细节的更多相关文章
- Linux内核源代码分析方法
Linux内核源代码分析方法 一.内核源代码之我见 Linux内核代码的庞大令不少人"望而生畏",也正由于如此,使得人们对Linux的了解仅处于泛泛的层次.假设想透析Linux ...
- Linux内核源代码获取教程
Linux内核源代码获取方法 什么叫Linux 什么叫Linux内核 Linux内核源代码的获取 什么叫Linux? Linux是一套免费使用和自由传播的类Unix操作系统,是一个基于POSIX和UN ...
- 在windows下解压缩Linux内核源代码出现重复文件原因
在windows下解压缩Linux内核源代码出现重复文件原因 2009年06月30日 13:35 来源:ChinaUnix博客 作者:embededgood 编辑:周荣茂 原因一.因为在Lin ...
- Linux内核源代码情景分析系列
http://blog.sina.com.cn/s/blog_6b94d5680101vfqv.html Linux内核源代码情景分析---第五章 文件系统 5.1 概述 构成一个操作系统最重要的就 ...
- Linux内核源代码
说明:只供学习交流 一,目录结构 Linux内核源代码采用树形结构进行组织,非常合理地把功能相关的文件都放在同一个子目录下,使得程序更具有可读性. 二,目录结构 arch目录 arch是archite ...
- Linux内核源代码目录树结构
Linux内核源代码目录树结构. arch:包含和硬件体系结构相关的代码,每种平台占一个相应的目录.和32位PC相关的代码存放在i386目录下,其中比较重要的包括kernel(内核核心部分).mm(内 ...
- 《深入分析Linux内核源代码》读书、私藏笔记大放送
秉承着"不懂操作系统原理的程序员不是合格的程序员"的至理名言,鄙人又是买陈莉君老师的“Linux教学视频”,又是研读其力作<深入分析Linux内核源代码>,先将总结笔记 ...
- Ubuntu:编译Linux内核源代码和内核模块
1. 目的 内核模块需要运行在Linux 3.8.13内核中,因此需要为此内核重新编译内核模块源代码. 2. 步骤 1.在Ubuntu 14.04 64位(内核3.13.0-24-generic)上, ...
- linux内核源代码、配置与编译
内核源代码下载:www.kernel.org Linux内核源代码采用树形结构进行组织,非常合理地把功能相关的文件都放在同一个子目录下,使得程序更具可读性. linux内核代码最好不要在windows ...
随机推荐
- C/C++ Resources
C/C++ Resources 一.C/C++相关资源 语言标准及文档● ISO C99http://www.open-std.org/JTC1/SC22/WG14/www/docs/n1124.pd ...
- 爬虫框架: DotnetSpider
[开源 .NET 跨平台 数据采集 爬虫框架: DotnetSpider] [一] 初衷与架构设计 一 ,为什么要造轮子 有兴趣的同学可以去各大招聘网站看一下爬虫工程师的要求,大多是JAVA,PYTH ...
- LIS小结(O(∩_∩)O~哄哄)
~\(≧▽≦)/~啦啦啦,昨天说的是LCS,今天我们要学习的是LIS,什么是LIS呢? LIS: 最长有序子序列(递增/递减/非递增/非递减)这么说还是有些模糊,举个例子: 在一个无序的序列a1,a ...
- Codeforces 475D CGCDSSQ 求序列中连续数字的GCD=K的对数
题目链接:点击打开链接 #include <cstdio> #include <cstring> #include <algorithm> #include < ...
- CentOS6-釋放ip重新分配,centos7 ifconifg没有ip
http://bbs.csdn.net/topics/390725823 系统win7 ,dhcp自动获取ip虚拟机是10.0 安装之后我装了ubuntu 选用 NAT网络, 刚装完我能上网 ,但是 ...
- THashMD5,THashSHA1,THashBobJenkins,TIdHashMessageDigest5的用法
[delphi] view plain copy unit Unit1; interface uses Winapi.Windows, Winapi.Messages, System.SysUtils ...
- 猎豹移动(金山网络)2015校园招聘(c++project师)
1.已知类MyString的原型为: class MyString { public: MyString(const char *str=NULL);//普通构造函数 MyString(const M ...
- Visual Studio 2008中FormatX源代码格式化插件
原地址:http://www.cr173.com/html/15492_1.html 我总是对组里的兄弟代码规范性近乎完美的要求,举个简单的例子: 1. 每个方法必须有注释,方法参数详细说明 2. ...
- 使用ROW_NUMBER()查询:列名 'RowNumber' 无效。
原文:使用ROW_NUMBER()查询:列名 'RowNumber' 无效. 使用ROW_NUMBER()方法查询结果集:语句如下: select ROW_NUMBER() OVER(ORDER ...
- 8月30号周五香港接单ING~~化妆品只加10元!!!!!!
8月30号周五香港接单ING~~化妆品只加10元!!!!!! 8月30号周五香港接单ING~~化妆品只加10元!!!!!!