正点原子 发表于 2020-6-4 15:53:02

【正点原子Linux连载】第二十二章串口格式化函数移植实验--摘自【正点原子】I.MX6U嵌入式Linux驱动开发指南

本帖最后由 正点原子 于 2020-10-24 16:04 编辑

1)实验平台:正点原子阿尔法Linux开发板
2)平台购买地址:https://item.taobao.com/item.htm?id=603672744434
3)全套实验源码+手册+视频下载地址:http://www.openedv.com/thread-300792-1-1.html
4)本章实例源码下载:
5)对正点原子Linux感兴趣的同学可以加群讨论:876919289
6)关注正点原子公众号,获取最新资料






第二十二章串口格式化函数移植实验

上一章实验我们实现了UART1基本的数据收发功能,虽然可以用来调试程序,但是功能太单一了,只能输出字符。如果需要输出数字的时候就需要我们自己先将数字转换为字符,非常的不方便。学习STM32串口的时候我们都会将printf函数映射到串口上,这样就可以使用printf函数来完成格式化输出了,使用非常方便。本章我们就来学习如何将printf这样的格式化函数移植到I.MX6U-ALPHA开发板上。

22.1串口格式化函数简介
      格式化函数说的是printf、sprintf和scanf这样的函数,分为格式化输入和格式化输出两类函数。学习C语言的时候常常通过printf函数在屏幕上显示字符串,通过scanf函数从键盘获取输入。这样就有了输入和输出了,实现了最基本的人机交互。学习STM32的时候会将printf映射到串口上,这样即使没有屏幕,也可以通过串口来和开发板进行交互。在I.MX6U-ALPHA开发板上也可以使用此方法,将printf和scanf映射到串口上,这样就可以使用SecureCRT作为开发板的终端,完成与开发板的交互。也可以使用printf和sprintf来实现各种各样的格式化字符串,方便我们后续的开发。串口驱动我们上一章已经编写完成了,而且实现了最基本的字节收发,本章我们就通过移植网上别人已经做好的文件来实现格式化函数。
22.2硬件原理分析
      本章所需的硬件和上一章相同。
22.3实验程序编写
      本实验对应的例程路径为:开发板光盘-> 1、裸机例程->14_printf。
本章实验所需要移植的源码已经放到了开发板光盘中,路径为:1、例程源码->5、模块驱动源码->2、格式化函数源码->stdio,文件夹stdio里面的文件就是我们要移植的源码文件。本章实验在上一章例程的基础上完成,将stdio文件夹复制到实验工程根目录中,如图22.3.1所示:

图22.3.1添加实验源码
      stdio里面有两个文件夹:include和lib,这两个文件夹里面的内容如图22.3.2所示:

图22.3.2stdio所有源码文件
      图22.3.2就是stdio里面的所有文件,stdio里面的文件其实是从uboot里面移植过来的。后面学习uboot以后大家有兴趣的话可以自行从uboot源码里面“扣”出相应的文件,完成格式化函数的移植。这里要注意一点,stdio中并没有实现完全版的格式化函数,比如printf函数并不支持浮点数,但是基本够我们使用了。
      移植好以后就要测试相应的函数工作是否正常,我们使用scanf函数等待键盘输入两个整数,然后将两个整数进行相加并使用printf函数输出结果。在main.c里面输入如下内容:
