博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
grub学习(1) 第一阶段启动
阅读量:4068 次
发布时间:2019-05-25

本文共 3554 字,大约阅读时间需要 11 分钟。

 

BIOS/UEFI将控制权交过来

作用:读取第一个扇区

    分解:
        先检查控制器是否正确dx
        通过int13是否支持LBA/CHS模式
        通过int13将第一个扇区读取到缓存
        然后将缓存的数据拷贝到预期位置
        跳转到预期的位置,执行第一个扇区的代码

boot.S	.text	/* Tell GAS to generate 16-bit instructions so that this code works	   in real mode. */	.code16.globl _start, start;_start:start:	jmp	LOCAL(after_BPB)	nop	/* do I care about this ??? */

第一次跳转:

/* 啰啰嗦嗦这一堆, 就是保证dl为0x80, 默认为硬盘 */LOCAL(after_BPB):	. = _start + GRUB_BOOT_MACHINE_DRIVE_CHECK	boot_drive_check:        jmp     3f	/* grub-setup may overwrite this jump */        testb   $0x80, %dl        jz      2f3:	/* Ignore %dl different from 0-0x0f and 0x80-0x8f.  */	testb   $0x70, %dl	jz      1f2:	    movb    $0x80, %dl1:	/*	 * ljmp to the next instruction because some bogus BIOSes	 * jump to 07C0:0000 instead of 0000:7C00.	 */	ljmp	$0, $real_start

第二次跳转:

跳转后检测是否支持LBA

real_start:	/* set up %ds and %ss as offset from 0 */	xorw	%ax, %ax	movw	%ax, %ds	movw	%ax, %ss		/* set up the REAL stack */	movw	$GRUB_BOOT_MACHINE_STACK_SEG, %sp	//ss:sp 0x0000:0x2000		pushw	%dx //入栈保存, 下面有int调用,防止被破坏		/* set %si to the disk address packet */	movw	$disk_address_packet, %si	/* check if LBA is supported */	movb	$0x41, %ah	movw	$0x55aa, %bx	int	$0x13		/* 上述代码的解释如下:		磁盘扩展探测: INT 13H, AH=41H 		检测磁盘扩展读(LBA/CHS)支持情况。详细描述如下。		参数:		寄存器        描述		AH=0x41    扩展检测函数序号		DL        驱动器编号(第一块硬盘为0x80,第二块为0x81,依次类推)		BX        0x55AA		结果:		寄存器        描述		CF        支持清零,不支持置1		AH        错误码或者主版本号		BX        0x55AA		CX        接口支持掩码				1 – 使用打包结构体存取设备				2 – 驱动器加锁和弹出				4 – 支持增强型磁盘驱动器(EDD)	*/

封装disk_address_packet,读取第一个扇区

/* 下面还有Int调用, dx再保存一下 */	popw	%dx	pushw	%dx	lba_mode:	xorw	%ax, %ax	movw	%ax, 4(%si)	incw	%ax	/* set the mode to non-zero */	movb	%al, -1(%si)	/* the blocks */	movw	%ax, 2(%si)	/* the size and the reserved byte */	movw	$0x0010, (%si)	/* the absolute address */	movl	kernel_sector, %ebx	movl	%ebx, 8(%si)	movl	kernel_sector + 4, %ebx	movl	%ebx, 12(%si)	/* the segment of buffer address */	movw	$GRUB_BOOT_MACHINE_BUFFER_SEG, 6(%si)/* * BIOS call "INT 0x13 Function 0x42" to read sectors from disk into memory *	Call with	%ah = 0x42 *			%dl = drive number *			%ds:%si = segment:offset of disk address packet *	Return: *			%al = 0x0 on success; err code on failure */	movb	$0x42, %ah	int	$0x13	/*	上述代码的解释如下:		LBA模式读: INT 13H, AH=42H 		LBA模式的读采用打包的数据结构作为参数。		参数:		寄存器        描述		AH=42H    扩展读函数序号		DL        驱动器编号(第一块硬盘为0x80,第二块为0x81,依次类推)		DS:SI        segment:offset指针,指向磁盘地址包DAP (Disk Address Packet)		DAP结构体的格式描述如下:		偏移量        大小        描述		00H        1 Byte        DAP大小=16=0x10		01H        1 Byte        未用,必须置0		02H~03H    2 Bytes        需要读的扇区数		(有些BIOS限制不能超过127扇区)		04H~07H    4 Bytes        segment:offset指针,指向内存缓冲区,读取到的		扇区内容放置在该缓冲区		08H~0FH    8 Bytes        需要读的连续扇区的起始扇区编号		(第一个扇区的编号是0)		结果:		寄存器        描述		CF        失败置1,成功清零		AH        返回码				读取第一个扇区, 把第一个扇区的数据成功则数据被读到了0x7000:0x0000(内存0x700000)位置	*/		movw	$GRUB_BOOT_MACHINE_BUFFER_SEG, %bx	jmp	LOCAL(copy_buffer)

把数据从0x7000:0x0000(内存0x700000)位置拷贝buff到0x0000:0x8000

LOCAL(copy_buffer):	/*	 * We need to save %cx and %si because the startup code in	 * kernel uses them without initializing them.	 */	pusha	pushw	%ds	movw	$0x100, %cx	movw	%bx, %ds	xorw	%si, %si	movw	$GRUB_BOOT_MACHINE_KERNEL_ADDR, %di	movw	%si, %es	cld	rep	movsw	popw	%ds	popa	/* boot kernel */	jmp	*(kernel_address)

深入理解 GNU GRUB - 02 boot.S 2.1 相关BIOS例程

https://blog.csdn.net/cppgp/article/details/6360976

grub2 1.95 源码分析之一 —— boot.S 分析及注释

https://blog.csdn.net/cppgp/article/details/2060146

深入理解 GNU GRUB - 02 boot.S 2.4 boot.S详细注释

https://blog.csdn.net/cppgp/article/details/6361020

你可能感兴趣的文章
PHP那点小事--三元运算符
查看>>
fastcgi_param 详解
查看>>
Linux中的进程
查看>>
学习python(1)——环境与常识
查看>>
学习设计模式(3)——单例模式和类的成员函数中的静态变量的作用域
查看>>
一文看清HBase的使用场景
查看>>
解析zookeeper的工作流程
查看>>
搞定Java面试中的数据结构问题
查看>>
慢慢欣赏linux make uImage流程
查看>>
linux内核学习(7)脱胎换骨解压缩的内核
查看>>
以太网基础知识
查看>>
慢慢欣赏linux 内核模块引用
查看>>
kprobe学习
查看>>
慢慢欣赏linux CPU占用率学习
查看>>
Homebrew指令集
查看>>
React Native(一):搭建开发环境、出Hello World
查看>>
React Native(二):属性、状态
查看>>
JSX使用总结
查看>>
React Native(四):布局(使用Flexbox)
查看>>
React Native(七):Android双击Back键退出应用
查看>>