MIT6.828学习之homework5:xv6 CPU alarm

向xv6添加一个功能,当进程使用CPU时间时,该功能会定期发出警报

这个作业主要是分两步完成:
第一步是添加alarm系统调用,这跟homework 3那里添加date系统调用基本一样,根据hint一步步下去就行。这里就不再赘述。
第二步是设置陷入后内核的处理,即修改trap.c/trap()函数,这个是比较难的。

 Hint:Add some new field in struct proc and initialize proc fields in allocproc() in proc.c.
 
 //proc.h/struct proc
 int alarmticks;			   // set the standard for the alarm
  int alarminterval;           // how many ticks have passed since the last call
  void (*alarmhandler)();	   // a function pointer  

//proc.c/allocproc()/found
  // Initialzize some part of ticks
  p->alarminterval = 0;
  p->alarmticks = -1; //if there is no sys_alarm, it will never be valid

这一步还初始化了alarmticks=-1,真是学到了。
void (*alarmhandler)(); 函数指针定义在结构体里,以前也用的少,得多练

Hint: Every tick, the hardware clock forces an interrupt, which is handled in trap() by case T_IRQ0 + IRQ_TIMER; you should add some code here.

Hint: You only want to manipulate a process's alarm ticks if there's a process running and if the timer interrupt came from user space; you want something like

    if(myproc() != 0 && (tf->cs & 3) == 3) ...

Hint: In your IRQ_TIMER code, when a process's alarm interval expires, you'll want to cause it to execute its handler. How can you do that?

Hint: You need to arrange things so that, when the handler returns, the process resumes executing where it left off. How can you do that? 

//trap.c/trap():
case T_IRQ0 + IRQ_TIMER:
    if(cpuid() == 0){
      acquire(&tickslock);
      ticks++;
	  wakeup(&ticks);
      release(&tickslock);
	}
	//if there's a process running and if the timer interrupt came from user space
	if(myproc() != 0 && (tf->cs & 3) == 3){
		myproc()->alarminterval++;
		//cprintf("interval %d alarmticks: %d\n",myproc()->alarminterval,myproc()->alarmticks);
		if(myproc()->alarminterval == myproc()->alarmticks){
			myproc()->alarminterval = 0;
			//myproc()->alarmhandler();是不是每个人写这里都会这样写,hahaha
	    	//cprintf("ticks: %d alarmticks: %d\n", ticks,myproc()->alarmticks);
			//cprintf("%d alarm!\n",myproc()->alarmticks);
	  		//lapiceoi();

			//push the old eip to stack
	  		tf->esp -= 4;
			*((uint*)(tf->esp)) = tf->eip;
			//what in eip will be the next instruction to execute
			tf->eip = (uint)myproc()->alarmhandler;
	    }
	     
	}    
    
    lapiceoi();
    break;

在trap()中试了好多次myproc()->alarmhandler();完全没有用,一度以为是结构体中定义错了,结果是这样:

既然handler在用户态,那么内核态必然不能执行;需要中断切换回用户态后才能执行。那么,如何使得切换回用户态后,执行handler,执行完毕继续执行原来的代码(old eip)呢?很简单,利用函数返回的机制,save and restore,将原来的eip压栈,然后将eip修改为handler的地址即可。对这一块不太清楚的话,可以去看一下trapasm.S,看一下这部分代码是如何陷入中断,然后返回的。
感谢孟永康

写好了这些之后,发现还是不行,
在这里插入图片描述
于是我就把myproc()->alarminterval跟myproc()->alarmticks输出来看看:
在这里插入图片描述
发现interval只到6就停了,让我想起了那个hint:

If you only see one "alarm!", try increasing the number of iterations in alarmtest.c by 10x.

我就把alarmtest.c中i<25500000改成i<250500000
在这里插入图片描述结果还是不太对劲,为什么还是只有5个alarm,点点也不规律且比别人多很多,这是为什么?
可能跟虚拟机时钟频率有关?

最后

还有个问题,就是为什么会陷入到case T_IRQ0 + IRQ_TIMER?
系统在固定的时间间隔都发生一次时钟中断,每当计数器溢出的时候,就会产生中断,陷入到case T_IRQ0 + IRQ_TIMER去处理,处理完后在计数器重置,返回原进程。

“时钟中断”是特别重要的一个中断,因为整个操作系统的活动都受到它的激励。系统利用时钟中断维持系统时间、促使环境的切换,以保证所有进程共享CPU;利用时钟中断进行记帐、监督系统工作以及确定未来的调度优先级等工作。可以说,“时钟中断”是整个操作系统的脉搏。
谢谢Farmwang

参考

Linux之时钟中断详解
HW xv6 CPU Alarm

MIT6.828的第三次作业(homework 3)涉及到操作系统的定时器和中断处理。在这个作业中,学生需要向xv6操作系统添加一个新的系统调用,名为alarm(interval, handler)。当应用程序调用alarm(n, fn)时,内核将在程序消耗每个n个“ticks”的CPU时间后,调用应用程序函数fn。tick是xv6中由硬件定时器产生中断的频率决定的时间单位。 这个作业的目标是实现一个用户级中断/故障处理程序,它可以定期向正在使用CPU时间的进程发出警报。这对于计算密集型进程非常有用,因为它们可以通过限制占用的CPU时间来提高效率,或者对于需要定期执行某些操作的进程也非常适用。 因此,mit6.828hw3主要围绕定时器、中断处理和系统调用展开,学生需要添加新的系统调用并实现相应的功能。这个作业的目的是让学生更深入地理解操作系统的工作原理和中断处理的机制。<span class="em">1</span><span class="em">2</span><span class="em">3</span> #### 引用[.reference_title] - *1* [MIT6.828-2016-中文:MIT 6.828(操作系统)的中文版本](https://download.csdn.net/download/weixin_42098104/14998195)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 50%"] - *2* *3* [MIT6.828_HW5_xv6 CPU alarm](https://blog.csdn.net/Small_Pond/article/details/92838818)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 50%"] [ .reference_list ]
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值