uboot实验0

来源:互联网 发布:sql创建存储过程语法 编辑:程序博客网 时间:2024/05/18 02:36
shell命令:$?查看上一个命令执行结果,0是正常,非0是出错。
           #!/bin/sh -e 这个-e选项,前面命令$?的值为非0 就退出该脚本文件。
           
uboot设置两个命令:set bootcmd nand read.jffs2 0x30007FC0 kernel\;bootm 0x30007FC0
要用\;分开

问题1:root=/dev/mtdblock2与root=/dev/mtdblock3(韦东山uboot)区别?

问题2: 内核为什么存放在这里0x30008000
mkimage使用方法:
http://www.360doc.com/content/10/1227/10/496343_81668858.shtml

第一课:
pc启动,BIOS-引导操作系统--识别c、d盘--运行应用程序qq
BIOS--从硬盘上读入内核

嵌入式系统:
bootloader -- linux内核--挂接根文件系统--应用程序

bootloader目的:启动内核、
              需要:从flash读出内核,放到sdram
    uboot(是bootloader的一种)实现的功能:
            硬件相关的初始化-①关看门狗,初始化sdram,初始化时钟(开始时钟时12MHz,2440最大是400MHz)。为了开发方便增加“初始化串口,写flash功能、网卡、usb”
            ②设置栈。从flash读到sdram中。
            ③启动内核


制作补丁文件:diff

解压缩:tar xjf xxx.tar.bz2

打补丁:patch -pn(忽略n个目录,从左往右数):patch -p1 < ../u-boot-1.1.6_jz2440.patch


配置:使程序支持特殊的单板 make 100ask24x0_config :Configuring for 100ask24x0 board...
    分析Makefile:
        读uboot中的readme文件,有详细说明
    分析配置过程:make 100ask24x0_config
        SRCTREE        := $(CURDIR)
        MKCONFIG    := $(SRCTREE)/mkconfig
        
        @$(MKCONFIG) $(@:_config=) arm arm920t 100ask24x0 NULL s3c24x0
            第一个“@”在Makefile一般用来解析shell命令,如@if [ ! -d $(CPU) ]; then mkdir $(CPU); fi后面跟的是shell的判断语句。
        =>mkconfig 100ask24x0 arm arm920t 100ask24x0 NULL s3c24x0
                mkconfig是一个脚本文件,分析这个脚本文件。
                
                
                
        $(@:_config=)详解:替换引用规则。将$@目标中的_config替换为_config=“空格”。
        http://blog.sina.com.cn/s/blog_89fa41ef0100t6bj.html
        uboot编译过程分析:
        http://blog.csdn.net/wu407797466/article/details/7844348
        uboot顶层config.mk分析:
        http://zqwt.012.blog.163.com/blog/static/12044684201031174754807/
        
编译:make时,要是不指定目标就是想生成第一个目标
            make clean 不完全清除
            make distclean完全清除
顶层makefile中:
OBJS  = cpu/arm920t/start.o


LIBS  = lib_generic/libgeneric.a
LIBS += board/100ask24x0/lib100ask24x0.a
LIBS += cpu/arm920t/libarm920t.a
LIBS分析:把xxx目录下的文件编译好之后,打包生成xxx.a的一个静态库


$(obj)u-boot:        depend version $(SUBDIRS) $(OBJS) $(LIBS) $(LDSCRIPT)
        UNDEF_SYM=`$(OBJDUMP) -x $(LIBS) |sed  -n -e 's/.*\(__u_boot_cmd_.*\)/-u\1/p'|sort|uniq`;\
        cd $(LNDIR) && $(LD) $(LDFLAGS) $$UNDEF_SYM $(__OBJS) \
            --start-group $(__LIBS) --end-group $(PLATFORM_LIBS) \
            -Map u-boot.map -o u-boot

编译打印出的信息:
UNDEF_SYM=`arm-linux-objdump -x lib_generic/libgeneric.a board/100ask24x0/lib100ask24x0.a
                 cpu/arm920t/libarm920t.a cpu/arm920t/s3c24x0/libs3c24x0.a
                 lib_arm/libarm.a fs/cramfs/libcramfs.a fs/fat/libfat.a fs/fdos/libfdos.a
                 fs/jffs2/libjffs2.a fs/reiserfs/libreiserfs.a fs/ext2/libext2fs.a net/libnet.a
                 disk/libdisk.a rtc/librtc.a dtt/libdtt.a drivers/libdrivers.a
                 drivers/nand/libnand.a drivers/nand_legacy/libnand_legacy.a
                 drivers/usb/libusb.a drivers/sk98lin/libsk98lin.a
                 common/libcommon.a |sed  -n -e 's/.*\(__u_boot_cmd_.*\)/-u\1/p'|sort|uniq`;\
             进入这个目录:
        cd /work/system/u-boot-1.1.6 &&
              连接:如何组织这些xxx.a文件,查看board/100ask24x0/u-boot.lds的链接脚本
         arm-linux-ld -Bstatic -T /work/system/u-boot-1.1.6/board/100ask24x0/u-boot.lds -Ttext 0x33F80000  $UNDEF_SYM cpu/arm920t/start.o \
            --start-group lib_generic/libgeneric.a board/100ask24x0/lib100ask24x0.a
            cpu/arm920t/libarm920t.a cpu/arm920t/s3c24x0/libs3c24x0.a lib_arm/libarm.a
            fs/cramfs/libcramfs.a fs/fat/libfat.a fs/fdos/libfdos.a fs/jffs2/libjffs2.a
            fs/reiserfs/libreiserfs.a fs/ext2/libext2fs.a net/libnet.a
            disk/libdisk.a rtc/librtc.a dtt/libdtt.a drivers/libdrivers.a
            drivers/nand/libnand.a drivers/nand_legacy/libnand_legacy.a drivers/usb/libusb.a
            drivers/sk98lin/libsk98lin.a common/libcommon.a
            --end-group -L /work/gcc-3.4.5-glibc-2.3.6/bin/../lib/gcc/arm-linux/3.4.5 -lgcc \
            -Map u-boot.map -o u-boot
