ucore lab2
程序员文章站
2022-07-12 16:55:05
...
challange我还是懒得写,不过这个lab2的challange类似于csapp的malloc lab,可以说是很类似,不止challange,我起初没注意他的数据结构形式,写错了,当成fastbin那种写的
整套实验基本就是用提供的函数实现功能,比起之前做的csapp和cs144的lab难度友好太多了
练习一
static void
default_init(void) {
list_init(&free_list);
nr_free = 0;
}
static void
default_init_memmap(struct Page *base, size_t n) {
assert(n > 0);
struct Page *p = base;
SetPageProperty(p);
for (; p != base + n; p ++) {
assert(PageReserved(p));
p->flags = p->property = 0;
SetPageProperty(p);
set_page_ref(p, 0);
list_add_before(&free_list, &(p->page_link));
}
base->property = n;
nr_free += n;
}
static struct Page *
default_alloc_pages(size_t n) {
assert(n > 0);
if (n > nr_free) {
return NULL;
}
struct Page *page = NULL;
list_entry_t *le = &free_list;
list_entry_t *nextle;
while ((le = list_next(le)) != &free_list) {
struct Page *p = le2page(le, page_link);
if (p->property >= n) {
page = p;
break;
}
}
if (page != NULL) {
int temp;
struct Page *tempPage;
for(temp=0;temp<n;temp++){
nextle=list_next(le);
tempPage=le2page(le, page_link);
SetPageReserved(tempPage);
ClearPageProperty(tempPage);
list_del(le);
le = nextle;
}
if (page->property > n) {
le2page(le,page_link)->property = page->property - n;
}
ClearPageProperty(page);
SetPageReserved(page);
nr_free -= n;
}
return page;
}
static void
default_free_pages(struct Page *base, size_t n) {
assert(n > 0);
struct Page *p = base;
for (; p != base + n; p ++) {
assert(!PageReserved(p) && !PageProperty(p));
p->flags = 0;
set_page_ref(p, 0);
}
base->property = n;
SetPageProperty(base);
list_entry_t *le = list_next(&free_list);
while (le != &free_list) {
p = le2page(le, page_link);
le = list_next(le);
if (base + base->property == p) {
base->property += p->property;
ClearPageProperty(p);
list_del(&(p->page_link));
}
else if (p + p->property == base) {
p->property += base->property;
ClearPageProperty(base);
base = p;
list_del(&(p->page_link));
}
}
nr_free += n;
le=list_next(&free_list);
while(le!=&free_list)
{
p=le2page(le,page_link);
if(base+base->property<=p){
assert(base+base->property!=p);
break;
}
le=list_next(le);
}
list_add(&free_list, &(base->page_link));
}
说一下free,记得merge,当我free掉的一个能和他周围的合并的话,那就合并,并且alloc时也能取一部分然后分割合并,做过堆题的pwn对这应该很熟悉了,然后就。。没什么好说的,剩下俩练习注释就跟我自己注解的一样详细,一行一注释,没啥好解释的了,直接代码吧
另外上面free里面对于插入链表的le的位置搜索我起初没有,当时我没有发现问题,这里是看了答案才添上去的
练习2
pde_t *pdep = &pgdir[PDX(la)];
if (!(*pdep & PTE_P)) {
struct Page *page;
//不需要分配或是分配失败
if (!create || (page = alloc_page()) == NULL) {
return NULL;
}
set_page_ref(page, 1);
uintptr_t pa = page2pa(page);
memset(KADDR(pa), 0, PGSIZE);
*pdep = pa | PTE_U | PTE_W | PTE_P;
}
return &((pte_t *)KADDR(PDE_ADDR(*pdep)))[PTX(la)];
练习三
if (ptep&PTE_P) { //(1) check if this page table entry is present
struct Page *page = pte2page(*ptep); //(2) find corresponding page to pte
page_ref_dec(page) //(3) decrease page reference
if(page->ref==0) free_page(page); //(4) and free this page when page reference reachs 0
*ptep = 0; //(5) clear second page table entry
tlb_invalidate(pgdir,la); //(6) flush tlb
challange不想写,csapp的lab有类似的实现,继续看书去了