1. 51單片機程序STC12c5a60s2串口通信程序 求詳細指導
雙串口 SendData_one是串口1發送 SendData_two是串口2發送 busy變數悉咐作用是發啟漏送睜旁純完成檢測標志,發送完成為0
2. 請問51單片機與51單片機之間的串口通信程序怎麼寫
1、查詢方式:
#include<reg51.h>
main()
{
unsigned char dat;
TMOD=0x20;
TH1=TL1=0xfd;
SCON=0x50;
TR1=1;
while(1)
{
if(RI)//接收
{
RI=0;
dat=SBUF;
}
SBUF=dat;//發送
while(!TI);
TI=0;
}
}
2、中斷方式:
#include<reg51.h>
unsigned char dat;
bit flag;
void uart_isr() interrupt 4
{
if(RI)//接收
{
RI=0;
dat=SBUF;
flag=1;
}
if(TI)TI=0;
}
main()
{
TMOD=0x20;
TH1=TL1=0xfd;
SCON=0x50;
TR1=1;
EA=1;
ES=1;
flag=0;
while(1)
{
if(flag)
{
SBUF=dat;
flag=0;
}
}
}
3. 51單片機串口通信的過程
單片機要用串口通信,用中斷是最好不過的了,因為單片機的內部運行速度非常快(相對串口來說的),發送後需要等好久,這段時間你可以安排它做別的事,當然你可以不用中斷,那就是由軟體來模擬串口進行,但這樣程序設計就更麻煩,單片機也不能做別的事了!
4. 51單片機串口接收中斷連續接收字元串,中斷一直佔有CPU時間直到字元串接收完畢
1樓薯譽的說法明顯不對,串口接收時有標志位RI,當串口接收到一個字元(8位)時,RI會自動被置1,此時CPU會從主程序轉去執行串列中斷,普通單串口51單片機一般為 interrupt 4 子程序,當執行完時會自動回滲冊到主程序繼續執行,因此自 interrupt 4子程序結尾要把RI清零,以接受下一個中斷,否則無法再接收下一個數據
interrupt 4主程序中一般處理方式是將接收寄存器SBUF中的數據轉存到事先定義的緩存中,如果是接受字元串時請叢手宏注意緩存需移位,常式如下:
void Serial_interrupt() interrupt 4
{
uchar temp;
rec_data[i++]=SBUF; // rec_data為事先定義的接收緩存,可以持續接收,直到你需要串口數據時來取為止
RI=0;//接收中斷信號清零,表示將繼續接收
}
5. 如何51單片機的串口發送多個數據和接受多個數據
你發送時,用循環控制,發幾個位元組,循環幾次。連續發送多個數據,都是小意思,也是最基本的了。
接收更好辦了,用中斷接收,中斷一次接收一次,你就保存一次唄,這有什麼難的。
6. 51單片機接收上位機發送的多個位元組的串口通信
具體程序可以參考樓下的常式
串口通信的概念非常簡單,串口按位(bit)發送和接收位元組。盡管比按位元組(byte)的並行通信慢,但是串口可以在使用一根線發送數據的同時用另一根線接收數據。它很簡單並且能薯豎夠實現遠距離通信。比如IEEE488定義並行通行狀態時,規定設備線總長不得超過20米,並且任意兩個設備間的長度不得超過2米;而對於串口而言,長度可達1200米。典型地,串口用於ASCII碼字元的傳輸。
通信使用3根線完成:(1)地線,(2)發送,(3)接收。由於串口通信是非同步的,埠能夠在一根線上發送數據同時在另一根線上接收數據。其他線用於握手,但是不是必須的。串口通信最重要的參數是波特率、數據位、停止位和奇偶校驗。對於兩個進行通信的埠,這些參數必須匹配:
a,波特率:這是一個衡量通信速度的參數。它表示每秒鍾傳送的bit的個數。例如300波特表示每秒鍾發送300個bit。當我們提到時鍾周期時,我們就是指波特率例如如果協議需要4800波特率,那麼時鍾運坦是4800Hz。這意味著串口通信在數據線上的采樣率為4800Hz。通常電話線的波特率為14400,28800和36600。波特率可以遠遠大於這些值,但是波特率和距離成反比。高波特率常常用於放置的很近的儀器間的通信,典型的例子就是GPIB設備的通信。
b,數據位:這是衡量通信中實際數據位的參數。當計算機發送一個信息包,實際的數據不會是8位的,標準的值是5、7和8位。如何設置取決於你想傳送的信息。比如,標準的ASCII碼是0~127(7位)。擴展的ASCII碼是0~255(8位)。如果數據使用簡單的文本(標准 ASCII碼),那麼每個數據包使用7位數據。每個包是指一個位元組,包括開始/停止位,數據位和奇偶校驗位。由於實際數據位取決於通信協議的選取,術語「包」指任何通信的情況。
c,停止位:用於表示單個包的最後一位。典型的值為1,1.5和2位。由於數據是在傳輸線上定時的,並且每一個設備有其自己的時鍾,很可能在通信中兩台設備間出現了小小的不同步。因此停止位不僅僅是表示傳輸的結束,並且提供計算機校正時鍾同步的機會。適用於停止位的位數越多,不同時鍾同步的容忍程度越大,但是數據傳輸率同時也越慢。
d,奇偶校驗位:在串口通信中一種簡單的檢錯方式。有四種檢錯方式:偶、奇、高和低。當然沒有校驗位也是可以的。對於偶和奇校驗的情況,串口會設置校驗位(數據位後面的一位),用一個值確保傳輸的數據有偶個或者奇個邏輯高位。例如,如果數據是011,那麼對於偶校驗,校驗位為0,保證邏輯高的位數是偶數個。
如果是奇校驗,校驗位位數悄大1,這樣就有3個邏輯高位。高位和低位不真正的檢查數據,簡單置位邏輯高或者邏輯低校驗。這樣使得接收設備能夠知道一個位的狀態,有機會判斷是否有雜訊干擾了通信或者是否傳輸和接收數據是否不同步。
7. 51單片機與PC機之間的硬體如何串口連接
單片機和微機通信的電氣標准要一致,微機串口一般是RS232電氣標准,所以要加電平轉換晶元,大多用MAX232,一般單片機實驗板上都提供這樣的標准串口。
要隱判或分別編寫上位機和下位機軟體程序,單沖亂片機程序參照常式、教科書進行編寫;上位機微機可採用VB,組態軟體,Labview等軟體編寫,一般若是簡單的通信,上位機程序編寫很簡單,例如VB中學會使用mscomm控制項,有VB最基礎知識的一天就能學會。
大可以沒有單片機,沒有MAX232,沒有串列介面這些硬體就可以實現學習並掌握單片機與微機之間的串口通信。proteus可以模擬單片機,也是主流軟體。
如今的筆記本電腦幾乎都沒灶伍有保留串口,而用USB介面取而代之,不過沒關系,有了虛擬串口和串口調試助手,這些都解決了。你可以搜索一下虛擬串口,真的很不錯的。
8. 如何實現2個51單片機之間通過串口通信的源程序
匯編編寫的模擬串口通信程序
T2作為波特率控制
UART_RXD 是硬中斷0或1口,如果能進入中斷,說明該線有一個起始位產生,進入中斷後調
用下面的接收程序。退出硬中斷之前還需要將硬中斷標志重新復位。
UART_TXD是任何其它IO即可。
UART_SEND:
PUSH IE
PUSH DPH
PUSH DPL
PUSH PSW
PUSH 00H
PUSH ACC
CLR EA
SETB UART_TXD ;START BIT
MOV R0,A
CLR TR2 ;TR2置1,計數器2啟動,時間計數啟動。
MOV A,RCAP2L;計數器2重新裝載值
MOV TL2,A ;置計數器2初值 ;T2需要重新裝載
MOV A,DPH
MOV A,RCAP2H
MOV TH2,A
MOV A,R0
SETB TR2 ;TR2置1,計數器
JNB TF2,$
CLR TF2
JNB TF2,$
CLR TF2
CLR UART_TXD ;START BIT
JNB TF2,$
CLR TF2
JNB TF2,$
CLR TF2
MOV R0,#08H
UART_SEND_LOOP:
RRC A
MOV UART_TXD,C ;8 BIT
JNB TF2,$
CLR TF2
JNB TF2,$
CLR TF2
DJNZ R0,UART_SEND_LOOP
SETB UART_TXD ;END BIT
JNB TF2,$
CLR TF2
JNB TF2,$
CLR TF2
POP ACC
POP 00H
POP PSW
POP DPL
POP DPH
POP IE
RET
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
UART_REC:
PUSH IE
PUSH DPH
PUSH DPL
CLR EA
CLR TR2 ;TR2置1,計數器2啟動,時間計數啟動。
MOV A,RCAP2L;計數器2重新裝載值
MOV TL2,A ;置計數器2初值 ;T2需要重新裝載
MOV A,DPH
MOV A,RCAP2H
MOV TH2,A
JB UART_RXD,$ ;REC
SETB TR2 ;TR2置1,計數器2啟動,時間計數啟動。
JNB TF2,$
CLR TF2 ;0.5 BIT
JNB TF2,$
CLR TF2 ;1 BIT
JNB TF2,$
CLR TF2 ;1.5 BIT
MOV C,UART_RXD
MOV ACC.0,C
JNB TF2,$
CLR TF2
JNB TF2,$
CLR TF2 ;2.5
MOV C,UART_RXD
MOV ACC.1,C
JNB TF2,$
CLR TF2
JNB TF2,$
CLR TF2 ;3.5
MOV C,UART_RXD
MOV ACC.2,C
JNB TF2,$
CLR TF2
JNB TF2,$
CLR TF2 ;4.5
MOV C,UART_RXD
MOV ACC.3,C
JNB TF2,$
CLR TF2
JNB TF2,$
CLR TF2 ;5.5
MOV C,UART_RXD
MOV ACC.4,C
JNB TF2,$
CLR TF2
JNB TF2,$
CLR TF2 ;6.5
MOV C,UART_RXD
MOV ACC.5,C
JNB TF2,$
CLR TF2
JNB TF2,$
CLR TF2 ;7.5
MOV C,UART_RXD
MOV ACC.6,C
JNB TF2,$
CLR TF2
JNB TF2,$
CLR TF2 ;8.5
MOV C,UART_RXD
MOV ACC.7,C
JNB TF2,$
CLR TF2 ;9.5
JNB UART_RXD,$ ;等待停止位,並重新復位計數器
SETB UART_RXD
POP DPL
POP DPH
POP IE
RET
補充回答:
串口調試
1. 發送:向匯流排上發命令
2. 接收:從匯流排接收命令,並分析是地址還是數據。
3. 定時發送:從內存中取數並向主機發送.
經過調試,以上功能基本實現,可以通過上位機對單片機進行實時控制。
程序如下:
//這是一個單片機C51串口接收(中斷)和發送常式,可以用來測試51單片機的中斷接收
//和查詢發送,發送沒有必要用中斷,因為程序的開銷是一樣的
#include <reg51.h>
#include<stdio.h>
#include <string.h>
#define INBUF_LEN 4 //數據長度
unsigned char inbuf1[INBUF_LEN];
unsigned char checksum,count3 , flag,temp,ch;
bit read_flag=0;
sbit cp=P1^1;
sbit DIR=P1^2;
int i;
unsigned int xdata *RAMDATA; /*定義RAM地址指針*/
unsigned char a[6] ={0x11,0x22,0x33,0x44,0x55,0x66} ;
void init_serialcomm(void)
{
SCON=0x50; //在11.0592MHz下,設置串列口波特率為9600,方式1,並允許接收
PCON=0x00;
ES=1;
TMOD=0x21; //定時器工作於方式2,自動裝載方式
TH0=(65536-1000)%256;
TL0=(65536-1000)/256;
TL1=0xfd;
TH1=0xfd;
ET0=1;
TR0=1;
TR1=1;
// TI=0;
EA=1;
// TI=1;
RAMDATA=0x1F45;
}
void serial () interrupt 4 using 3
{
if(RI)
{ RI=0;
ch=SBUF;
TI=1; //置SBUF空
switch(ch)
{
case 0x01 :printf("A"); TI=0;break;
case 0x02 :printf("B"); TI=0;break;
case 0x03 :printf("C"); TI=0;break;
case 0x04 :printf("D"); TI=0;break;
default :printf("fg"); TI=0;break;
}
}
}
//向串口發送一個字元
void timer0() interrupt 1 using 3{
// char i;
flag++;
TH0=0x00;
TL0=0x00;
if(flag==10)
{// cp=!cp;
// for(i=0;i<6;i++)
P2=0x25;
TI=1;
temp=*RAMDATA;
printf("%c",temp);
TI=0;
// RAMDATA--;
flag=0;
}
}
//主程序
main()
{
init_serialcomm(); //初始化串口
//向6264中送數據
{
*RAMDATA=0x33;
}
while(1)
{
*RAMDATA=0x33;;
}
}
調試需要注意的問題:
1. 發送過程:在發送時必須保證TI=1:即發送緩沖器為空,否則將導致數據發不出去,如果想強制發送可以用:TI=1.具體發送數據:利用printf(「abcd」);函數直接發送即可。
2. 接收過程:在接收時多選用中斷方式,這樣可以節約CPU的時間,提高效率,
9. 怎麼樣通過51單片機串口一次發送3個16進制數據
配置好串口,然後寫到SBUF裡面就能自動發送
10. 51單片機串口接收到一個字元串後怎樣從中提取想的內容請提供常式!
可以。
unsigned char buff[32];
unsigned int len;
unsigned char receiveByte()
{
while(RI==0); //等待接收數據
RI = 0;
return SBUF;
}
void receiveString()
{
unsigned char bbyte;
len = 0;
do
{
bbyte = receiveByte();
buff[len++] = bbyte;
}
while(bbyte!=0x00);
}
這世譽個程序可以搜啟段接旁拍受一個字元串,就是以00結尾的字元串。