可知:分析uboot的第一个文件是/cpu/arm920t/start.S
      链接脚本:board/100ask24x0/u-boot.lds--知道代码的组织顺序
                 +0x33f80000
                 uboot存放的地址,它的值可以修改。在/board/100ask24x0/config.mk中定义了这个值

烧写
天嵌提供的uboot(通过jlink烧写在nor flash),通过tftp下载新的uboot到nand flash:
新的uboot放在E:\Program Files\TftpdWin目录


uboot命令:
    按 ?或 help查看uboot所有命令
    print查看uboot的环境变量
    设置环境变量:set xxx xxx
    save:保存
    reset:重启
    
回到菜单:menu
退出菜单:q 。进入uboot命令界面。


uboot源码分析:
分析第一个文件:cpu/arm920t/start.S
硬件相关的初始化,uboot的第一阶段,从cpu/arm920t/start.S文件开始:
            a设置管理模式
            b关看门狗
            c屏蔽中断
            d初始化sdram
            e设置栈
            f时钟
            g重定位--代码从flash考到sdram中
            h清bss段
            i调用start_armboot--c函数
用c语言实现的一些复杂代码,第二阶段:
            uboot的最终目标:启动内核。
                                             要做:①从flash上读出内核。②启动内核。
            uboot的内存使用情况:完全手册上的:275页
            从Board.c (lib_arm)    中的start_armboot函数开始:
            
                gd->bd->bi_arch_number = MACH_TYPE_S3C2440;
            /* adress of boot parameters */
            gd->bd->bi_boot_params = 0x30000100;
            CFI是一个公开的标准的从Flash Memory器件中读取数据的接口,Common Flash Interface。
            
            flash_init函数实现对nor flash的初始化,nor
            
            uboot是单片机程序,需自己实现分配、释放动态内存的功能:mem_malloc_init
            
            nand_init函数实现对nand flash的初始化。
            
            env_relocate函数,环境变量的初始化,在uboot下输入print出现一大推环境变量。
                                      来源:①在代码中写死,默认的;②可修改的,存放在flash中
                                      uboot启动后先查看flash上有没有环境变量,若没有,才使用默认的环境变量。
            for (;;) {
                main_loop ();
            }
            main_loop-->             Main.c (common)    31364
                s = getenv ("bootcmd"); uboot print打印:从flash上读出内核:nand read.jffs 0x30007fc0 kernel
                             启动命令                    启动内核:         bootm 0x30007fc0
                 run_command (s, 0);
            
            uboot控制界面:
                readline(读入串口的数据)函数
                run_command("menu", 0);
                
            uboot的核心就是:命令。 run_command函数
            
            分析了命令才知道内核的启动流程,启动方式。
uboot命令: ① 输入字符串(命令)根据命令的name找到
                                                   |
                        ② 动作--某些函数        <-
    命令的结构体:
     {
         name=
         functure=
     }
            
bootm命令分析:

bootm 0x30007FC0

U_BOOT_CMD(
     bootm,    CFG_MAXARGS,    1,    do_bootm,
     "bootm   - boot application image from memory\n",
     "[addr [arg ...]]\n    - boot application image stored in memory\n"
     "\tpassing arguments 'arg ...'; when booting a Linux kernel,\n"
     "\t'arg' can be the address of an initrd image\n"
#ifdef CONFIG_OF_FLAT_TREE
    "\tWhen booting a Linux kernel which requires a flat device-tree\n"
    "\ta third argument is required which is the address of the of the\n"
    "\tdevice-tree blob. To boot that kernel without an initrd image,\n"
    "\tuse a '-' for the second argument. If you do not pass a third\n"
    "\ta bd_info struct will be passed instead\n"
#endif
);

#define Struct_Section  __attribute__ ((unused,section (".u_boot_cmd")))

