projects
/
pintos-anon
/ blobdiff
commit
grep
author
committer
pickaxe
?
search:
re
summary
|
shortlog
|
log
|
commit
|
commitdiff
|
tree
raw
|
inline
| side by side
thread: Properly protect 'all_list' around insertion.
[pintos-anon]
/
src
/
userprog
/
pagedir.c
diff --git
a/src/userprog/pagedir.c
b/src/userprog/pagedir.c
index 820755ff7ce27911fa67e2926409a1e3f9bde507..a6a87b827ba16a12157d94df6f2a7233b7c59e8e 100644
(file)
--- a/
src/userprog/pagedir.c
+++ b/
src/userprog/pagedir.c
@@
-3,7
+3,7
@@
#include <stddef.h>
#include <string.h>
#include "threads/init.h"
#include <stddef.h>
#include <string.h>
#include "threads/init.h"
-#include "threads/
mmu
.h"
+#include "threads/
pte
.h"
#include "threads/palloc.h"
static uint32_t *active_pd (void);
#include "threads/palloc.h"
static uint32_t *active_pd (void);
@@
-18,7
+18,7
@@
pagedir_create (void)
{
uint32_t *pd = palloc_get_page (0);
if (pd != NULL)
{
uint32_t *pd = palloc_get_page (0);
if (pd != NULL)
- memcpy (pd,
base
_page_dir, PGSIZE);
+ memcpy (pd,
init
_page_dir, PGSIZE);
return pd;
}
return pd;
}
@@
-32,15
+32,15
@@
pagedir_destroy (uint32_t *pd)
if (pd == NULL)
return;
if (pd == NULL)
return;
- ASSERT (pd !=
base
_page_dir);
+ ASSERT (pd !=
init
_page_dir);
for (pde = pd; pde < pd + pd_no (PHYS_BASE); pde++)
for (pde = pd; pde < pd + pd_no (PHYS_BASE); pde++)
- if (*pde & P
G
_P)
+ if (*pde & P
TE
_P)
{
uint32_t *pt = pde_get_pt (*pde);
uint32_t *pte;
for (pte = pt; pte < pt + PGSIZE / sizeof *pte; pte++)
{
uint32_t *pt = pde_get_pt (*pde);
uint32_t *pte;
for (pte = pt; pte < pt + PGSIZE / sizeof *pte; pte++)
- if (*pte & P
G
_P)
+ if (*pte & P
TE
_P)
palloc_free_page (pte_get_page (*pte));
palloc_free_page (pt);
}
palloc_free_page (pte_get_page (*pte));
palloc_free_page (pt);
}
@@
-85,8
+85,9
@@
lookup_page (uint32_t *pd, const void *vaddr, bool create)
return &pt[pt_no (vaddr)];
}
return &pt[pt_no (vaddr)];
}
-/* Adds a mapping from user virtual page UPAGE to kernel virtual
- address KPAGE in page directory PD.
+/* Adds a mapping in page directory PD from user virtual page
+ UPAGE to the physical frame identified by kernel virtual
+ address KPAGE.
UPAGE must not already be mapped.
KPAGE should probably be a page obtained from the user pool
with palloc_get_page().
UPAGE must not already be mapped.
KPAGE should probably be a page obtained from the user pool
with palloc_get_page().
@@
-95,22
+96,21
@@
lookup_page (uint32_t *pd, const void *vaddr, bool create)
Returns true if successful, false if memory allocation
failed. */
bool
Returns true if successful, false if memory allocation
failed. */
bool
-pagedir_set_page (uint32_t *pd, void *upage, void *kpage,
- bool writable)
+pagedir_set_page (uint32_t *pd, void *upage, void *kpage, bool writable)
{
uint32_t *pte;
ASSERT (pg_ofs (upage) == 0);
ASSERT (pg_ofs (kpage) == 0);
ASSERT (is_user_vaddr (upage));
{
uint32_t *pte;
ASSERT (pg_ofs (upage) == 0);
ASSERT (pg_ofs (kpage) == 0);
ASSERT (is_user_vaddr (upage));
- ASSERT (vtop (kpage) >> PTSHIFT < ram_pages);
- ASSERT (pd !=
base
_page_dir);
+ ASSERT (vtop (kpage) >> PTSHIFT <
init_
ram_pages);
+ ASSERT (pd !=
init
_page_dir);
pte = lookup_page (pd, upage, true);
if (pte != NULL)
{
pte = lookup_page (pd, upage, true);
if (pte != NULL)
{
- ASSERT ((*pte & P
G
_P) == 0);
+ ASSERT ((*pte & P
TE
_P) == 0);
*pte = pte_create_user (kpage, writable);
return true;
}
*pte = pte_create_user (kpage, writable);
return true;
}
@@
-118,9
+118,10
@@
pagedir_set_page (uint32_t *pd, void *upage, void *kpage,
return false;
}
return false;
}
-/* Returns the kernel virtual address that user virtual address
- UADDR is mapped to in PD, or a null pointer if UADDR is not
- present. */
+/* Looks up the physical address that corresponds to user virtual
+ address UADDR in PD. Returns the kernel virtual address
+ corresponding to that physical address, or a null pointer if
+ UADDR is unmapped. */
void *
pagedir_get_page (uint32_t *pd, const void *uaddr)
{
void *
pagedir_get_page (uint32_t *pd, const void *uaddr)
{
@@
-129,7
+130,7
@@
pagedir_get_page (uint32_t *pd, const void *uaddr)
ASSERT (is_user_vaddr (uaddr));
pte = lookup_page (pd, uaddr, false);
ASSERT (is_user_vaddr (uaddr));
pte = lookup_page (pd, uaddr, false);
- if (pte != NULL && (*pte & P
G
_P) != 0)
+ if (pte != NULL && (*pte & P
TE
_P) != 0)
return pte_get_page (*pte) + pg_ofs (uaddr);
else
return NULL;
return pte_get_page (*pte) + pg_ofs (uaddr);
else
return NULL;
@@
-148,9
+149,9
@@
pagedir_clear_page (uint32_t *pd, void *upage)
ASSERT (is_user_vaddr (upage));
pte = lookup_page (pd, upage, false);
ASSERT (is_user_vaddr (upage));
pte = lookup_page (pd, upage, false);
- if (pte != NULL && (*pte & P
G
_P) != 0)
+ if (pte != NULL && (*pte & P
TE
_P) != 0)
{
{
- *pte &= ~P
G
_P;
+ *pte &= ~P
TE
_P;
invalidate_pagedir (pd);
}
}
invalidate_pagedir (pd);
}
}
@@
-163,7
+164,7
@@
bool
pagedir_is_dirty (uint32_t *pd, const void *vpage)
{
uint32_t *pte = lookup_page (pd, vpage, false);
pagedir_is_dirty (uint32_t *pd, const void *vpage)
{
uint32_t *pte = lookup_page (pd, vpage, false);
- return pte != NULL && (*pte & P
G
_D) != 0;
+ return pte != NULL && (*pte & P
TE
_D) != 0;
}
/* Set the dirty bit to DIRTY in the PTE for virtual page VPAGE
}
/* Set the dirty bit to DIRTY in the PTE for virtual page VPAGE
@@
-175,10
+176,10
@@
pagedir_set_dirty (uint32_t *pd, const void *vpage, bool dirty)
if (pte != NULL)
{
if (dirty)
if (pte != NULL)
{
if (dirty)
- *pte |= P
G
_D;
+ *pte |= P
TE
_D;
else
{
else
{
- *pte &= ~(uint32_t) P
G
_D;
+ *pte &= ~(uint32_t) P
TE
_D;
invalidate_pagedir (pd);
}
}
invalidate_pagedir (pd);
}
}
@@
-192,7
+193,7
@@
bool
pagedir_is_accessed (uint32_t *pd, const void *vpage)
{
uint32_t *pte = lookup_page (pd, vpage, false);
pagedir_is_accessed (uint32_t *pd, const void *vpage)
{
uint32_t *pte = lookup_page (pd, vpage, false);
- return pte != NULL && (*pte & P
G
_A) != 0;
+ return pte != NULL && (*pte & P
TE
_A) != 0;
}
/* Sets the accessed bit to ACCESSED in the PTE for virtual page
}
/* Sets the accessed bit to ACCESSED in the PTE for virtual page
@@
-204,10
+205,10
@@
pagedir_set_accessed (uint32_t *pd, const void *vpage, bool accessed)
if (pte != NULL)
{
if (accessed)
if (pte != NULL)
{
if (accessed)
- *pte |= P
G
_A;
+ *pte |= P
TE
_A;
else
{
else
{
- *pte &= ~(uint32_t) P
G
_A;
+ *pte &= ~(uint32_t) P
TE
_A;
invalidate_pagedir (pd);
}
}
invalidate_pagedir (pd);
}
}
@@
-219,13
+220,14
@@
void
pagedir_activate (uint32_t *pd)
{
if (pd == NULL)
pagedir_activate (uint32_t *pd)
{
if (pd == NULL)
- pd =
base
_page_dir;
+ pd =
init
_page_dir;
/* Store the physical address of the page directory into CR3
aka PDBR (page directory base register). This activates our
new page tables immediately. See [IA32-v2a] "MOV--Move
/* Store the physical address of the page directory into CR3
aka PDBR (page directory base register). This activates our
new page tables immediately. See [IA32-v2a] "MOV--Move
- to/from Control Registers" and [IA32-v3] 3.7.5. */
- asm volatile ("movl %0, %%cr3" :: "r" (vtop (pd)));
+ to/from Control Registers" and [IA32-v3a] 3.7.5 "Base
+ Address of the Page Directory". */
+ asm volatile ("movl %0, %%cr3" : : "r" (vtop (pd)) : "memory");
}
/* Returns the currently active page directory. */
}
/* Returns the currently active page directory. */
@@
-235,7
+237,7
@@
active_pd (void)
/* Copy CR3, the page directory base register (PDBR), into
`pd'.
See [IA32-v2a] "MOV--Move to/from Control Registers" and
/* Copy CR3, the page directory base register (PDBR), into
`pd'.
See [IA32-v2a] "MOV--Move to/from Control Registers" and
- [IA32-v3
] 3.7.5
. */
+ [IA32-v3
a] 3.7.5 "Base Address of the Page Directory"
. */
uintptr_t pd;
asm volatile ("movl %%cr3, %0" : "=r" (pd));
return ptov (pd);
uintptr_t pd;
asm volatile ("movl %%cr3, %0" : "=r" (pd));
return ptov (pd);
@@
-254,9
+256,8
@@
invalidate_pagedir (uint32_t *pd)
{
if (active_pd () == pd)
{
{
if (active_pd () == pd)
{
- /* We cleared a page-table entry in the active page
- table, so we have to invalidate the TLB. See
- [IA32-v3], section 3.11. */
+ /* Re-activating PD clears the TLB. See [IA32-v3a] 3.12
+ "Translation Lookaside Buffers (TLBs)". */
pagedir_activate (pd);
}
}
pagedir_activate (pd);
}
}