uboot启动后在内存中运行裸机程序hello

摘要:
修改后,重新编译uboot。箱子在DNW Bin下执行dnw50008000 USB下载uboot到内存50008000,转到50008000,运行我刚从内存50008000下载的程序,发现我修改的内容没有显示。重新执行dnw50008000、nandesase0100000、nandwrite。uboot50008000010000,然后直接从nand开始。发现我的修改已经打印出来了。

如题,实现过程中发现3额问题,先写下来,待解答:

1、uboot启动后再dnw上打印许多信息,我想改变其中的打印信息或加上自己的打印信息以证明程序运行到何处。修改完后重新编译uboot.bin。

在DNW下执行dnw 50008000 USB下载uboot.bin到内存50008000处, go 50008000,从内存50008000处运行我刚下载的程序,发现我修改的内容并未显示。

重新执行dnw 50008000,nand erase 0 100000,nand write.uboot 50008000 0 100000,后从nand直接启动,发现我修改的内容被打印出来了。

总结:可能的原因:1、程序下载到50008000,但50008000处并非有执行命令。2、确实从50008000处执行了,但uboot.bin里的start.s会调用原来nand里的uboot.bin执行

2、uboot里有个examples文件夹里有hello_world应用程序(姑且这么说吧):

我dnw 50008000 hello_world.bin,go 50008000,执行后重启了。

看了makefile里LOAD_ADDR = 0xc100000,dnw c10000 hello_world.bin,go c1008000,执行后停住了

然后又看了半天makefile,太繁琐,无果,没解决掉。

3、自己写了个hello.c

dnw 50008000 ,go 50008000,运行ok,打印出hello world.

参考并引用:http://blog.csdn.net/liushaowei2008/article/details/7739046

printf函数是 uboot 实现的,我们只需要调用就行了。当然了,这个首先得到你u boot 的printf函数地址。这需要你自己 编译 uboot,因为每个人
的printf函数地址不一定一样。查看System.map 文件 ,找到printf地址。就行了。
调用时我们可以这样用:

  1. void (*show)(char*,...) = 0xc7e11650;
  2. ........
  3. show("hello world/n");
  4. .......

现在我们来个hello world 的例子:
贴一下代码:

  1. void (*show)(char *,...) = 0xc7e11650;
  2. int main(void)
  3. {
  4.     show("hello world./n");
  5.     return 0;
  6. }

(hello.c)
就这么简单。(一个hello world 能多复杂啊?嘎嘎~)
下面我们来说一下编译和连接:
你也会用:arm-linux-gcc hello.c
但是这是不对的,为什么呢? 我们来仔细想一个问题,我们是裸机(好吧,我承认稍微穿了一点),没有操作系统 。想想arm 执行时,它希望
执行的第一条指令是什么?肯定是一条有效的指令了。但是我们生成的这个a.out的前面是有效的可执行的语句么?也许你已经想到了,它的头不是什么
有效指令,是ELF头信息,还有你的用户 名呢,用户名不能执行吧?呵呵,开玩笑。

还有一个问题。
gcc默认的连接地址是你想要的么?八成不是吧。
鉴于以上原因我们要分步进行:
1:编译
arm-linux-gcc -c hello.c -o hello.o
生成hello.o文件。
2:链接 指定我们要的链接地址0x50000000
arm-linux-ld -Ttext=0x50000000 hello.o -o hello
这时你用arm-linux-objdump -d hello 反汇编一下,看看指令的起始地址是50000000吧?
3:去除头ELF头信息
arm-linux-objcopy -L elf32-littlearm -O binary hello hello.bin
这里elf32-littlearm 是指定大小端,咱小端的。
就这样,我们可以在裸板上运行 的二进制程序 就这样成了。为了以后方便可以把上面的指令写在Makefile里,一个make就all了。


总结:就是函数的入口地址搞不清楚,不是在50008000,故失败,先放这里,这个不着急,等有时间再来仔细研究研究。

免责声明:文章转载自《uboot启动后在内存中运行裸机程序hello》仅用于学习参考。如对内容有疑问,请及时联系本站处理。

上篇关于求模和求余Django 查询语句汇总下篇

宿迁高防,2C2G15M,22元/月;香港BGP,2C5G5M,25元/月 雨云优惠码:MjYwNzM=

相关文章

基于335X的UBOOT网口驱动分析

基于335X的UBOOT网口驱动分析     一、软硬件平台资料 1、  开发板:创龙AM3359核心板,网口采用RMII形式 2、  UBOOT版本:U-Boot-2016.05,采用FDT和DM。 参考链接: https://blog.csdn.net/hahachenchen789/article/details/53339181   二、网口相关代...

centos8+oracle19开机自启动

centos8+oracle19开机自启动 一、将oratab最后一项调整"Y"cat /etc/orataborclpdb:/home/app/oracle/product/19.2.0/db_1:Y 二、建立oracle.sh执行文件cat /usr/bin/oracle.sh#!/bin/bash # script For oracle19c.se...

Java:程序开机自启动

一、加到开机自动启动程序的注册表: package com.zit; import java.io.IOException; public classStart { public static voidChangeStart(boolean isStartAtLogon) throws IOException{ String...

x-pack本地安装方式

一.首先下载本地安装包,我使用的ELK是5.6.1版本: https://artifacts.elastic.co/downloads 二.进入到elasticsearch/bin(所有节点)和kibana/bin安装x-pack:(都是非root) bin/elasticsearch-plugin install file:///绝对路径/x-pack....

修改CENTOS 环境变量

1. 之前发现PATH变量里有一部分路径有冗余,于是想恢复PATH,首先命令行下先执行以下命令 #PATH=/usr/lib64/qt-3.3/bin:/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin:/root/bin 2. 重新source /etc/profile #set Ha...

shell网络管理

背景知识  联网就是通过网络将主机进行互联并采用不同的规范配置网络上的节点。我们以 TCP/IP 作为网络栈,所有的操作都是基于它进行的。网络是计算机系统中重要的部分。连接在网络上的每个节点都分配了一个用作标识作用的独一的 IP 地址。有很多联网参数,如子网掩码、路由、端口和 DNS 等,我们需要对这些知识有一个基本的理解。   Internet 依靠 T...