Uboot启动流程 (3)

文章详细分析了Uboot在启动Linux内核时的步骤,包括bootz命令的执行函数do_bootz,如何设置全局变量images,以及不同BOOT阶段如BOOTM_STATE_START、BOOTM_STATE_LOADOS等的处理。在启动过程中,涉及到内核镜像、ramdisk、设备树的查找和加载,最后通过boot_jump_linux函数跳转到Linux内核入口点执行。

前面分析了Uboot在启动内核前所做的准备工作,现在针对bootz命令进行分析内核启动的过程。当Uboot启动后,我们可以设置bootcmd为以下内容,当倒计时结束则会启动内核:

 不管是 bootz 还是 bootm 命令,在启动 Linux 内核的时候都会用到一个重要的全局变量:images

cmd/bootm.c
bootm_headers_t images;	        	        /* pointers to os/initrd/fdt images */

是一个bootm_headers_t的结构体:

typedef struct bootm_headers {
#ifndef USE_HOSTCC
	        image_info_t	        os;	        	        /* OS 镜像信息 */
	        ulong	        	        ep;	        	        /* OS 入口点 */

	        ulong	        	        rd_start, rd_end;/* ramdisk 开始和结束位置 */

	        char	        	        *ft_addr;	        /* 设备树地址 */
	        ulong	        	        ft_len;	        	        /* 设备树长度 */

	        ulong	        	        initrd_start; //initrd 开始位置
	        ulong	        	        initrd_end; //initrd 结束位置
	        ulong	        	        cmdline_start; //cmdline 开始位置
	        ulong	        	        cmdline_end;  //cmdline 结束位置
	        bd_t	        	        *kbd;
#endif

	        int	        	        verify;	        	        /* getenv("verify")[0] != 'n' */
//表示 BOOT 的不同阶段
#define	        BOOTM_STATE_START	        (0x00000001) 
#define	        BOOTM_STATE_FINDOS	        (0x00000002)
#define	        BOOTM_STATE_FINDOTHER	        (0x00000004)
#define	        BOOTM_STATE_LOADOS	        (0x00000008)
#define	        BOOTM_STATE_RAMDISK	        (0x00000010)
#define	        BOOTM_STATE_FDT	        	        (0x00000020)
#define	        BOOTM_STATE_OS_CMDLINE	        (0x00000040)
#define	        BOOTM_STATE_OS_BD_T	        (0x00000080)
#define	        BOOTM_STATE_OS_PREP	        (0x00000100)
#define	        BOOTM_STATE_OS_FAKE_GO	        (0x00000200)	        /* 'Almost' run the OS */
#define	        BOOTM_STATE_OS_GO	        (0x00000400)
	        int	        	        state;

#ifdef CONFIG_LMB
	        struct lmb	        lmb;	        	        /* for memory mgmt */
#endif
} bootm_headers_t;
typedef struct image_info {
	ulong		start, end;		/* blob 开始和结束位置 */
	ulong		image_start, image_len; /* 镜像起始地址(包括 blob)和长度 */
	ulong		load;			/* 系统镜像加载地址 */
	uint8_t		comp, type, os;		/* 镜像压缩、类型, OS 类型 */
	uint8_t		arch;			/* CPU 架构 */
} image_info_t;

do_bootz 函数

bootz 命令的执行函数为 do_bootz:

int do_bootz(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
{
	int ret;

	/* Consume 'bootz' */
	argc--; argv++;

	if (bootz_start(cmdtp, flag, argc, argv, &images))
		return 1;

	/*
	 * We are doing the BOOTM_STATE_LOADOS state ourselves, so must
	 * disable interrupts ourselves
	 */
	bootm_disable_interrupts();//关闭中断

	images.os.os = IH_OS_LINUX; //设置 images.os.os 为 IH_OS_LINUX,也就是设置系统镜像为 Linux
	ret = do_bootm_states(cmdtp, flag, argc, argv,
			      BOOTM_STATE_OS_PREP | BOOTM_STATE_OS_FAKE_GO |
			      BOOTM_STATE_OS_GO,
			      &images, 1);//执行不同的 BOOT 阶段,这里要执行的 BOOT 阶段有: 
			               //BOOTM_STATE_OS_PREP 、BOOTM_STATE_OS_FAKE_GO 和BOOTM_STATE_OS_GO

	return ret;
}

bootz_start 主要用于初始化 im

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

小吴伴学者

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值