I.MX裸机点灯过程

        刚开始学习I.MX6Ull的裸机开发,这里来记录一下今天的学习,本文章适合想要开始学习Linux驱动开发的朋友,内容简单,利用的是正点原子的视频与开发板,只是讲了开发步骤,对细节感兴趣的也可以去看看正点原子的视频。

一、ARM汇编基础

        与STM32单片机不同,stm32开发板的启动文件中已经将SP指针初始化、DDR初始化。正点原子的Linux开发板并没有初始化这些,所以C语言环境还没准备好,不能直接运行C语言代码,我们利用汇编语言将C语言环境搭建好后就可以执行C语言代码了。这里刚开始只介绍了两个常用并且十分重要的指令,LDR、STR。他们是存储器访问指令,由于ARM不能直接的访问存储器,所以一般是我们将需要配置的值先保存到寄存器中,然后借助存储器访问指令将通用寄存器的的配置数据写入到I.MX6LL寄存器中。

1、LDR指令

1 LDR R0, =0X0209C004 @将寄存器地址 0X0209C004 加载到 R0 中,即 R0=0X0209C004
2 LDR R1, [R0] @读取地址 0X0209C004 中的数据到 R1 寄存器中

 2、STR指令

1 LDR R0, =0X0209C004 @将寄存器地址 0X0209C004 加载到 R0 中,即 R0=0X0209C004
2 LDR R1, =0X20000002 @R1 保存要写入到寄存器的值,即 R1=0X20000002
3 STR R1, [R0] @将 R1 中的值写入到 R0 中所保存的地址中

         需要注意的是这两个指令都是操控32位数据。如果需要按照字节与半字进行操作的话需要给LDR、STR后面分别加上B或者H。LDRB、LDRH。

二、汇编LED灯实验

        点灯是单片机的灵魂,就如各种编程的hello world一样,下面就是正点原子提供给我们的点灯代码。

        利用STM32点灯的时候我们是先进行初始化,初始化就包括了使能端口时钟、端口配置、设置高低电平控制灯的开关。Linux开发板也是如此,只不过用汇编控制寄存器的方式来实现。首先我们先看他和STM32GPIO口的命名有什么不同,STM32 中的 IO 都是 PA0~15、PB0~15 这样命名的,而I.MX6ULL 的 IO 命名规则是IOMUXC_SW_MUX_CTL_PAD_xx_IOxx。根据这两个xx也可以判断出引脚是什么功能,如GPIO1_IO01、UART1_TX_DATA、JTAG_MOD。之后我们再看I.MX6ULL的点灯过程。由于板上的LED内部已经连接了GPIO1_IO03,所以我们直接对GPIO1_IO03进行配置即可:1、使能 GPIO1 时钟 2、设置 GPIO1_IO03 的复用功能 3、配置 GPIO1_IO03 4、设置 GPIO。与STM32的初始化并没有太大的区别。下面就是具体初始化的代码,都是通过控制寄存器上每个位来实现初始化。

