๐ฉ๐ปโ๐ป GITHUB ๋ ํฌ์งํ ๋ฆฌ
๐ฉ๐ปโ๐ป GITHUB Memory Mapped Files ์ด์
Anonymous Memory๊ฐ ์๋ File-Backed memory = Memory Mapped Page์ ๋ํด ๊ตฌํํด์ผํ๋ค.
File backed page์ ์๋ ๋ด์ฉ๋ฌผ๋ค์ ๋ชจ๋ ๋์คํฌ์์ ์กด์ฌํ๊ณ ์๋ ํ์ผ์ ๋ณต์ฌํ ๊ฒ์ด๋ค. ๋ง์ฝ ํ์ด์ง ํดํธ๊ฐ ์ผ์ด๋๋ฉด ๋ฐ๋ก ๋ฌผ๋ฆฌ ํ๋ ์์ด ํ ๋น๋๊ณ ๋ฌผ๋ฆฌ ํ๋ ์์ ํ์ผ์ ๋ฐ์ดํฐ๊ฐ ๋ณต์ฌ๋๋ค.
๋์คํฌ์ ์๋ ํ์ผ์ ๋ํ ์ ์ ๊ฐ์ ํ์ด์ง๋ฅผ ๋ฏธ๋ฆฌ ๊ฐ์ ์ฃผ์ ๊ณต๊ฐ์ ํ ๋นํด์ฃผ๋ ๊ฒ์ mmap์ด๋ผ ํ๊ณ , ํ์ด์ง์ ๋ฌผ๋ฆฌ ๋ฉ๋ชจ๋ฆฌ๊ฐ ์ฐ๊ฒฐ๋ ๊ฒฝ์ฐ ๊ทธ ์ฐ๊ฒฐ์ ๋์ด์ฃผ๋ ๊ฒ์ munmap์ด๋ผ ํ๋ค.
๋ง์ฝ file backed page๊ฐ memory unmapped๋๊ฑฐ๋ swap out ๋๋ฉด, ํด๋น ๋ฉ๋ชจ๋ฆฌ์ ๋ณํ๊ฐ ์๊ธด ๊ฒฝ์ฐ(dirty bit) ๊ทธ ๋ณํ๋ฅผ ํ์ผ์ ์ ๋ฐ์ดํธํ๊ณ memory unmapped๋๊ฑฐ๋ swap out๋์ด์ผ ํ๋ค.
mmap() ์์คํ ์ฝ์ ์ํด ๋งคํ๋ ๊ฐ์ ๋ฉ๋ชจ๋ฆฌ๋ ์คํ๊ณผ ํ ์ฌ์ด์ ๋ฏธํ ๋น ๊ณต๊ฐ(์คํ๋ ์๋๊ณ ํ๋ ์๋)์ ๋งคํ๋๋ค.
/** Project 3-Memory Mapped Files */
#include "include/filesys/off_t.h";
#include "stddef.h";
void *mmap(void *addr, size_t length, int writable, int fd, off_t offset);
void munmap(void *addr);
/** Project 3-Memory Mapped FIles */
#ifdef VM
case SYS_MMAP:
f->R.rax = mmap(f->R.rdi, f->R.rsi, f->R.rdx, f->R.r10, f->R.r8);
break;
#endif
/** Project 3-Memory Mapped FIles */
#ifdef VM
void
*mmap(void *addr, size_t length, int writable, int fd, off_t offset) {
if (!addr || pg_round_down(addr) != addr || is_kernel_vaddr(addr) || is_kernel_vaddr(addr + length))
return NULL;
if (offset != pg_round_down(offset) || offset % PGSIZE != 0)
return NULL;
if (spt_find_page(&thread_current()->spt, addr))
return NULL;
struct file *file = process_get_file(fd);
if ((file >= STDIN && file <= STDERR) || file == NULL)
return NULL;
if (file_length(file) == 0 || (long)length <= 0)
return NULL;
return do_mmap(addr, length, writable, file, offset);
}
#endif
/** Project 3-Memory Mapped Files */
#include "include/filesys/off_t.h";
#include "stddef.h";
void *mmap(void *addr, size_t length, int writable, int fd, off_t offset);
void munmap(void *addr);
extern struct lock filesys_lock;
/** Project 3-Memory Mapped FIles */
#include "threads/vaddr.h"
#include "userprog/syscall.c"
.
.
.
void *
do_mmap (void *addr, size_t length, int writable,
struct file *file, off_t offset) {
/** Project 3-Memory Mapped FIles */
lock_acquire(&filesys_lock);
struct file *mfile = file_reopen(file);
void *ori_addr = addr;
size_t read_bytes = (length > file_length(mfile)) ? file_length(mfile) : length;
size_t zero_bytes = PGSIZE - read_bytes % PGSIZE;
ASSERT((read_bytes + zero_bytes) % PGSIZE == 0);
ASSERT(pg_ofs(addr) == 0);
ASSERT(offset % PGSIZE == 0);
struct vm_load_arg *aux;
while (read_bytes > 0 || zero_bytes > 0) {
size_t page_read_bytes = read_bytes < PGSIZE ? read_bytes : PGSIZE;
size_t page_zero_bytes = PGSIZE - page_read_bytes;
aux = (struct vm_load_arg *)malloc(sizeof(struct vm_load_arg));
if (!aux)
goto err;
aux->file = mfile;
aux->ofs = offset;
aux->read_bytes = page_read_bytes;
if (!vm_alloc_page_with_initializer(VM_FILE, addr, writable, lazy_load_segment, aux)) {
goto err;
}
read_bytes -= page_read_bytes;
zero_bytes -= page_zero_bytes;
addr += PGSIZE;
offset += page_read_bytes;
}
lock_release(&filesys_lock);
return ori_addr;
err:
free(aux);
lock_release(&filesys_lock);
return NULL;
}
/** Project 3-Memory Mapped Files */
#include "include/filesys/off_t.h";
#include "stddef.h";
void *mmap(void *addr, size_t length, int writable, int fd, off_t offset);
void munmap(void *addr);
/** Project 3-Memory Mapped FIles */
#ifdef VM
case SYS_MMAP:
f->R.rax = mmap(f->R.rdi, f->R.rsi, f->R.rdx, f->R.r10, f->R.r8);
break;
case SYS_MUNMAP:
munmap(f->R.rdi);
break;
#endif
/** Project 3-Memory Mapped Files */
void munmap(void *addr) {
do_munmap(addr);
}
/** #Project 3: Memory Mapped Files */
bool lazy_load_segment(struct page *page, void *aux);
static bool
lazy_load_segment (struct page *page, void *aux) {
/** Project 3-Anonymous Page */
struct vm_load_arg *aux_p = aux;
.
.
.
bool
lazy_load_segment (struct page *page, void *aux) {
/** Project 3-Anonymous Page */
struct vm_load_arg *aux_p = aux;
.
.
.
/** Project 3-Memory Mapped FIles */
#include "threads/mmu.h"
#include "threads/vaddr.h"
#include "userprog/process.h"
#include "userprog/syscall.h"
void
do_munmap (void *addr) {
/** Project 3-Memory Mapped FIles */
struct thread *curr = thread_current();
struct page *page;
lock_acquire(&filesys_lock);
while ((page = spt_find_page(&curr->spt, addr))) {
if (page)
destroy(page);
addr += PGSIZE;
}
lock_release(&filesys_lock);
}
bool
file_backed_initializer (struct page *page, enum vm_type type, void *kva) {
/* Set up the handler */
page->operations = &file_ops;
struct file_page *file_page = &page->file;
/** Project 3-Memory Mapped Files */
struct vm_load_arg *aux = (struct vm_load_arg *)page->uninit.aux;
file_page->file = aux->file;
file_page->offset = aux->ofs;
file_page->page_read_bytes = aux->read_bytes;
return true;
}
static void
file_backed_destroy (struct page *page) {
struct file_page *file_page UNUSED = &page->file;
/** Project 3-Memory Mapped Files */
if (pml4_is_dirty(thread_current()->pml4, page->va)) {
file_write_at(file_page->file, page->va, file_page->page_read_bytes, file_page->offset);
pml4_set_dirty(thread_current()->pml4, page->va, false);
}
if (page->frame) {
list_remove(&page->frame->frame_elem);
page->frame->page = NULL;
page->frame = NULL;
free(page->frame);
}
pml4_clear_page(thread_current()->pml4, page->va);
}
void
spt_remove_page (struct supplemental_page_table *spt, struct page *page) {
/** Project 3-Memory Mapped Files */
hash_delete(&thread_current()->spt.spt_hash, &page->hash_elem);
vm_dealloc_page (page);
return true;
}
bool
supplemental_page_table_copy (struct supplemental_page_table *dst UNUSED,
struct supplemental_page_table *src UNUSED) {
/** Project 3-Memory Mapped Files */
struct hash_iterator iter;
hash_first(&iter, &src->spt_hash);
while (hash_next(&iter)) {
struct page *src_page = hash_entry(hash_cur(&iter), struct page, hash_elem);
enum vm_type type = src_page->operations->type;
void *upage = src_page->va;
bool writable = src_page->writable;
if (type == VM_UNINIT) {
void *aux = src_page->uninit.aux;
vm_alloc_page_with_initializer(page_get_type(src_page), upage, writable, src_page->uninit.init, aux);
}
else if (type == VM_FILE) {
struct vm_load_arg *aux = malloc(sizeof(struct vm_load_arg));
aux->file = src_page->file.file;
aux->ofs = src_page->file.offset;
aux->read_bytes = src_page->file.page_read_bytes;
if (!vm_alloc_page_with_initializer(type, upage, writable, NULL, aux))
return false;
struct page *dst_page = spt_find_page(dst, upage);
file_backed_initializer(dst_page, type, NULL);
dst_page->frame = src_page->frame;
pml4_set_page(thread_current()->pml4, dst_page->va, src_page->frame->kva, src_page->writable);
}
else {
if (!vm_alloc_page(type, upage, writable))
return false;
if (!vm_claim_page(upage))
return false;
struct page *dst_page = spt_find_page(dst, upage);
memcpy(dst_page->frame->kva, src_page->frame->kva, PGSIZE);
}
}
return true;
}
if ((!not_present && write) || (fault_addr < 0x400000 ))
{
exit(-1);
}
if ((!not_present && write) || (fault_addr < 0x400000 ))
{
exit(-1);
}
pass tests/userprog/args-none
pass tests/userprog/args-single
pass tests/userprog/args-multiple
pass tests/userprog/args-many
pass tests/userprog/args-dbl-space
pass tests/userprog/halt
pass tests/userprog/exit
pass tests/userprog/create-normal
pass tests/userprog/create-empty
pass tests/userprog/create-null
pass tests/userprog/create-bad-ptr
pass tests/userprog/create-long
pass tests/userprog/create-exists
pass tests/userprog/create-bound
pass tests/userprog/open-normal
pass tests/userprog/open-missing
pass tests/userprog/open-boundary
pass tests/userprog/open-empty
pass tests/userprog/open-null
pass tests/userprog/open-bad-ptr
pass tests/userprog/open-twice
pass tests/userprog/close-normal
pass tests/userprog/close-twice
pass tests/userprog/close-bad-fd
pass tests/userprog/read-normal
pass tests/userprog/read-bad-ptr
pass tests/userprog/read-boundary
pass tests/userprog/read-zero
pass tests/userprog/read-stdout
pass tests/userprog/read-bad-fd
pass tests/userprog/write-normal
pass tests/userprog/write-bad-ptr
pass tests/userprog/write-boundary
pass tests/userprog/write-zero
pass tests/userprog/write-stdin
pass tests/userprog/write-bad-fd
pass tests/userprog/fork-once
pass tests/userprog/fork-multiple
pass tests/userprog/fork-recursive
pass tests/userprog/fork-read
pass tests/userprog/fork-close
pass tests/userprog/fork-boundary
pass tests/userprog/exec-once
pass tests/userprog/exec-arg
pass tests/userprog/exec-boundary
pass tests/userprog/exec-missing
pass tests/userprog/exec-bad-ptr
pass tests/userprog/exec-read
pass tests/userprog/wait-simple
pass tests/userprog/wait-twice
pass tests/userprog/wait-killed
pass tests/userprog/wait-bad-pid
pass tests/userprog/multi-recurse
pass tests/userprog/multi-child-fd
pass tests/userprog/rox-simple
pass tests/userprog/rox-child
pass tests/userprog/rox-multichild
pass tests/userprog/bad-read
pass tests/userprog/bad-write
pass tests/userprog/bad-read2
pass tests/userprog/bad-write2
pass tests/userprog/bad-jump
pass tests/userprog/bad-jump2
pass tests/vm/pt-grow-stack
pass tests/vm/pt-grow-bad
pass tests/vm/pt-big-stk-obj
pass tests/vm/pt-bad-addr
pass tests/vm/pt-bad-read
pass tests/vm/pt-write-code
pass tests/vm/pt-write-code2
pass tests/vm/pt-grow-stk-sc
pass tests/vm/page-linear
pass tests/vm/page-parallel
pass tests/vm/page-merge-seq
pass tests/vm/page-merge-par
FAIL tests/vm/page-merge-stk
FAIL tests/vm/page-merge-mm
pass tests/vm/page-shuffle
pass tests/vm/mmap-read
pass tests/vm/mmap-close
pass tests/vm/mmap-unmap
pass tests/vm/mmap-overlap
pass tests/vm/mmap-twice
pass tests/vm/mmap-write
pass tests/vm/mmap-ro
pass tests/vm/mmap-exit
pass tests/vm/mmap-shuffle
pass tests/vm/mmap-bad-fd
pass tests/vm/mmap-clean
pass tests/vm/mmap-inherit
pass tests/vm/mmap-misalign
pass tests/vm/mmap-null
pass tests/vm/mmap-over-code
pass tests/vm/mmap-over-data
pass tests/vm/mmap-over-stk
pass tests/vm/mmap-remove
pass tests/vm/mmap-zero
pass tests/vm/mmap-bad-fd2
pass tests/vm/mmap-bad-fd3
pass tests/vm/mmap-zero-len
pass tests/vm/mmap-off
pass tests/vm/mmap-bad-off
pass tests/vm/mmap-kernel
pass tests/vm/lazy-file
pass tests/vm/lazy-anon
FAIL tests/vm/swap-file
FAIL tests/vm/swap-anon
FAIL tests/vm/swap-iter
FAIL tests/vm/swap-fork
pass tests/filesys/base/lg-create
pass tests/filesys/base/lg-full
pass tests/filesys/base/lg-random
pass tests/filesys/base/lg-seq-block
pass tests/filesys/base/lg-seq-random
pass tests/filesys/base/sm-create
pass tests/filesys/base/sm-full
pass tests/filesys/base/sm-random
pass tests/filesys/base/sm-seq-block
pass tests/filesys/base/sm-seq-random
pass tests/filesys/base/syn-read
pass tests/filesys/base/syn-remove
pass tests/filesys/base/syn-write
pass tests/threads/alarm-single
pass tests/threads/alarm-multiple
pass tests/threads/alarm-simultaneous
pass tests/threads/alarm-priority
pass tests/threads/alarm-zero
pass tests/threads/alarm-negative
pass tests/threads/priority-change
pass tests/threads/priority-donate-one
pass tests/threads/priority-donate-multiple
pass tests/threads/priority-donate-multiple2
pass tests/threads/priority-donate-nest
pass tests/threads/priority-donate-sema
pass tests/threads/priority-donate-lower
pass tests/threads/priority-fifo
pass tests/threads/priority-preempt
pass tests/threads/priority-sema
pass tests/threads/priority-condvar
pass tests/threads/priority-donate-chain
FAIL tests/vm/cow/cow-simple
7 of 141 tests failed.
tests/vm/page-merge-seq
tests/vm/page-merge-par
tests/vm/page-merge-stk
tests/vm/page-merge-mm
๐น page-merge ๊ด๋ จ ํ ์คํธ๋ค์ด ์ ๋ถ ํต๊ณผํ์ง ๋ชปํ๋ค. ์ด์ ๊ฐ ๋ญ๊น...
open์ด ์คํจํ๋ค๊ณ ๋ฌ๋ค...
ํ์์๊ฒ ๋ฌผ์ด๋ณด๋ ์๋๊ฐ ๋น ๋ฅธ๊ฑฐ๋ผ๊ณ ํ๋ค..(?)
๊ทธ๋ฆฌ๊ณ fdt๋ฅผ linked_list๋ก ๊ตฌํํ ํ์ ์ด ๋ฌธ์ ๊ฐ ๋ฐ์ํ์ง ์๋๋ค.
ํ์ ๋ง๋ก๋ linked_list๊ฐ ๊ฒ์ ์๋๊ฐ ๋๋ ค์ ์๋ ๋ฌธ์ ๊ฐ ๋ฐ์ํ์ง ์๋๋ค๊ณ ํ๋ค.
ํด๊ฒฐํ์!!!!!!!!!
bool
create(const char *file, unsigned initial_size)
{
check_address(file);
lock_acquire(&filesys_lock);
bool success = filesys_create(file, initial_size);
lock_release(&filesys_lock);
return success;
}
bool
remove(const char *file)
{
check_address(file);
lock_acquire(&filesys_lock);
bool success = filesys_remove(file);
lock_release(&filesys_lock);
return success;
}
int
open(const char *file)
{
check_address(file);
lock_acquire(&filesys_lock);
struct file *newfile = filesys_open(file);
if (newfile == NULL)
goto err;
int fd = process_add_file(newfile);
if (fd == -1)
file_close(newfile);
lock_release(&filesys_lock);
return fd;
err:
lock_release(&filesys_lock);
return -1;
}
/** Project 3-Memory Mapped FIles */
#include "userprog/syscall.h"
static bool
load (const char *file_name, struct intr_frame *if_) {
struct thread *t = thread_current();
struct ELF ehdr;
struct file *file = NULL;
off_t file_ofs;
bool success = false;
int i;
/* Allocate and activate page directory. */
t->pml4 = pml4_create();
if (t->pml4 == NULL)
goto done;
process_activate(thread_current());
/* Open executable file. */
lock_acquire(&filesys_lock); /** Project 3-Memory Mapped FIles */
file = filesys_open(file_name);
if (file == NULL) {
printf("load: %s: open failed\n", file_name);
goto done;
}
/** project2-System Call - ํ์ผ ์คํ ๋ช
์ ๋ฐ ์ ๊ทผ ๊ธ์ง ์ค์ */
t->runn_file = file;
file_deny_write(file); /** Project 2: Denying Writes to Executables */
/* Read and verify executable header. */
if (file_read(file, &ehdr, sizeof ehdr) != sizeof ehdr || memcmp(ehdr.e_ident, "\177ELF\2\1\1", 7) || ehdr.e_type != 2 || ehdr.e_machine != 0x3E // amd64
|| ehdr.e_version != 1 || ehdr.e_phentsize != sizeof(struct Phdr) || ehdr.e_phnum > 1024) {
printf("load: %s: error loading executable\n", file_name);
goto done;
}
/* Read program headers. */
file_ofs = ehdr.e_phoff;
for (i = 0; i < ehdr.e_phnum; i++) {
struct Phdr phdr;
if (file_ofs < 0 || file_ofs > file_length(file))
goto done;
file_seek(file, file_ofs);
if (file_read(file, &phdr, sizeof phdr) != sizeof phdr)
goto done;
file_ofs += sizeof phdr;
switch (phdr.p_type) {
case PT_NULL:
case PT_NOTE:
case PT_PHDR:
case PT_STACK:
default:
/* Ignore this segment. */
break;
case PT_DYNAMIC:
case PT_INTERP:
case PT_SHLIB:
goto done;
case PT_LOAD:
if (validate_segment(&phdr, file)) {
bool writable = (phdr.p_flags & PF_W) != 0;
uint64_t file_page = phdr.p_offset & ~PGMASK;
uint64_t mem_page = phdr.p_vaddr & ~PGMASK;
uint64_t page_offset = phdr.p_vaddr & PGMASK;
uint32_t read_bytes, zero_bytes;
if (phdr.p_filesz > 0) {
/* Normal segment.
* Read initial part from disk and zero the rest. */
read_bytes = page_offset + phdr.p_filesz;
zero_bytes = (ROUND_UP(page_offset + phdr.p_memsz, PGSIZE) - read_bytes);
} else {
/* Entirely zero.
* Don't read anything from disk. */
read_bytes = 0;
zero_bytes = ROUND_UP(page_offset + phdr.p_memsz, PGSIZE);
}
if (!load_segment(file, file_page, (void *)mem_page, read_bytes, zero_bytes, writable))
goto done;
} else
goto done;
break;
}
}
/* Set up stack. */
if (!setup_stack(if_))
goto done;
/* Start address. */
if_->rip = ehdr.e_entry;
success = true;
done:
/* We arrive here whether the load is successful or not. */
// file_close(file);
lock_release(&filesys_lock); /** Project 3-Memory Mapped FIles */
return success;
}
void check_valid_buffer(void *buffer, size_t size, bool writable);
/** Project 3-Memory Mapped Files ๋ฒํผ ์ ํจ์ฑ ๊ฒ์ฌ */
void check_valid_buffer(void *buffer, size_t size, bool writable) {
for (size_t i = 0; i < size; i += 8) {
/* buffer๊ฐ spt์ ์กด์ฌํ๋์ง ๊ฒ์ฌ */
struct page *page = check_address(buffer + i);
if (!page || (writable && !(page->writable)))
exit(-1);
}
}
์ด๋ค๋์๋ ++ ์ฆ๊ฐ์ผ๋ก ํด์ผ ํต๊ณผํ๊ณ , ์ด๋ค๋์๋ +=8 ์ฆ๊ฐ์ผ๋ก ํด์ผ ํต๊ณผ๊ฐ ๋๋ค.
ํ์ง๋ง ์ง๊ธ์ +=8๋ก ๊ณ์ ํต๊ณผ๋๋ ์ถ์ธ...
์ด์ ๋ ๋ชจ๋ฅด๊ฒ ๋ฐ.. ใ
ใ
open ๋ฌธ์ ์ TIMEOUT ๋ฌธ์ ๊ฐ ๋ฐ๋ณต๋๋ค๋ฉด ์ด ์ฆ๊ฐ์ ์ค์ด๊ฑฐ๋ ๋๋ ค์ ํด๊ฒฐํด๋ณด์ ใ
ใ
int
read(int fd, void *buffer, unsigned length)
{
#ifdef VM
check_valid_buffer(buffer, length, true);
#endif
...
}
int
write(int fd, const void *buffer, unsigned length)
{
#ifdef VM
check_valid_buffer(buffer, length, false);
#endif
...
}
์ฌ๊ธฐ๊น์ง ํ๋๋ฐ๋ fork์์ ์ค๋ฅ๊ฐ ๋ด์๋ค...
project1์์ ๊ตฌํํ donate_prorty()
๋ฌธ์ ์๋ค ใ
ใ
if (t == NULL)
break;
์กฐ๊ฑด์ ์ถ๊ฐํด์ฃผ์
void
donate_priority()
{
struct thread *t = thread_current();
int priority = t->priority;
for (int depth = 0; depth < 8; depth++)
{
if (t->wait_lock == NULL)
break;
t = t->wait_lock->holder;
/** Project 3-Memory Mapped Files */
if (t == NULL)
break;
t->priority = priority;
}
}
pass tests/userprog/args-none
pass tests/userprog/args-single
pass tests/userprog/args-multiple
pass tests/userprog/args-many
pass tests/userprog/args-dbl-space
pass tests/userprog/halt
pass tests/userprog/exit
pass tests/userprog/create-normal
pass tests/userprog/create-empty
pass tests/userprog/create-null
pass tests/userprog/create-bad-ptr
pass tests/userprog/create-long
pass tests/userprog/create-exists
pass tests/userprog/create-bound
pass tests/userprog/open-normal
pass tests/userprog/open-missing
pass tests/userprog/open-boundary
pass tests/userprog/open-empty
pass tests/userprog/open-null
pass tests/userprog/open-bad-ptr
pass tests/userprog/open-twice
pass tests/userprog/close-normal
pass tests/userprog/close-twice
pass tests/userprog/close-bad-fd
pass tests/userprog/read-normal
pass tests/userprog/read-bad-ptr
pass tests/userprog/read-boundary
pass tests/userprog/read-zero
pass tests/userprog/read-stdout
pass tests/userprog/read-bad-fd
pass tests/userprog/write-normal
pass tests/userprog/write-bad-ptr
pass tests/userprog/write-boundary
pass tests/userprog/write-zero
pass tests/userprog/write-stdin
pass tests/userprog/write-bad-fd
pass tests/userprog/fork-once
pass tests/userprog/fork-multiple
pass tests/userprog/fork-recursive
pass tests/userprog/fork-read
pass tests/userprog/fork-close
pass tests/userprog/fork-boundary
pass tests/userprog/exec-once
pass tests/userprog/exec-arg
pass tests/userprog/exec-boundary
pass tests/userprog/exec-missing
pass tests/userprog/exec-bad-ptr
pass tests/userprog/exec-read
pass tests/userprog/wait-simple
pass tests/userprog/wait-twice
pass tests/userprog/wait-killed
pass tests/userprog/wait-bad-pid
pass tests/userprog/multi-recurse
pass tests/userprog/multi-child-fd
pass tests/userprog/rox-simple
pass tests/userprog/rox-child
pass tests/userprog/rox-multichild
pass tests/userprog/bad-read
pass tests/userprog/bad-write
pass tests/userprog/bad-read2
pass tests/userprog/bad-write2
pass tests/userprog/bad-jump
pass tests/userprog/bad-jump2
pass tests/vm/pt-grow-stack
pass tests/vm/pt-grow-bad
pass tests/vm/pt-big-stk-obj
pass tests/vm/pt-bad-addr
pass tests/vm/pt-bad-read
pass tests/vm/pt-write-code
pass tests/vm/pt-write-code2
pass tests/vm/pt-grow-stk-sc
pass tests/vm/page-linear
pass tests/vm/page-parallel
pass tests/vm/page-merge-seq
pass tests/vm/page-merge-par
pass tests/vm/page-merge-stk
pass tests/vm/page-merge-mm
pass tests/vm/page-shuffle
pass tests/vm/mmap-read
pass tests/vm/mmap-close
pass tests/vm/mmap-unmap
pass tests/vm/mmap-overlap
pass tests/vm/mmap-twice
pass tests/vm/mmap-write
pass tests/vm/mmap-ro
pass tests/vm/mmap-exit
pass tests/vm/mmap-shuffle
pass tests/vm/mmap-bad-fd
pass tests/vm/mmap-clean
pass tests/vm/mmap-inherit
pass tests/vm/mmap-misalign
pass tests/vm/mmap-null
pass tests/vm/mmap-over-code
pass tests/vm/mmap-over-data
pass tests/vm/mmap-over-stk
pass tests/vm/mmap-remove
pass tests/vm/mmap-zero
pass tests/vm/mmap-bad-fd2
pass tests/vm/mmap-bad-fd3
pass tests/vm/mmap-zero-len
pass tests/vm/mmap-off
pass tests/vm/mmap-bad-off
pass tests/vm/mmap-kernel
pass tests/vm/lazy-file
pass tests/vm/lazy-anon
FAIL tests/vm/swap-file
FAIL tests/vm/swap-anon
FAIL tests/vm/swap-iter
FAIL tests/vm/swap-fork
pass tests/filesys/base/lg-create
pass tests/filesys/base/lg-full
pass tests/filesys/base/lg-random
pass tests/filesys/base/lg-seq-block
pass tests/filesys/base/lg-seq-random
pass tests/filesys/base/sm-create
pass tests/filesys/base/sm-full
pass tests/filesys/base/sm-random
pass tests/filesys/base/sm-seq-block
pass tests/filesys/base/sm-seq-random
pass tests/filesys/base/syn-read
pass tests/filesys/base/syn-remove
pass tests/filesys/base/syn-write
pass tests/threads/alarm-single
pass tests/threads/alarm-multiple
pass tests/threads/alarm-simultaneous
pass tests/threads/alarm-priority
pass tests/threads/alarm-zero
pass tests/threads/alarm-negative
pass tests/threads/priority-change
pass tests/threads/priority-donate-one
pass tests/threads/priority-donate-multiple
pass tests/threads/priority-donate-multiple2
pass tests/threads/priority-donate-nest
pass tests/threads/priority-donate-sema
pass tests/threads/priority-donate-lower
pass tests/threads/priority-fifo
pass tests/threads/priority-preempt
pass tests/threads/priority-sema
pass tests/threads/priority-condvar
pass tests/threads/priority-donate-chain
FAIL tests/vm/cow/cow-simple
5 of 141 tests failed.
swap in/out๊ณผ cow test ์ ์ธํ๊ณ ์ ๋ถ PASS๋ค!!!!๐