IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 嵌入式 -> 【4】stm32 驱动芯片实现单工和半双工通信,并对比分析(附代码) -> 正文阅读

[嵌入式]【4】stm32 驱动芯片实现单工和半双工通信,并对比分析(附代码)

0、项目背景

基于MCU的SPI驱动CMT2300A射频收发器,实现数据的发送和接收。

1、单工模式下数据的发送与接收

(1)STM32的驱动收发芯片CMT2300A,实现数据的发送端TX:

//单工模式下,数据发送
u8 Radio_Send_FixedLen(const u8 pBuf[], u8 len)
{
	u32 delay;
	CMT2300A_GoStby();             
	CMT2300A_ClearInterruptFlags();
	CMT2300A_ClearTxFifo();        
	CMT2300A_EnableWriteFifo();    //使能SPI写入FIFO,
	CMT2300A_WriteFifo(pBuf, len); // 将pBuf中的内容,写入到CMT2300A_FIFO
	CMT2300A_GoTx();               // 启动发送
	delay = 1000;                  	
	while(1)
	{
    //查询数据是否发送完成
    if(CMT2300A_ReadGpio3())  /* Read INT2, TX_DONE */
		{
			CMT2300A_ClearInterruptFlags();	
			CMT2300A_GoSleep();        							
			return 1; // 
		}		
		if(delay==0) 发送超时溢出,防止芯片死机,客户可根据实际开发情况调整超时时间
		{
			RF_Init(); //初始化CMT2300A的读写寄存器
			return 0; // 发送超时
		}		
		system_delay_100us(2);
		delay--;
	}
}

(2)STM32的驱动收发芯片CMT2300A,实现数据的接收端RX:


//单工模式:接收数据
u8 Radio_Recv_FixedLen(u8 pBuf[],u8 len)
{
#ifdef ENABLE_ANTENNA_SWITCH
      //查询一帧数据数据是否接收完成: PKT_DONE
      //先查询接收一包数据是否完成,再进入接收状态
      if(CMT2300A_ReadGpio2())  /* Read INT2, PKT_DONE */
		{
			CMT2300A_GoStby();             //进入睡眠模式
			CMT2300A_ReadFifo(pBuf,len);   //读FIFO中的内容
			CMT2300A_ClearRxFifo();        //清除接收FIFO
			CMT2300A_ClearInterruptFlags();
			CMT2300A_GoRx(); //进入接收模式						
			return 1;
		}
		return 0;
}
int main(void) //单收例程
{
	u8 i=0;	  
	  //CMT2300A是否存在
	  if(TRUE==CMT2300A_IsExist()) { 
        views_print_line(0, "CMT2300A ready RX");
      }	
	  while(1)
		{
		   if(Radio_Recv_FixedLen(g_rxBuffer,RF_PACKET_SIZE))
			 {
				  g_nRfRxtimeoutCount=0;  //清除 Time Out计数
				  g_nRecvCount++;         //接收计数			 
			    for(i=0;i<RF_PACKET_SIZE;i++) //Clear Buff
				   g_rxBuffer[i]=0;				 
			 }       
       if(g_nRfRxtimeoutCount>RF_RX_TIMEOUT) //根据实际应用可以调整Time Out
			 {
				    g_nRfRxtimeoutCount=0;
					CMT2300A_GoSleep();
					CMT2300A_GoStby();
					CMT2300A_ClearInterruptFlags();
					CMT2300A_ClearRxFifo();
					CMT2300A_GoRx();
			 }				 
		}		
}

2、半双工模式下数据的发送与接收

(1)MCU的驱动芯片CMT2300,实现数据发送:(数据发送完进入接收状态)

