MIT_6.828_2018_xv6_lazy_page_allocation

作业地址:xv6 lazy page allocation

Part One: Eliminate allocation from sbrk()

在sysproc.c中找到sys_sbrk(void)函数,注释掉:

 /*
  if(growproc(n) < 0)
    return -1;
*/ 

即可。

Part Two: Lazy allocation

在trap.c中将default情况改为如下:

  default:
    if(myproc() == 0 || (tf->cs&3) == 0){
      // In kernel, it must be our mistake.
      cprintf("unexpected trap %d from cpu %d eip %x (cr2=0x%x)\n",
              tf->trapno, cpuid(), tf->eip, rcr2());
      panic("trap");
    }

	//缺页的情况
	if (tf->trapno == T_PGFLT)
	{
		char* pa;
		uint addr =  PGROUNDDOWN(rcr2());
		pa = kalloc();

		if (pa == 0)
		{
			panic("in functio trap:out of memory\n");
			return;
		}
		
		memset(pa,0,PGSIZE);
		
		if (mappages(myproc()->pgdir,(void*)addr,PGSIZE,V2P(pa),PTE_W|PTE_U)<0)
		{
			panic("error occurs while mapping:in function trap\n");
			return ;
		}

		break;

	}
	//缺页情况结束

    // In user space, assume process misbehaved.
    cprintf("pid %d %s: trap %d err %d on cpu %d "
            "eip 0x%x addr 0x%x--kill proc\n",
            myproc()->pid, myproc()->name, tf->trapno,
            tf->err, cpuid(), tf->eip, rcr2());
    myproc()->killed = 1;
  }

  // Force process exit if it has been killed and is in user space.
  // (If it is still executing in the kernel, let it keep running
  // until it gets to the regular system call return.)
  if(myproc() && myproc()->killed && (tf->cs&3) == DPL_USER)
    exit();

  // Force process to give up CPU on clock tick.
  // If interrupts were on while locks held, would need to check nlock.
  if(myproc() && myproc()->state == RUNNING &&
     tf->trapno == T_IRQ0+IRQ_TIMER)
    yield();

  // Check if the process has been killed since we yielded
  if(myproc() && myproc()->killed && (tf->cs&3) == DPL_USER)
    exit();

大概思想就是:为发生错误的地址处分配一个物理页,并将其进行相应的映射。

Optional challenges

Handle negative sbrk() arguments

在sysproc.c的sys_sbrk(void)里面添加一个判断语句:

	if (n < 0)
	{
		if (growproc(n)<0)	
			return -1;
	}

为负的情况直接释放掉。

Handle error cases such as sbrk() arguments that are too large

判断虚拟地址是否涉及到内核部分:

	if (addr+n>KERNBASE)
	{
		cprintf("ABOVE KERNBASE!\n");
		return -1;
	}

所以最终的sys_sbrk应该是下面这样:

int
sys_sbrk(void)
{
  int addr;
  int n;

  if(argint(0, &n) < 0)
    return -1;

  addr = myproc()->sz;

	if (n < 0)
	{
		if (growproc(n)<0)	
			return -1;
	}

	if (addr+n>KERNBASE)
	{
		cprintf("ABOVE KERNBASE!\n");
		return -1;
	}
 /*
  if(growproc(n) < 0)
    return -1;
*/ 
 myproc()->sz += n;
 return addr;
}

后面的略。

END.

  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值