1.Linux內核
????????
1.1 Linux內核的任務
- 從技術層面講,內核是硬件和軟件之間的一個中間層,作用是將應用層序的請求傳遞給硬件,并充當底層驅動程序,對系統中的各種設備和組件進行尋址。
- 從應用程序的角度講,應用程序與硬件沒有聯系,只與內核有聯系,內核是應用程序知道的層次中的最底層。在實際工作中內核抽象出了相關的細節。
- 從資源管理的角度講,內核是一個資源管理程序。負責將可用的共享資源(如CPU時間,磁盤空間,網絡連接等)分配到各個系統進程。
- 從系統層面將,內核相當于是一個庫,提供了一組面向系統的命令。系統調用相對于應用程序來說,就像調用普通函數一樣。
1.2 Linux系統層次結構
? ? ? ? ? ? ? ? ? ? ? ?
- Linux系統結構中位于最上層的是用戶(或應用程序)空間。這是用戶應用程序執行的地方。用戶空間之下的是內核空間,Linux內核正是位于此。
????????1)GNU C Library(glibc)也在此。提供了 連接內核的系統調用接口,還提供了在用戶空間應用程序和內核之間進行轉換的機制
????????2)內核和用戶空間的應用程序使用的是不同的保護地址空間。每個用戶空間的進程都使用自己的虛擬地址空間(進程是資源分配的獨立單位),而內核則占用單獨的地址空間。 - Linux內核可進一步分為3層,最上面的是系統調用接口,它實現了一些基本功能,例如:read,write。系統調用接口之下是內核代碼,可以更加精確地定義為獨立于體系機構的內核代碼(Linux所支持的所有處理器體系結構所通用的)。在這些代碼之下是依賴于體系結構的代碼,構成了BSP(Board Support Package)的部分——是嵌入式系統開發中的核心組件,充當硬件與操作系統之間的橋梁。它提供底層硬件驅動、配置及接口。
- 內核被劃分為多個子系統。Linux也可以看作是一個整體,因為它會將所有這些基本服務都集成在內核中。這與微內核的體系結構不同,后者會提供一些基本的服務,例如通信,I/O,內存和進程管理等
?
2. Linux內核體系結構
? ? ? ?Linux內核的主要組件是:系統調用接口,進程管理,內存管理,虛擬文件系統,網絡堆棧,設備驅動程序,硬件架構的相關代碼。
2.1 系統調用接口(SCI,system call interface)
? ? ? ?該層提供了某些機制執行從用戶空間到內核的函數調用。該接口依賴于體系結構,甚至在相同的處理器族內也是如此。SCI層實際是一個非常有用的函數調用多路復用和多路分解服務。
2.2 進程管理(PM, process management)
- 進程管理的重點是進程的執行。在Linux并不區分線程和進程,代表了單獨的處理器虛擬化(線程代碼、數據、堆棧和CPU寄存器)。內核通過SCI提供了一個應用程序編程接口(API)來創建一個新進程(fork, exec 或 Portable Operating System Interface),停止進程(kill, exit)。并在它們之間進行通信和同步(signal)
- 進程管理還包括處理活動進程之間共享CPU的需求。內核實現了一種新型的調度算法,不管有多少個線程正在競爭CPU,這種算法都可以在固定時間內進行操作——O(1)調度程序,這個名字就表示它調度多個線程所使用的時間和調度一個線程所使用的時間是相同的。同樣也可以支持多處理器。
2.3 內存管理(MM, memory management)
? ? ? ?內核所管理的另外一個重要資源是內存。內存是按照所謂的內存頁方式進行管理的(大部分體系來說都是 4KB)。Linux包括了管理可用內存的方式,以及物理和虛擬映射所使用的硬件機制。Linux的內存管理不止4KB緩沖區,而是對4KB緩沖區提供一種抽象,如 Slab分配器 ——通過??分層管理??(伙伴系統 + Slab)和??對象重用??,高效解決了小內存塊的分配問題。這種內存管理的方式使用4KB緩沖區為基數,然后從中分配結構并跟蹤內存頁使用情況。這樣就允許根據系統需要來動態調整內存使用 (頁面交換算法)
?
2.4 虛擬文件系統(VFS,virtual file system)
? ? ? ?虛擬文件系統是Linux內核中文件系統的通用的接口抽象。VFS在SCI和內核所支持的文件系統之間提供了一個交換層
2.5 網絡堆棧
網絡堆棧在設計上遵循模擬協議本身的分層體系結構,如IP協議是傳輸協議TCP下面的核心網絡層協議。TCP之上的協議是 socket層,通過SCI進行調用,socket層網絡子系統的標準API,它為各種網絡協議提供了一個用戶接口。從原始幀訪問到IP協議數據單元(PDU),再到UDP,socket層提供了一種標準化的方式進行管理連接,并在各個終點之間移動數據。
2.6 設備驅動程序(大部分代碼)
設備驅動程序是用于管理硬件設備并與之交互的核心組件。它們充當用戶空間與硬件之間的橋梁,使應用程序無需直接操作底層硬件即可使用設備功能。
2.7 依賴體系結構的代碼
3. Linux驅動的paltform機制
? ? ? ?Linux的paltform機制將本身的資源注冊進內核,由內核統一管理,在驅動程序中使用這些資源時通過platform_device提供的標準接口進行申請并使用。這樣提供了驅動和資源管理的獨立性,并且擁有較好的可移植性和安全性。
? ? ? ?platform機制分為以下三個步驟:
? ? ? ?1)總線注冊階段
????????????????內核啟動初始化main.c文件中的kernal_init()→do_basic_setup()→driver_init()→platform_bus_init()→bus_register(&platform_bus_type),由此注冊了一條platform總線(虛擬總線,platform_bus)。
????????2)驅動注冊階段
????????????????Platform_driver_register()→driver_register()→bus_add_driver()→driver_attach()→bus_for_each_dev(),對在每個掛在虛擬的platform bus的設備作__deriver_attach()→driver_probe_device(),判斷drv→bus→match()是否執行成功,此時通過指針執行platform_match→strncmp(pdev→name,drv→name,BUS_ID_SIZE),如果相符就調用really_probe(實際就是執行相應設備的platform_driver→probe(platform_device)。)開始真正的探測,如果probe成功,則綁定設備到該驅動。
????????從上面可以看出,platform機制最后還是調用了bus_register(),device_add(),driver_register()這三個關鍵的函數。
????????關鍵結構體:?
struct platform_device {const char* name; //設備名稱,要與platform_driver的name一樣,這樣總線才能匹配成功u32 id; //id號,插入總線下相同name的設備編號(一個驅動可以有多個設備),如果只有一個設備填-1struct device dev; //內嵌的具體的device結構體,其中成員platform_data,是個void *類型,可以給平臺driver提供各種數據(比如:GPIO引腳等等)u32 num_resources; //資源數量,struct resource * resource; //資源結構體,保存設備的信息 };
struct resource {resource_size_t start; //起始資源,如果是地址的話,必須是物理地址resource_size_t end; //結束資源,如果是地址的話,必須是物理地址const char *name; //資源名unsigned long flags; //資源的標志//比如IORESOURCE_MEM,表示地址資源, IORESOURCE_IRQ表示中斷引腳... ...struct resource *parent, *sibling, *child; //資源拓撲指針父、兄、子,可以構成鏈表 };
涉及到的函數如下(在dev設備的入口出口函數中用到)
int platform_device_register(struct platform_device * pdev);//注冊dev設備 int platform_device_unregister(struct platform_device * pdev);//注銷dev設備
? ? ? ? ? ? ? ? platform機制的好處:
? ? ? ? ? ? ? ? 1. 提供了platform_bus_type類型的總線,把那些不是總線型的soc設備都添加到這條虛擬總線上。使得,總線——設備——驅動的模式可以得到普及。
? ? ? ? ? ? ? ? 2. 提供了platform_device和platform_driver類型的數據結構,將傳統的device和driver數據結構嵌入其中,并且加入resource成員,以便于和Open Firmware這種動態傳遞設備的新型bootloader和kernal接軌。
參考引用:linux_kernel_wiki/文章/Linux內核架構和工作原理.md at main · 0voice/linux_kernel_wiki