UART(Universal Asynchronous Receiver/Transmitter,通用異步收發傳輸器)的歷史可以追溯到早期計算機和通訊設備發展時期。是一種經典的串列通訊協議,已存在幾十年,並且在今天嵌入式系統中仍然廣泛使用。
早期通訊系統主要依賴電報和電話等技術,這些技術是同步通訊的初步形式。隨著數位技術發展,出現了需要將資料從一個設備傳輸到另一個設備的需求。
隨著電腦的發展,串列通信成為了一種普遍方式,用來讓電腦和周邊設備之間傳遞資料。最早期串列通信主要是使用 Modem 來進行資料的傳輸,這些系統使用同步通信,需要發送和接收雙方保持精確的時鐘同步。
在 20 世紀 70 年代,為了簡化通信過程,異步串列通信技術逐漸興起,這就是UART 的開始。UART技術允許設備之間不需要共享時鐘,而是通過開始位元(Start Bit)和結束位元(Stop Bit)來標記每個資料位元組的開始和結束,這種方式大大降低了同步通信的複雜性。
UART在 1980 年代和 1990 年代成為計算機串列埠(如RS-232標準)中常見的通信方式。這些介面廣泛應用於各種設備,包括鍵盤、滑鼠、打印機和早期的網絡通信設備。
隨著嵌入式系統和物聯網(IoT)的興起,UART依然是微控制器和各種感測器之間通訊的主要方式。因為硬體要求低、操作簡單而繼續在許多應用中保持流行。
UART 的基本通訊原理:
UART 是異步的,這意味著它的發送端和接收端不需要共享一個共同的時鐘信號來同步資料。取而代之,使用特殊的開始位和結束位來標記資料位元組的開頭和結尾。
在 UART 通訊中,資料是以 bit 的形式逐位傳送的。資料流的結構如下:
開始位元(Start Bit):發送端會首先發送一個開始位,這通常是低電位(0),表示資料傳輸的開始。
資料位元(Data Bits):接著會發送實際的資料位,通常是 5 至 9 位(常見是 8 位),這些位代表了要傳送的實際資料。
奇偶校驗位元(Optional Parity Bit):為了檢測傳輸過程中可能發生的錯誤,有時會加入一個奇偶校驗位來進行錯誤檢查。
停止位元(Stop Bit):資料位之後是停止位,這通常是一個或多個高電位(1),標誌著資料的結束。
鮑率是 UART 通訊中的一個關鍵參數,表示每秒傳輸的 bit 數。發送端和接收端必須使用相同的鮑率來確保資料傳輸的準確性。
UART 通訊是全雙工的,這意味著資料可以同時在兩個方向傳輸。每台設備都有一個發送端(TX)和一個接收端(RX),可以同時進行資料發送和接收。
UART(通用異步收發傳輸器)時,其實是在說一種讓兩台設備互相溝通的方式。這種溝通就像是在兩台設備之間搭建了一條無形的「橋」,讓它們可以互相傳遞訊息。
基本原理
UART 是一種串行通訊方式,意思是它一次傳輸一個 bits ,而不是同時傳輸多個 bits 。這就像排隊過橋,訊息中的每個 bits 都按順序依次傳送。這種傳輸方式用到的兩條主要線路是:
TX (Transmit,傳輸線):這是負責發送訊息的線路。當設備A要告訴設備B一些訊息時,它會通過自己的TX線把訊息傳送出去。這些訊息會沿著TX線走,傳到設備B的RX線。
RX (Receive,接收線):這是負責接收訊息的線路。設備B的RX線會接收到來自設備A的訊息,然後設備B就可以讀取並處理這些訊息。
當設備A有訊息要發送給設備B時,它會把訊息轉換成一連串的二進位數字(即 bits ),然後通過它的TX線發送出去。
設備B的RX線會「監聽」設備A的TX線,一旦有訊息到達,設備B就會接收這些 bits ,然後把它們轉換回原本的訊息。
UART 被稱為「異步」傳輸,意思是發送和接收不需要一個共同的時鐘信號來同步。
換句話說,設備A和設備B之間不需要在一開始就「握手」,說「嘿,我們開始同步計時吧!」 相反地,設備B只需確保它以和設備A相同的速度(鮑率)來接收訊息即可。這就像兩個人通過對講機說話,對方只要打開對講機就可以聽到。
準備三條杜邦線,分寫用下列的方式連接
IO5 ---> TX
IO21 ---> RX
TX1(機器 A) IO 5 連接到 RX2(機器 B) IO 21
RX1(機器 A) IO 21 連接到 TX2(機器 B) IO 5
GND(機器 A) 連接到 GND(機器 B)
如果有個場景:
機器A 發出清除螢幕訊息,機器B收到,就會清除螢幕,然後在螢幕上顯示,機器A: wb.cls(),然後回傳訊息通知機器A,工作已完成。機器A收到工作完成訊息,在螢幕上顯示機器B螢幕已清除。然後結束程式。
實驗方法:
您可以用一台桌機或筆電,使用兩條 USB 線,連接兩台不同的玩學機。舉例來說,一台玩學機用 Thonny 使用 COM5,另一台玩學機用 WiFiBoy Playground 程式,使用 COM12。這樣您就能模擬坐在兩台不同的電腦前面,進行互相通訊的實驗。
機器 A
# 兩台 WiFiBoy 連線通訊
# UART 通訊
# 我是機器A
# IO5 ---> TX
# IO21 ---> RX
from machine import UART, Pin
import time
# 設定 UART 1,鮑率為 9600
uart1 = UART(1, baudrate=9600, tx=Pin(5), rx=Pin(21))
led = Pin(16, Pin.OUT)
led.value(0)
print('Machine A Ready!')
# 發送清除螢幕的訊息給機器B
uart1.write("CLEAR_SCREEN")
# 等待機器B回應
while True:
if uart1.any():
response = uart1.read().decode('utf-8')
if response == "Clear Screen Done!":
wb.cls()
wb.str("Machine B Screen Cleaned", 10, 10, 2) # 在螢幕上顯示訊息
print("Received from Machine B:", response)
break
time.sleep(1)
機器 B
from machine import UART, Pin
import time
# 設定 UART 1,鮑率為 9600
uart1 = UART(1, baudrate=9600, tx=Pin(5), rx=Pin(21))
led = Pin(16, Pin.OUT)
led.value(0)
print('Machine B Ready!')
received_data = ""
while True:
if uart1.any(): # 檢查是否有資料可讀
led.value(1)
char = uart1.read().decode('utf-8') # 讀取一個字元並解碼
received_data += char # 將字元累積到 received_data 字串中
# 判斷是否收到了完整的命令
if "CLEAR_SCREEN" in received_data:
print("Clearing screen...")
wb.cls()
uart1.write("Clear Screen Done!") # 回傳訊息通知已完成
led.value(0)
time.sleep(0.1)
執行結果