Skip to content

Commit

Permalink
proj 3 task 1 sync and structure
Browse files Browse the repository at this point in the history
  • Loading branch information
AstatineAi committed May 13, 2024
1 parent 0335767 commit 7bef336
Showing 1 changed file with 37 additions and 2 deletions.
39 changes: 37 additions & 2 deletions lecture_note/docs/pintos/proj3.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

!!! warning "No plagiarism"
If you are enrolled in CS130, you may not copy code from this repository.
Project 3 强调设计, 具体实现因人而异.
Project 3 强调设计, 具体实现因人而异. 如果你真的没有头绪, 可以先看看 design document 模板.

!!! warning "急了急了急了"
Project 3 基于 Project 2, 希望你的 Project 2 足够 robust 且有合适的非法地址检测.
Expand Down Expand Up @@ -219,6 +219,8 @@ Pintos 的内存结构决定了我们需要管理的部分为加载可执行文

## Task 1: Paging

### 结构

首先需要建立 page table 结构, 把每个 frame 需要从 user pool 取得 (`palloc_get_page (PAL_USER)`, 需要清空则改为 `palloc_get_page (PAL_USER | PAL_ZERO)` ) 的过程套壳, 方便记录信息. 在分配一个 page 之后, 需要调用 `install_page` 将 page 添加到当前进程的 page directory 中.

```c
Expand Down Expand Up @@ -283,6 +285,39 @@ struct sup_page_table_entry {

按照 page 大小决定每个 page 需要多少 sector, 建立一个总 sector 数除以每个 page 需要的 sector 数的 bitmap, 每个 bit 代表这个 swap slot 是否被占用.

### 同步问题

1. 当多个进程申请 frame 时的 race condition
- `palloc_get_page` 内置了锁, 保证分配是原子的
- 一个 frame 从 `palloc_get_page` 获取到, 另一个需要 evict frame, 两个进程的 critical section 是修改 frame table 部分, 需要加锁
- 两个进程同时 evict frame, 需要保证不 evict 同一个 frame
2. 一个进程 page fault 时, 另一个进程正在 evict frame
- fault 申请到的新 frame 不能被 evict, 把 frame pin 住
3. 正在被 evict 的 frame 被原来的 frame 持有者访问
- 保证在换出等等操作之前进入如下状态: 原来持有者通过 page table 访问此 frame 时引起 page fault
- 需要使用 `pagedir_clear_page` 清除 page table 中的映射关系
4. 正在从 disk 读取 page 时, 此 page 的 frame 不应该被其他进程 evict
- 读取完成之前不加入 frame table.
5. 在 syscall 时发生的 page fault
- 参见 Task 4
6. 多个 page fault 的处理可以并发进行
- 保证对同一个 frame 的操作是串行的
- 需要 I/O 的靠 I/O 的锁互斥
- 需要 swap 的靠 swap block 的锁互斥

### page fault 情况与对策

| 情况编号 | `not_present` | `write` | `user` | 情况 | 对策 |
| ------- | ------------- | ------- | ------ | --- | --- |
| (1) | `false` | `false` | `false` | 内核非法访问 | `kill()` |
| (2) | `false` | `false` | `true` | 用户非法访问 | `kill()` (导致 `exit(-1)` ) |
| (3) | `false` | `true` | `false` | 同理 1 (例如写不可写的内存) ||
| (4) | `false` | `true` | `true` | 同理 2 ||
| (5) | `true` | `false` | `false` | 在 syscall 中遇到 page fault | 尝试载入 & pin, 在 syscall 结束之前 unpin |
| (6) | `true` | `false` | `true` | 被换出/没有加载/栈增长 | 尝试载入 |
| (7) | `true` | `true` | `false` | 同 5 ||
| (8) | `true` | `true` | `true` | 同 6 ||

## Task 2: Stack growth

在最开始分配一个 page 作为栈, 后续考虑栈增长的情况. 按照 80x86 PUSHA 最多在 esp 低 32 字节的位置引发 page fault, 考虑将 32 字节作为分界, 低于 32 字节时分配新的 page, 否则视为非法访问.
Expand All @@ -299,4 +334,4 @@ mummap 会将文件从内存中移除, 将 dirty 的 page 写回文件.

## Task 4: Accessing user memory

需要保证在进入内核时, 用户内存是合法的, 且需要避免一些持有资源情况下遇到 page fault, 对 supplmentary page table 加入
需要保证在进入内核时, 用户内存是合法的, 且需要避免一些持有资源情况下遇到 page fault 的情况.

0 comments on commit 7bef336

Please sign in to comment.