嵌入式C语言编程中经验教训总结(六)硬件接口匹配
在嵌入式控制系统中,通常是以主控芯片为中心,通过I/O接口、总线等方式和外设(例如lcd,键盘,电机、传感器等)连接在一起,组成一个系统,因此在嵌入式开发的过程中,如何有效地管理好各种外设,协调工作,共同完成系统功能就是必须解决的问题,相对于主控芯片,外设往往为低速、笨重、大功率、智能化程度低或非智能化的功能模块,本文针对嵌入式系统常见接口做出总结,对控制过程中常犯错误进行了总结
GPIO类
例如控制led等闪烁
LED闪烁程序:错误代码如下:
#include <REG52.H>
#include <INTRINS.H>
void Led()
{
unsigned int i =0;
while (1)
{
P0=0xFE;
Delay(100);//100ms
P0=0xFF;
}
}
上面代码中至少有一处错误和两处需要改进优化的地方:
- 运行后会造成LED看上去长亮或长灭(这个和硬件电路的LED另一端接高和低有关),原因就在于闪烁的占空比没有控制好,实际上如果用示波器看,还是可以看到LED等的高低变化的,只是P0=0xFF到P0=0xFE时间只有一个指令周期,和Delay(100)函数的100ms相比,肉眼就无法分辨了。
- 程序中使用对蒸锅P0端口赋值的方法,实际控制的只有P0^0一个bit,这在P0其他端口没有使用时没有问题,如果有别的功能占用,就会对P0其他端口造成干扰。
- 不适用于多任务系统。
如此场景,类似的还有蜂鸣器、继电器、电机启停控制等场景,如果不能匹配好输出频率和占空比,不仅达不到控制的目的,严重的话还会损坏外设,造成严重后果。
串行总线类
嵌入式系统中,常用的串行总线有:
1 I2C
2 SPI
3 UART
4 CAN
5 USB
6 RS485 、RS422
7. I2S、SPDIF
串行接口 (Serial Interface)是指数据一位一位地顺序传送。其特点是通信线路简单,利用较低的线路成本就可以实现双向通信(或单向控制),控制过程最容易犯的错误有:
(1)电平匹配
嵌入式系统中,TTL电平多为3.3V或5V代表1,0V代表逻辑0,如下图:
而在实际通信中,例如UART232通信中,RS232是负逻辑电平,它定义
+5到+12V为低电平,而-12到-5V为高电平,这就需要逻辑转换或电平转换电路来完成。例如对RS485接口:
就需要把主处理器处理输出的单端的信号转为为差分的A B信号进行传输,还要准确控制通信的方向。如果时序配合不好,就会造成通信数据帧的数据误差,造成通信失败。
(2)多机通讯
RS232一般用于点对点的通信,而RS485可以实现一对多通信,总线上允许连接的设备理论上可以达到128个。如果想要在RS485的基础之上拥有全双工的通信能力,那我们就需要使用RS422接口。这时候,主控制器往往作为主设备,其他为从设备,从设备之间不能通信。为了避免信号的反射和回波,需要在接收端接入终端匹配电阻,其阻值约等于传输电缆的特性阻抗。在短距离传输时,可不接端接电阻,端接电阻接在传输电缆的最远端,
I2C总线上也可以同时挂接不同地址的多个设备,主机发送数据到从机的状态下:主机控制SCL信号线和SDA信号线,从机只是在SCL线为高的时候去被动读取SDA线。主机读取从机的数据的状态下:主机来发出时钟信号,从机只是保证在时钟信号合适时刻将数据送到SDA线。
SPI (Serial Peripheral interface)是一种同步串行传输,主要应用在EEPROM,Flash,实时时钟等, SPI接口由MOSI(串行数据输出),MISO(串行数据输入),SCLK(串行移位时钟),/SS(从设备使能信号),四种信号构成。多机通讯时,SPI由一个主设备和一个或多个从设备组成,于I2C不同的是,SPI接口的从设备不是通过地址来区分的,而是通过增加SS信号线来完成,通信过程中, MOSI(串行数据输出),MISO(串行数据输入),SCL(串行移位时钟)都是公用的,而SS为各个从设备各自独有,每增加一个从设备,那么就要增加一个SS使能信号。
(3)波特率匹配
在串行通信中,最关键的参数不过于波特率了,它不仅决定了通信的速度,在工业应用环境中,往往周围都有各种各样其他设备一起工作,环境复杂,另外,有些设备的波特率是存在误差的,一般在2.5%的误差范围下,是可以保证可靠传输,但是,如果一个报文过长,就会存在误差积累的问题,造成数据帧校验识别,所以,在使用上应注意避免发送太长数据的包。
另外,在满足使用需要情况下,尽量采用较低波特率,这样不仅可以提高抗干扰能力,也降低了对线路的要求。