0
  • 聊天消息
  • 系统消息
  • 评论与回复
登录后你可以
  • 下载海量资料
  • 学习在线课程
  • 观看技术视频
  • 写文章/发帖/加入社区
会员中心
创作中心

完善资料让更多小伙伴认识你,还能领取20积分哦,立即完善>

3天内不再提示

怎样用UART与PC通信

454398 来源:工程师吴畏 2019-07-31 17:12 次阅读

示意图

怎样用UART与PC通信

微控制器通信 - 什么是UART

微控制器经常发现自己处于具有特定功能的专用电路中,例如测量,监控和控制。但是,有些情况下将微控制器连接到计算机可能非常有益甚至是必要的(例如,设备配置)。有几种方法可以实现PC-Microcontroller通信

通过Wi-Fi(如ESP8266模块)

以太网

USB

虽然这些形式的通信可能允许高数据传输速率,但它们很难使用,大多数微控制器都有另外一种类型的通信,称为UART,它代表通用异步接收器/发送器。

这是一个简单的串行连接,可以是用于以低速发送少量数据,并且使用和实现极其简单。使UART更加便捷的是,有USB转串口转换器可用于允许微控制器通过USB使用虚拟COM端口与PC通信。

串行概述

使用微控制器和计算机的串行通信可包括许多不同的设置,包括奇偶校验和停止位。但是,在本教程中,我们将介绍最简单的串行通信形式,这也是最常见的形式之一。所以我们首先要看的是如何发送串行数据。首先,我们来看看硬件

微控制器上最简单形式的串行外设是一个美化的移位寄存器,它使用两个独立的I/O引脚来发送数据(TxDn)和接收数据(RxDn)

当需要从设备发送数据时,它会将数据发送到其发送移位寄存器中,然后逐位计时数据,直到所有数据都已发送完毕。当需要读取数据时,接收器首先需要检测是否正在接收某些数据。

一旦满足此条件,接收器就会将数据移入移位寄存器。完成后,可以从接收移位寄存器中读取器件,并以其认为合适的任何方式处理数据。

UART模块的简单框图

UART模块中使用的协议本身(有时称为RS-232)包含有助于数据传输/接收的选项和附加功能。下图显示了典型的UART传输,包括起始位,数据本身,奇偶校验位和停止位。

从ATmega168数据表中获取的图像

IDLE - 如果没有发生传输,则传输线必须保留逻辑1(5V,3.3V等)

起始位 - UART线上的下降沿表示传输即将开始

数据位 - 这些是我们的实际数据位发送,并且位首先发送到最低位(位0,位1 。..位7)

奇偶校验位 - 此可选位可用作错误检查的基本形式具有等于所有位组合的异或(XOR)的值

停止位 - 这是停止传输所必需的并且是逻辑1.有时,可以使用两个停止位,但通常只使用一个

ATmega上的UART

ATmega168上的UART模块非常复杂,因为它允许不同的操作模式(包括同步传输),但我们将配置UART以使用适用于99%基于UART的项目的最常见设置。

时钟

我们需要配置的第一件事是UART模块的时钟源(这也配置了UART运行的模式) 。由于我们将使用异步传输(时钟不传输,只有数据),我们将使用“正常异步”。为此,我们在UCSRnC寄存器中将UMSEL位设置为0.

奇偶校验位和停止位

由于大多数传输不需要奇偶校验,我们将禁用该位。为此,我们需要将两个UPM位都设置为0,这可以在UCSR寄存器中找到。

对于停止位,我们只会使用一个停止位,通过清除UCSRnB寄存器中的USBS位来完成。

数据大小

UART模块能够以不同的位宽发送数据,但对于大多数项目,我们将使用8位数据大小,因为我们的微控制器是一个8位器件。为此,我们将寄存器UCSRnB和UCSRnC中的UCSZ位的值设置为011。

波特率

在谈到串行通信时,波特率通常是指每秒传输的数据位数,可以认为是连接速度。串行通信的典型波特率包括9600,115200和10417.

对于我们的串行设置,我们将使用9600的波特率(非常常见的波特率)。波特率可以使用下面的公式计算,但是,使用第163-165页上的表格更容易。

由于我们的ATmega168连接到8MHz振荡器,我们可以查看下表,看看我们将UBRR寄存器设置为什么值。

对于9600波特,我们将使用值51.请注意,您的CLKDIV8位可能已设置,如果是这种情况,那么您的波特率可能比您预期的慢8倍。如果是这种情况,请尝试使用UBRR值12而将U2X0设置为开,或使用更高的时钟速度。

