重庆大学操作系统实验二线程及其调度.docx

上传人:b****6 文档编号:5894023 上传时间:2023-01-01 格式:DOCX 页数:15 大小:135.24KB
下载 相关 举报
重庆大学操作系统实验二线程及其调度.docx_第1页
第1页 / 共15页
重庆大学操作系统实验二线程及其调度.docx_第2页
第2页 / 共15页
重庆大学操作系统实验二线程及其调度.docx_第3页
第3页 / 共15页
重庆大学操作系统实验二线程及其调度.docx_第4页
第4页 / 共15页
重庆大学操作系统实验二线程及其调度.docx_第5页
第5页 / 共15页
点击查看更多>>
下载资源
资源描述

重庆大学操作系统实验二线程及其调度.docx

《重庆大学操作系统实验二线程及其调度.docx》由会员分享,可在线阅读,更多相关《重庆大学操作系统实验二线程及其调度.docx(15页珍藏版)》请在冰豆网上搜索。

重庆大学操作系统实验二线程及其调度.docx

重庆大学操作系统实验二线程及其调度

重庆大学操作系统实验二(线程及其调度)

重庆大学

学生实验报告

 

实验课程名称操作系统原理

开课实验室重庆大学DS1501

学院软件工程年级2013专业班

学生姓名学号

开课时间2015至2016学年第一学期

 

总成绩

教师签名

洪明坚

 

重庆大学软件学院制

《操作系统原理》实验报告

开课实验室:

DS15012016年1月6日

学院

软件学院

年级、专业、班

姓名

成绩

课程

名称

操作系统原理

实验项目

名称

线程及其调度

指导教师

教师评语

教师签名:

年月日

一、实验目的(软件需求文档)

掌握线程的创建

掌握线程的调度

a)静态优先级调度

b)动态优先级调度

二、实验原理(软件设计文档)

系统调用接口,线程相关函数:

•Step1:

定义线程函数

voidtsk_foo(void*pv)

