linux內核啟動文檔翻譯(i386)
本文檔的翻譯是基于linux內核版本2.6.11.1的,本人英語超難,但是由于學習linux內核代碼也硬著頭皮看英文文檔,看的過程中感覺能夠學到許多東西所以決定發點時間把這篇翻譯下來了,里面很很多的不準確希望大家糾正和指導。希望共同探討和學習,這也是自己學習linux源代碼的一部分內容,接下來會有更多關于這方面的知識和大家分享,包括詳細的內核運行原理和超詳細的內核代碼注釋,期待和大家分享學習過程中的點點滴滴。每天成長一點點嘛!這篇文章雖然不長,但也發了我一天的時間,主要還是因為我英文太差的緣故吧。文章中翻譯不當之處或錯誤還請大家提出來以便我盡快改正和學習。
寫在前面的一點知識:
ramdisk一個作用就是用來解決boot過程中mount根文件系統的“先有雞還是先有蛋”的問題的。
一般來說,根文件系統在形形色色的存儲設備上,不同的設備又要不同的硬件廠商的驅動,比如intel的南橋自然需要intel的ide/sata驅動,VIA的南橋需要VIA的ide/sata驅動,根文件系統也有不同的文件系統的可能,比如ubuntu發行版可能一般用ext3,suse可能就不是了,不同的文件系統也需要不同的文件系統模塊;假如把所有驅動/模塊都編譯進內核,那自然沒問題,但是這樣就違背了“內核”的精神或本質,所以一般來說驅動/模塊都駐留在根文件系統本身上/lib/modules/xxx,那么“雞蛋”問題就來了,現在要mount根文件系統卻需要根文件系統上的模塊文件,怎么辦?于是,就想出ramdisk,內核總是能安裝ramdisk的,然后把所有可能需要的驅動/模塊都放在ramdisk上,首先,讓內核將ramdisk當作根文件系統來安裝,然后再用這個根文件系統上的驅動來安裝真正的根文件系統,就將這個矛盾問題解決了.
ramdisk還舉出一個作用,現在的發行版在boot時一般都是圖形界面的,那么,ramdisk就可以放framebuffer驅動和一些圖片來做這種簡單的動畫。
說明:文章中的“命令行”都應該是“命令行參數”更好吧。從下面開始是英文和我翻譯中文的對照。
THE LINUX/I386 BOOT PROTOCOL(Linux/I386啟動協議)
----------------------------
H. Peter Anvin <hpa@zytor.com>(作者郵箱)
Last update 2002-01-01(最后更新時間2002-01-01)
On the i386 platform, the Linux kernel uses a rather complicated boot convention. This has evolved partially due to historical aspects, as well as the desire in the early days to have the kernel itself be a bootable image, the complicated PC memory model and due to changed expectations in the PC industry caused by the effective demise of real-mode DOS as a mainstream operating system.
在i386平臺,linux內核使用了一個相當復雜的啟動協議。這個特別的演變是由于歷史各個方面,在早期的愿望是內核本身是可引導的鏡像,復雜的PC機內存模型和由于期望改變在個人計算機產業中有效的終止實模式DOS而作為主流的操作系統。
Currently, four versions of the Linux/i386 boot protocol exist.
當前,四種版本的Linux/i386啟動協議存在。
Old kernels: zImage/Image support only. Some very early kernels may not even support a command line.
老的內核:zImage/Image格式僅僅被支持。一些非常早的內核甚至可能不支持命令行。
Protocol 2.00: (Kernel 1.3.73) Added bzImage and initrd support, as well as a formalized way to communicate between the boot loader and the kernel. setup.S made relocatable,although the traditional setup area still assumed writable.
協議2.00:(Kernel 1.3.73)增加了bzImage 和 initrd支持,以及引導加載程序和內核之間的通信的正式方式。setup.S 作出可重定位,盡管傳統setup區域仍假定可寫。
Protocol 2.01: (Kernel 1.3.76) Added a heap overrun warning.
協議2.01:(Kernel 1.3.76)添加堆溢出警告
Protocol 2.02: (Kernel 2.4.0-test3-pre3) New command line protocol.Lower the conventional memory ceiling. No overwrite of the traditional setup area, thus making booting safe for systems which use the EBDA from SMM or 32-bit BIOS entry points. zImage deprecated but still supported.
協議2.02: (Kernel 2.4.0-test3-pre3) 新的命令行協議。降低常規的內存上限。傳統setup區域不能重寫,從而使安全的啟動系統,使用從SMM(System Management Mode系統管理模式)或32位BIOS入口點 EBDA(Extended BIOS Data Area可擴展的BIOS數據區域)。zImage 不贊成但是仍然支持。
Protocol 2.03: (Kernel 2.4.18-pre1) Explicitly makes the highest possible initrd address available to the bootloader.
協議2.03: (Kernel 2.4.18-pre1) 明白地安排最高initrd地址可用引導裝入過程
**** MEMORY LAYOUT(內存布局)
The traditional memory map for the kernel loader, used for Image or
zImage kernels, typically looks like:
傳統的內核裝載內存映射,使用Image or zImage內核,典型地看起來像:
| |
0A0000 +------------------------+
| Reserved for BIOS | Do not use. Reserved for BIOS EBDA.(不使用。為BIOS EBDA保留)
09A000 +------------------------+
| Stack/heap/cmdline | For use by the kernel real-mode code.(實模式內核代碼使用)
098000 +------------------------+
| Kernel setup | The kernel real-mode code.(實模式內核代碼)
090200 +------------------------+
| Kernel boot sector | The kernel legacy boot sector.(內核啟動扇區)
090000 +------------------------+
| Protected-mode kernel | The bulk of the kernel image.(保護模式,大的內核映像)
010000 +------------------------+
| Boot loader | <- Boot sector entry point 0000:7C00(啟動裝載進入點0000:7c00)
001000 +------------------------+
| Reserved for MBR/BIOS |(為MBR(master boot record主引導記錄)BIOS保留)
000800 +------------------------+
| Typically used by MBR |(典型被MBR使用)
000600 +------------------------+
| BIOS use only |(僅僅被BIOS使用)
000000 +------------------------+
When using bzImage, the protected-mode kernel was relocated to 0x100000 ("high memory"), and the kernel real-mode block (boot sector,setup, and stack/heap) was made relocatable to any address between 0x10000 and end of low memory.
當使用bzImage,保護模式內核是移動到0x100000(“高內存”),實模式模塊(boot sector,setup, and stack/heap)被裝載到地址0x10000 到最低內存的結尾的任何地方。
Unfortunately, in protocols 2.00 and 2.01 the command line is still required to live in the 0x9XXXX memory range, and that memory range is still overwritten by the early kernel.The 2.02 protocol resolves that problem.
幸運地,在協議2.00和2.01中命令行仍然被要求存在0x9XXXXX內存區域,那段內存區域仍然被早期內核重寫。2.02協議解決了那個問題。
It is desirable to keep the "memory ceiling" -- the highest point in low memory touched by the boot loader -- as low as possible, since some newer BIOSes have begun to allocate some rather large amounts of memory, called the Extended BIOS Data Area, near the top of low memory. The boot loader should use the "INT 12h" BIOS call to verify how much low memory is available.
期望保持內存上限--在低內存的最高點被引導加載程序接觸--盡可能的低,因為一些新的BIOSes 已經開始分配一些相當大的內存數量,叫做可擴展BIOS的數據區域,在低內存的頂端附近。引導加載程序應該使用 "INT 12h" BIOS 中斷調用確定有多大的低內存是可利用的。
Unfortunately, if INT 12h reports that the amount of memory is too low, there is usually nothing the boot loader can do but to report an error to the user. The boot loader should therefore be designed to take up as little space in low memory as it reasonably can. For zImage or old bzImage kernels, which need data written into the
0x90000 segment, the boot loader should make sure not to use memory above the 0x9A000 point; too many BIOSes will break above that point.
幸運地,如果INT 12h中斷調用報告內存總量太少,則通常沒有引導加載程序能啟動并且報告一個錯誤給用戶。因此引導加載程序應該被設計在低內存占用盡量少量的空間。因為zImage 或 老的bzImage內核,需要數據被寫在0x90000段處,引導加載程序應該確保不使用高于0x9A000點的內存;太多的BIOSes將破壞那個點以上的內存。
**** THE REAL-MODE KERNEL HEADER(實模式內核開頭)
In the following text, and anywhere in the kernel boot sequence, "a sector" refers to 512 bytes. It is independent of the actual sector size of the underlying medium.
在下面的文本中,在內核啟動順序的任何地方,“一個扇區”是指512字節。它是下面媒介的實際扇區大小的獨立(意思不依賴具體的存儲介質,一個扇區都是指512字節)。
The first step in loading a Linux kernel should be to load the real-mode code (boot sector and setup code) and then examine the following header at offset 0x01f1. The real-mode code can total up to 32K, although the boot loader may choose to load only the first two sectors (1K) and then examine the bootup sector size.
第一步在裝載一個linux內核應該被裝載實模式代碼(boot sector 和setup代碼)然后檢查接下來在偏移0x01f1處的header代碼。實模式代碼能達到32K,但是引導加載程序可能選擇裝載僅僅開始的兩個扇區(1K)然后檢查啟動扇區的大小。
The header looks like:
Header看起來像:
Offset(偏移量)Proto(協議)Name(名字)Meaning(意思)
/Size(大?。?/span>
01F1/1 ALL setup_sects The size of the setup in sectors
(所有) (setup設置扇區的大小)
01F2/2 ALL root_flags If set, the root is mounted readonly
如果被設置,root被只讀掛載
01F4/2 ALL syssize DO NOT USE - for bootsect.S use only
不使用-僅僅被bootsect.S 使用
01F6/2 ALL swap_dev DO NOT USE - obsolete
(不使用-已不用的)
01F8/2 ALL ram_size DO NOT USE - for bootsect.S use only
不使用-僅僅被bootsect.S 使用
01FA/2 ALL vid_mode Video mode control
視頻模式控制
01FC/2 ALL root_dev Default root device number
默認的根設備號
01FE/2 ALL boot_flag 0xAA55 magic number
0xAA55 魔法數字
0200/2 2.00+ jump Jump instruction
2.00以上 跳轉指令
0202/4 2.00+ header Magic signature "HdrS"
魔法信號"HdrS"
0206/2 2.00+ version Boot protocol version supported
協議版本 啟動協議版本支持
0208/4 2.00+ realmode_swtch Boot loader hook (see below)
實模式轉換 引導裝載程序鉤子(看下面)
020C/2 2.00+ start_sys The load-low segment (0x1000) (obsolete)
開始系統段 低裝載段0x1000(已過時)
020E/2 2.00+ kernel_version Pointer to kernel version string
內核版本 指向內核版本字符串
0210/1 2.00+ type_of_loader Boot loader identifier
裝載類型 引導裝載程序標志
0211/1 2.00+ loadflags Boot protocol option flags
裝載標志 引導協議可選標志
0212/2 2.00+ setup_move_size Move to high memory size (used with hooks)
Setup移動大小 移動到高內存大?。ㄊ褂勉^子)
0214/4 2.00+ code32_start Boot loader hook (see below)
32位代碼啟動 引導裝載程序鉤子(看下面)
0218/4 2.00+ ramdisk_image initrd load address (set by boot loader)
Ramdisk鏡像 initrd(初始化跟設備)裝載地址(被引導裝載程序設置)
021C/4 2.00+ ramdisk_size initrd size (set by boot loader)
Ramdisk大小 initrd 大?。ū灰龑аb載程序設置)
0220/4 2.00+ bootsect_kludge DO NOT USE - for bootsect.S use only
不使用-僅僅被bootsect.S 使用
0224/2 2.01+ heap_end_ptr Free memory after setup end
2.01以上 堆結束指針 setup結束以后是自由內存
0226/2 N/A pad1 Unused
0228/4 2.02+ cmd_line_ptr 32-bit pointer to the kernel command line
2.02以上 命令行參數指針 32位指向內核命令行參數
022C/4 2.03+ initrd_addr_max Highest legal initrd address
2.03以上 initrd最大地址 最高合法的initrd地址
For backwards compatibility, if the setup_sects field contains 0, the real value is 4.
為了后面的兼容性,如果setup_sects區域包含0,真實的值是4。
If the "HdrS" (0x53726448) magic number is not found at offset 0x202,the boot protocol version is "old". Loading an old kernel, the following parameters should be assumed:
如果"HdrS" (0x53726448) 魔法數字沒有在偏移0x202處被找到,啟動協議版本是“老的”。裝載一個老的內核,下面的參數應該被假設:
Image type = zImage 映像內核=zImage
initrd not supported initrd不被支持
Real-mode kernel must be located at 0x90000.實模式內核必須位于0x90000
Otherwise, the "version" field contains the protocol version,e.g. protocol version 2.01 will contain 0x0201 in this field. When setting fields in the header, you must make sure only to set fields supported by the protocol version in use.
否則,“version”區域包含協議版本,例如協議本版2.01將包含0x0201在這個區域。當設置區域在header中時,你必須確保僅僅設置區域被使用的協議版本所支持。
The "kernel_version" field, if set to a nonzero value, contains a pointer to a null-terminated human-readable kernel version number string, less 0x200. This can be used to display the kernel version to the user. This value should be less than (0x200*setup_sects). For example, if this value is set to 0x1c00, the kernel version number string can be found at offset 0x1e00 in the kernel file. This is a valid value if and only if the "setup_sects" field contains the value 14 or higher.
"kernel_version" 字段,如果被設置為一個非零值,包含一個指向(NULL)空結束的人可讀的內核版本數字字符串,小于0x200。這個能夠被使用顯示內核版本給用戶看。這個值應該小于(0x200*setup的扇區數)。例如,如果這個值被設置為0x1c00,內核版本數字字符串能夠被找到在內核文件偏移0x1e00處。如果并且僅僅如果"setup_sects"字段包含值14或更高這是一個有效值
Most boot loaders will simply load the kernel at its target address directly. Such boot loaders do not need to worry about filling in most of the fields in the header. The following fields should be filled out, however:
大多數引導裝載程序將簡單直接的裝載內核到它的目的地址。這樣引導裝載程序不需要擔心在header填充很多的字段。然而,下面的字段應該被填充:
vid_mode:Please see the section on SPECIAL COMMAND LINE OPTIONS.
視頻模式:請看特殊的命令行可選部分
type_of_loader:裝載類型
If your boot loader has an assigned id (see table below), enter 0xTV here, where T is an identifier for the boot loader and V is a version number. Otherwise, enter 0xFF here.
如果你的引導裝載程序有一個被指派的id(看下面的表格),進入0xTV這兒,T是一個引導裝載程序的標志符,V是一個版本數字。否則,進入0xFF這兒。
Assigned boot loader ids:指派的引導裝載程序(以下9種)
0 LILO
1 Loadlin
2 bootsect-loader
3 SYSLINUX
4 EtherBoot
5 ELILO
7 GRuB
8 U-BOOT
Please contact <hpa@zytor.com> if you need a bootloader ID value assigned.
請聯系 <hpa@zytor.com>如果你需要一個引導裝載程序被指派的ID值
loadflags, heap_end_ptr:裝載標志,堆結束指針
If the protocol version is 2.01 or higher, enter the offset limit of the setup heap into heap_end_ptr and set the 0x80 bit (CAN_USE_HEAP) of loadflags. heap_end_ptr appears to be relative to the start of setup (offset 0x0200).
如果協議版本是2.01或更高,設置setup堆棧的限制到heap_end_ptr(堆結束指針)處和設置0x80位(能夠使用堆棧)標志。heap_end_ptr(堆結束指針)顯示相對setup的開始(偏移0x0200)。
setup_move_size: setup移動的大小
When using protocol 2.00 or 2.01, if the real mode kernel is not loaded at 0x90000, it gets moved there later in the loading sequence. Fill in this field if you want additional data (such as the kernel command line) moved in addition to the real-mode kernel itself.
當使用協議2.00或2.01,如果實模式內核是不裝載在0x90000,它在加載序號以后被移動那里。如果你需要額外的數據(例如內核命令行)被移動,那么填充這個字段增加到實模式內核自身。
ramdisk_image, ramdisk_size:內存盤映像,內存盤大小
If your boot loader has loaded an initial ramdisk (initrd), set ramdisk_image to the 32-bit pointer to the ramdisk data and the ramdisk_size to the size of the ramdisk data.
如果你的引導裝載程序已經裝載一個初始化的內存盤(initrd),設置內存盤映像(ramdisk_image)為一個32位指針指向內存盤數據和設置內存盤大小(ramdisk_size)為內存盤數據的大小。
The initrd should typically be located as high in memory as possible, as it may otherwise get overwritten by the early kernel initialization sequence. However, it must never be located above the address specified in the initrd_addr_max field. The initrd should be at least 4K page aligned.
初始化的內存盤(initrd)應該典型地位于盡可能的高的內存,因為它可能被早的內核初始化序列覆蓋寫。然而,它必須從來不位于在專門化的initrd_addr_max 字段以上的地址。初始化的內存盤(initrd)應該被設置至少4K頁對齊。
cmd_line_ptr:命令行指針
If the protocol version is 2.02 or higher, this is a 32-bit pointer to the kernel command line. The kernel command line can be located anywhere between the end of setup and 0xA0000.Fill in this field even if your boot loader does not support a command line, in which case you can point this to an empty string (or better yet, to the string "auto".) If this field is left at zero, the kernel will assume that your boot loader does not support the 2.02+ protocol.
如果協議是2.02或更高,這是一個32位指針指向內核命令行。內核命令行能位于setup結束至0xA0000的任何地方。填充這個字段雖然你的引導裝載程序不支持一個命令行,它能使你這個字段指向一個空字符串(或更好,是一個“auto”字符串)如果這個字段被留下在零,內核將假設你的引導裝載程序不支持2.02以上的協議。
ramdisk_max:內存盤最大
The maximum address that may be occupied by the initrd contents. For boot protocols 2.02 or earlier, this field is not present, and the maximum address is 0x37FFFFFF. (This address is defined as the address of the highest safe byte, so if your ramdisk is exactly 13107131072 2 bytes long and this field is 0x37FFFFFF, you can start your ramdisk at 0x37FE0000.)
可能被初始化內存盤內容占用的最大地址。對于引導協議2.02或更早,這個字段是不存在的,并且最大地址是0x37FFFFFF。(這個地址被定義為最高的安全字節,因此如果你的內存盤確切的131072 字節長并且這個區域是0x37FFFFFF,你能開始你的內存盤在0x37FE0000)。
**** THE KERNEL COMMAND LINE內核命令行
The kernel command line has become an important way for the boot loader to communicate with the kernel. Some of its options are also relevant to the boot loader itself, see "special command line options"below.
內核命令行已近是改變引導裝載程序和內核通信的一種重要方式。一些它的可選項也是有關于引導裝載程序自身的,看下面的“特殊的命令行可選項”。
The kernel command line is a null-terminated string up to 255 characters long, plus the final null.
內核命令行是一個NULL(空)終止的加上最后的null到達255個字符長度的字符串。
If the boot protocol version is 2.02 or later, the address of the kernel command line is given by the header field cmd_line_ptr (see above.)
如果引導協議版本是2.02或更晚,內核的命令行地址被header字段 cmd_line_ptr 給出(看上面)。
If the protocol version is *not* 2.02 or higher, the kernel command line is entered using the following protocol:
如果協議版本不是2.02或更高,內核命令行被輸入使用下面的協議:
At offset 0x0020 (word), "cmd_line_magic", enter the magic number 0xA33F.
在偏移0x0020(字),“cmd_line_magic”,輸入魔法數字0xA33F。
At offset 0x0022 (word), "cmd_line_offset", enter the offset of the kernel command line (relative to the start of the real-mode kernel).
在偏移0x0022(字),"cmd_line_offset", 輸入內核命令行的偏移量(與實模式內核開始有關)
The kernel command line *must* be within the memory region covered by setup_move_size, so you may need to adjust this field.
內核命令行必須在被setup_move_size內存區域大小覆蓋以內,因此你可能需要調整這個字段。
**** SAMPLE BOOT CONFIGURATION引導程序配置樣例
As a sample configuration, assume the following layout of the real mode segment:
作為一個樣例配置,假設實模式段有下面的布局:
0x0000-0x7FFF Real mode kernel實模式內核
0x8000-0x8FFF Stack and heap棧和堆
0x9000-0x90FF Kernel command line內核命令行
Such a boot loader should enter the following fields in the header:
如此一個引導裝載程序應該進入下面字段,在header中。
unsigned long base_ptr; /* base address for real-mode segment */實模式的段地址
if ( setup_sects == 0 ) {
setup_sects = 4;
}
if ( protocol >= 0x0200 ) {
type_of_loader = <type code>;
if ( loading_initrd ) {
ramdisk_image = <initrd_address>;
ramdisk_size = <initrd_size>;
}
if ( protocol >= 0x0201 ) {
heap_end_ptr = 0x9000 - 0x200;
loadflags |= 0x80; /* CAN_USE_HEAP */
}
if ( protocol >= 0x0202 ) {
cmd_line_ptr = base_ptr + 0x9000;
} else {
cmd_line_magic = 0xA33F;
cmd_line_offset = 0x9000;
setup_move_size = 0x9100;
}
} else {
/* Very old kernel */
cmd_line_magic = 0xA33F;
cmd_line_offset = 0x9000;
/* A very old kernel MUST have its real-mode code
loaded at 0x90000 */一個老的內核必須有它的實模式代碼裝載在0x90000
if ( base_ptr != 0x90000 ) {
/* Copy the real-mode kernel */復制實模式內核
memcpy(0x90000, base_ptr, (setup_sects+1)*512);
/* Copy the command line */復制命令行
memcpy(0x99000, base_ptr+0x9000, 256);
base_ptr = 0x90000; /* Relocated */重映射
}
/* It is recommended to clear memory up to the 32K mark */它要求清除內存到32K標志
memset(0x90000 + (setup_sects+1)*512, 0,
(64-(setup_sects+1))*512);
}
**** LOADING THE REST OF THE KERNEL(裝載剩余的內核部分)
The non-real-mode kernel starts at offset (setup_sects+1)*512 in the kernel file (again, if setup_sects == 0 the real value is 4.) It should be loaded at address 0x10000 for Image/zImage kernels and 0x100000 for bzImage kernels.
非實模式內核開始在內核文件偏移 (setup_sects+1)*512 處(重復一下,如果 setup_sects == 0 真實值是4)。作為Image/zImage它應該被裝載在地址0x10000 ,作為bzImage它應該被裝載在地址0x100000
The kernel is a bzImage kernel if the protocol >= 2.00 and the 0x01 bit (LOAD_HIGH) in the loadflags field is set:
如果協議大于等于2.00并且在裝載標志(loadflags )字段的0x01位(高裝載)被設置,則內核是一個bzImage(大模式內核)。
is_bzImage = (protocol >= 0x0200) && (loadflags & 0x01);//偽代碼表示
load_address = is_bzImage ? 0x100000 : 0x10000;//偽代碼表示
Note that Image/zImage kernels can be up to 512K in size, and thus use the entire 0x10000-0x90000 range of memory. This means it is pretty much a requirement for these kernels to load the real-mode part at
0x90000. bzImage kernels allow much more flexibility.
注意that Image/zImage(小模式內核)能夠到達512K大小,因此使用整個 0x10000-0x90000 內存區域。這意味著對這些內核它是相當多的要求來裝載實模式部分在0x90000。bzImage內核允許更多的靈活性。
**** SPECIAL COMMAND LINE OPTIONS(特殊的命令行可選項)
If the command line provided by the boot loader is entered by the user, the user may expect the following command line options to work. They should normally not be deleted from the kernel command line even
though not all of them are actually meaningful to the kernel. Boot loader authors who need additional command line options for the boot loader itself should get them registered in Documentation/kernel-parameters.txt to make sure they will not conflict with actual kernel options now or in the future.
如果被引導裝載程序提供的命令行被用戶輸入,用戶可能期望根據下面的命令行的可選項來運行。通常不應該從內核命令行刪除他們,即使不是所有的他們對內核來說都有實際上的意義。針對引導裝載程序自身的需要額外的命令行可選項的引導裝載程序作者應該從注冊在Documentation/kernel-parameters.txt這個文件中得到他們,來確保他們將不會和現在或將來的實際的內核可選項產生沖突。
vga=<mode>VGA=《模式》(也就是顯卡模式配置)
<mode> here is either an integer (in C notation, either decimal, octal, or hexadecimal) or one of the strings
"normal" (meaning 0xFFFF), "ext" (meaning 0xFFFE) or "ask" (meaning 0xFFFD). This value should be entered into the vid_mode field, as it is used by the kernel before the command line is parsed.
<模式>這兒不是一個整數(在C語言中的記號,不是十進制,八進制,就是十六進制)就是一個字符串“正常”(0xFFFF代表的意義),“ext”(0xFFFE代表的意義),“ask”(0xFFFD代表的意義)。這個值應該被輸入視頻模式(vid_mode)字段,在命令行被解析以前被內核使用。
mem=<size>
<size> is an integer in C notation optionally followed by K, M or G (meaning << 10, << 20 or << 30). This specifies the end of memory to the kernel. This affects the possible placement of an initrd, since an initrd should be placed near end of memory. Note that this is an option to *both* the kernel and the bootloader!
在C語言的表示<size> 是隨意地跟著K,M或G的一個整數(意思左移10,20,30位), 這指定內核的內存末端。這可能影響的地方是一個初始化的內存盤(initrd),因為初始化的內存盤(initrd)應該被放置在內存末端的附近。注意在內核(kernel)和引導裝載程序(bootloader)都是一個可選項。
initrd=<file>
An initrd should be loaded. The meaning of <file> is obviously bootloader-dependent, and some boot loaders (e.g. LILO) do not have such a command.
這個初始化的內存盤應該被裝載。<file>的意思明顯是依賴于引導裝載程序(bootloader),并且一些引導裝載程序(bootloader)(像LILO)沒有如此的一個命令。
In addition, some boot loaders add the following options to the user-specified command line:
另外,一些啟動裝載程序增加以下選擇項到用戶指定的命令行:
BOOT_IMAGE=<file>
The boot image which was loaded. Again, the meaning of <file> is obviously bootloader-dependent.
被裝載的引導鏡像。再一次,<file>的意思明顯是依賴于引導裝載程序(bootloader)。
Auto(自動)
The kernel was booted without explicit user intervention.
內核被引導沒有明顯的用戶交互。
If these options are added by the boot loader, it is highly recommended that they are located *first*, before the user-specified or configuration-specified command line. Otherwise, "init=/bin/sh" gets confused by the "auto" option.
如果這些選擇項由啟動裝載程序增加,在用戶指定或配置指定的命令行之前我們極力推薦他們是被第一個被找出的。 否則, “init=/bin/sh”由“自動”選項拒絕。
**** RUNNING THE KERNEL運行內核
The kernel is started by jumping to the kernel entry point, which is located at *segment* offset 0x20 from the start of the real mode kernel. This means that if you loaded your real-mode kernel code at 0x90000, the kernel entry point is 9020:0000.
內核跳轉到位于的內核入口點被啟動的, 從實模式內核開始的地址處段偏移 0x20。這意味著如果您加載您的實時模式內核代碼在 0x90000,內核入口點是 9020:0000。
At entry, ds = es = ss should point to the start of the real-mode kernel code (0x9000 if the code is loaded at 0x90000), sp should be set up properly, normally pointing to the top of the heap, and interrupts should be disabled. Furthermore, to guard against bugs in the kernel, it is recommended that the boot loader sets fs = gs = ds =es = ss.
在入口,ds = es = ss應該指向實模式內核代碼開始的地方(如果代碼被裝載在ox90000處就是0x9000),SP(堆棧指針)的開始應該適當地設定,通常指向堆的頂端,并且所有的中斷應該被禁止。此外,為了在內核控制產生錯誤(bugs),建議啟動裝載程序設置fs = gs = ds =es = ss。
In our example from above, we would do:
在來至上面我們的例程,我們應該做:
/* Note: in the case of the "old" kernel protocol, base_ptr must be == 0x90000 at this point; see the previous sample code */
注意:在老內核協議的情況下,在base_ptr這一點必須是在0x90000 ,看以前樣例代碼
seg = base_ptr >> 4;
cli(); /* Enter with interrupts disabled! */禁止中斷
/* Set up the real-mode kernel stack */建立實模式內核堆棧
_SS = seg;
_SP = 0x9000; /* Load SP immediately after loading SS! */在裝載了SS(堆棧段)以后立即裝載堆棧指針(SP)
_DS = _ES = _FS = _GS = seg;
jmp_far(seg+0x20, 0); /* Run the kernel */運行內核
If your boot sector accesses a floppy drive, it is recommended to switch off the floppy motor before running the kernel, since the kernel boot leaves interrupts off and thus the motor will not be switched off, especially if the loaded kernel has the floppy driver as a demand-loaded module!
如果您的引導扇區訪問(軟盤)磁盤驅動器,推薦在運行內核之前關閉馬達。因為內核引導停止中斷,因此電機將不會關閉,特別是如果在加載的內核有軟盤驅動程序作為需求加載的模塊 !
**** ADVANCED BOOT TIME HOOKS先進的啟動時間掛鉤
If the boot loader runs in a particularly hostile environment (such as LOADLIN, which runs under DOS) it may be impossible to follow the standard memory location requirements. Such a boot loader may use the following hooks that, if set, are invoked by the kernel at the appropriate time. The use of these hooks should probably be
considered an absolutely last resort!
如果你的引導裝載程序運行在一個特別的不穩定的環境中(例如LOADIN,運行在DOS之下)它可能不能按照標準內存位置的要求。因為一個引導裝載程序可能使用下面那樣的鉤子,如果設置,被內核在合適的時間調用。使用這些鉤子可能應考慮一個絕對最后的手段。
IMPORTANT: All the hooks are required to preserve %esp, %ebp, %esi and %edi across invocation.
重要:所有在調用的鉤子要求保護esp寄存器, ebp寄存器, esi寄存器 和edi寄存器
realmode_swtch:實模式切換
A 16-bit real mode far subroutine invoked immediately before entering protected mode. The default routine disables NMI, so your routine should probably do so, too.
在進入保護模式以前16位實模式遠子程序立即調用。默認例程禁止NMI(不可屏蔽中斷),因此你的例程也應該可能這樣做。
code32_start:32位代碼開始
A 32-bit flat-mode routine *jumped* to immediately after the transition to protected mode, but before the kernel is uncompressed. No segments, except CS, are set up; you should set them up to KERNEL_DS (0x18) yourself.
在過渡到保護模式以后立即跳轉到一個32位的線性平板模式運行路線,但是在內核被解壓之前。除了CS代碼段是沒有段被建立;你應該建立你自己的內核數據段(KERNEL_DS)(0x18)。
After completing your hook, you should jump to the address that was in this field before your boot loader overwrote it.
在完成您的勾子以后,您應該跳到在這個字段的地址,在您的啟動裝載程序重寫它之前。
浙公網安備 33010602011771號