728x90
코드
static bool
load_segment (struct file *file, off_t ofs, uint8_t *upage,
uint32_t read_bytes, uint32_t zero_bytes, bool writable) {
ASSERT ((read_bytes + zero_bytes) % PGSIZE == 0);
ASSERT (pg_ofs (upage) == 0);
ASSERT (ofs % PGSIZE == 0);
file_seek (file, ofs);
while (read_bytes > 0 || zero_bytes > 0) {
/* Do calculate how to fill this page.
* We will read PAGE_READ_BYTES bytes from FILE
* and zero the final PAGE_ZERO_BYTES bytes. */
size_t page_read_bytes = read_bytes < PGSIZE ? read_bytes : PGSIZE;
size_t page_zero_bytes = PGSIZE - page_read_bytes;
/* Get a page of memory. */
uint8_t *kpage = palloc_get_page (PAL_USER);
if (kpage == NULL)
return false;
/* Load this page. */
if (file_read (file, kpage, page_read_bytes) != (int) page_read_bytes) {
palloc_free_page (kpage);
return false;
}
memset (kpage + page_read_bytes, 0, page_zero_bytes);
/* Add the page to the process's address space. */
if (!install_page (upage, kpage, writable)) {
printf("fail\n");
palloc_free_page (kpage);
return false;
}
/* Advance. */
read_bytes -= page_read_bytes;
zero_bytes -= page_zero_bytes;
upage += PGSIZE;
}
return true;
}
목적
file 내에서 ofs부터 시작해 upage라는 주소공간에 세그먼트를 불러들입니다. 이 함수를 통해 초기화된 페이지들에 대해서 만약 writable이 true로 넘어왔다면 writable해야 하고, 그렇지 않으면 read-only여야 합니다. 만약 메모리 할당 에러나 디스크 읽기 에러가 난 경우에는 false를 반환합니다.
요약: 파일[ofs:] 로 읽어서 페이지 할당받고 가상->물리 매핑도 추가해줌.
루틴
호출되는 곳
/userprog/process.c의 load 함수
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;
}
- PT_LOAD : ELF의 타입이다. PT_LOAD는 loadable한 elf파일. 더 많은 정보는 [ELF1] 1-2를 보라고 한다.
- validate_segment : PHDR이 valid하고 loadable segment를 가리키는지 확인한다.
- PHDR : ELF 내 세그먼트의 종류, ELF header, Program header, Section header가 있다. (참고할 곳)
728x90
'SW사관학교 정글 4기 > pintos' 카테고리의 다른 글
install_page (0) | 2022.06.11 |
---|---|
[Project 2 - Userprogram] 시스템콜, 시스템콜 핸들러 (0) | 2022.06.05 |
Project 2: User Programs 검색어 목록 (0) | 2022.05.30 |
pintos alarm clock 테스트 에러 (0) | 2022.05.28 |
내가 자꾸 까먹어서 만든 pintos 코드 없는 함수 사전 (0) | 2022.05.28 |
댓글