启用接收/传输

我们需要设置几个启用位,其他启用位是可选的。我们需要使能的前两位是RXEN和TXEN,它们使能接收器和发送器。

我们可以设置两个中断使能位,这意味着当我们的UART模块完成发送或接收数据时,中断将触发(对实时应用程序有用)。

读/写UART

有趣的是,AVR UART外设对接收和发送寄存器使用相同的I/O地址。当写入UART数据寄存器(UDRn)时,数据被发送到UART发送器移位寄存器,当从UART数据寄存器读取时,返回来自UART接收器的数据。

一些有用的控制信号

一个寄存器UCSR0A可以帮助确定UART的状态模块,因为它有几个状态位。

RXC0,第7位,如果接收缓冲区中有需要读取的数据,则为1

TXC0,第6位,一旦传输将为1已完成

如果发送缓冲区为空,UDRE0,位5将为1

FE0,位4,发出帧错误警告

DOR0,第3位,发出数据溢出警告(当收到的数据太多且接收缓冲区已满时)

当奇偶校验时,UPE0,位2将为1在接收到的字节上检测到错误

一个简单的UART示例

此示例将介绍如何创建一个echo设备,该设备将等待连接的PC向UART线路发送一个字节。一旦检测到,AVR将立即发回相同的字节以回显消息。

/*

* AVR UART.c

*

* Created: 09/01/2018

* Author : RobinLaptop

*/

// These are really useful macros that help to get rid of unreadable bit masking code

#define setBit(reg, bit) (reg = reg | (1 《《 bit))

#define clearBit(reg, bit) (reg = reg & ~(1 《《 bit))

#define toggleBit(reg, bit) (reg = reg ^ (1 《《 bit))

#define clearFlag(reg, bit) (reg = reg | (1 《《 bit))

#include

int main(void)

{

// Initialize Registers

// Configure register UCSRA

setBit(UCSR0A, U2X0); // Double the BRG speed (since I am using a 8MHz crystal which is divided by 8)

clearBit(UCSR0A, MPCM0); // Normal UART communication

// Configure register UCSRB

clearBit(UCSR0B, RXCIE0); // We will not enable the receiver interrupt

clearBit(UCSR0B, TXCIE0); // We will not enable the transmitter interrupt

clearBit(UCSR0B, UDRIE0); // We will not enable the data register empty interrupt

setBit(UCSR0B, RXEN0); // Enable reception

setBit(UCSR0B, TXEN0); // Enable transmission

clearBit(UCSR0B, UCSZ02); // 8 bit character size

// Configure register UCSRC

clearBit(UCSR0C, UMSEL00); // Normal Asynchronous Mode

clearBit(UCSR0C, UMSEL01);

clearBit(UCSR0C, UPM00); // No Parity Bits

clearBit(UCSR0C, UPM01); // No Parity Bits

clearBit(UCSR0C, USBS0); // Use 1 stop bit

setBit(UCSR0C, UCSZ01); // 8 bit character size

setBit(UCSR0C, UCSZ00);

// Configure the baud rate register (this is a combination of both UBRR0L and UBRR0H)

// Despite using an 8MHz crystal my Fosc is 1MHz since the CLK8DIV fuse bit is dividing the clock

// by 8. When I try to change this fuse the AVR locks me out!

UBRR0 = 12;

while (1)

{

// Wait until data has been received

while(!(UCSR0A & (1 《《 RXC0)));

// Now send the same byte back

UDR0 = UDR0;

// Wait until the Data Transmit Register is empty

while(!(UCSR0A & (1 《《 TXC0)));

}

}

声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉
  • PC
    PC
    +关注

    关注

    9

    文章

    2065

    浏览量

    154006
  • uart
    +关注

    关注

    22

    文章

    1227

    浏览量

    101165
  • ATmega168
    +关注

    关注

    0

    文章

    9

    浏览量

    9278