#define U_BOOT_CMD(name,maxargs,rep,cmd,usage,help) \
cmd_tbl_t __u_boot_cmd_##name Struct_Section = {#name, maxargs, rep, cmd, usage, help}

分区概念:
    对于pc硬盘分区后,就存在一个分区表。在其他电脑中可以识别这个分区表。
    对于嵌入式系统来说,flash上没有分区表。那么这个flash如何分,就已经在源码中写死了。
                        100ask24x0.h (include\configs)在这个文件中。


nand read.jffs2 0x30007FC0 kernel
       jffs2本来是一种文件格式,在这里和文件格式没有关系,用这个命令read.jffs2后不需要也对齐,方便使用。
从nand读出内核:从哪里读--kernel分区 kernel 0x00200000 0x00060000
                              到哪里去--0x30007FC0地址
在uboot输入mtd命令:kernel  0x00200000(大小)      0x00060000(地址)
bootm 0x30007FC0
做了:①根据头部移动内核到合适的地方。uboot与内核交流通过参数,会把参数存放在某个地址,内核可以读取这个地址上的数据。这个地址是30000100
            ②启动do_bootm_linux
uImage = 头部信息+真正的内核
         image_header_t结构体Image.h中
         {
             ih_load;加载地址
                    ih_ep;    入口地址
         }

uboot参数分析:
    setup_start_tag (bd);
        100ask24x0.c (board\100ask24x0):    gd->bd->bi_boot_params = 0x30000100;
                                                                                Global_data.h (include\asm-arm)
                                                                                typedef    struct    global_data {
                                                                                            bd_t        *bd;
                                                                                            unsigned long    flags;
                                                                                            unsigned long    baudrate;
                                                                                            unsigned long    have_console;    /* serial_init() was called */
                                                                                            unsigned long    reloc_off;    /* Relocation Offset */
                                                                                            unsigned long    env_addr;    /* Address  of Environment struct */
                                                                                            unsigned long    env_valid;    /* Checksum of Environment valid? */
                                                                                            unsigned long    fb_base;    /* base address of frame buffer */
                                                                                          ...
                                                                                        } gd_t;
                                            #define DECLARE_GLOBAL_DATA_PTR     register volatile gd_t *gd asm ("r8")
                                        
        params = (struct tag *) bd->bi_boot_params;
    
    setup_memory_tags (bd);
    setup_commandline_tag (bd, commandline);
    setup_end_tag (bd);



lowlevel_init:初始化存储控制器,让内存可以使用。lowlevel_init.S (board\100ask24x0)    5129

stack_setup:设置栈,栈设置好后才可调用c函数。
clock_init:初始化时钟。2440可产生: FCLK for CPU;HCLK: Advanced High-performance Bus(AHB)主要用于高性能模块(如CPU、DMA和DSP等)之间的连接。 PCLK for the APB bus peripheral,用于I2C,SPI等低速总线。
            S3C2440A_UserManual_Rev13的238页,有关于时钟的框图。






附件:
uboot命令:
autoscr - run script from memory
base    - print or set address offset
bdinfo  - print Board Info structure
boot    - boot default, i.e., run 'bootcmd'
bootd   - boot default, i.e., run 'bootcmd'
bootelf - Boot from an ELF image in memory
bootm   - boot application image from memory
bootp   - boot image via network using BootP/TFTP protocol
bootvx  - Boot vxWorks from an ELF image
chpart  - change active partition
cmp     - memory compare
coninfo - print console devices and information
cp      - memory copy
crc32   - checksum calculation
date    - get/set/reset date & time
dcache  - enable or disable data cache
echo    - echo args to console
erase   - erase FLASH memory
flinfo  - print FLASH memory information
fsinfo  - print information about filesystems
fsload  - load binary file from a filesystem image
go      - start application at address 'addr'
help    - print online help
icache  - enable or disable instruction cache
iminfo  - print header information for application image
imls    - list all images found in flash
itest   - return true/false on integer compare
loadb   - load binary file over serial line (kermit mode)
loads   - load S-Record file over serial line
loadx   - load binary file over serial line (xmodem mode)
loady   - load binary file over serial line (ymodem mode)
loop    - infinite loop on address range
ls      - list files in a directory (default /)
md      - memory display
menu - display a menu, to select the items to do something
mm      - memory modify (auto-incrementing)
mtdparts- define flash/nand partitions
mtest   - simple RAM test
mw      - memory write (fill)
nand    - NAND sub-system
nboot   - boot from NAND device
nfs     - boot image via network using NFS protocol
nm      - memory modify (constant address)
ping    - send ICMP ECHO_REQUEST to network host
printenv- print environment variables
protect - enable or disable FLASH write protection
rarpboot- boot image via network using RARP/TFTP protocol
reset   - Perform RESET of the CPU
run     - run commands in an environment variable
saveenv - save environment variables to persistent storage
setenv  - set environment variables
sleep   - delay execution for some time
tftpboot- boot image via network using TFTP protocol
usbslave - get file from host(PC)
version - print monitor version
0 0
原创粉丝点击