AVR單片機學習(七)異步串行口UART
作者:zww 1988 來源:本站原創(chuàng) 點擊數(shù):
… 更新時間:2014年04月18日 【字體:
大 中 小】
串行通訊技術概述
異步串行通訊原理
UART與電腦的通訊
M16的USART
中斷方式使用USART步驟
一、串行通訊技術概述
串行通訊的通俗定義:
一位發(fā)送一位(相對與并行,)當然通過 位同步 幀同步
串行通訊的分類
同步串行通訊
時鐘線、數(shù)據(jù)線、通過時鐘保持數(shù)據(jù)同步
SPI,IIC
屬于同步串口通訊
異步串口通信
只有一根數(shù)據(jù)線,通過波特率保證數(shù)據(jù)同步(顧名思義沒有時鐘線只有數(shù)據(jù)線)
UART
無線通信一般均為異步串行通信(相對于無形之中只能有一根天線)
波特率
每秒發(fā)送碼元時間寬度為(1/9600)S
大概是在100個微妙左右
發(fā)送方按照波特率發(fā)出數(shù)據(jù)
接收方按照波特率確定碼元時間寬度對數(shù)據(jù)進行采樣
幀格式
8位數(shù)據(jù)格式

idle 空閑時候保持高電平
在發(fā)送數(shù)據(jù)的時候先發(fā)送一位起始位 低電平0
然后數(shù)據(jù) 0 1 。。。。8 位
P這位是可選的一般在多級通訊的時候需要發(fā)送9位數(shù)據(jù)在第9位時候 是地址位
SP1(必選的一位停止位 是1) 也可以選2位 加一個SP2
但是一般都是1位 起始位 1位停止位 8位數(shù)據(jù)位
之后數(shù)據(jù)繼續(xù)保持空閑高電平
接線圖
發(fā)送端:TXD
接收端:RXD
交叉連接

RS232電平標準
邏輯1 :-15V
邏輯0 :+15V
DB9 接口定義
TXD。遥兀摹。牵模巍∪即可瞞足絕大數(shù)應用場合

下面是開發(fā)板電路圖

MAX3232標示的是3.3V的芯片我們用的是5V MAX232 芯片標示錯了 不論引腳封裝還是順序都是完全相同的。
MAX 232
芯片能提供2路串口我們只用一個。由于這個電路圖上是按照DB9定義的走線了所以我們就得用交叉線來跟PC通訊了。
M16的USART特點
全雙工操作(獨立的串行接受合發(fā)送寄存器,不像51是公用同一個寄存器,只能半雙工)
異步或同步操作(當然同步一般用不到。所以我們只當異步串行口使用)
支持5,6,7,8或9個數(shù)據(jù)位和1個或2個停止位(一般用的最多是8位數(shù)據(jù) 1位停止)
硬件支持的奇偶校驗操作(一般用不到,有限的場合通信質(zhì)量還是可靠的,沒必要加上校驗)
三個獨立的中斷源(看技術文檔《一》)
噪聲濾波,包括錯誤的起始位檢測,以及數(shù)字低通濾波器
USART
寄存器 universal
(通用的大體的) synchronous(同步)
asynchronous(異步)R/T(接受/發(fā)送)
UDR
UCSRA
UCSRB
UCSRC
UBRRL與UBRRH

《一》
Three Separate Interrupts (3個 分離 獨立的中斷 ) TX
complete 發(fā)送完成中斷 ,TX Data Register Empty
發(fā)送數(shù)據(jù)寄存器空 中斷
RX Complete 接受完成中斷。
以下是整段中文解釋
通用同步和異步串行接收器合轉(zhuǎn)發(fā)器(USART)是一個高度靈活的串行通訊設備。主要特點為:
全雙工操作(獨立的串行接收和發(fā)送寄存器)
異步或同步操作
主機或從機提供時鐘的同步操作
高精度的波特率發(fā)生器
支持5,6,7,8,或9個數(shù)據(jù)位合1個 或 2個停止位
硬件支持的奇偶數(shù)校驗操作
數(shù)據(jù)過渡檢測
偵錯誤檢測
噪聲濾波,寶貨粗無的起始位檢測,以及數(shù)字低通濾波器
三個獨立的中斷:發(fā)送結(jié)束中斷,發(fā)送數(shù)據(jù)寄存器空中斷,以及接受結(jié)束中斷
多處理器通訊模式
倍速率異步通訊模式
三個獨立中斷的前兩個中斷我們一般用不到的因為我們發(fā)送之前查詢一下發(fā)送數(shù)據(jù)寄存器是否忙(可供使用)就可以了,沒必要采用這兩個中斷,但是接受一般采用中斷方式,因為我們不可能一直不停的查詢。而查詢發(fā)送終中斷最多耽誤發(fā)送一個字節(jié)的時間。
噪聲濾波使用起來通信質(zhì)量相比其他單片機的通信質(zhì)量大大提升,怎么操作USART呢 ?
首先介紹下有關的寄存器
第一個寄存器I/O
數(shù)據(jù)寄存器 UDR

