奔跑吧 Linux 內核入門篇, 2/e

笨叔 陳悅

  • 奔跑吧 Linux 內核入門篇, 2/e-preview-1
  • 奔跑吧 Linux 內核入門篇, 2/e-preview-2
奔跑吧 Linux 內核入門篇, 2/e-preview-1

買這商品的人也買了...

商品描述

本書基於Linux 5.0和ARM64處理器循序漸進地講述Linux內核的理論與實驗。本書共16章,主要介紹Linux系統基礎知識、Linux內核基礎知識、ARM64架構基礎知識、內核編譯和調試、內核模塊、簡單的字符設備驅動、系統調用、進程管理、內存管理、同步管理、中斷管理、調試和性能優化、開源社區、文件系統、虛擬化與雲計算等方面的內容,並通過一個綜合能力訓練來引導讀者動手實現一個小的操作系統。

本書適合Linux開發人員、嵌入式開發人員以及對Linux感興趣的程序員閱讀,也適合作為高等院校電腦相關專業的教材。

 

 

 

作者簡介

笨叔,Linux內核愛好者,出版過《奔跑吧Linux內核》《奔跑吧Linux內核入門篇》。


陳悅,Linux內核愛好者,南昌大學教師,主要負責計算機方面的“操作系統”“彙編語言”與“計算機組成原理”等課程的教學與研究。

目錄大綱

目錄

第1章Linux系統基礎知識1
1.1 Linux系統的發展歷史1
1.2 Linux發行版2
1.2.1 Red Hat Linux 2
1.2.2 Debian Linux 3
1.2.3 SuSE Linux 4
1.2.4優麒麟Linux 4
1.3 Linux內核介紹5
1.3.1 Linux內核目錄結構5
1.3.2宏內核和微內核7
1.3.3 Linux內核概貌8
1.4如何學習Linux內核11
1.5 Linux內核實驗入門12
1.5.1實驗1-1:在虛擬機中安裝優麒麟Linux 20.04系統12
1.5.2實驗1-2:給優麒麟Linux系統更換“心臟” 15
1.5.3實驗1-3:使用QEMU虛擬機來運行Linux系統17
1.5.4實驗1-4:創建基於UbuntuLinux的根文件系統22
1.5.5實驗1 -5:創建基於QEMU +RISC-V的Linux系統22

第2章Linux內核基礎知識24
2.1 Linux常用的編譯工具24
2.1.1 GCC 24
2.1.2 ARM GCC 25
2.1.3 GCC編譯26
2.2 Linux內核中常用的C語言技巧27
2.3 Linux內核中常用的數據結構和算法33
2.3.1鍊錶33
2. 3.2紅黑樹36
2.3.3無鎖環形緩衝區38
2.4 Vim工具的使用40
2.4.1 Vim 8介紹40
2.4.2 Vim的基本模式41
2.4.3 Vim中3種模式的切換41
2.4.4 Vim光標的移動42
2.4.5刪除、複製和粘貼43
2.4.6查找和替換43
2.4.7與文件相關的命令44
2 .5 git工具的使用44
2.5.1安裝git 45
2.5.2 git基本操作45
2.5.3分支管理48
2.6實驗50
2.6.1實驗2-1:GCC編譯50
2.6.2實驗2-2:內核鍊錶54
2.6.3實驗2-3:紅黑樹54
2.6.4實驗2-4:使用Vim工具54
2.6.5實驗2-5 :把Vim打造成一個強大的IDE編輯工具55
2.6.6實驗2-6:建立一個git本地倉庫63
2.6.7實驗2-7:解決分支合併衝突65
2.6.8實驗2-8:利用git來管理Linux內核開發67
2 .6.9實驗2-9:利用git來管理項目代碼69

