Windows XP Windows 7 Windows 2003 Windows Vista Windows 綜合教學 Linux 系統教學
Windows 10 Windows 8 Windows 2008 Windows NT Windows Server 電腦軟體教學

Linux 進程創建核心機制:fork() 系統調用深度解析與代碼實戰

編輯:Linux 系統常見問題解答

fork() 基本語義

fork() 是 Unix/Linux 創建新進程的核心系統調用。調用一次,返回兩次:

  • 父進程:返回子進程 PID(>0)
  • 子進程:返回 0
  • 失敗:返回 -1,設定 errno

完整示例代碼

#include <stdio.h>
#include <sys/types.h>
#include <unistd.h>

int main() {
    pid_t pid;
    int n = 4;

    printf("Before fork: PID=%d, n=%d\n", getpid(), n);

    pid = fork();  // 此處分叉為兩個進程

    if (pid < 0) {
        perror("fork failed");
        return 1;
    } else if (pid == 0) {  // 子進程
        n++;
        printf("Child: PID=%d, PPID=%d, n=%d\n", getpid(), getppid(), n);
    } else {  // 父進程
        n--;
        printf("Parent: PID=%d, Child PID=%d, n=%d\n", getpid(), pid, n);
    }

    printf("End: PID=%d, n=%d\n", getpid(), n);
    return 0;
}

執行結果分析

Before fork: PID=1234, n=4
Child: PID=1235, PPID=1234, n=5
Parent: PID=1234, Child PID=1235, n=3
End: PID=1235, n=5
End: PID=1234, n=3

關鍵觀察:

  1. 變數獨立:父子進程擁有獨立的 n 副本,修改互不影響
  2. 執行順序不定:調度器決定誰先跑,輸出順序可能交錯
  3. PPID:子進程 getppid() 返回父進程 PID

內核層面創建流程

  1. 複製 task_struct:分配新 task_struct,複製父進程大部分欄位
  2. 分配 PID:從 pidmap 分配唯一 PID
  3. 複製內存描述符:mm_struct、頁表、VMA 鏈表(Copy-on-Write 標記頁面只讀)
  4. 複製檔案描述符表:files_struct,引用計數 +1,父子共享打開檔案偏移量
  5. 複製信號處理:sighand_struct
  6. 加入任務鏈表:掛入 task_list、PID 雜湊表
  7. 返回:父進程返回子 PID,子進程返回 0

Copy-on-Write (COW) 機制

  • fork 後,父子共享物理頁框,頁表標記 只讀
  • 任一方嘗試寫入 → 頁面錯誤 → 內核分配新頁框、複製內容、更新頁表 → 繼續執行
  • 極大提升 fork 效能,尤其配合 exec() 時(子進程立即替換映像,無實際複製)

fork() 失敗常見原因

errno原因
EAGAIN進程數達上限(RLIMIT_NPROC 或 /proc/sys/kernel/pid_max)
ENOMEM內核內存不足,無法分配 task_struct、頁表等

vfork() 與 clone() 變體

  • vfork():不複製頁表,子進程在父進程地址空間運行,必須立即調用 exec() 或 _exit(),否則導致父進程損壞。歷史優化產物,現代 COW 已使其優勢微乎其微。
  • clone():Linux 專用,可精細控制共享資源(CLONE_VM、CLONE_FS、CLONE_FILES、CLONE_SIGHAND、CLONE_THREAD),執行緒庫(pthread)底層即基於 clone()。

實戰注意事項

  1. fork 後立即檢查返回值,區分父子邏輯
  2. 子進程若不執行 exec,應調用 _exit() 而非 exit(),避免雙重刷新 stdio 緩衝區
  3. 父進程需 wait()/waitpid() 回收子進程,防止殭屍進程
  4. 多進程寫入同一檔案需協調(鎖、追加模式、分離檔案)
Copyright © Windows教程網 All Rights Reserved