share the same I/O address
共享相同的I/O地址 referred to as USART 稱為USART 數(shù)據(jù)寄存器或
UDR
其實就是發(fā)送數(shù)據(jù)和接受數(shù)據(jù)寄存器都采樣同一個名稱UDR
但是怎么樣區(qū)分呢? 、
寫 就是 發(fā)送
讀就是接受
第一段下面就是吧呵呵!本人英文不好呵呵 the Transmit Data Buffer
Register(TXB)Will be the destination for data written to the UDR
Register location ,Reading teh UDR Register location will return
the contents of the Receive Data Buffer Register (RXB).
第二個寄存器是
UCSRA 控制狀態(tài)寄存器A

第七位和第六位
接受完成(置位)
發(fā)送完成(置位)
這兩段最后一句是說可以用接受中斷標志合發(fā)送中斷標志,自己慢慢看哦。

第5位是 數(shù)據(jù)寄存器空 ,就是檢測UDR 是否準備好接受新的數(shù)據(jù)。indicates 表明
the UDRE flag indicates if the
transmit buffer (UDR) is ready to receive new
data 這個UDRE標志指出 發(fā)送緩沖器(UDR
)是否準備號接受新數(shù)據(jù) 假如UDRE is one ,the buffer empty , and therefore ready
to written
已準備好進行數(shù)據(jù)接受。所以這一位我們發(fā)送之前對這一位查詢是否置位,如果置位了就可以往里寫數(shù)據(jù)了,進行發(fā)送操作。

第4位:幀錯誤
第三位數(shù)據(jù)溢出
第二位 :(parity)奇偶校驗錯誤
一般我們是用不到的,沒必要管他

第1位:雙 發(fā)送 速度
倍速發(fā)送跟設置波特率有影響的一般情況下把我們也是不用管的
如果將這位置位的話那么算出來的波特率就得乘以2.
this bit only has effect for the asynchronous
operation 這個位 僅對 有effect (效果) for the
asynchronous operation 異步操作

第0位:多處理器 communication 通訊 模式 這一位我們一般也是用不到的。
所以這個UCSRA
這個控制狀態(tài)寄存器一般用的最多的是第五位
UDRE 數(shù)據(jù)寄存器空
第三個寄存器是控制狀態(tài)寄存器B


這個寄存器是平時用的最多的寄存器
第七位:RXCIE :RX 結(jié)束中斷使能
如果是使用USART 的接受中斷的話這一位必須置位 使能
writing
this bit to one enables interrupt on the RXC
flag.寫1 使能中斷RXC 標志(置位后使能RXC中斷)
一個USART
接受中斷結(jié)束 將生成 一個
RXCIE 位寫1 ,這個全局中斷標志SREG is
寫 UCSRA
寄存器的RXC位置位1時可以產(chǎn)生USART 接受結(jié)束中斷。
第六位:TXCIE TX 發(fā)送中斷結(jié)束使能
別人的解釋:置位后使能TXC中斷,當TXCIE 為1 時,全局中斷標志位SREG
置位,UCSRA寄存器的TXC置為1時可以產(chǎn)生UCSRA發(fā)送結(jié)束中斷。(看多經(jīng)典比我上面的一個一個字解釋好吧)
當然第六位我們一邊用不到的。
第五位:USART
數(shù)據(jù)寄存器空中斷使能 也不常用

第4位:接受使能
第3位:發(fā)送使能
這兩位非常重要如果要用串行口 這兩位必須使能。取代了通用端口了。

第2位 :UCSZ2 字符長度
這UCSZ2 位combined
(結(jié)合)UCSRC寄存器的 UCSZ1:0在一起可以設置數(shù)據(jù)幀所包含的數(shù)據(jù)位數(shù)(字符長度)。
一般我們用8位 。 可以設置成5--9位 當然在AVR
上電復位之后它的寄存器默認設置就是8位所以這我們也不用設置


這個第1位和第0位分別是 :接受數(shù)據(jù)位8 和 發(fā)送數(shù)據(jù)位
8
這兩位僅僅對于數(shù)據(jù)長度設置成9位的時候才是有作用的他們分別是第9個數(shù)據(jù)位,所以我們這也是用不到。
第四個寄存器:控制狀態(tài)寄存器C
第七位:寄存器選擇
這個位選擇開始訪問 UCSRC 或 UBRRH
寄存器。讀UCSRC 該位為1 ,寫UCSRC
時 URSEL為1.
估計 UCSRC 和 UBRRH
共享一個地址。這一點對編程沒有影響。所以這一位不管。