第3章ARM64架構基礎知識75
3.1 ARM64架構介紹76
3.1.1 ARMv8-A架構介紹76
3.1.2常見的ARMv8處理器76
3.1.3 ARM64的基本概念77
3.1.4 ARMv8處理器的運行狀態78
3.1.5 ARMv8架構支持的數據寬度79
3.1.6不對齊訪問79
3.2 ARMv8寄存器79
3.2.1通用寄存器79
3.2.2處理器狀態寄存器80
3.2.3特殊寄存器82
3.2.4系統寄存器84
3.3 A64指令集85
3.3.1算術和移位操作指令85
3.3.2乘和除操作指令86
3.3.3移位操作指令87
3.3.4位操作指令87
3.3.5條件操作指令87
3.3.6內存加載指令89
3.3.7多字節內存加載和存儲指令91
3.3.8非特權訪問級別的加載和存儲指令91
3.3.9內存屏障指令92
3.3.10獨占訪存指令92
3. 3.11跳轉指令92
3.3.12異常處理指令93
3.3.13系統寄存器訪問指令93
3.4 ARM64異常處理95
3.4.1異常類型95
3.4.2同步異常和異步異常96
3.4.3異常的發生和退出96
3.4.4異常向量表97
3.5 ARM64內存管理99
3.5.1頁表100
3.5.2頁表映射101
3.6實驗平台:樹莓派102
3.6.1樹莓派4介紹103
3.6.2實驗3-1:在樹莓派上安裝優麒麟Linux 20.04系統104
3.6.3實驗3-2 :彙編語言練習—查找最大數105
3.6.4實驗3-3:彙編語言練習—通過C語言調用彙編函數105
3.6.5實驗3-4:彙編語言練習—通過彙編語言調用C函數106
3.6.6實驗3-5:彙編語言練習—GCC內聯彙編106
3.6.7實驗3-6:在樹莓派上編寫一個裸機程序106

第4章內核編譯和調試107
4.1內核配置107
4.1.1內核配置工具107
4.1.2 .config文件108
4.2實驗4-1:通過QEMU虛擬機調試ARMv8的Linux內核110
4.3實驗4-2:通過Eclipse + QEMU單步調試內核111

第5章內核模塊116
5.1從一個內核模塊開始116
5.2模塊參數120
5.3符號共享122
5.4實驗123
5.4.1實驗5-1:編寫一個簡單的內核模塊123
5.4.2實驗5-2:向內核模塊傳遞參數124
5.4.3實驗5-3:在模塊之間導出符號124

第6章簡單的字符設備驅動125
6.1從一個簡單的字符設備開始126
6.1.1一個簡單的字符設備126
6.1.2實驗6-1:寫一個簡單的字符設備驅動131
6.2字符設備驅動詳解131
6.2.1字符設備驅動的抽象131
6.2.2設備號的管理133
6.2.3設備節點133
6.2.4字符設備操作方法集134
6.3 misc機制136
6.3. 1 misc機制介紹136
6.3.2實驗6-2:使用misc機制來創建設備驅動136
6.4一個簡單的虛擬設備138
6.4.1實驗6-3:為虛擬設備編寫驅動138
6. 4.2實驗6-4:使用KFIFO環形緩衝區改進設備驅動141
6.5阻塞I/O和非阻塞I/O 143
6.5.1實驗6-5:把虛擬設備驅動改成非阻塞模式144
6.5.2實驗6-6:把虛擬設備驅動改成阻塞模式147
6.6 I/O多路復用151
6.6.1 Linux內核的I/O多路復用151
6.6 .2實驗6-7:向虛擬設備中添加I/O多路復用支持152
6.6.3實驗6-8:為什麼不能喚醒讀寫進程157
6.7添加異步通知159
6.7.1異步通知介紹159
6.7.2實驗6-9:向虛擬設備添加異步通知159
6.7.3實驗6-10:解決驅動的宕機難題163
6.8本章小結164

第7章系統調用166
7.1系統調用的概念166
7.1.1系統調用和POSIX標準167
7. 1.2系統調用表167
7.1.3用程序訪問系統調用169
7.1.4新增系統調用170
7.2實驗170
7.2.1實驗7-1:在樹莓派上新增一個系統調用170
7.2.2實驗7-2:在Linux主機上新增一個系統調用170

第8章進程管理172
8.1進程172
8.1.1進程的由來172
8.1.2進程描述符174
8.1.3進程的生命週期176
8.1.4進程標識178
8.1.5進程間的家族關係179
8.1.6獲取當前進程181
8.2進程的創建和終止183
8.2.1寫時復制技術185
8.2.2 fork()函數186
8.2.3 vfork()函數187
8.2.4 clone()函數187
8.2.5內核線程188
8. 2.6 do_fork()函數189
8.2.7終止進程191
8.2.8殭屍進程和託孤進程191
8.2.9進程0和進程1 192
8.3進程調度193
8.3.1進程的分類193
8.3.2進程的優先級和權重193
8.3.3調度策略195
8.3.4時間片198
8.3.5經典調度算法198
8.3.6 Linux O(n)調度算法200
8.3.7 Linux O(1)調度算法200
8.3.8 Linux CFS算法201
8.3.9進程切換204
8.3.10與調度相關的數據結構210
8.4多核調度214
8.4.1調度域和調度組215
8.4.2負載的計算218
8.4.3負載均衡算法221
8.4.4 Per-CPU變量222
8.5實驗223
8.5.1實驗8-1:fork和clone系統調用223
8.5.2實驗8-2:內核線程224
8.5.3實驗8-3:後台守護進程224
8.5.4實驗8-4:進程權限224
8.5.5實驗8 -5:設置優先級224
8.5.6實驗8-6:Per-CPU變量225

