参考博文“OK6410启动分析”可知S3C6410在nand flash启动时硬件会自动将NANDflash中前8K的程序完整复制到S3C6410片内内存中(OK6410的nand flash一页是4K),但是这前8K并不是连续的2页内容,6410为了兼容2K页的nand flash启动时自动拷贝nand flash前4页的内容到片内内存执行,而且拷贝时只拷每页中的前2KByte,面对这样的拷贝方式,如果我们的裸机代码小于2k则可以正常运行,但是如果编译出来的.bin文件大于2K就要注意了,不能直接把逻辑代码直接一股脑写到nand flash当中,在我们前面的裸机实验当中编译出来的逻辑代码都小于2K,上电启动后可以直接在片内RAM中运行。
像自己写的bootloader源码初始化硬件后直接把内核拷贝到SDRAM中,不像2440自己写的bootloader那样想拷贝自己到SDRAM中,跳过去运行以后再初始化内核参数拷贝内核到SDRAM中再启动内核,编译出来.bin文件很小。但是当逻辑程序大于2K怎么办?解决办法如下:
1、只烧写前4页的前2K,前4页的后2K不用,处理方法有两种:
①用烧写命令多次烧写,比如示例如下:
参考博文“百问网6410第1期Nand flash的问题”,编译得到uart.bin文件(8.83 KB )后,从SD卡启动,利用SD卡上的u-boot,将uart.bin 文件写入nand flash中,操作步骤如下:
a. dnw 50008000 //将uart.bin发送到内存地址50008000处
b. nand erase 0 100000 //擦除nand flash 0地址开始的1M空间
c. nand write 50008000 0 1000 //将uart.bin 偏移为0开始的4k写入第1页nand flash
d. nand write 50008800 1000 1000 //将uart.bin 偏移为2k开始的4k写入第2页nand flash
e. nand write 50009000 2000 1000 //将uart.bin 偏移为4k开始的4k写入第3页nand flash
f. nand write 50009800 3000 1000 //将uart.bin 偏移为6k开始的4k写入第4页nand flash
g. nand write 5000A000 4000 FE000
//将uart.bin 偏移为8k开始的剩余(1M - 8k)内容写入nand flash 第5页开始之后的空间
这样nand flash前4页的每页前2k便保存了uart.bin文件的前8k内容。
②用"mlc_boot_tool"工具处理一下BIN文件:
以"Ok6410_mlc_demo"目录下的"16th_nand_all"为例子
a. cd Ok6410_mlc_demo
b. make clean
c. make // 得到 uart.bin ,发现他大于2K,所以需要处理
d. ./mlc_boot_tool uart.bin wy.bin // 重新生成的 wy.bin 就这最用下载到开发板上面的bin文件
注意:
为什么需要"mlc_boot_tool"工具呢?请结合源码和6410的启动流程自行分析。
a、S3C6410 nand启动,会自动拷贝前8K数据到SRAM中,但是我们的MLC nand每页大小为4K的,而6410的CPU硬件决定了在它自动拷贝的时候每页只能拷贝2K。即NAND启动时,nand的前4页中,每页中的前2K数据才是有用的。
b、所以我们的工具就是把bin文件前面连续的8K数据拆出来放到MLC NAND的前4页里去。即:BIN文件中的第1个2K数据放在NAND的第1页,第2个2K数据放在第2页,第3个2K数据放在第3页,第4个2K数据放在第4页。 因为MLC NAND页大小为4K,所以前面4页只有一半的空间被用到了。从第5页开始,每页的4K空间都被用到了。
c、mlc_boot_tool工具就是把bin文件做成:(2k有用数据+2k无用数据) x 4 + 剩余数据
2、代码重定位的时候自动判断,前4页中只拷贝2K,其他页正常拷贝:
参考博文“百问网6410第1期Nand flash的问题”修改nand_read函数,如果是前4页,则只读取每页的前2k内容;如果是前4页之后,则读取每页的全部内容。
3、按照博文“烧写OK6410裸板方法汇总”来烧写nand flash即可。
====================================================================
番外篇:
1、6410 NAND问题
答:对于OK6410,需要处理一下BIN文件。我们发布的源码里有这一段话:
(2).处理bin文件
以"Ok6410_mlc_demo"目录下的"16th_nand_all"为例子
a. cd Ok6410_mlc_demo
b. make clean
c. make // 得到 uart.bin ,发现他大于2K,所以需要处理
d. ./mlc_boot_tool uart.bin wy.bin // 重新生成的 wy.bin 就这最用下载到开发板上面的bin文件
注意:
为什么需要"mlc_boot_tool"工具呢?请结合源码和6410的启动流程自行分析。
①. S3C6410 nand启动,会自动拷贝前8K数据到SRAM中,但是我们的MLC nand每页大小为4K的,而6410的
CPU硬件决定了在它自动拷贝的时候每页只能拷贝2K。即NAND启动时,nand的前4页中,每页中的前2K数
据才是有用的。
②. 所以我们的工具就是把bin文件前面连续的8K数据拆出来放到MLC NAND的前4页里去。即:BIN文件中的第
1个2K数据放在NAND的第1页,第2个2K数据放在第2页,第3个2K数据放在第3页,第4个2K数据放在第4
页。因为MLC NAND页大小为4K,所以前面4页只有一半的空间被用到了。从第5页开始,每页的4K空间都被
用到了。
③. mlc_boot_tool工具就是把bin文件做成:(2k有用数据+2k无用数据) x 4 + 剩余数据
2、我这最近在玩GSM模块,需要用到uart; 我发现在终端中,开发板自己本身用的是s3c2410_serial0, 我想知道是如何来确定引脚引脚与设备文件的关系?在/dev下,还有很多tty设备文件,这些是具体怎么关联到引脚上的?
答:/dev/tty1,2...等都是虚拟的设备,不用管它。
你只需要管/dev/s3c2410_serial0,1,2;在驱动程序里,它会操作的UART的对应寄存器,设置对应的引脚
3、 dm9k问题这里dm9000的操作有个地方不大明白?
static void dm9000_reset(board_info_t * db)
{
// RESET device
writeb(DM9000_NCR, db->io_addr);
udelay(200);
writeb(NCR_RST, db->io_data);
udelay(200);
}
reset操作就是往下面寄存器写NCR_RST,可是上面函数中db->io_addr代表S3C2410_CS4
而db->io_data代表S3C2410_CS4 + 4,可是这两个东西到底代表什么呢?寄存器?
答:对于DM9000,要把数据B写入地址A,是这样操作的:
先把A作为数值发给io_addr;再把B作为数值发给io_data。io_addr和io_data的差别在于地址线BIT2,对应DM9000的CMD引脚。
『本文转载自网络,版权归原作者所有,如有侵权请联系删除』