//半双工模式:数据发送,发送完数据后设备进入接收状态
void Radio_Send_FixedLen(const u8 pBuf[], int len)
{
	u32 delay;
	int sendlen = 0;	
	while(sendlen < len)
	{	
		CMT2300A_GoStby();
		CMT2300A_ClearInterruptFlags();
		CMT2300A_ClearTxFifo();
		CMT2300A_EnableWriteFifo();	
        //pBuf+sendlen写到CMT2300的FIFO中,一次写64byte	
		CMT2300A_WriteFifo(pBuf+sendlen, 64); 
		//进入发送状态
		CMT2300A_GoTx(); 
		delay = 1000; 
		while(1)
		{
			//发送完成标识:TX_DONE_FLG
			if(CMT2300A_MASK_TX_DONE_FLG & CMT2300A_ReadReg(CMT2300A_CUS_INT_CLR1)) 
			{					
				break;				
			}		
		}	
	}
	CMT2300A_ClearTxFifo();
	CMT2300A_ClearRxFifo();
	CMT2300A_ClearInterruptFlags();
	CMT2300A_GoStby();
	CMT2300A_EnableReadFifo();    //读FIFO使能		
	CMT2300A_GoRx();	    //发送完数据,进入接收状态
	CMT2300A_DelayMs(1);
}

(2)MCU的驱动芯片CMT2300,实现数据接收:

u8 Radio_Recv_FixedLen(u8 pBuf[],u8 len)
{
	if(CMT2300A_MASK_PKT_OK_FLG & CMT2300A_ReadReg(CMT2300A_CUS_INT_FLAG)) 
	{
		CMT2300A_GoStby();
		CMT2300A_ReadFifo(pBuf,len);//读FIFO中的数据,接收到的数据先存储在FIFO中
		CMT2300A_ClearRxFifo();
		CMT2300A_ClearInterruptFlags();
		CMT2300A_EnableReadFifo();
		CMT2300A_GoRx();		//进入接收状态		
		return 1;
	}
	return 0;
}

(3)两个设备之间进行半双工通信,主发,从收

主机发送数据,发送完成后,进入接收状态

从机接收主机发送的数据后,自己发送数据,发送数据完成后,进入接收状态

int32_t main(void)
{	
	while (1)
	{				
		if(timer1ms >= 1000)
		{
			//主机模式:发送
			if(MorS == MASTER)
			{		
				for(i = 0; i < RF_PACKET_SIZE; i++)
				{
					//UART串口发送数据:u_txBuffer[i]
					Uart_SendDataPoll(M0P_UART1,u_txBuffer[i]); 
				}
				if(IsExist_2300a)
				{
					//2300发送数据
					Radio_Send_FixedLen(g_txBuffer,FIFO_DEPTH);	
				}
			}					
		}
		//从机模式:接收
        //从机接收完主机发送的数据,自己再发送数据,发送数据完成后,进入接收状态
		if(IsExist_2300a)
		{
			//判断数据接收完成,再发送数据              
			if(Radio_Recv_FixedLen(g_rxBuffer,FIFO_DEPTH))
			{								
				if(MorS == SLAVE)//从机模式
				{
					//把2300接收到数据,复制到串口的发送缓存区
					//u_txBuffer <==  g_rxBuffer
					memcpy(u_txBuffer,g_rxBuffer+2,FIFO_DEPTH-2);
					//发送数据
					Radio_Send_FixedLen(g_txBuffer,RF_PACKET_SIZE);												
				}
				if(r_rf_frameindex < (RF_PACKET_SIZE / FIFO_DEPTH))
				r_rf_frameindex++;
			}
			//最后进入接收状态
			if(g_nRfRxtimeoutCount>RF_RX_TIMEOUT0) 
			{
				g_nRfRxtimeoutCount=0;
				CMT2300A_GoSleep();
				CMT2300A_GoStby();
				CMT2300A_ClearInterruptFlags();
				CMT2300A_ClearRxFifo();
				CMT2300A_GoRx();
			}			
		}	
	}		
}

  嵌入式 最新文章
基于高精度单片机开发红外测温仪方案
89C51单片机与DAC0832
基于51单片机宠物自动投料喂食器控制系统仿
《痞子衡嵌入式半月刊》 第 68 期
多思计组实验实验七 简单模型机实验
CSC7720
启明智显分享| ESP32学习笔记参考--PWM(脉冲
STM32初探
STM32 总结
【STM32】CubeMX例程四---定时器中断(附工
上一篇文章      下一篇文章      查看所有文章
加:2022-05-08 08:17:54  更:2022-05-08 08:18:57 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/26 3:44:27-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码