Open3

OSを作る (Operating Systems: Three Easy Pieces、ゼロからOS自作入門)

Mathew ChanMathew Chan

Operating Systems: Three Easy Pieces ゼロからOS自作入門
https://github.com/syarochan/Operating-Systems-Three-Easy-Pieces-in-japanese https://www.amazon.co.jp/ゼロからのOS自作入門-内田-公太/dp/4839975868

4. Abstraction

OSはどうやってプログラムをプロセスに変換しますか?

  1. 必要なプログラムを少しずつにプロセスのプロセスのアドレス空間にロード
  2. OSがruntime stackをプロセスに割り当てます
  3. 任意:メモリがそれ以上に必要がある時、heapやmalloc()で割り当てます
  4. I/Oなどの初期化タスクを行います

*1. paginationとswappingのメカニズムを通して、遅延的な読み込みを実現します。
*2. スタックを使用するのは、ローカル変数、関数のパラメータ、戻りアドレスです。

プロセス=実行中のプログラム

プロセスの状態

  • Running(実行中)
  • Ready(準備完了)
  • Blocked(ブロック状態:他のイベントが発生するまで実行できません)

HW

  1. Run process-run.py with the following flags: -l 5:100,5:100.
    What should the CPU utilization be (e.g., the percent of time the
    CPU is in use?) Why do you know this? Use the -c and -p flags to
    see if you were right.

P1が完了するとプロセス2が実行されます。
CPU利用率=100%

  1. Now run with these flags: ./process-run.py -l 4:100,1:0.
    These flags specify one process with 4 instructions (all to use the
    CPU), and one that simply issues an I/O and waits for it to be done.
    How long does it take to complete both processes? Use -c and -p
    to find out if you were right.

t=11

  1. Switch the order of the processes: -l 1:0,4:100. What happens
    now? Does switching the order matter? Why? (As always, use -c
    and -p to see if you were right)

Yes, order matters because the CPU is free to process P1 while P0 is waiting for IO to finish in the blocked state.

  1. We’ll now explore some of the other flags. One important flag is
    -S, which determines how the system reacts when a process issues an I/O. With the flag set to SWITCH ON END, the system
    will NOT switch to another process while one is doing I/O, instead waiting until the process is completely finished. What happens when you run the following two processes (-l 1:0,4:100
    -c -S SWITCH_ON_END), one doing I/O and the other doing CPU
    work?

P0の完了までP1が実行されません。

  1. Now, run the same processes, but with the switching behavior set
    to switch to another process whenever one is WAITING for I/O (-l
    1:0,4:100 -c -S SWITCH ON IO). What happens now? Use -c
    and -p to confirm that you are right.

Q3のように、P0の状態がBLOCKEDに変換すると、P1が実行されます。

  1. One other important behavior is what to do when an I/O completes. With -I IO_RUN_LATER, when an I/O completes, the process that issued it is not necessarily run right away; rather, whatever was running at the time keeps running. What happens when you run this combination of processes? (./process-run.py -l 3:0,5:100,5:100,5:100 -S SWITCH_ON_IO -c -p -I IO_RUN_LATER) Are system resources being effectively utilized?
Mathew ChanMathew Chan

MacでMikanOS

参考資料

https://zenn.dev/karaage0703/articles/1bdb8930182c6c#3.4-ブートローダからピクセルを描く

DockerとVSCodeの環境構築

brew install xquartz

XQuartzのターミナル(Macのターミナルではない)で以下のコマンドを実行します

xhost + 127.0.0.1

mikanos-devcontainerをクローンします

git clone https://github.com/karaage0703/mikanos-devcontainer

VSCodeでCmd+PでRemote-Containers: Open Folder in Container...を選択し、mikanos-devcontainerを選択します

VSCode内のターミナルはvscode ➜ /workspaces/mikanos-devcontainer (master) $ になったら、Docker内のターミナルに入れました。

Repo内でMikanOSをクローンし、edk2のフォルダにlnでMikanLoaderをリンクします。

cd /workspaces/mikanos-devcontainer/
git clone https://github.com/uchan-nos/mikanos.git
OS_DIR=/workspaces/mikanos-devcontainer/mikanos
cd ~/edk2
ln -s $HOME/workspace/mikanos/MikanLoaderPkg ./
source edksetup.sh
cp /workspaces/mikanos-devcontainer/target.txt Conf/target.txt

初めてのカーネル

cd $OS_DIR
git checkout osbook_day03a
cd kernel
clang++ -O2 -Wall -g --target=x86_64-elf -ffreestanding -mno-red-zone -fno-exceptions -fno-rtti -std=c++17 -c main.cpp
ld.lld --entry KernelMain -z norelro --image-base 0x100000 --static -o kernel.elf main.o

main.cppで簡単の関数でカーネルを作れそうです。

extern "C" void KernelMain() {
  while (1) __asm__("hlt");
}
  • asm: assembly
  • hlt: 「halt」の意味。CPUをIdle状態にさせる命令

Mathew ChanMathew Chan

ゼロからOS自作入門 3.3

Page allocation

UEFIでpage size = 4KiB=0x1000によって、
page数 = (kernel_file_size + 0xfff) / 0x1000

C++では切り捨て(Rounding division)を実行するので、0xfff (4095を足すとkernel_file_sizeの値を切り上げます(Round up)。