feat: docs & ARCH 2.2, 2.3, 2.4
This commit is contained in:
82
kernel/docs/memory/introduction.md
Normal file
82
kernel/docs/memory/introduction.md
Normal file
@@ -0,0 +1,82 @@
|
||||
# Управление памятью: концептуальная модель
|
||||
|
||||
## Архитектурная философия
|
||||
|
||||
Управление памятью в Elyz построено как **трёхуровневая иерархия**,
|
||||
где каждый уровень решает свою задачу и взаимодействует с соседними
|
||||
через строго определённые интерфейсы.
|
||||
|
||||
```
|
||||
Уровень 1: BitmapPMM (глобальный, физический)
|
||||
│
|
||||
│ предоставляет сырые фреймы
|
||||
▼
|
||||
Уровень 2: PMActor + BuddyAllocator (распределённый, физический)
|
||||
│
|
||||
│ управляет диапазонами, выдаёт под-диапазоны
|
||||
▼
|
||||
Уровень 3: AddressSpace (VMM) (виртуальный)
|
||||
│
|
||||
│ отображает физические фреймы в виртуальные адреса
|
||||
▼
|
||||
CPU (MMU, page tables)
|
||||
```
|
||||
|
||||
### Зачем три уровня?
|
||||
|
||||
- **BitmapPMM** — глобальный аллокатор физических фреймов. Простой,
|
||||
надёжный, но неэффективный для частых alloc/free маленьких блоков.
|
||||
Используется для начальной загрузки и для Page Table страниц.
|
||||
|
||||
- **BuddyAllocator + PMActor** — распределённая модель. Каждый актор
|
||||
управляет своим диапазоном физической памяти через buddy-алгоритм.
|
||||
Это даёт: (1) изоляцию — актор A не может истощить память актора B;
|
||||
(2) масштабирование — акторы могут работать параллельно;
|
||||
(3) предсказуемость — каждый актор знает свой лимит.
|
||||
|
||||
- **AddressSpace (VMM)** — виртуальные адресные пространства. PML4,
|
||||
VMA-деревья, copy-on-write, lazy mapping. Использует PMM для
|
||||
аллокации Page Table страниц (через `pmm_alloc` в `paging.rs`).
|
||||
|
||||
### Разделение ответственности по файлам
|
||||
|
||||
| Файл | Компонент | Роль в абстракции |
|
||||
|------|-----------|-------------------|
|
||||
| `address.rs` | PhysAddr / VirtAddr / HHDM | Базовые типы для адресов |
|
||||
| `pmm.rs` | BitmapPMM | Глобальный менеджер физических фреймов |
|
||||
| `buddy.rs` | BuddyAllocator | O(1) buddy allocator (intrusive list) |
|
||||
| `pm_manages.rs` | PMActor + PMActorQueue | Актёр физической памяти + MPSC очередь |
|
||||
| `pm_router.rs` | PMRouter | Lock-free маршрутизация запросов/ответов |
|
||||
| `paging.rs` | PageTable | Аппаратные 4-уровневые page tables |
|
||||
| `vmm.rs` | AddressSpace + VMA | Виртуальные адресные пространства |
|
||||
| `allocator.rs` | SlabAllocator | Кучевой аллокатор (global_allocator) |
|
||||
| `mod.rs` | Экспорт | Фасад подсистемы |
|
||||
|
||||
### Поток данных: типичная аллокация
|
||||
|
||||
```
|
||||
Процесс A хочет 16 страниц:
|
||||
1. Код пользователя отправляет PMRequest::Allocate в PMActor через
|
||||
PMRouter::alloc_channel() + actor.submit_request()
|
||||
2. Когда актор получает CPU, process_messages() вызывает
|
||||
buddy.alloc_pages(16)
|
||||
3. BuddyAllocator находит блок порядка 4 (2^4 = 16) или больше,
|
||||
разбивает его при необходимости
|
||||
4. PMActor создаёт Capability с CapObject::Memory { phys, size_pages }
|
||||
5. Ответ (PMResponse::Allocated) отправляется через PMRouter
|
||||
6. Получатель может отобразить фреймы в своё AddressSpace через
|
||||
map_region() или map_shared()
|
||||
```
|
||||
|
||||
### Поток данных: page fault
|
||||
|
||||
```
|
||||
CPU ловит #PF (page fault):
|
||||
1. interrupt.rs: rust_page_fault_handler() читает CR2
|
||||
2. Получает блокировку KERNEL_SPACE
|
||||
3. process_pending_revocations() — обрабатывает накопленные отзывы
|
||||
4. handle_fault() проверяет: это COW? это lazy region?
|
||||
5. Если COW — копируем страницу (copy-on-write)
|
||||
6. Если lazy — alloc_frame() из PMM + map_page()
|
||||
7. Если нераспознанный fault — KERNEL PANIC
|
||||
```
|
||||
Reference in New Issue
Block a user