第六位:USART 模式選擇
默認是置0 :異步操作
一般同步用不到。至少我用過的同步操作就用過一次就是對PS2鍵盤驅(qū)動的時候用到了同步模式一般是用不到同步模式的。

第五位和第四位組合起來組成 奇偶數(shù)校驗模式
these bits enable and set type of parity generation
and check .這兩位設置奇偶校驗模式并使能奇偶校驗。
Disabled (禁止) Reserved(保留)
Enabled ,Even parity 偶校驗 Enabled ,odd parity
(奇校驗)
一般我們不用校驗 所以不用設置這兩位

第3位:停止位選擇
默認停止位是1位
一般不用設置 默認停止位1位

第2位和第1位:設置字符長度
可以看到 8位是 0 1
1
而我們?nèi)タ纯碪CSRC 寄存器上電復位的初始值為
UCSZ1 UCSZ0
都是1 而UCSZ2 是0 所以默認為8位


0 1 1 8位數(shù)據(jù)所以我們一般對這2位 不做設置的。默認就8位了。

第0位:最后一位是 :時鐘極性
這一項僅對同步的時候有用,this bit is used for synchronous mode
only. 同步模式我們也用不到所以這一位我們也不用管。
第五個寄存器波特率寄存器
UBRRL 和
UBRRH

相當于一個12位的二進制數(shù):低8位是UBRRL
高4位是(8:11)是UBRRH的低四位。
解釋:UCSRC寄存器與UBRRH 寄存器公用相同的I/O地址。對該寄存器的訪問,請參見P162 訪問
UBRRH/RCSRC寄存器。
我們計算波特率的時候只要將計算出的值的低8位寫入這個UBRRL就行了。高8位寫入UBRRH
URSEL 這位我們不用管編譯器自動處理好。



下面的表格就粘貼了太累了!
下面就講講怎樣使用這個USART、、、
---------------------------------------------------------------
第一步:設置波特率
#define F_CPU 16000000
#define BAUD 9600
UBRRH = (FOSC / BAUD0/16-1)/256
UBRRL = (FPSC/BAUD0/16-1)%6
第二步:使能發(fā)送、接受接受完成中斷
UCSRB |= (1<<
RXEN)|(1<<TXEN)|(1<<RXCIE);
第三步:使能全局中斷
sei();
第四步:查詢方式發(fā)送、中斷方式接受
發(fā)送: while(!(UCSRA & (1<< UDRE))); UDR
=c;
接受中斷:c = UDR ;
波特率怎么算的呢?在UART 下的時鐘產(chǎn)生 下有波特率發(fā)生器下圖

正常我們使用非倍速的時候

equations 方程 calculating 計算
一個是波特率的計算公式一個是UBRR值的計算公式 這個UBRR
就是上面那個波特率寄存器(UBRRL UBRRH拼接起來顯示的數(shù)值)。 UBRR
的值就等于主頻除以波特率 再減 1. 而我們就是采用宏定義的方法定義主頻 和 波特率
UBRR = 主頻 / 波特率/ 16
-1 由于是UBBRH 整除256
取出高8位
可以理解右移掉低 8位
UBRR = 主頻 / 波特率/ 16
-1 由于是UBBRH 求余256
取出高8位
左移掉 高8位
用宏定義的好處 修改波特率方便。
實際演示下
編譯如下代碼:

然后下載進入,打開串口調(diào)試工具 選擇對應的COM我的COM3 和COM4
而COM4是仿真器用了所以我選擇COM3 波特率選擇9600
校驗位 我們選NO 第四欄 8位 我們選1位 。我們一般把16進制給勾上 ,16進制顯示
16進制發(fā)送給勾上。(不然的話它自動查找ASCII碼表顯示對應的字符,將字符顯示出來)然后點擊清空從填 ,現(xiàn)在驗證下
反正我測試接受到的都是0 不知道為什么?
其實9600的波特率每秒最多發(fā)送多少字符 是9600 /10
960個字符因此串行速度還是非常快的
這就是串口發(fā)送的程序我們通常寫成一個函數(shù)

中斷方式使用USART步驟
第一步:設置波特率
#define F_CPU 16000000
#define BAUD 9600
UBRRH = (F_CPU/BAUD/16-1)/256
UBRRL = (F_CPU/BAUD/16-1)%6
第二步:使能發(fā)送 、接受、接受完成中斷
UCSRRB |=
(1<<RXEN)|(1<<TXEN)|(1<<RICIE);
第三步:使能全局中斷
sei();
第四步:查詢方式發(fā)送、中斷方式接受
發(fā)送: while(!(UCSRA
&(1<<UDRE)));
UDR =c;
接受中斷:c = UDR;
如果用中斷接受必須在GCC單片機程序 找中斷向量名稱
接受中斷完成如下圖

SIG_UART_RECV呵呵
給帶更改如下

中斷接受、就講到這里!
氣死人了,這個教程我實驗不成功、、、