{

printf("Thisistaskfoowithtid=%d\r\n“,task_getid());

task_exit(0);

}

•Step2:

申请用户栈

unsignedchar*stack_foo;

stack_foo=(unsignedchar*)malloc(1024*1024);

–线程退出后,才能把用户栈用free释放掉!

•Step3:

创建线程

inttid_foo;

tid_foo=task_create(stack_foo+1024*1024,tsk_foo,(void*)0);

三、使用仪器、材料(软硬件开发环境)

Notepad++

expenv

四、实验步骤(实现的过程)

随机生成3组非负整数列表,创建3个线程,分别用3种不同的排序算法(插入,冒泡,选择)对列表进行排序

三线程:

voidtsk_foo_line1(void*pv)

{

intm;

inti;

intarry[50];

srand(time(NULL));

for(i=0;i<50;i++){

m=random()%200;

if(m<0){m=0-m;}

draw(i*10,0,0+m);

arry[i]=m;

}

sort_m(arry,50,0);

task_exit(0);

}

voidtsk_foo_line2(void*pv)

{

intm;

inti;

intarry[50];

srand(time(NULL));

for(i=0;i<50;i++){

m=random()%200;

if(m<0){m=0-m;}

draw(i*10,345,345+m);

arry[i]=m;

}

sort_x(arry,50,345);

task_exit(0);

}

 

voidtsk_foo_line3(void*pv)

{

intm;

inti;

intarry[50];

srand(time(NULL));

for(i=0;i<50;i++){

m=random()%200;

if(m<0){m=0-m;}

draw(i*10,690,690+m);

arry[i]=m;

}

sort_c(arry,50,690);

task_exit(0);

}

voiddraw(intx,inty1,inty2){

inti;

for(i=y1;i

setPixel(i,x,RGB(255,255,255));

}

voidresetBK(intx,inty1,inty2){

inti;

for(i=y1;i

setPixel(i,x,RGB(0,0,0));

}

三排序:

冒泡

voidsort_m(int*arry,intn,intl){

inti,j,tem;

intt=500/n;

for(i=0;i

for(j=0;j

if(*(arry+j)>*(arry+j+1)){

resetBK(j*t,l,l+*(arry+j));

resetBK(j*t+t,l,l+*(arry+j+1));

tem=*(arry+j);

*(arry+j)=*(arry+j+1);

*(arry+j+1)=tem;

draw(j*t,l,l+*(arry+j));

draw(j*t+t,l,l+*(arry+j+1));

}

}

}

插入

voidsort_c(int*arry,intn,intl){

inti,j,key;

intt=500/n;

for(j=n-2;j>=0;j--){

key=*(arry+j);i=j+1;

resetBK(j*t,l,l+key);

while(i

*(arry+i-1)=*(arry+i);

draw(i*t-t,l,l+*(arry+i-1));

i=i+1;

}

*(arry+i-1)=key;

draw(i*t-t,l,l+key);

}

}

选择

voidsort_x(int*arry,intn,intl){

inti=0,j=0,lowindex=0;

intt=500/n;

for(i=0;i

lowindex=i;

for(j=n-1;j>i;j--)

if(arry[j]

lowindex=j;

if(lowindex!

=i)

{

resetBK(i*t,l,l+*(arry+i));

resetBK(lowindex*t,l,l+*(arry+lowindex));

inttemp=arry[i];

arry[i]=arry[lowindex];

arry[lowindex]=temp;

draw(i*t,l,l+*(arry+i));

draw(lowindex*t,l,l+*(arry+lowindex));

}

}

}

线程控制块tcb中增加nice属性,在函数sys_task_create中初始化nice=0

/*

系统调用getpriority的执行函数

获取当前线程的优先级

*/

intsys_getpriority(inttid)

{

if(tid==0)returng_task_running->nice+NZERO;//获取当前线程的nice值

uint32_tflags;structtcb*tsk;

save_flags_cli(flags);

tsk=get_task(tid);

restore_flags(flags);

returntsk->nice+NZERO;//获取线程的nice值

}

/*

系统调用setpriority的执行函数

调整当前线程的优先级

*/

//把线程tid的nice设为(prio-NZERO)

intsys_setpriority(inttid,intprio)

{

uint32_tflags;structtcb*tsk;

if(tid==0){

save_flags_cli(flags);

g_task_running->nice=prio-20;//设置当前线程的nice值

restore_flags(flags);

return0;

}

//if(tsk==NULL)return-1;

if(prio<0)prio=0;//prio必须在[0,2*NZERO-1]

if(prio>40)prio=40;

save_flags_cli(flags);

tsk=get_task(tid);//用save_flags_cli/restore_flags保护

restore_flags(flags);

tsk->nice=prio-20;//设置线程的nice值

return0;

}

把这两个个函数做成系统调用,分别是getpriority(inttid),setpriority(inttid,intprio)

静态调度schedule:

voidschedule(){

structtcb*select=g_task_head;

structtcb*my_select=g_task_running;

while(select!

=NULL){

if((select->tid!

=0)&&(select->state==TASK_STATE_READY))

{

//if(my_select==NULL){my_select=select;continue;}

if(select->nice<=my_select->nice)//选择等待队列里的线程优先级高的

my_select=select;

if(my_select->tid==0){//跳过task0运行

my_select=select;

}

}

select=select->next;

}

if(my_select==g_task_running){

if(g_task_running->state==TASK_STATE_READY)

return;

my_select=task0;//仅当没有其他可运行的线程时,才能调度

}

g_resched=0;

switch_to(my_select);

}

线程控制块tcb中

增加estcpu属性,在函数sys_task_create中初始化estcpu=0;

增加priority属性,在函数sys_task_create中初始化priority=0;

timer.c中增加全局变量g_load_avg:

表示系统的平均负荷

用浮点(float-point)表示g_load_avg和estcpu:

精度高,效率低

动态调度schedule:

voidschedule()

{

structtcb*select=g_task_head;

structtcb*my_select=g_task_running;

while(select!

=NULL)

{

select->priority=127-fixedpt_toint(fixedpt_div(select->estcpu,fixedpt_fromint(4)))-select->nice*2;//计算所有线程的priority

select=select->next;

}

//动态优先级

select=g_task_head;

while(select!

=NULL){

if((select->tid!

=0)&&(select->state==TASK_STATE_READY)){

if(my_select->prioritypriority)

{

my_select=select;//选择等待队列里的线程优先级高的

}

elseif(my_select->tid==0)

{

my_select=select;

}

}

select=select->next;

}

if(my_select==g_task_running){

if(my_select->state==TASK_STATE_READY)

return;

my_select=task0;

}

printk("0x%d->0x%d\r\n",(g_task_running==NULL)?

-1:

g_task_running->tid,select->tid);

g_resched=0;

switch_to(my_select);

}

timer.c中添加如下

g_task_running->estcpu=fixedpt_add(g_task_running->estcpu,FIXEDPT_ONE);//计算线程使用CPU时间estcpu

if(g_timer_ticks%HZ==0){//每隔一秒计算一次

intnready=0;//表示处于就绪状态的线程个数

structtcb*my_select=g_task_head;

intnice;//g_task_running->nice;

//my_select=g_task_head;

fixedptratio;

while(my_select!

=NULL){

if(my_select->state==TASK_STATE_READY)nready++;

nice=my_select->nice;

ratio=fixedpt_mul(FIXEDPT_TWO,g_load_avg);//每秒钟为所有线程(运行、就绪和等待)更新一次

ratio=fixedpt_div(ratio,fixedpt_add(ratio,FIXEDPT_ONE));

my_select->estcpu=fixedpt_add(fixedpt_mul(ratio,my_select->estcpu),

fixedpt_fromint(nice));

my_select=my_select->next;

}

fixedptr59_60=fixedpt_div(fixedpt_fromint(59),fixedpt_fromint(60));//计算系统的平均负荷g_load_avg

fixedptr01_60=fixedpt_div(FIXEDPT_ONE,fixedpt_fromint(60));

g_load_avg=fixedpt_add(fixedpt_mul(r59_60,g_load_avg),

fixedpt_mul(r01_60,fixedpt_fromint(nready)));

}

主函数:

intmode=0x0118;

initGraphics(mode);

inty=0;

for(y=0;y

setPixel(g_mib.XResolution/3,y,RGB(0,125,125));

setPixel(g_mib.XResolution/3*2,y,RGB(0,125,125));

}

int*pcode_exit;

//申请用户栈

unsignedchar*stack_foo1=(unsignedchar*)malloc(1024*1024);

unsignedchar*stack_foo2=(unsignedchar*)malloc(1024*1024);

unsignedchar*stack_foo3=(unsignedchar*)malloc(1024*1024);

unsignedchar*stack_foo4=(unsignedchar*)malloc(1024*1024);

inttid_foo1,tid_foo2,tid_foo3;

setpriority(0,8);

//创建冒泡排序线程函数1

tid_foo1=task_create(stack_foo1+1024*1024,tsk_foo_line1,(void*)0);

setpriority(tid_foo1,1);

//创建选择排序线程函数2

tid_foo2=task_create(stack_foo2+1024*1024,tsk_foo_line2,(void*)0);

setpriority(tid_foo2,10);

//创建插入排序线程函数3

tid_foo3=task_create(stack_foo3+1024*1024,tsk_foo_line3,(void*)0);

setpriority(tid_foo3,8);

setpriority(0,35);

//用户栈释放

task_wait(tid_foo1,pcode_exit);

free(stack_foo1);

task_wait(tid_foo2,pcode_exit);

free(stack_foo2);

task_wait(tid_foo3,pcode_exit);

free(stack_foo3);

 

五、实验结果及分析(实现的效果,包括屏幕截图、系统总体运行情况和测试情况等)

静态优先级:

动态优先级:

 

 

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 自然科学

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1