mkimage那些事

在编译linux内核时,往往会涉及到以下3个命令:
• make Image
• make zImage
• make uImage
那么,这3个命令分别是做什么的?所生成的对象又有什么区别呢?

Image为普通的内核映像文件,而zImage为压缩过的内核映像文件(其中的z字母就是压缩的意思)。一般情况下,编译出来的Image大约为4M,而zImage不到2M。uImage它是uboot专用的映像文件,它是在zImage之前加上一个长度为64字节的“头”,说明这个内核的版本、加载位置、生成时间、大小等信息;其0x40之后与zImage没区别。换句话说,如果直接从uImage的0x40位置开始执行,那么zImage和uImage没有任何区别。

为什么要用uboot 的mkimage工具处理内核映像zImage呢?
因为uboot在用bootm命令引导内核的时候,bootm需要读取一个64字节的文件头,来获取这个内核映象所针对的CPU体系结构、OS、加载到内存中的位置、在内存中入口点的位置以及映象名等等信息。这样bootm才能为OS设置好启动环境,并跳入内核映象的入口点。而mkimage就是添加这个文件头的专用工具。具体的实现请看uboot中bootm的源码和mkimage的源码。
那究竟要如何生成uImage呢?这就要从uboot处来想办法了。
uboot源代码make完成后,tools/目录下会生成一个mkimage工具,这个工具可以用来制作不压缩或者压缩的多种可启动映象文件。可以将mkimage这个工具拷贝到usr/bin等用户目录下,这样直接在命令行输入这个命令就可以运行,而无需每次都手工指定到uboot/tools这个目录下去,提高执行效率。当然,直接在ubuntu系统中安装一下uboot的mkimage命令,效果更好。
#sudo apt-get install uboot-mkimage

下面介绍下mkimage这个工具的用法:
-A:指定 CPU 的体系结构,对于ZYNQ,值为arm

-O:指定操作系统类型,对于ZYNQ,取值为linux。
可以取以下值:
openbsd、netbsd、freebsd、4_4bsd、linux、svr4、esix、solaris、irix、sco、dell、ncr、lynxos、vxworks、psos、qnx、u-boot、rtems、artos

-T:指定映象类型,对于ZYNQ,常取值kernel , ramdisk。
可以取以下值:
standalone、kernel、ramdisk、multi、firmware、script、filesystem

-C:指定映象压缩方式,可用值有:
:none 不压缩(一般使用这个,因为 zImage 是已经被 bzip2 压缩过的自解压内核);
:gzip 用 gzip 的压缩方式;
:bzip2 用 bzip2 的压缩方式;

-a:指定image的load addr

-e:指定image的entry point
根据情况不同,
entry point = load addr +0x40
或者
entry point = load addr

-n:image在头结构中的命名

-d:指定制作映象的datafile源文件;

(-x ==> set XIP (execute in place) ,一般不常用。)

举例:
生成uImage的方法: 利用mkimage 命令 把zImage 包装 ,
mkimage -A arm -O linux -T kernel -C none -a 00008000 -e 00008000 -n linux-kernel -d ./zImage ./uImage

调整一下上面的 -a -e -x 参数什么的, 你会发现 这些参数不同, 就会导致你 tftp dowload或者fatload的地址会有不同, 有的时候kernel会run不起来。
关于压缩及非压缩内核bootm启动的全面总结:
能够启动内核的以下几种情况:
(1)非压缩的Image内核:
-a=-e = 00008000 ,–c=none,fatload_addr= 0x00f00000
(2)非压缩的Image内核:
-a= 00008000 ,-e = 00008040,–c=none,fatload_addr=0x00008000
(3)非压缩的Image内核:
-a=-e = 00008000 ,–c=gzip,fatload_addr= 0x01000000
(4)压缩的zImage内核:
-a=-e = 00008000 ,–c=none,fatload_addr= 0x01000000
(5)压缩的zImage内核:
-a= 00008000 ,-e = 00008040,–c=none,fatload_addr=0x00008000
(6)压缩的zImage内核:
-a=-e = 00008000 ,–c=gzip,fatload_addr= 0x01000000

生成uramdisk.image.gz的方法:
mkimage -A arm -O linux -T kernel -C gzip -n linux-ramdisk -d ./zramdisk.image.gz ./uramdisk.image.gz

以上命令,将gzip_image格式的镜像封装成了UIMAGE格式。加了0x40字节的U_HEADER。

补充说明:
#gunzip ramdisk.image.gz
这个命令将ramdisk.image.gz先解压到当前文件夹下面,得到一个ramdisk.image文件。这是一个RAWFS格式的镜像。
#chmod u+rwx ramdisk.image
为了确保能够操作,给它加上权限。
#sudo mount -o loop ramdisk.image /mnt/tmp_mnt/
把这个RAWFS文件mount到/mnt/tmp_mnt/目录下。
。。。。
然后一顿复制删除等等

#sudo umount /mnt/tmp_mnt/
把目录/mnt/tmp_mnt/卸载掉。umount就是干这个活。

#gzip -v9 ramdisk.image
把RAWFS文件ramdisk.image打包压缩,在当前目录下,生成ramdisk.image.gz。这是一个gzip_image格式的镜像文件。

#mkimage -A arm -O linux -T ramdisk -C gzip -d ./ramdisk.image.gz ./uramdisk.image.gz
把ramdisk.image.gz制作成uramdisk.image.gz。

另外,
如果手上有一个uramdisk.image.gz,希望得到原始的ramdisk.image.gz。
#sudo dd if=./uramdisk.image.gz of=./ramdisk.image.gz skip=16 bs=4
利用dd命令截掉前面的0x40个字节,就得到了。

  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值