第9章內存管理226
9.1從硬件角度看內存管理226
9.1.1內存管理的“遠古時代” 226
9.1.2地址空間的抽象228
9.1.3分段機制229
9. 1.4分頁機制230
9.2從軟件角度看內存管理234
9.2.1 free命令234
9.2.2從應用編程角度看內存管理235
9.2.3從內存佈局圖角度看內存管理236
9.2.4從進程角度看內存管理239
9.2.5從內核角度看內存管理243
9.3物理內存管理244
9.3.1物理頁面244
9.3.2內存管理區250
9 .3.3分配和釋放頁面252
9.3.4關於內存碎片化258
9.3.5分配小塊內存260
9.4虛擬內存管理268
9.4.1進程地址空間268
9.4.2內存描述符mm_struct 269
9.4.3 VMA管理270
9.4.4 VMA屬性273
9.4.5 VMA查找操作276
9.4.6 malloc()函數277
9.4.7 mmap()/munmap()函數280
9.5缺頁異常284
9.5.1 do_page_fault()函數285
9.5.2匿名頁面缺頁異常286
9.5.3文件映射缺頁中斷286
9.5.4寫時復制缺頁異常287
9.6內存短缺287
9.6.1頁面回收算法287
9.6.2 OOM Killer機制289
9.7內存管理日誌信息以及調試信息289
9.7.1 vm_stat計數289
9.7.2 meminfo分析291
9.7.3夥伴系統信息293
9.7.4查看內存管理區的信息294
9.7.5查看進程相關的內存信息296
9 .7.6查看系統內存信息的工具298
9.8內存管理實驗300
9.8.1實驗9-1:查看系統內存信息301
9.8.2實驗9-2:獲取系統的物理內存信息301
9.8.3實驗9-3:分配內存301
9.8.4實驗9-4:slab 302
9.8.5實驗9-5:VMA 302
9.8.6實驗9-6:mmap 302
9.8.7實驗9-7:映射用戶內存303
9.8.8實驗9-8:OOM 303

第10章同步管理304
10.1原子操作與內存屏障305
10.1.1原子操作305
10 .1.2內存屏障309
10.2自旋鎖機制310
10.2.1自旋鎖的定義310
10.2.2 Qspinlock的實現311
10.2.3自旋鎖的變種312
10.2. 4自旋鎖和raw_spin_lock 313
10.3信號量314
10.4互斥鎖315
10.5讀寫鎖317
10.5.1讀寫鎖的定義317
10.5.2讀寫信號量318
10. 6 RCU 320
10.7等待隊列323
10.7.1等待隊列頭323
10.7.2等待隊列節點324
10.8實驗324
10.8.1實驗10-1:自旋鎖324
10.8. 2實驗10-2:互斥鎖325
10.8.3實驗10-3:RCU鎖325

第11章中斷管理326
11.1 Linux中斷管理機制326
11.1.1 ARM中斷控制器327
11.1.2關於ARM Vexpress V2P開發板的例子327
11.1.3關於Virt開發板的例子329
11.1.4硬件中斷號和Linux中斷號的映射330
11.1.5註冊中斷331
11 .2軟中斷和tasklet 333
11.2.1軟中斷334
11.2.2 tasklet 335
11.2.3 local_bh_disable()/local_bh_enable() 336
11.2.4小結337
11.3工作隊列機制337
11.3.1工作隊列的類型338
11.3.2使用工作隊列340
11.3.3小結340
11.4實驗341
11.4.1實驗11-1:tasklet 341
11.4.2實驗11 -2:工作隊列341
11.4.3實驗11-3:定時器和內核線程341

