话接上贴,上贴说到用 tiM3输出PWM驱动舵机,实现了我们智能家居当中的第一步,简单的控制。这回我们来说说 STM32f0的串口。从第一讲开始,介绍的f0的功能基本上都是先输出,后输入,这样才能在下一讲中利用上一讲的知识看到效果,这一讲也一样,我们之所以说串口,是为了下一讲AD时调试起来方便。就这样,我们开始stm32f0的串口之行。 要想使用串口,我们必须先了解才行,串口作为 通信当中最最通用的一种通信手段,从诞生之初,一直到现在,见证了n多种通信手段的诞生、淘汰,但串口却延续了下来,这源于串口不但简单,而且方便。 从选型手册中我们可以看到,我们用的stm32f30r8这款片子共有两个串口。而且都是同步、异步串行口。
通过参考手册,我们可以看出,stm32f030r8这款片子的两个串口分别是串口1、串口2。而且通过下图,我们可以看出,这两个串口可以实现的功能可是相当的多。它们有硬件流控、DMA收发、多机通信、同步模式、单线单工模式、接收超时中断、自动波特率检测等众多功能,其实这些功能别的片子也都有,只是stm32用这么低的价格实现了这么多功能,这才叫好。我们工程师开发的时候,大多数情况下最重要的一点还是要性价比高的,对吧。stm32f0系列就做到了这一点。
我们就用最简单的通信好吧,也不用什么DMA,不用流控,根据板子的硬件,我们怎么方便怎么来,调通了就ok,好吧。。。 我们只是用串口的异步全双工模式,好吧,两根线就可以了,TX、RX。 说到串口,其实也就关心下它的几个常用参数就行,波特率、停止位等,很简单,根据下表,我们可以查到不同波特率情况下的误差有多大:
其实,像stm32f0这种能跑到几十兆的片子,我们最通用的波特率应该是115200,但从图中可以看出,用115200的波特率会有一定的误差,虽然这误差很小,但如果我们一股脑发送大量数据的话,传送的数据很可能就会累计误差,一旦误差达到一定程度,接受的数据就会有问题了。所以,我们还是保险一点,选一个没有误差的波特率吧。从图中看到2Mb和38400都没有误差,我们只是为了调通串口,还是选择一个最通用的波特率9600,好吧。其实通信这东西,有时候并不是越快越好,你像我们板子上用的电平转换芯片是cp2102,这个芯片算是比较高级的串口电平转换芯片了,跑到115200是绝对没有问题的,但市面上很多垃圾方案,像一些pl2303的廉价模块或者数据线,用的晶振是那种廉价的,大批量数据,能稳定在9600的波特率就算不错了,所以说,大家开发过程中,如果遇到数据错误,并不一定是程序的问题,可以查阅一下硬件,确保硬件足够可靠之后,再想别的问题。2Mb是很高的速率了,这么高的波特率,好多硬件都支撑不住,所以我们选择9600波特率好吧。 翻了翻手册,感觉当中讲的没啥有意思的了,大家如果新手,最好还是看看的好,我在这里就不多介绍了,直接看寄存器好吧。在这之前,我们先看看板子的硬件好吧,要不然用到那些通信口,都不知道,编程时怎么配置IO啊!对不。。。 我对着原理图的mcu部分瞅了好久,也没发现和cp2102中TXD/RXD对接的网络标号,忽然一想,这可能是因为板子上使用了串口的跳线,经过了排阵的原因,于是乎查找排针,终于找到了JP4这个排针:
从这上面看到,这板子做的还比较人性,可以通过跳线选择串口1和串口2,市面上很多板子为了方便,直接将TXD和RXD接到了串口1上,兼有串口下载、通信功能,这样板子上其它串口用起来就费劲了。我们用的微雪的这板子设计非常合理! 这样,我们保留板子的默认排针接插顺序,按照板子上的接法,使用的是PA2、PA3这两个引脚,我们查阅手册,发现这两个引脚可以分别作为串口1、串口2的串行脚:
事实上是不是这样呢?仔细看TX和RX的后面有个(1)和(2)的小标注,我们翻到本页最下面查看发现:
标注说,PA2只能做串口2的TX,PA3只能做串口2的RX。。。 那就这样,我们就选择板子默认的串口2做为我们此次实验的通信口好吧。。。 这次实验不涉及到别的外设,只有串口2一个。所以我们从模板开始建立工程好吧,拷贝IAR_Template文件夹重命名为UART2。然后在User目录下新建两个文件:
把 .c 文件加入工程中的User分组中,从固件库中拷贝如下两个文件到User目录下:
并将 .c文件加入工程中的User分组下:
在uart2.c中输入如下内容:
下面详细分析: 2-11行为配置GPIOA的第2、3引脚为复用功能输出,13、14行配置引脚为第一复用输出,这里面要注意的是GPIO_PinSourcex而不是GPIO_Pin_x,之前吃过亏,所以以后这里一定要记住。 第16-30行配置uart2的工作参数,比如波特率为9600、数据位为8位,停止位1位、无校验、无流控、双工模式等。 31-40行配置了串口的中断。这里面有个地方需要注意下,我们待会再说,第41-46行就是简单的函数调用,为了直观。在uart2.h中输入:
很简单对吧,修改stm32f0xx_it.c文件,加入:
这里面也有一个陷阱,待会说。修改stm32f0xx_it.h:
然后修改main.c文件:
这样就结束了配置,我点击编译之后,选择调试和下载,结果死活没反应,啥反应也没有,查看各个寄存器,一点也没有改变,暂停调试,发现卡在了设置时钟里面,还记得stm32f0的bootloader帮我们设置了时钟吧,就是卡在那里面,点击下载当前程序,也没反应。然后我很纳闷,查找了好久,才发现,需要在工程设置里面选中下面这个:
因为我最近在研究IAR的手册,所以联系的时候把这个勾给取消了,这导致程序下载不进去,就自然没法调试了。。。选中之后,发现程序正常了,而且我们用串口助手发送一个数据,会看到f0给我们返回了同一数据:
至此该工程结束了,其实刚开始还打算介绍下串口的重定向,使用printf之类,结果发现现在已经9页了,挺长的了,介绍串口重定向的就留后面再说,好吧,这节还有问题没讲呢。。。 下面说说这里面的问题: 第一:我参考了固件库里面的串口例程,调试的时候发现可以进接收中断,但进不了if那个判断,后来想起来,搞f103的时候这里也是一样,f103的固件库里判断标志位的那个函数有问题,这里会不会也一样,我把固件库的
改成文件中的,就正常工作了,大家使用的时候注意这个问题。 第二:看uart2.c的第39行,这里我还得吐槽下f0的固件库,太难用了,远不如f1的固件库那么直观,那么方便,一开始我忘记了有这么一个函数,结果调试的时候发现接收中断没有打开,后来查找src文件里的开中断函数,这才发现这个函数,大家玩的时候也注意这里。 好了,最常用的通信口串口到这里就结束了,串口重定向的介绍,就留到下节好吧。。。这样的话AD这块下节就不说了,先说串口重定向,好吧。。。
|