.global _start /* 全局标号 */
 
 /*
 * 描述: _start 函数,程序从此函数开始执行此函数完成时钟使能、
 * GPIO 初始化、最终控制 GPIO 输出低电平来点亮 LED 灯。
 */
 _start:
 /* 例程代码 */
 /* 1、使能所有时钟,一共有七组 */
 ldr r0, =0X020C4068 /* 寄存器 CCGR0 */
 ldr r1, =0XFFFFFFFF 
 str r1, [r0] 
 
 ldr r0, =0X020C406C /* 寄存器 CCGR1 */
 str r1, [r0]

 ldr r0, =0X020C4070 /* 寄存器 CCGR2 */
 str r1, [r0]
 
 ldr r0, =0X020C4074 /* 寄存器 CCGR3 */
 str r1, [r0]
 
 ldr r0, =0X020C4078 /* 寄存器 CCGR4 */
 str r1, [r0]
 
 ldr r0, =0X020C407C /* 寄存器 CCGR5 */
 str r1, [r0]
 
 ldr r0, =0X020C4080 /* 寄存器 CCGR6 */
 str r1, [r0]
 

 /* 2、设置 GPIO1_IO03 复用为 GPIO1_IO03 */
 ldr r0, =0X020E0068 /* 将寄存器 SW_MUX_GPIO1_IO03_BASE 加载到 r0 中 */
 ldr r1, =0X5 /* 设置寄存器 SW_MUX_GPIO1_IO03_BASE 的 MUX_MODE 为 5 */
 str r1,[r0]

 /* 3、配置 GPIO1_IO03 的 IO 属性 
 *bit 16:0 HYS 关闭
 *bit [15:14]: 00 默认下拉
 *bit [13]: 0 kepper 功能
 *bit [12]: 1 pull/keeper 使能
 *bit [11]: 0 关闭开路输出
 *bit [7:6]: 10 速度 100Mhz
 *bit [5:3]: 110 R0/6 驱动能力
 *bit [0]: 0 低转换率
 */
 ldr r0, =0X020E02F4 /*寄存器 SW_PAD_GPIO1_IO03_BASE */
 ldr r1, =0X10B0
 str r1,[r0]

 /* 4、设置 GPIO1_IO03 为输出 */
 ldr r0, =0X0209C004 /*寄存器 GPIO1_GDIR */
 ldr r1, =0X0000008 
 str r1,[r0]

 /* 5、打开 LED0
 * 设置 GPIO1_IO03 输出低电平
 */
 ldr r0, =0X0209C000 /*寄存器 GPIO1_DR */
 ldr r1, =0 
 str r1,[r0]

 /*
 * 描述: loop 死循环
 */
 loop:
 b loop

        以上代码就是I.MX6ULL的点灯程序,只使用的LDR、STR两个指令,对没有汇编基础的小新也是很友好的。第 2 行定义了一个全局标号_start,_start相当于内存地址,代码就是从_start 这个标号开始顺序往下执行的,很像C语言的函数。

三、编译下载代码验证

        这里就利用到了交叉编译工具。

        1、arm-linux-gnueabihf-gcc -g -c led.s -o led.o

       命令就是将 led.s 编译为 led.o,其中“-g”选项是产生调试信息,GDB 能够使用这些 调试信息进行代码调试。“-c”选项是编译源文件,但是不链接。“-o”选项是指定编译产生的文 件名字,这里我们指定 led.s 编译完成以后的文件名字为 led.o。执行上述命令以后就会编译生成一个 led.o 文件。

        2、arm-linux-gnueabihf-ld -Ttext 0X87800000 led.o -o led.elf

        链接文件,就是将所有.o文件链接到一个指定的链接位置。上述命令中-Ttext 就是指定链接地址,“-o”选项指定链接生成的 elf 文件名,这里我们命名 为 led.elf。上述命令执行完以后就会在工程目录下多一个 led.elf 文件。

        3、arm-linux-gnueabihf-objcopy -O binary -S -g led.elf led.bin

        格式准换,由于led.elf 文件也不是我们最终烧写到 SD 卡中的可执行文件,我们要烧写的.bin 文件,因此还需要将 led.elf 文件转换为.bin 文件。就是上述命令。上述命令中,“-O”选项指定以什么格式输出,后面的“binary”表示以二进制格式输出, 选项“-S”表示不要复制源文件中的重定位信息和符号信息,“-g”表示不复制源文件中的调试信息。

        以上的步骤其实可以写成一个Makefile文件,make一下就可以执行完,很方便。以后会写一个关于Makefile的博客,这里就不提了。

        4、此时的.bin文件并不能直接的烧入到I.MX6U,因为其内部没有flash,96K的ROM我们用户也不可以调用。所以我们可以从外置的存储介质来烧入代码。我使用的是SD卡。这个步骤需要使用正点原子提供的imxdownload裸机烧写软件。将他copy到工程根目录下与led.bin在一起,之后还要修改imxdownload的文件权限,利用Linux的一个命令chmod给文件可执行的权限。最后执行./imxdownload led.bin /dev/sdd  执行后文件夹多了一个load.imx文件,他其实就是imxdownload给led.bin文件加了一些数据头以后生成的。这里有些是Linux的基础知识,不懂得话一定要先学会使用Linux在开始Linux驱动的学习。

        下来就可以在裸机上验证了,记得把BOOT_CFG调成以下状态:

设置好后按下复位键,等初始化完成后就可以看到灯亮了。

 

        这里只是记录了点灯的过程,让新人们有个大概的思路,细节还是要看正点原子的文档,讲的很好。 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

西邮小菜机

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值