|
今晚學(xué)了一些SPI的資料,但玩單片機(jī)畢竟不能只看而不實(shí)踐,于是寫了個(gè)利用兩片AT89C51的GPIO接口軟件模擬SPI實(shí)現(xiàn)雙MCU通信的程序。
實(shí)現(xiàn)目標(biāo):
兩片AT89C51均通過軟件模擬SPI的方式建立通信,主機(jī)循環(huán)發(fā)送數(shù)值0~9,從機(jī)將接收到的數(shù)值顯示在數(shù)碼管上且將該數(shù)值返回給主機(jī),主機(jī)也將從機(jī)返回的數(shù)值顯示在數(shù)碼管上。
主機(jī)源碼:
#include<reg51.h>
#include<intrins.h>
sbit SCLK=P1^0;
sbit MOSI=P1^1;
sbit MISO=P1^2;
sbit SS=P1^3;
void Delay_ms() //延時(shí)一段時(shí)間
{
unsigned char i,j,k;
_nop_();
i=4;
j=129;
k=119;
do
{
do
{
while(--k);
}
while(--j);
}
while(--i);
}
void Delay1ms()
{
unsigned char i,j;
_nop_();
i=2;
j=199;
do
{
while(--j);
}
while(--i);
}
void SPI_M_Write(unsigned char dat) //主機(jī)發(fā)送數(shù)據(jù)
{
unsigned char i;
SS=0;
for(i=0;i<8;i++)
{
if(dat&0x80)
{
MOSI=1;
}
else
{
MOSI=0;
}
dat<<=1;
SCLK=1;
_nop_();
_nop_();
SCLK=0;
_nop_();
_nop_();
}
SS=1;
Delay1ms();
}
unsigned char SPI_M_Read() //主機(jī)接收數(shù)據(jù)
{
unsigned char i;
unsigned char dat=0;
SS=0;
for(i=0;i<8;i++)
{
dat<<=1;
dat|=MISO;
SCLK=1;
_nop_();
_nop_();
SCLK=0;
_nop_();
_nop_();
}
SS=1;
return dat;
}
void main()
{
unsigned char LEDS[]={0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x6F};
unsigned char i,temp;
SCLK=0;
P2=0x00;
while(1)
{
for(i=0;i<10;i++)
{
SPI_M_Write(i);
Delay_ms();
temp=SPI_M_Read();
P2=LEDS[temp];
Delay_ms();
}
}
}
從機(jī)源碼:
#include<reg51.h>
#include<intrins.h>
sbit SCLK=P1^0;
sbit MOSI=P1^1;
sbit MISO=P1^2;
sbit SS=P1^3;
void Delay_ms() //延時(shí)一段時(shí)間
{
unsigned char i,j,k;
_nop_();
i=4;
j=129;
k=119;
do
{
do
{
while(--k);
}
while(--j);
}
while(--i);
}
void SPI_S_Write(unsigned char dat) //從機(jī)發(fā)送數(shù)據(jù)
{
unsigned char i;
while(SS==1);
for(i=0;i<8;i++)
{
while(SCLK==0);
while(SCLK==1);
dat<<=1;
if(dat&0x80)
{
MISO=1;
}
else
{
MISO=0;
}
}
while(SS==0);
}
unsigned char SPI_S_Read() //從機(jī)接收數(shù)據(jù)
{
unsigned char i;
unsigned char dat=0;
while(SS==1);
for(i=0;i<8;i++)
{
while(SCLK==0);
while(SCLK==1);
dat<<=1;
dat|=MOSI;
}
while(SS==0);
return dat;
}
void main()
{
unsigned char LEDS[]={0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x6F};
unsigned char i,temp;
P2=0x00;
while(1)
{
for(i=0;i<10;i++)
{
temp=SPI_S_Read();
P2=LEDS[temp];
Delay_ms();
SPI_S_Write(i);
Delay_ms();
}
}
}
原理圖如下:
|
-
評分
-
查看全部評分
|