收藏 人收藏

    评论

    相关推荐

    通信技术:UART串口通信开源代码实操!

    今天我们分享的是关于UART串口通信示例,欢迎大家探讨
    的头像 发表于 11-05 11:56 2764次阅读
    <b class='flag-5'>通信</b>技术:<b class='flag-5'>UART</b>串口<b class='flag-5'>通信</b>开源代码实操!

    UART通信协议介绍和数据传输工作流程

    UART是一种通用串行数据总线,用于异步通信。该总线双向通信,可实现全双工传输和接收。UART通常用来实现与PC之间数据
    的头像 发表于 10-24 14:20 365次阅读
    <b class='flag-5'>UART</b><b class='flag-5'>通信</b>协议介绍和数据传输工作流程

    怎样用THS3201实现输出功率可调?

    怎样用THS3201实现输出功率可调?
    发表于 08-26 08:28

    OPA735加OPA333,怎样用TINA TI去仿真?

    当输入信号VG1从7.06V慢慢变化到7.22V时。 输出电压Vout的变化必须是接近线性变化的。我想知道我该怎样用TINA TI去仿真?怎样设置那个输入信号VG1才能达到我的目的。因为这个电压源好像
    发表于 08-02 08:39

    怎样用STM8L的PB3/TIM2_TRIG的引脚测量脉宽?

    怎样用STM8L的PB3/TIM2_TRIG的引脚测量脉宽?
    发表于 05-07 06:55

    stm32f100怎样用重映射功能?

    的是stm32f100c8t6b芯片,现在想用将PB1映射为TIM1_CH3N,在调用GPIO_PinAFConfig(GPIOB,GPIO_PinSource1,GPIO_AF_TIM1)时, GPIO_PinAFConfig和GPIO_AF_TIM1都没定义,stm32f100
    发表于 05-07 06:06

    如何用cubemx做lin通信

    怎样用cubemx做lin通信,没有找到相应的函数,只有一个init函数,如下设置后,生成了与lin有关的代码,连中断都没有。请高手指点 /* USART3 init function
    发表于 04-26 07:44

    UART串口通信协议是什么?

    UART (Universal Asynchronous Receiver/Transmitter) 是一种通信接口协议,用于实现串口通信。它是一种简单的、可靠的、广泛应用的串口通信
    的头像 发表于 03-19 17:26 1249次阅读

    STM32F412G-DISCO怎样用MX生成fatfs的代码?

    STM32F412G-DISCO怎样用MX生成fatfs的代码? SD卡例程能跑,但mx生成的代码不能正常运行,我生成代码后是不是还要配置一些东西?(我生成后只写了测试代码) 问题解决了,虽然我不知道我为什么不能直接使用mx生成的代码去操作sd卡,但我通过复制粘贴例程的代码完成了测试。
    发表于 03-12 08:15

    浅谈UART通信的异步通信机制

    波特率表示每秒钟传送的码元符号的个数,它是对符号传输速率的一种度量。在UART通信中,波特率用于描述通信速度,其单位是bps(每秒钟传输的bit的数量)。
    发表于 02-19 16:19 731次阅读
    浅谈<b class='flag-5'>UART</b><b class='flag-5'>通信</b>的异步<b class='flag-5'>通信</b>机制

    uart与usart区别 usart可以当uart

    USART实际上包含了UART的功能,并增加了支持同步通信的能力。在大多数微控制器中,UART通常是USART功能的一部分,USART可以配置为UART模式进行异步
    发表于 01-17 15:46 1.8w次阅读
    <b class='flag-5'>uart</b>与usart区别 usart可以当<b class='flag-5'>uart</b><b class='flag-5'>用</b>吗

    怎样用表来判断加热管的好坏?

    怎样用表来判断加热管的好坏? 万表是电工常用的测量仪器,它可以用来判断加热管的好坏。加热管是一种常见的加热元件,广泛应用于家电、机械设备和工业生产中。在选择和使用加热管时,我们需要了解其电阻值
    的头像 发表于 12-20 17:21 5019次阅读

    无线通信怎样用电磁波表示1和0

    为什么频率越高,能携带的信息就越多?以数字信号为例,信息就是一串串的1和0,所以先搞清楚怎样用电磁波表示1和0。
    发表于 12-05 14:44 1741次阅读
    无线<b class='flag-5'>通信</b>:<b class='flag-5'>怎样用</b>电磁波表示1和0

    ADAU1452做FFT分析,怎样设定取样点的数量?

    请问,我想用ADAU1452做FFT分析,怎样设定取样点的数量,还有就是怎样用单片机读出分析得到的复数结果数组?谢谢!
    发表于 11-29 06:42

    怎样用ADAU1761设计DRC的压缩/扩展?

    请问怎样用ADAU1761设计DRC的压缩/扩展。我在SigmaStudio 4.5的模块中只找到RMS。如果ADAU1761设计DRC要怎样
    发表于 11-28 06:41