示例代码22.3.1 main.c文件代码
/**************************************************************
Copyright © zuozhongkai Co., Ltd. 1998-2019. All rights reserved.
文件名   : main.c
作者   : 左忠凯
版本   : V1.0
描述   : I.MX6U开发板裸机实验14 串口print实验
其他   : 本实验在串口上移植printf,实现printf函数功能,方便以后的
程序调试。
论坛   : www.openedv.com
日志   : 初版V1.0 2019/1/15 左忠凯创建
**************************************************************/
1#include "bsp_clk.h"
2#include "bsp_delay.h"
3#include "bsp_led.h"
4#include "bsp_beep.h"
5#include "bsp_key.h"
6#include "bsp_int.h"
7#include "bsp_uart.h"
8#include "stdio.h"
9
10/*
11* @description      : main函数
12* @param                : 无
13* @return               : 无
14*/
15int main(void)
16{
17      unsignedchar state = OFF;
18      int a , b;
19
20                int_init();      /* 初始化中断(一定要最先调用!)      */
21      imx6u_clkinit();      /* 初始化系统时钟      */
22      delay_init();      /* 初始化延时                        */
23      clk_enable();      /* 使能所有的时钟      */
24      led_init();      /* 初始化led                           */
25      beep_init();      /* 初始化beep                            */
26      uart_init();      /* 初始化串口,波特率115200         */
27
28      while(1)
29      {
30      printf("输入两个整数,使用空格隔开:");
31      scanf("%d %d",&a,&b);/* 输入两个整数 */
32      printf("\r\n数据%d + %d = %d\r\n\r\n", a, b, a+b);/* 输出和 */
33
34      state =!state;
35      led_switch(LED0,state);
36      }
37
38      return0;
39}
      第30行使用printf函数输出一段提示信息,第31行使用函数scanf等待键盘输入两个整数。第32行使用printf函数输出两个整数的和。程序很简单,但是可以验证printf和scanf这两个函数是否正常工作。
22.4编译下载验证
22.4.1编写Makefile和链接脚本
      修改Makefile中的TARGET为printf,在INCDIRS中加入“stdio/include”,在SRCDIRS中加入“stdio/lib”,修改后的Makefile如下:
示例代码22.4.1.1 Makefile文件代码
1CROSS_COMPILE         ?= arm-linux-gnueabihf-
2TARGET               ?=printf
3
4/* 省略掉其它代码...... */
5
6INCDIRS      :=      imx6ul \
7                stdio/include \
8                bsp/clk \
9                bsp/led \
10                bsp/delay\
11                bsp/beep \
12                bsp/gpio \
13                bsp/key \
14                bsp/exit \
15               bsp/int \
16                bsp/epittimer \
17                bsp/keyfilter \
18                bsp/uart
19
20 SRCDIRS                :=      project \
21                stdio/lib \
22                bsp/clk \
23                bsp/led \
24                bsp/delay \
25                bsp/beep \
26                bsp/gpio \
27                bsp/key \
28                bsp/exit \
29                bsp/int \
30                bsp/epittimer \
31                bsp/keyfilter \
32                bsp/uart
33
34/* 省略掉其它代码...... */
35
36$(COBJS): obj/%.o : %.c
37$(CC) -Wall -Wa,-mimplicit-it=thumb -nostdlib -fno-builtin -c -O2$(INCLUDE) -o $@ [      DISCUZ_CODE_75      ]lt;
38
39 clean:
40rm -rf $(TARGET).elf $(TARGET).dis $(TARGET).bin $(COBJS)$(SOBJS)
第2行修改变量TARGET为“printf”,也就是目标名称为“printf”。
      第7行在变量INCDIRS中添加stdio相关头文件(.h)路径。
      第28行在变量SRCDIRS中添加stdio相关文件(.c)路径。
      第37行在编译C文件的时候添加了选项“-Wa,-mimplicit-it=thumb”,否则的话会有如下类似的错误提示:
thumb conditional instruction should be in IT block -- `addcs r5,r5,#65536'
      链接脚本保持不变。
22.4.2编译下载
      使用Make命令编译代码,编译成功以后使用软件imxdownload将编译完成的printf.bin文件下载到SD卡中,命令如下:
chmod 777 imxdownload                        //给予imxdownload可执行权限,一次即可
./imxdownload printf.bin /dev/sdd                //烧写到SD卡中
      烧写成功以后将SD卡插到开发板的SD卡槽中,打开SourceCRT,设置好连接,然后复位开发板。SourceCRT显示如图22.4.2.1所示:


图22.4.2.1 SourceCRT默认显示界面
      根据图22.4.2.1所示的提示,输入两个整数,使用空格隔开,输入完成以后按下“回车键”,结果如图22.4.2.2所示:

图22.4.2.2计算输入结果显示
从图22.4.2.2可以看出,输入了32和5,这两个整数,然后计算出32+5=37。计算和显示都正确,说明格式化函数移植成功,以后我们就可以使用printf来调试程序了。

页: [1]
查看完整版本: 【正点原子Linux连载】第二十二章串口格式化函数移植实验--摘自【正点原子】I.MX6U嵌入式Linux驱动开发指南