用仿真器解决Linux内核加载问题
来源:互联网 发布:basic和vb 编辑:程序博客网 时间:2024/06/11 00:39
快乐虾
http://blog.csdn.net/lights_joy/
欢迎转载,但请保留作者信息
在使用合众达DVS6467T开发板时遇到一个问题,在内核选项中加上initramfs的支持,结果在bootm时内核加载失败:
## Booting image at 8e000000 ...
Image Name: Linux-2.6.10_mvl401-davinci_evm-
Image Type: ARM Linux Kernel Image (uncompressed)
Data Size: 3479208 Bytes = 3.3 MB
Load Address: 80008000
Entry Point: 80008000
Verifying Checksum ... OK
OK
Starting kernel ...
UncompressingLinux..........................................................................................................................................................done, booting the kernel.
然后就没有下文了。
这种情况其实在刚开始调试内核时经常会遇到,通常也只能通过内核功能的添加和删除来初步判断问题的位置。但我们现在有仿真器这个神器,就不再需要这么摸索了。
下面有请仿真器大神上场。
首先启动uboot并将内核tftp到板上。Bootm后出现上文所提的现象。
在ccs下用仿真器连接设备:很显然pc跑飞了,但此时已经无法得到更多信息了。
再来一次。
用uboot将内核tftp下载到设备上,在bootm之前用ccs连接到设备,此时ccs将在uboot的代码中中断下来:
添加两个断点:
因为0x80008000这个地址是Linux内核的入口地址。
在ccs中继续执行,uboot继续工作,我们也可以通过串口和uboot进行交互。
在串口中输入bootm,此时仿真器将在内核入口处中断下来:
通过单步执行,很容易发现程序跑飞的位置:
/*
* The following fragment of code is executedwith the MMU on, and uses
* absolute addresses; this is not positionindependent.
*
* r0 = cp#15 control register
* r1 = machine ID
* r9 = processor ID
*/
.type __mmap_switched, %function
__mmap_switched:
adr r3,__switch_data + 4
ldmia r3!,{r4, r5, r6, r7}
cmp r4,r5 @ Copy data segment if needed
1: cmpne r5,r6
ldrne fp,[r4], #4
strne fp,[r5], #4
bne 1b
mov fp,#0 @ Clear BSS (and zero fp)
1: cmp r6,r7
strcc fp,[r6],#4
bcc 1b
在这里清除BSS段时程序飞了。通过检查各寄存器的值感觉并没有什么异常,但当内核执行到这里时,可以发现mmu已经启用了,那么问题估计和这个有关了。
看看之前执行的MMU相关的一段代码:
/*
* Setup the initial page tables. We only setup the barest
* amount which are required to get the kernelrunning, which
* generally means mapping in the kernel code.
*
* r8 =machinfo
* r9 =cpuid
* r10 = procinfo
*
* Returns:
* r0,r3, r5, r6, r7 corrupted
* r4 =physical page table address
*/
.type __create_page_tables, %function
__create_page_tables:
ldr r5,[r8, #MACHINFO_PHYSRAM] @ physram
pgtbl r4,r5 @ page table address
………..
/*
* Nowsetup the pagetables for our kernel direct
*mapped region. We round TEXTADDR down tothe
*nearest megabyte boundary. It is assumedthat
* thekernel fits within 4 contigous 1MB sections.
*/
add r0,r4, #(TEXTADDR & 0xff000000)>> 18 @ start of kernel
str r3,[r0, #(TEXTADDR & 0x00f00000) >> 18]!
add r3,r3, #1 << 20
str r3,[r0, #4]! @ KERNEL + 1MB
add r3,r3, #1 << 20
str r3,[r0, #4]! @ KERNEL + 2MB
add r3,r3, #1 << 20
str r3,[r0, #4] @ KERNEL + 3MB
……
很显然这里只配置了内核代码开始的3M空间,而我们的内核在加上initramfs之后,bss段的一部分数据是处于3M之外的,这也是正是内核跑飞的原因!!
知道原因就好办了,修改下这段代码:
/*
* Nowsetup the pagetables for our kernel direct
*mapped region.
*/
add r0,r4, #(TEXTADDR & 0xff000000)>> 18
str r3,[r0, #(TEXTADDR & 0x00f00000) >> 18]!
ldr r6,=(TEXTADDR + 0x01000000 - 1)
add r0,r0, #4
add r6,r4, r6, lsr #18
1: cmp r0,r6
add r3,r3, #1 << 20
strls r3,[r0], #4
bls 1b
再编译运行,搞定!!
- 用仿真器解决Linux内核加载问题
- 解决Linux加载失败问题
- linux内核加载的小问题----Linux内核的Oops
- 调整Linux内核解决C500k问题
- linux内核模块加载
- Linux内核加载过程
- Linux内核加载流程
- Linux 内核加载过程
- linux内核加载可执行文件
- Linux内核加载过程
- ftp加载linux内核
- linux 内核驱动加载
- 关于Linux内核可加载模块的版本问题
- linux内核模块编译或加载时找不到符号问题
- 转载一篇解决vmware不支持新内核linux的问题
- linux内核编译之后还是有问题,与解决
- linux 下通过修改内核参数解决大量TIME_WAIT问题
- DSP仿真器的问题
- Win10 Mobile For MI4体验
- SKlear中的LabelEncoding和OneHotEncoding
- git基本命令
- Python11
- 忘记密码解决,Win7 Administrator账号密码忘记 解决办法
- 用仿真器解决Linux内核加载问题
- 黑科技 —— Type-C 接口与 USB3.1
- Linux内核分析 实验1
- Codeforces Round #401 (Div. 2) B. Game of Credit Cards
- 游戏开发中常用的设计模式
- C语言中,整型变量x小于0,是否可知x*2也小于0
- ubuntu开机启动Mongo脚本以及使用root权限执行的脚本(快捷方式)
- 科普:虚拟服务器(VPS)和虚拟主机(空间)的区别
- 阿里巴巴iconfont使用方式