第12章調試和性能優化343
12.1 printk()輸出函數和動態輸出343
12.1.1 printk()輸出函數343
12.1.2動態輸出345
12.1.3實驗12-1:使用printk()輸出函數347
12.1.4實驗12-2:使用動態輸出347
12.2 proc和debugfs 347
12.2.1 proc文件系統347
12.2.2 sys文件系統350
12.2.3 debugfs文件系統351
12. 2.4實驗12-3:使用procfs 351
12.2.5實驗12-4:使用sysfs 353
12.2.6實驗12-5:使用debugfs 355
12.3 ftrace 355
12.3.1 irqsoff跟踪器357
12.3.2 function跟踪器358
12.3.3動態ftrace 359
12.3.4事件跟踪361
12.3.5實驗12-6:使用ftrace 363
12.3.6實驗12-7:添加新的跟踪點363
12.3.7實驗12-8:使用示踪標誌366
12.3.8實驗12-9:使用kernelshark分析數據369
12.4分析Oops錯誤371
12.4.1 Oops錯誤介紹371
12.4.2實驗12-10 :分析Oops錯誤371
12.5 perf性能分析工具375
12.5.1 perf list命令376
12.5.2利用perf採集數據377
12.5.3 perf stat 378
12.5.4 perf top 379
12.5.5實驗12-11:使用perf工具進行性能分析380
12.5.6實驗12-12:採集perf數據以生成火焰圖381
12.6內存檢測381
12.6.1實驗12-13:使用slub_debug檢查內存洩漏382
12.6.2實驗12- 14:使用kmemleak檢查內存洩漏387
12.6.3實驗12-15:使用kasan檢查內存洩漏389
12.6.4實驗12-16:使用valgrind檢查內存洩漏393
12.7使用kdump解決死機問題394
12 .7.1 kdump介紹394
12.7.2實驗12-17:搭建ARM64的kdump實驗環境395
12.7.3實驗12-18:分析一個簡單的宕機案例398
12.8性能和測試401
12 .8.1性能和測試概述401
12.8.2 eBPF介紹402
12.8.3 BCC介紹403
12.8.4實驗12-19:運行BCC工具進行性能測試404

第13章開源社區405
13.1什麼是開源社區405
13.1.1開源軟件的發展歷史405
13.1.2 Linux基金會406
13.1.3開源協議406
13.1.4 Linux內核社區408
13.1.5國內開源社區409
13.2參與開源社區409
13.2.1參與開源項目的好處409
13.2.2如何參與開源項目410
13.3實驗13-1:使用cppcheck檢查代碼411
13.4實驗13-2:提交第一個Linux內核補丁412
13.5實驗13-3:管理和提交多個補丁組成的補丁集414

第14章文件系統419
14.1文件系統的基本概念419
14.1.1文件419
14.1.2目錄422
14.2文件系統的基本概念和知識423
14.2.1文件系統的佈局423
14.2.2索引數據塊428
14.2.3管理空閒塊430
14.2.4高速緩存430
14.3虛擬文件系統層431
14.4文件系統的一致性436
14.5一次寫磁盤的全過程439
14.6文件系統實驗440
14.6.1實驗14-1:查看文件系統440
14. 6.2實驗14-2:刪除文件內容441
14.6.3實驗14-3:塊設備441
14.6.4實驗14-4:動手寫一個簡單的文件系統441

第15章虛擬化與雲計算442
15.1虛擬化技術442
15.1.1虛擬化技術的發展歷史442
15.1.2虛擬機管理程序的分類444
15.1.3內存虛擬化445
15.1.4 I/O虛擬化445
15.2容器技術446
15.3雲計算448
15.3.1雲編排450
15.3.2 OpenStack介紹451
15.3.3 Kubernetes介紹451
15.4實驗452
15.4.1實驗15-1:製作Docker鏡像並發布452
15.4.2實驗15-2:部署Kubernetes服務452

第16章綜合能力訓練:動手寫一個小OS 453
16.1實驗準備454
16.1.1開發流程454
16.1.2配置串口線454
16.1.3寄存器地址457
16.2入門動手篇457
16.2.1實驗16-1:輸出“Welcome BenOS!” 457
16.2.2使用GDB + QEMU調試BenOS 465
16.2.3使用J-Link仿真器調試樹莓派466
16.2. 4實驗16-2:切換異常等級473
16.2.5實驗16-3:實現簡易的printk()函數473
16.2.6實驗16-4:中斷473
16.2.7實驗16-5:創建進程475
16.3進階挑戰篇475
16.4高手完善篇476