Pintos에서는 pml4 (Page-Map-Level-4) 라고 부른다
페이지 테이블 인터페이스는 내부 구조 접근 용이하게 uint64_t *
로 표현한다
페이지 테이블 인터페이스와 내부 구조 설명이다
이름 그대로 역할 한다
uint64_t * pml4_create (void);
새로운 페이지 테이블을 생성해 반환
새 페이지 테이블은 Pintos의 표준 커널 가상 페이지 매핑은 포함하지만, 사용자 가상 매핑은 포함 X
메모리 확보 실패시 NULL 포인터 반환
void pml4_destroy (uint64_t *pml4);
pml4
가 보유한 모든 자원을 해제
void pml4_activate (uint64_t *pml4);
pml4
를 활성화
활성 페이지 테이블은 CPU가 메모리 참조를 변환할 때 사용하는 테이블
페이지 테이블이 보관하는 페이지 ↔ 프레임 매핑을 조회하거나 갱신
실행 중 외에도 중단된 프로세스의 비활성 페이지 테이블에서도 동작한다
필요 시 TLB 플러시 한다
TLB 플러시: CPU가 캐시해둔 TLB 엔트리 버려서 다음에 새로운 페이지 테이블 내용 다시 읽게 하는 동작
bool pml4_set_page (uint64_t *pml4, void *upage, void *kpage, bool rw);
사용자 페이지 upage
를 커널 가상 주소 kpage
가 식별하는 프레임에 매핑
rw == true
-> 읽기/쓰기 가능
rw == false
-> 읽기 전용
조건:
upage
는 매핑되어 있지 않아야 함
kpage
는 palloc_get_page(PAL_USER)
로 얻은 커널 가상 주소여야 함
성공 시 true
,
실패 시 false
반환
void * pml4_get_page (uint64_t *pml4, const void *uaddr);
uaddr
이 매핑된 프레임 조회
매핑되어 있으면 해당 프레임의 커널 가상 주소 반환, 아니면 NULL
반환
void pml4_clear_page (uint64_t *pml4, void *upage);
페이지를 pml4
에서 “not present” 상태로 표시, 이후 해당 페이지 접근 시 페이지 폴트 발생
단, 접근(accessed) 및 더티(dirty) 비트를 확인을 위해 나머지 PTE 비트들은 보존
x86-64 하드웨어는 페이지 교체 알고리즘 구현을 돕기 위해 각 페이지 테이블 엔트리(PTE)에 두 개의 보조 비트를 제공한다
Accessed 비트: 해당 페이지에 읽기/쓰기가 발생하면 CPU가 1로 설정
Dirty 비트: 해당 페이지에 쓰기가 발생하면 CPU가 1로 설정
CPU는 이를 0으로 재설정 안하며 필요하면 운영체제에서 직접 초기화한다
하나의 프레임을 여러 페이지가 가리킬 때다
어떤 주소로 접근했을 때 해당 PTE만 갱신되고, 다른 PTE는 갱신 안되는 문제
vpage
의 PTE에 dirty
또는 accessed
비트가 설정되어 있으면 true
, 아니면 false
반환
bool pml4_is_dirty (uint64_t *pml4, const void *vpage);
bool pml4_is_accessed (uint64_t *pml4, const void *vpage);
vpage
의 PTE가 존재하면 dirty
또는 accessed
비트를 주어진 값으로 설정
void pml4_set_dirty (uint64_t *pml4, const void *vpage, bool dirty);
void pml4_set_accessed (uint64_t *pml4, const void *vpage, bool accessed);