
| Linux カーネルの機能 | |||
|---|---|---|---|
プロセスとは
プロセスの構造
プロセスは、以下のようにセグメント (分類) に分けて、メモリ上に配置します。

| セグメント | 説明 |
|---|---|
| テキストセグメント | CPU が実行する機械語命令 (プログラム本体) |
| データセグメント | 初期化済みの static 変数 or グローバル変数 |
| bss セグメント | 初期化していない static 変数 or グローバル変数 |
| ヒープセグメント | プロセス実行時に動的に確保される領域 (malloc 等) |
| スタックセグメント | スコープが終了すると消えるデータ (ローカル変数、関数パラメータ、メソッド等) |
プロセス管理とは

プロセス管理は、1つのプロセスが CPU を独占して、他のプロセスが動かなくなる事を防ぎます
プロセス管理では、以下の3つの仕組みを利用します。
- プロセスの状態遷移:プロセスの状態を定義
- PCB (Process Control Block):プロセスの状態などを記録したブロック
- CPU スケジューラー (短期スケジューラー):CPU にプロセスを割り当て (プロセスの状態を変更)

| 状態 | 説明 |
|---|---|
| 開始 | 初期化するための状態 |
| 実行可能 | CPU の割り当て待ちの状態 |
| 実行中 | プロセスに CPU を割り当て中の状態 他のプロセスに割り込まれて中断すると、「実行可能」状態に移行 |
| 待機 | デバイスの I/O (SSD 等のデータ読み書き)待ちの状態 I/O 処理が終わると「実行可能」状態に移行 |
| 終了 | プロセスの処理が完了・中止した状態 |
| 処理 | 説明 | プロセスの状態 |
|---|---|---|
| ディスパッチ | プロセスに CPU の割り当て (実行) | 「実行可能」から「実行中」に変更 |
| プリエンプション | プロセスに CPU を剥奪 (一時中断) | 「実行中」から「実行可能」に変更 |
一時中断したプロセスを再開するには、「前回どこまで処理したか」という情報が必要です。
この情報は PCB と呼ばれるブロックに保存します。
PCB はプロセスの再開時に利用されます。

PCB の内容は以下のとおりです。
| 項目 | 説明 |
|---|---|
| Process ID | プロセスを一意に識別する番号 (PID) |
| State | 現在のプロセスの状態 |
| Pointer | 親プロセスのポインタ |
| Priority | プロセスの優先度 |
| Program | 次に実行する命令のポインタ |
| CPU registers | 「実行中」状態のプロセスのレジスタの値(?) |
| I/O Information | プロセスに割り当てられた I/O デバイスのリスト |
| Accounting information | プロセスの実行に使用されるCPUの量、時間制限、実行ID |

CPU スケジューラーが、ディスパッチ・プリエンプションするプロセスは、スケジューリングアルゴリズムによって決定します。
スケジューリングアルゴリズム
スケジューリングアルゴリズムには、主に以下の4つが存在します。
- First Come First Serve (FCFS)
- Shortest Job Next (SJN)
- Priority Based Scheduling
- Round Robin Scheduling
FCFS は、以下の特徴を持ちます。
- FIFO(First In First Out) キューにて実装
- non-preemptive(割り込み不可能)
- 平均待ち時間が長い

| Process | Wait Time : Service Time - Arrival Time |
|---|---|
| P0 | 0 - 0 = 0 |
| P1 | 5 - 1 = 4 |
| P2 | 8 - 2 = 6 |
| P3 | 16 - 3 = 13 |
平均待ち時間: (0+4+6+13) / 4 = 5.75
SJN は、以下の特徴を持ちます。
- 平均待ち時間を最小に抑えるためのアルゴリズム
- non-preemptive(割り込み不可能)
- CPU 処理時間を事前に知っている(もしくは計算する)必要があります

| Process | Wait Time : Service Time - Arrival Time |
|---|---|
| P0 | 0 - 0 = 0 |
| P1 | 5 - 1 = 4 |
| P2 | 14 - 2 = 12 |
| P3 | 8 - 3 = 5 |
平均待ち時間: (0 + 4 + 12 + 5)/4 = 21 / 4 = 5.25
Priority Based Scheduling は、以下の特徴を持ちます。
- 同じ優先度のプロセスは先着順です
- 優先度は、メモリ要件、時間要件等に基づいて決定します

| Process | Wait Time : Service Time - Arrival Time |
|---|---|
| P0 | 0 - 0 = 0 |
| P1 | 11 - 1 = 10 |
| P2 | 14 - 2 = 12 |
| P3 | 5 - 3 = 2 |
平均待ち時間: (0 + 10 + 12 + 2)/4 = 24 / 4 = 6
なお、プロセスの優先度は以下のコマンドの結果の PRI 列で確認可能です。(低いほうが優先度が高い)
F UID PID PPID PRI NI VSZ RSS WCHAN STAT TTY TIME COMMAND 1 0 2 0 20 0 0 0 - S ? 0:01 [kthreadd] 1 0 4 2 0 -20 0 0 - I< ? 0:00 [kworker/0:0H]
PRI は NI(nice 値)を元に決定するため、nice コマンドにてプロセスの優先度を変更可能です。
Round Robin Scheduling は以下の特徴を持ちます。
- preemptive(割り込みが発生する)ため、プロセスが並行して動作可能
- クオンタムの期間が終了すると、割り込みが発生し次のプロセスに処理が移る
クオンタムが3だとすると、3経過ごとにプロセスが切り替わる。

