[No00003A]操作系统Operating Systems 内核级线程Kernel Threads内核级线程实现Create KernelThreads
开始核心级线程
内核级线程对多核的支持怎么样?
和用户级相比,核心级线程有什么不同?
ThreadCreate 是系统调用,内核管理TCB ,内核负责切换线程
如何让切换成型? − − 内核栈,TCB
- 用户栈是否还要用? 执行的代码仍然在用户态,还要进行函数调用
- 一个栈到一套栈;两个栈到两套栈
- TCB 关联内核栈,那用户栈怎么办?
用户栈和内核栈之间的关联
所有中断( 时钟、外设、INT指令) 都引起上述切换
中断( 硬件) 又一次帮助了操作系统…
仍然是那个A() ,B() ,C() ,D()…
认真体会从内核返回( 中断返回) 时的样子…
开始内核中的切换:switch_to
switch_to: 仍然是通过TCB 找到内核栈指针;然后通过ret 切到 某个内核程序; 最后再用CS:PC 切到
sys_read(){ 启动磁盘读; 将自己变成阻塞;找到next;switch_to(cur, next);}
回答上面的问号??, ???, ????…
???: sys_read 函数的某个地方
??: interrupt 之前的某个地方
???: sys_xxx 函数中的某个地方
最关键的地方来了: T 创建时如何填写?? , ????
?? 500 ,函数C()的开始地址
???? 一段能完成第二级返回的代码,一段包含iret 的代码…
内核线程switch_to 的五段论
ThreadCreate! 做成那个样子…
用户级线程、核心级线程的对比
操作系统Operating Systems内核级线程实现Create Kernel Threads
核心级线程的两套栈,核心是内核栈…
整个故事要从进入内核开始—— 某个中断开始…
切换五段论中的中断入口和中断出口
void sched_init(void)
{set_system_gate(0x80,&system_call);}
初始化时将各种中断处理设置好
_system_call:
push %ds..%fs
pushl %edx...
call sys_fork
pushl %eax
内核栈:
movl _current,%eax
cmpl $0,state(%eax)
jne reschedule
cmpl $0,counter(%eax)
je reschedule
ret_from_sys_call:
reschedule:
pushl $ret_from_sys_call
jmp _schedule
切换五段论中的schedule
切换五段论中的switch_to
Linux 0.11 用tss切换,但也可以用栈切换,因为tss 中的信息可以写到内核栈中
另一个故事ThreadCreate 就顺了…
从sys_fork 开始CreateThread
_sys_fork:
push %gs; pushl %esi
...
pushl %eax
call _copy_process
addl $20,%esp
ret
int copy_process(int nr,long ebp,long edi,long esi,long gs,longnone,long ebx,long ecx,long edx, longfs,long es,long ds,long eip,longcs,long eflags,long esp,long ss)
copy_process的细节:创建栈
p=(struct task_struct *)get_free_page();// 申请内存空间
p->tss.esp0 = PAGE_SIZE + (long) p;
p->tss.ss0 = 0x10;// 创建内核栈
p->tss.ss = ss & 0xffff;
p->tss.esp = esp;// 创建用户栈(和父进程共用栈)
申请内存空间;
创建TCB;
创建内核栈和用户栈;
填写两个 stack;
关联栈和TCB;
copy_process 的细节:执行前准备
p->tss.eip = eip;
p->tss.cs = cs & 0xffff;// 将执行地址cs:eip 放在tss 中
p->tss.eax = 0;
p->tss.ecx = ecx;// 执行时的寄存器也放进去了
p->tss.ldt = _LDT(nr);
set_tss_desc(gdt+(nr<<1) + 仔细体会tss 将要承担的作用…
FIRST_TSS_ENTRY, &(p->tss));
set_ldt_desc(gdt+(nr<<1) +
FIRST_LDT_ENTRY, &(p->ldt));// 内存跟着切换
p->state = TASK_RUNNING;
copy_process( ...,long eip,long cs,longe flags,long esp,long ss)
...
填写两个stack;
第三个故事: 如何执行我们想要的代码?
int main(int argc, char * argv[])
{ while(1) { scanf("%s", cmd);
if(!fork()) {exec(cmd);} wait(0); }
ThreadCreate(*A) 中的A 必须体现? 用户输入hello 命令,exec(hello)
fork() 何时返回0 ,何时不会? 首先要找到fork() 怎么返回?
mov %eax, __NR_fork
INT 0x80
mov res,%eax 如何到这条指令?
父进程用iret ,因为要从核心态到用户态;那么子进程呢? 仔细想一想…
结构: 子进程进入A ,父进程等待…
故事要从exec 这个系统调用开始
if(!fork()) {exec(cmd);}
_system_call:
push %ds .. %fs
pushl %edx..
call sys_execve
_sys_execve:
lea EIP(%esp),%eax
pushl %eax
call _do_execve
EIP = 0x1C
终于可以让AA 执行了…
int do_execve( * eip,...
{ p += change_ldt(...;
eip[0] = ex.a_entry;
eip[3] = p; ...
struct exec {
unsigned long a_magic;
unsigned a_entry; //口 入口 };
eip[0] = esp + 0x1C; eip[3] = esp +0x1C+0x0C = esp + 0x28 ( 正好是SP)
ex.a_entry 是可执行程序入口地址,产生可执行文件时写入…
- 理解switch_to 对应的栈切换,将自己变成计算机
- ThreadCreate的目的就是初始化这样一套栈
[No00003A]操作系统Operating Systems 内核级线程Kernel Threads内核级线程实现Create KernelThreads的更多相关文章
- [No00003D]操作系统Operating Systems信号量的代码实现Coding Semaphore &死锁处理Deadlock
操作系统Operating Systems信号量的代码实现Coding Semaphore &死锁处理Deadlock 可以操刀了—从纸上到实际 从Linux 0.11 那里学点东西… 读磁盘 ...
- [No00003C]操作系统Operating Systems进程同步与信号量Processes Synchronization and Semaphore
操作系统Operating Systems进程同步与信号量Processes Synchronization and Semaphore 进程合作:多进程共同完成一个任务 从纸上到实际:生产者− − ...
- [No000039]操作系统Operating Systems用户级线程User Threads
多进程是操作系统的基本图像 是否可以资源不动而切换指令序列? 进程 = 资源 + 指令执行序列 线程: 保留了并发的优点,避免了进程切换代价 实质就是映射表不变而PC 指针变 多个执行序列+ 一个地址 ...
- [No000036]操作系统Operating Systems系统调用的实现System_Call
实现一个whoami 系统调用 系统调用的直观实现 问题+直观想法… 用户程序调用whoami, 一个字符串"systemcall "放在操作系统中(系统引导时载入) ,取出来打印 ...
- [No000038]操作系统Operating Systems -CPU
管理CPU ,先要使用CPU… CPU 的工作原理 CPU上电以后发生了什么? 自动的取指 — 执行 CPU 怎么工作? CPU怎么管理? 管理CPU 的最直观方法 设好PC 初值就完事! 看看这样做 ...
- [No000037]操作系统Operating Systems操作系统历史与硬件概况History of OS & Summaries!
培根:读史使人明智 操作系统的简史 (1955-1965) 计算机非常昂贵,上古神机IBM7094 ,造价在250万美元以上 计算机使用原则:只专注于计算 批处理操作系统(Batch system) ...
- [No000031]操作系统 Operating Systems 之Open the OS!
从打开电源开始… 这神秘的黑色背后发生着什么?… 打开电源,计算机执行的第一句指令什么? 计算模型(图灵机) ⇒ 我们要 关注 指针IP 及其 指向的内容 看看x86 PC (1) 刚开机时CPU 处 ...
- 【内核】linux2.6版本内核编译配置选项(二)
目录 Linux2.6版本内核编译配置选项(一):http://infohacker.blog.51cto.com/6751239/1203633 Linux2.6版本内核编译配置选项(二):http ...
- 【操作系统】二、JVM线程与Linux内核线程的映射
Linux从内核2.6开始使用NPTL (Native POSIX Thread Library)支持,但这时线程本质上还轻量级进程. Java里的线程是由JVM来管理的,它如何对应到操作系统的线程是 ...
随机推荐
- ABAP中RETURN与EXIT语句的区别
EXIT:1) EXIT如果出现在循环中,退出的是整个循环操作,.程序会从循环结束处开始继续执行,其作用相当于Java与C++中的break.2)EXIT如果出现在循环之外,退出的是当前执行的程序块( ...
- Atitit.在线充值功能的设计
Atitit.在线充值功能的设计 1. 流程1 2. Js sdk api 增加订单1 3. Java api 返回servlet处理1 3.1. 返回网址的本地host测试2 1. 流程 本地增 ...
- XMPP学习——1、介绍
XMPP(Extensible Messaging and Presence Protocol,前称Jabber[1])是一种以XML为基础的开放式实时通信协议,是经由互联网工程工作小组(IETF)通 ...
- Android 友盟分享躺过的几个坑,大坑,坑爹啊
前言:公司上线了一个项目,做Android 客户端集成友盟分享,在做得过程中,遇到了下面3个问题,希望其他小伙伴注意. ) 错误1: 1.错误描述 我是照着友盟的集成文档一步一步的集成的,做完后,发现 ...
- Android环境搭建和编写helloworld
一.配置jdk环境(学过java的请无视) 1.安装jdk jdk下载地址:http://www.oracle.com/technetwork/cn/java/javase/downloads/jdk ...
- Android 用Fragment创建一个选项卡
本文结合之前的动态创建fragment来进行一个实践,来实现用Fragment创建一个选项卡 本文地址:http://www.cnblogs.com/wuyudong/p/5898075.html,转 ...
- 我的Android第三章:Android的组件介绍
小编摘录了Android文档介绍Android四大组件的基本内容,感觉文档的内容写的很详细所以小编将它写入了博客 Android 使用Java语言开发.Android SDK 工具编译代码-以及任意数 ...
- java文件复制函数
在写代码中,经常会需要复制文件.这时候就可以把这些函数放到工具类里面. 下面是一个复制文件的函数: public class CopyFileUtil { private static String ...
- apache 日志轮询 linux cronolog
Linux下运行的Web服务器Apache,默认日志文件是不分割的,一个整文件既不易于管理,也不易于分析统计.安装cronolog后,可以将日志文件按时间分割,易于管理和分析. cronolog安装配 ...
- 全面理解JavaScript中的闭包的含义及用法
1.什么是闭包 闭包:闭包就是能够读取其他函数内部变量的函数;闭包简单理解成“定义在一个函数内部的函数”. 闭包的形式:即内部函数能够使用它所在级别的外部函数的参数,属性或者内部函数等,并且能在包含它 ...