成人免费xxxxx在线视频软件_久久精品久久久_亚洲国产精品久久久_天天色天天色_亚洲人成一区_欧美一级欧美三级在线观看

聊聊Linux 內核入口分析

系統 Linux
從啟動引導程序 bootloader(uboot)跳轉到 Linux 內核后,Linux 內核開始啟動,今天我們分析一下 Linux 內核啟動入口。

[[426259]]

本文轉載自微信公眾號「嵌入式Linux系統開發」,作者Jasonangel 。轉載本文請聯系嵌入式Linux系統開發公眾號。

從啟動引導程序 bootloader(uboot)跳轉到 Linux 內核后,Linux 內核開始啟動,今天我們分析一下 Linux 內核啟動入口。

跳轉過去初始化肯定是在匯編文件中,根據架構可以選擇不同的平臺,這里看一下鏈接匯編文件:

linux4.14/arch/arm/kernel/vmlinux.lds.S

這里可以看到鏈接時候 Linux 入口是 stext 段,這里是啟動引導程序跳轉過來的第一段Linux 代碼:

Linux入口地址

我們先看一下入口地址的確定,同一文件。

  1. SECTIONS 
  2.  /* 
  3.   * XXX: The linker does not define how output sections are 
  4.   * assigned to input sections when there are multiple statements 
  5.   * matching the same input section name.  There is no documented 
  6.   * order of matching. 
  7.   * 
  8.   * unwind exit sections must be discarded before the rest of the 
  9.   * unwind sections get included. 
  10.   */ 
  11.  /DISCARD/ : { 
  12.   *(.ARM.exidx.exit.text) 
  13.   *(.ARM.extab.exit.text) 
  14.   ARM_CPU_DISCARD(*(.ARM.exidx.cpuexit.text)) 
  15.   ARM_CPU_DISCARD(*(.ARM.extab.cpuexit.text)) 
  16.   ARM_EXIT_DISCARD(EXIT_TEXT) 
  17.   ARM_EXIT_DISCARD(EXIT_DATA) 
  18.   EXIT_CALL 
  19. #ifndef CONFIG_MMU 
  20.   *(.text.fixup) 
  21.   *(__ex_table) 
  22. #endif 
  23. #ifndef CONFIG_SMP_ON_UP 
  24.   *(.alt.smp.init) 
  25. #endif 
  26.   *(.discard) 
  27.   *(.discard.*) 
  28.  } 
  29.  
  30.  . = PAGE_OFFSET + TEXT_OFFSET; 
  31.  .head.text : { 
  32.   _text = .; 
  33.   HEAD_TEXT 
  34.  } 

這個 SECTIONS 比較長,只放一部分。在這里有個比較重要的東西:

  1. . = PAGE_OFFSET + TEXT_OFFSET; 

這一句表示了 Linux 系統真正的啟動地址。

PAGE_OFFSET 是 Linux 內核空間的虛擬起始地址,定義在:

linux4.14/arch/arm64/include/asm/memory.h

注意,這里的地址都很重要,很多地方會用到。當然,這里的地址可能會隨著 Linux 內核版本的不同和硬件的不同,會變化。這里沒有一個具體的數,因為 VA_BITS 中的數字是可選的,大家可以根據自己的平臺算一下。

TEXT_OFFSET 定義在:

linux4.14/arch/arm/Makefile 中:

這個值一般是 0x00008000 ,算出 PAGE_OFFSET 后加上這個值就是 Linux 內核的起始地址。

修改這個偏移量就可以使Linux內核拷貝到不同的地址,自己修改注意內存對齊。

stext 段

從上面的ENTRY(stext)可以知道,一開始是運行stext段,這個段內的代碼是 start_kernel 函數前匯編環境的初始化。

linux4.14/arch/arm64/kernel/head.S

preserve_boot_args 保存 bootloader 傳遞過來的參數。