| Process | Wait Time : Service Time - Arrival Time |
|---|---|
| P0 | (0 - 0) + (12 - 3) = 9 |
| P1 | (3 - 1) = 2 |
| P2 | (6 - 2) + (14 - 9) + (20 - 17) = 12 |
| P3 | (9 - 3) + (17 - 12) = 11 |
平均待ち時間: (9+2+12+11) / 4 = 8.5
プロセスの確認コマンド
USER PID %CPU %MEM VSZ RSS TTY STAT START TIME COMMAND root 1 0.0 0.0 43920 5732 ? Ss 2021 4:40 /usr/lib/systemd/systemd --switched-root --system --deserializ root 2 0.0 0.0 0 0 ? S 2021 0:00 [kthreadd]
| ヘッダ | 説明 |
|---|---|
| USER | ユーザー名 |
| PID | プロセス ID |
| %CPU | プロセスの使用率 |
| %MEM | 物理メモリに対するプロセスの割合 |
| VSZ | 仮想メモリに割り当てたプロセスのサイズ (メモリ管理の記事で説明) |
| RSS | 物理メモリに割り当てたプロセスのサイズ (メモリ管理の記事で説明) |
| TTY | 制御端末 |
| STAT | プロセスの状態 ・D 割り込み不可能なスリープ状態 (通常 IO 中) ・R 実行中または実行可能状態 (実行キューにある) ・S 割り込み可能なスリープ状態 (イベントの完了を待っている) ・T ジョブ制御シグナルまたはトレースされているために停止中の状態 ・W ページング状態 (2.6.xx カーネルからは無効) ・X 死んだ状態 (見えるべきではない) ・Z 消滅した (ゾンビ) プロセス ・I Idle 状態 |
| START | プロセスの起動日 |
| TIME | 累積した CPU 時間 |
| COMMAND | プロセスの実行コマンド |
スレッドとは

プロセスとスレッドの違い
以下に MySQL プロセスと、MySQL プロセスが持つスレッドの関係を示します。

プロセスとスレッドの違いを表にまとめると以下のとおりです。
| プロセス | スレッド | |
|---|---|---|
| 説明 | プログラムの実行単位 | CPU の利用単位 |
| メモリ | 子プロセス用に新規領域を確保 (共有メモリでプロセス間のデータにアクセス) | 親スレッドと子スレッド間で共有する (スタック以外) |
| 生成 | 遅い (メモリに新規領域を確保するため) | 速い |
スレッドの確認コマンド
USER PID LWP %CPU NLWP %MEM VSZ RSS TTY STAT START TIME COMMAND (中略) mysql 29942 29942 0.0 28 2.2 1382864 181528 ? Sl 09:45 0:00 /usr/sbin/mysqld --daemonize --pid-file=/var/run/mysqld/mysqld.pid mysql 29942 29943 0.0 28 2.2 1382864 181528 ? Sl 09:45 0:00 /usr/sbin/mysqld --daemonize --pid-file=/var/run/mysqld/mysqld.pid mysql 29942 29944 0.0 28 2.2 1382864 181528 ? Sl 09:45 0:00 /usr/sbin/mysqld --daemonize --pid-file=/var/run/mysqld/mysqld.pid (中略)
| ヘッダ | 説明 |
|---|---|
| USER | ユーザー名 |
| PID | プロセス ID |
| LWP | 軽量プロセス (Light Weight Process) またはスレッドの ID |
| %CPU | プロセスの使用率 |
| NLWP | LWP (スレッド) の数 |
| %MEM | 物理メモリに対するプロセスの割合 |
| VSZ | 仮想メモリに割り当てたプロセスのサイズ (メモリ管理の記事で説明) |
| RSS | 物理メモリに割り当てたプロセスのサイズ (メモリ管理の記事で説明) |
| TTY | 制御端末 |
| STAT | プロセスの状態 ・D 割り込み不可能なスリープ状態 (通常 IO 中) ・R 実行中または実行可能状態 (実行キューにある) ・S 割り込み可能なスリープ状態 (イベントの完了を待っている) ・T ジョブ制御シグナルまたはトレースされているために停止中の状態 ・W ページング状態 (2.6.xx カーネルからは無効) ・X 死んだ状態 (見えるべきではない) ・Z 消滅した (ゾンビ) プロセス ・I Idle 状態 |
| START | プロセスの起動日 |
| TIME | 累積した CPU 時間 |
| COMMAND | プロセスの実行コマンド |
CPU とは
CPU の処理の種類
CPU で並列処理するには、以下の方法が存在します。

CPU 確認コマンド
CPU の情報は、lscpu (もしくは cat /proc/cpuinfo) コマンドで確認可能です。
CPU: 2 //論理 CPU の(スレッドの割り当て可能な)数 オンラインになっている CPU のリスト: 0,1 コアあたりのスレッド数: 2 //ハイパースレッディングによる見せかけのコア数 ソケットあたりのコア数: 1 //1CPUに含まれるコア数 ソケット数: 1 //物理 CPU (実際の CPU)の数
関連情報
| Linux カーネルの機能 | |||
|---|---|---|---|
参考サイト
本記事は以下のサイトを参考にしました。









![[試して理解]Linuxのしくみ ―実験と図解で学ぶOS、仮想マシン、コンテナの基礎知識【増補改訂版】](https://m.media-amazon.com/images/I/51CKe00bsfL._SL160_.jpg)

































































