⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 avr单片机spi通讯实例程序.txt

📁 AVR单片机SPI通讯实例程序,一个SPI的实例
💻 TXT
字号:
 
本人的一个SPI的实例,通过SPI实现两机通讯, 采用中断方式实现双全工通讯。
  本例用两MEGA8515实现,连接为: 
    MISO----MISO 
    MOSI----MOSI 
    SCK ----SCK 
    /SS ----/SS 
  将要发送的数据加载到发送缓冲区的函数fill_tx_buffer和从接收缓冲区读出数据的函数read_rx_buffer未给出,根据各自需求请自己完成。 

#define SPI_RX_BUFFER_SIZE 10 
#define SPI_RX_BUFFER_MASK ( SPI_RX_BUFFER_SIZE - 1 ) 
#define SPI_TX_BUFFER_SIZE 10 
#define SPI_TX_BUFFER_MASK ( SPI_TX_BUFFER_SIZE - 1 ) 
#define SET_SPI_MODE PORTB.4 
#define SPI_MODE PINB.4 

static unsigned char SPI_RxBuf[SPI_RX_BUFFER_SIZE]; 
static volatile unsigned char SPI_RxHead; 
static unsigned char SPI_TxBuf[SPI_TX_BUFFER_SIZE]; 
static volatile unsigned char SPI_TxHead; 
//****************************************** 
// SPI 中断服务程序 
//****************************************** 
interrupt [SPI_STC] void spi_isr(void) 
{ 
unsigned char data; 
if(spi_m==0)                         //如果spi_m为0,表明是接收状态 
{ 
  data = SPDR;                       //读入接受到的数据 
    SPI_RxBuf[SPI_RxHead-1] = data;         //将接收到的数据存入接收缓存区 
    if ( SPI_RxHead == SPI_RX_BUFFER_MASK )   //如果是接收帧的最后一个数据   
    { 
      SPI_RxHead = 0;                 //已接收数据还原 
      MSTR=1;                       //接收完成,将SPI设回主方式 
      spi_trans_com=1;                 //置接收完成标志 
    } 
    else 
    {   
      SPI_RxHead++;                   //已接收数据计数器加1 
    } 
  
} 
else                               //如果spi_m为1,表明是发送状态 
  { 
                          
    if ( SPI_TxHead <= SPI_TX_BUFFER_MASK)   //如果要发送的数据还未全部发完 
    {   
      SPDR = SPI_TxBuf[SPI_TxHead];       //从发送缓存区取数发送 
      SPI_TxHead++;                   //已发送数据计数器加1 
    } 
    else                         //如果要发送的数据已全部发完 
      { 
      SPI_TxHead=0;                 //已发送数据计数器还原 
      DDRB.4=0; 
      SET_SPI_MODE=1;               //释放总线,以便接收方进入主发送。 
      spi_m=0;                     
      spi_sending=0;                 //清空发送中标记 
      } 
  
  } 

} 

//****************************************** 
// SPI 初始化 
//****************************************** 
void InitSPI(void) 
{ 

SPCR=0x52; 
SPI_RxHead = 0; 
SPI_TxHead = 0; 

} 

//****************************************** 
//发送数据 
//****************************************** 
void spi_send(void) 
{ 
if(spi_sending==0)     //发送中标记为0,表明spi发送空闲 
  { 
  
  fill_tx_buffer();   //调用fill_tx_buffer函数,将要发送的数据加载到发送缓冲区 
  while(PINB.4==0)   //如果PINB.4为低,表明总线被接受方占用,等待直至接受方发送完成。 
  {;} 
  
  InitSPI();       //初始化spi为主方式 
  DDRB.4=1; 
  SET_SPI_MODE=0;   //将PORTB.4拉低,强迫接收方进入从接收方式 
  spi_m=1;         //置spi_m标志表明为发送状态 
  delay_us(10); 
  spi_sending=1;     //置spi_sending标志表明发送进行中 
  SPDR=0xFF;       //开始发送,接收方接收到的第一个数据为0xFF应忽略 
  SPIE=1;         //开SPI中断, 
  SPI_TxHead = 0;   //已发送数据计数器清0 
  } 
} 

void main(void) 
{ 

... 
while(1) 
{ 
  ... 
  
  if(spi_trans_com==1) //如果接收完成标志为1,表明有所数据已接收 
  { 
    read_rx_buffer(); //调用read_rx_buffer函数,将接收到的数据从接收缓冲区读出 
    spi_trans_com=0; //读完清除接收完成标志 
  } 
  ... 

} 

}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -