Linux0.11学习笔记

Linux 0.11代码学习

任务切换

**目前状态:**中断程序已设置,第一个任务 init_task已初始化(sched.c),main()函数里通过move_to_user_mode()进入到Task 0。
目的:手工创建第二个任务 Task 1,并和Task 0不停切换。

做法:
在sched.c 创建第二个任务结构,所有值采用第一个:
union task_union{
struct task_struct task;
char stack[PAGE_SIZE];//(内核堆栈0)
};
//第一个任务的内核sp0=(&init_task+PAGE_SIZE),PAGE_SIZE定义为4096
static union task_union init_task={INIT_TASK,};
//第二个任务的内核sp0=(&second_task+PAGE_SIZE),PAGE_SIZE定义为4096
static union task_union second_task={INIT_TASK,};
//第二个任务的用户栈
long second_stack[PAGE_SIZE>>2];
long* second_stack_top=(long*)(&second_stack[PAGE_SIZE>>2]);

Linux 0.11的任务切换是通过 ljmp指令实现的。ljmp是个长跳转(CS:IP),32为系统下,CS和IP长度为4字节,其中IP在低4为,CS在高4字节。当ljmp 跳转的是一个任务段TSS时,就会发生任务切换,这时低4字节的值忽略。switch_to()里,通过 struct {long a,b}构建一个 跳转地址,a是低4字节,所以不用赋值,b赋值_TSS(n),即任务n对应的TSS段。 当Task 0通过ljmp跳到Task 1里时,CPU会把Task0的任务信息保存在_TSS(0),及init_task.task.tss里,并把Task 1的信息加载(second_task.task).
Task 0 并不是通过ljmp进来的,所以它对应的TSS里的值不必都正确初始化,只要0级堆栈设置正确就行。但我们想要跳转到 Task 1,必须把 Task 1里TSS和对应的LDT信息都设置正确。LDT我们可以和 Task 0的一样,及_LDT(1),具体如下:
second_task.task.tss.esp=(long)second_stack_top;
second_task.task.tss.esp0=(long)&second_task+PAGE_SIZE;
second_task.task.tss.eip=(long)second_task_disp_str;
second_task.task.tss.gs=0x1b;//init_task里是 0x17
second_task.task.tss.cs=0xf; //init_task里的是0x17
second_task.task.tss.ldt=_LDT(1);
second_task.task.tss.eflags=0x202;//init_task里的是0

然后把second_task里的TSS和LDT地址放到GDT表里对应的TSS和LDT段描述符,在我们的例子里,GDT对应如下
序号 偏移地址
0 0x0 NULL
1 0x8 code descriptor
2 0x10 DATA descriptor
3 0x16 //Linux没用,但我用作指向显存区域,用于显示字符串函数disp_str(相当于printf)
4 0x20 Task 0 TSS //_TSS(0)
5 0x28 Task 0 LDT //_LDT(0)
6 0x30 Task 1 TSS//_TSS(1)
7 0x38 Task 1 LDT //_LDT(1)

// 设置GDT里第二个任务的TSS和LDT段描述符
set_tss_desc((char*)(gdt+FIRST_TSS_ENTRY+2),&second_task.task.tss);
set_ldt_desc((char*)(gdt+FIRST_LDT_ENTRY+2),&second_task.task.ldt);

在时钟中断里开启调度函数
mov al,0x20
out 0x20,al
call schedule

详见我的主页https://codechina.csdn.net/m0_53755675

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值