el2_setup 是設置 Linux 啟動模式是 EL2。Linux 有 EL0、EL1、EL2、EL3 四種異常啟動模式,這里設置一開始是 EL2,EL2 支持虛擬內存技術,然后注釋說明后面又退回 EL1,在 EL1 啟動 kernel。EL3 一般是只在安全模式使用。

set_cpu_boot_mode_flag 保存上面 cpu 的啟動模式。

__create_page_tables 創建頁表。

__cpu_setup 初始化CPU,這里主要是初始化和 MMU 內存相關的 CPU 部分。

__primary_switch 這里會進行跳轉。

在同一個文件中,會跳轉到這里,739 行開啟了MMU。然后最重要的是跳轉到

__primary_switched 函數。先把 __primary_switched 地址放到 x8 寄存器中,再跳轉到 x8,也就是跳轉到 __primary_switched。

接下來分析 __primary_switched 函數:

324-327 初始化了 init 進程的內存信息,開辟了內存空間。

329-334 設置了向量表。

336-340 保存了FDT,也就是 flat device tree 。

 

342-348 清除了BSS 段,我們知道一般是內存四區:堆區、棧區、全局區、代碼區。其中全局區可以再分為 data 段和 BSS 段,BSS 段存儲了未初始化的變量,這里將BSS段進行清零操作,否則內存中的值是不確定的,這是一個傳統操作。

 

責任編輯:武曉燕 來源: 嵌入式Linux系統開發
相關推薦

2010-07-23 09:19:04

Linux內核

2020-11-05 09:59:24

Linux內核信號量

2010-08-28 15:38:11

2014-07-29 15:44:33

Linux內核Crash

2018-10-10 14:02:30

Linux系統硬件內核

2017-08-16 16:20:01

Linux內核態搶占用戶態搶占

2021-09-06 07:45:08

LinuxLinux內核

2009-12-11 15:10:22

2017-03-17 15:05:05

Linux內核源碼do_fork

2022-09-28 11:34:27

用戶行為數據業務

2023-04-28 08:42:08

Linux內核SPI驅動

2009-08-09 20:39:11

Linux內核虛擬環境虛擬主機

2021-09-08 06:51:53

CountDownLa閉鎖源碼

2021-02-20 06:08:07

LinuxWindows內核

2020-09-23 12:42:08

Linux

2020-10-13 10:51:10

Linux內核

2009-12-11 09:42:54

Linux內核源碼進程調度

2009-12-11 09:47:23

Linux內核源碼進程調度

2009-10-12 12:46:55

Linux內核SCSI IO

2022-11-30 08:19:15

內存分配Go逃逸分析
點贊
收藏

51CTO技術棧公眾號

主站蜘蛛池模板: 国产精品99一区二区 | 久久精品国产一区二区三区不卡 | 国产一区二区不卡 | 免费中文字幕日韩欧美 | 福利视频大全 | 日韩一区二区视频 | 一区二区亚洲 | 男女在线网站 | 成人不卡视频 | 亚洲午夜精品一区二区三区他趣 | 一区二区av在线 | 亚洲精品在线免费看 | 国产成人精品免费视频大全最热 | 欧美一区在线看 | 欧美一区中文字幕 | 日日操操 | 91精品国产乱码久久久久久久久 | 欧美国产精品一区二区 | 成人一级毛片 | 一区二区在线不卡 | 波多野结衣先锋影音 | 欧美三级视频在线观看 | 日韩精品成人在线 | 国产高清视频 | 亚洲精品国产a久久久久久 午夜影院网站 | 狠狠躁躁夜夜躁波多野结依 | 自拍视频在线观看 | 欧美激情一区二区三区 | 日本激情视频中文字幕 | 一区二区三区在线电影 | av影片在线 | 久久精品视频91 | 国产精品欧美一区二区 | 一区二区三区高清 | 成人不卡在线 | 久久国| 欧美a在线| 中文字幕乱码一区二区三区 | 久久日韩粉嫩一区二区三区 | 99精品99 | 91精品国产91久久久久久密臀 |