博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
bootm命令移植
阅读量:4285 次
发布时间:2019-05-27

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

bootloader的作用有两个,一是初始化软硬件,二是启动操作系统。bootm命令是从内存中运行某一程序,通常用该命令来启动操作系统。比如通过tftp下载内核到内存0x31000000处,可通过执行指令bootm 31000000启动内核。

ps:内核文件有两个:zImage和uImage,zImage是纯粹的内核程序,uImage则在zImage的基础上添加了信息头,一般来说bootm命令使用的是uImage。

bootm命令所完成的工作如下:

这里写图片描述

为了简单,这里省去了检查信息头这步骤,因此可采用zImage。

源文件为:

#include "atag.h"#include "string.h"#define SDRAM_KERNEL_START 0x31000000#define SDRAM_TAGS_START   0x30000100#define SDRAM_ADDR_START   0x30000000#define SDRAM_TOTAL_SIZE   0x04000000void (*theKernel)(int , int , unsigned int );/*定义了一个函数指针*/struct tag *pCurTag;const char *cmdline = "console=ttySAC0,115200 init=/init";/*这是Linux内核需要的命令行*/void setup_core_tag(){     pCurTag = (struct tag *)SDRAM_TAGS_START;     pCurTag->hdr.tag = ATAG_CORE;     pCurTag->hdr.size = tag_size(tag_core);      pCurTag->u.core.flags = 0;     pCurTag->u.core.pagesize = 4096;     pCurTag->u.core.rootdev = 0;     pCurTag = tag_next(pCurTag);}void setup_mem_tag(){     pCurTag->hdr.tag = ATAG_MEM;     pCurTag->hdr.size = tag_size(tag_mem32);      pCurTag->u.mem.start = SDRAM_ADDR_START;     pCurTag->u.mem.size = SDRAM_TOTAL_SIZE;     pCurTag = tag_next(pCurTag);}void setup_cmdline_tag(){     int linelen = strlen(cmdline);     pCurTag->hdr.tag = ATAG_CMDLINE;     pCurTag->hdr.size = (sizeof(struct tag_header)+linelen+1+4)>>2;     strcpy(pCurTag->u.cmdline.cmdline,cmdline);     pCurTag = tag_next(pCurTag);}void setup_end_tag(){    pCurTag->hdr.tag = ATAG_NONE;    pCurTag->hdr.size = 0;}void boot_linux(){    //1. 获取Linux启动地址    theKernel = (void (*)(int , int , unsigned int ))SDRAM_KERNEL_START;     /*将SDRAM_KERNEL_START强制转换为(void (*)(int , int , unsigned int ))类型指针,然后对函数指针进行赋值*/    //2. 设置启动参数    //2.1 设置核心启动参数    setup_core_tag();    //2.2 设置内存参数    setup_mem_tag();    //2.3 设置命令行参数    setup_cmdline_tag();    //2.4 设置参数结束标志    setup_end_tag();    //3. 启动Linux系统    theKernel(0,168,SDRAM_TAGS_START);/*调用函数,这是函数指针的用法*/    /*内核接受三个参数,第一个为0,第二个为处理器编号,第三个为启动参数的地址*/}

头文件为:

#define ATAG_CORE   0x54410001#define ATAG_MEM    0x54410002#define ATAG_CMDLINE    0x54410009#define ATAG_NONE   0x00000000struct tag_header {    unsigned int size;    unsigned int tag;};struct tag_core {    unsigned int flags;         unsigned int pagesize;    unsigned int rootdev;};struct tag_mem32 {    unsigned int    size;    unsigned int    start;  };struct tag_cmdline {    char    cmdline[1]; };struct tag {    struct tag_header hdr;    union {        struct tag_core     core;        struct tag_mem32    mem;        struct tag_cmdline  cmdline;    } u;};#define tag_size(type)  ((sizeof(struct tag_header) + sizeof(struct type)) >> 2)#define tag_next(t) ((struct tag *)((unsigned int *)(t) + (t)->hdr.size))

ps:启动Linux内核时,若内核启动一部分后停止,则问题很可能是写错了处理器编号。代码theKernel(0,168,SDRAM_TAGS_START)中的168为处理器S3C2440的编号。启动程序中的处理器编号会作为参数传递给内核,而内核中也存在着一个处理器编号序列,两者必须一样才能正常启动内核。

你可能感兴趣的文章
StanFord ML 笔记 第三部分
查看>>
《图像处理实例》 之 局部极值提取
查看>>
硬盘读取不了-->>完美解决
查看>>
《图像处理实例》 之 拓扑重建
查看>>
《图像处理实例》 之 寻找图纸标注
查看>>
《图像处理实例》 之 拟合求交点
查看>>
《图像处理实例》 之 填充封闭区域
查看>>
《图像处理实例》 之 疏密程度统计
查看>>
支持向量机(理论+opencv实现)
查看>>
K-means算法(理论+opencv实现)
查看>>
高斯混合模型(理论+opencv实现)
查看>>
VS2015+Python3.5的配置
查看>>
分水岭算法(理论+opencv实现)
查看>>
《图像处理实例》 之 精确寻找一个圆
查看>>
opencv3.1+contrib的配置大总结(配置了两天,遇到问题无数)
查看>>
opencv小问题大智慧
查看>>
《图像处理实例》 之 车牌定位
查看>>
《opencv学习》 之 OTSU算法实现二值化
查看>>
《图像处理实例》 之 答题卡检测
查看>>
图像矩的初步探索(第十一天)
查看>>