STM32使用NRF2401进行数据传送

NRF2401是一款由Nordic Semiconductor公司生产的单片射频收发芯片,以下是关于它的详细介绍:

一、主要特点

  1. 工作频段:NRF2401工作于2.4~2.5GHz的ISM(工业、科学和医疗)频段,该频段无需申请即可使用,广泛应用于各种无线通信设备。
  2. 内置功能模块:芯片内置了频率合成器、功率放大器、晶体振荡器和调制器等功能模块,使得其能够独立完成射频信号的收发处理。
  3. 低功耗设计:NRF2401具有极低的能耗,在-5dBm的功率发射时,工作电流仅为10.5mA;在接收模式下,工作电流为18mA。此外,它还支持多种低功率工作模式,进一步延长了电池使用寿命。
  4. 多通道通信:NRF2401支持多达125个数据通道,通道切换时间小于200微秒,满足多点通讯和调频需求。
  5. 高速数据传输:数据传输速率可达250Kbps或1Mbps(某些版本可能支持更高的速率,如2Mbps),适用于需要快速数据传输的应用场景。
  6. 自动重传和CRC校验:NRF2401支持自动检测和重发丢失的数据包,以及硬件CRC校验功能,提高了数据传输的可靠性和稳定性。

二、工作模式

NRF2401具有多种工作模式,包括收发模式、配置模式、空闲模式和关机模式。这些模式由PWR_UP、CE和CS三个引脚控制。
NRF24L01 芯片内部有状态机,控制着芯片在不同工作模式之间的转换。
NRF24L01 可配置为 Shutdown 、 Standby 、 Idle-TX 、 TX 和 RX 五种工作模式。

2.1、Shutdown 工作模式
在 Shutdown 工作模式下, Si24R1 所有收发功能模块关闭,芯片停止工作,消耗电流最小,但所有内部寄存器值和 FIFO 值保持不变,仍可通过 SPI 实现对 寄存器的读写。设置 CONFIG 寄存器的 PWR_UP 位的值为 0 ,芯片立即返回到 Shutdown 工作模式。
2.2、Standby 工作模式。
在 Standby 工作模式,只有晶体振荡器电路工作,保证了芯片在消耗较少电流的同时能够快速启动。设置 CONFIG 寄存器下的 PWR_UP 位的值为 1 ,芯片待时钟稳定后进入 Standby 模式。芯片的时钟稳定时间一般为 1.5~2ms ,与晶振的性能有关。当引脚 CE=1 时,芯片将由 Standby 模式进入到 Idle-TX 或 RX 模式,当 CE=0 时,芯片将由 Idle-TX 、 TX 或 RX 模式返回到 Standby 模式。
2.3、Idle-TX 工作模式
在 Idle-TX 工作模式下,晶体振荡器电路及时钟电路工作。相比于 Standby 模式,芯片消耗更多的电流。当发送端 TX FIFO 寄存器为空,并且引脚 CE=1 时,芯片进入到 Idle-TX 模式。在该模式下,如果有新的数据包被送到 TX FIFO 中,芯片内部的电路将立即启动,切换到 TX 模式将数据包发送。
在 Standby 和 Idle-TX 工作模式下,所有内部寄存器值和 FIFO 值保持不变, 仍可通过 SPI 实现对寄存器的读写。
2.4、TX 工作模式
当需要发送数据时,需要切换到 TX 工作模式。芯片进入到 TX 工作模式的条件为:TX FIFO 中有数据, CONFIG 寄存器的 PWR_UP 位的值为 1 , PRIM_RX 位的值为 0 ,同时要求引脚 CE 上有一个至少持续 10us 的高脉冲。芯片不会直接由 Standby 模式直接切换到 TX 模式,而是先立即切换到 Idle-TX 模式,再由 Idle-TX 模式自动切换到 TX 模式。 Idle-TX 模式切换到 TX 模式的时间为 120us~130us 之间,但不会超过 130us 。单包数据发送完成后,如果 CE=1, 则由 TX FIFO 的状态来决定芯片所处的工作模式,当 TX FIFO 还有数据,芯片继续保持在TX 工作模式,并发送下一包数据;当 TX FIFO 没有数据,芯片返回 Idle-TX 模式;如果 CE=0 ,立即返回 Standby 模式。数据发射完成后,芯片产生数据发 射完成中断。
2.5、RX 工作模式
当需要接收数据时,需要切换到 RX 工作模式。芯片进入到 RX 工作模式的条件为:设置寄存器 CONFIG 的 PWR_UP 位的值为 1 , PRIM_RX 位的值为 1 ,并且引脚 CE=1。芯片由 Standby 模式切换到 RX 模式的时间为 120~130us。当接 收到数据包的地址与芯片的地址相同,并且 CRC 检查正确时,数据会自动存入 RX FIFO,并产生数据接收中断。芯片最多可以同时存三个有效数据包,当 FIFO 已满,接收到的数据包被自动丢掉。
在接收模式下,可以通过 RSSI 寄存器检测接收信号功率。当接收到的信号 强度大于-60dBm 时, RSSI 寄存器的 RSSI 位的值将被设置为 1 。否则, RSSI=0 。
RSSI 寄存器的更新方法有两种:当接收到有效的数据包后, RSSI 会自动更新,此外,将芯片从 RX 模式换到 Standby 模式时 RSSI 也会自动更新。 RSSI 的值会随温度的变化而变化,范围在±5dBm 以内。

三、数据控制协议

四、代码参考

完整代码下载链接: https://download.csdn.net/download/qq_26043945/90412833

cs 复制代码
uint8_t SPI_RW(uint8_t byte){    
	// 用于存储接收到的数据
	uint8_t receivedData;
	// 发送缓冲区,指向要发送的数据
	const uint8_t *txBuf = &byte; 
	// 接收缓冲区,指向用于存储接收数据的变量
	uint8_t *rxBuf = &receivedData; 

	// 使用HAL库函数进行SPI通信,发送和接收数据
	HAL_StatusTypeDef status = HAL_SPI_TransmitReceive(&hspi2, txBuf, rxBuf, 1, 100);

	// 检查通信状态,这里简单处理为不检查(实际应用中应该检查)
	// if (status != HAL_OK) {
	//     // 处理错误情况
	// }

	// 返回接收到的数据
	return receivedData;

}




/********************************************************
函数功能:NRF2401引脚初始化                
入口参数:无
返回  值:无
*********************************************************/
void NRF2401_Init(void)
{
	//将CE(Chip Enable)引脚置低电平,禁用NRF2401芯片
	NRF_CE_0;
	//将CSN(Chip Select Not)引脚置高电平,禁用SPI通信
	NRF_CS_1;
	//将IRQ(Interrupt Request)引脚置高电平,准备接收中断信号
	NRF_IRQ_1;
}


/********************************************************
函数功能:写寄存器的值(单字节)                
入口参数:reg:寄存器映射地址(格式:WRITE__REG|reg)
					value:寄存器的值
返回  值:状态寄存器的值
*********************************************************/
uint8_t NRF2401_Write_Reg(uint8_t reg, uint8_t value)
{
	uint8_t status;

	//将CSN(Chip Select Not)引脚置低电平,启用SPI通信
	NRF_CS_0;
	status = SPI_RW(reg);				
	SPI_RW(value);
	
	//将CSN(Chip Select Not)引脚置高电平,禁用SPI通信
	NRF_CS_1;
	
	return(status);
}


/********************************************************
函数功能:写寄存器的值(多字节)                  
入口参数:reg:寄存器映射地址(格式:WRITE__REG|reg)
					pBuf:写数据首地址
					bytes:写数据字节数
返回  值:状态寄存器的值
*********************************************************/
uint8_t NRF2401_Write_Buf(uint8_t reg, const uint8_t *pBuf, uint8_t bytes)
{
	uint8_t status,byte_ctr;

	//将CSN(Chip Select Not)引脚置低电平,启用SPI通信
  NRF_CS_0;
  status = SPI_RW(reg);                          
  for(byte_ctr=0; byte_ctr<bytes; byte_ctr++)     
    SPI_RW(*pBuf++);   

	//将CSN(Chip Select Not)引脚置高电平,禁用SPI通信
	NRF_CS_1;
  return(status);       
}							  					   


/********************************************************
函数功能:读取寄存器的值(单字节)                  
入口参数:reg:寄存器映射地址(格式:READ_REG|reg)
返回  值:寄存器值
*********************************************************/
uint8_t NRF2401_Read_Reg(uint8_t reg)
{
 	uint8_t value;

	//将CSN(Chip Select Not)引脚置低电平,启用SPI通信
	NRF_CS_0;
	SPI_RW(reg);			
	value = SPI_RW(0);
	
	//将CSN(Chip Select Not)引脚置高电平,禁用SPI通信
	NRF_CS_1;

	return(value);
}


/********************************************************
函数功能:读取寄存器的值(多字节)                  
入口参数:reg:寄存器映射地址(READ_REG|reg)
					pBuf:接收缓冲区的首地址
					bytes:读取字节数
返回  值:状态寄存器的值
*********************************************************/
uint8_t NRF2401_Read_Buf(uint8_t reg, uint8_t *pBuf, uint8_t bytes)
{
	uint8_t status,byte_ctr;

	//将CSN(Chip Select Not)引脚置低电平,启用SPI通信
  NRF_CS_0;
  status = SPI_RW(reg);                           
  for(byte_ctr=0;byte_ctr<bytes;byte_ctr++)
    pBuf[byte_ctr] = SPI_RW(0);                   //读取数据,低字节在前
	
	//将CSN(Chip Select Not)引脚置高电平,禁用SPI通信
  NRF_CS_1;

  return(status);    
}


/********************************************************
函数功能:NRF2401接收模式初始化                      
入口参数:无
返回  值:无
*********************************************************/
void NRF2401_RX_Mode(void)
{
	NRF_CE_0;
	NRF2401_Write_Buf(WRITE__REG + RX_ADDR_P0, TX_ADDRESS, TX_ADR_WIDTH);	// 接收设备接收通道0使用和发送设备相同的发送地址
	NRF2401_Write_Reg(WRITE__REG + EN_AA, 0x01);               						// 使能接收通道0自动应答
	NRF2401_Write_Reg(WRITE__REG + EN_RXADDR, 0x01);           						// 使能接收通道0
	NRF2401_Write_Reg(WRITE__REG + RF_CH, 40);                 						// 选择射频通道0x40
	NRF2401_Write_Reg(WRITE__REG + RX_PW_P0, TX_PLOAD_WIDTH);  						// 接收通道0选择和发送通道相同有效数据宽度
	NRF2401_Write_Reg(WRITE__REG + RF_SETUP, 0x0f);            						// 数据传输率2Mbps,发射功率7dBm
	NRF2401_Write_Reg(WRITE__REG + CONFIG, 0x0f);              						// CRC使能,16位CRC校验,上电,接收模式
	NRF2401_Write_Reg(WRITE__REG + STATUS, 0xff);  												//清除所有的中断标志位
	NRF_CE_1;				                                    									// 拉高CE启动接收设备
}						


/********************************************************
函数功能:NRF2401发送模式初始化                      
入口参数:无
返回  值:无
*********************************************************/
void NRF2401_TX_Mode(void)
{
	NRF_CE_0;
	NRF2401_Write_Buf(WRITE__REG + TX_ADDR, TX_ADDRESS, TX_ADR_WIDTH);     // 写入发送地址
	NRF2401_Write_Buf(WRITE__REG + RX_ADDR_P0, TX_ADDRESS, TX_ADR_WIDTH);  // 为了应答接收设备,接收通道0地址和发送地址相同

	NRF2401_Write_Reg(WRITE__REG + EN_AA, 0x01);       											// 使能接收通道0自动应答
	NRF2401_Write_Reg(WRITE__REG + EN_RXADDR, 0x01);   											// 使能接收通道0
	NRF2401_Write_Reg(WRITE__REG + SETUP_RETR, 0x0a);  											// 自动重发延时等待250us+86us,自动重发10次
	NRF2401_Write_Reg(WRITE__REG + RF_CH, 40);         											// 选择射频通道0x40
	NRF2401_Write_Reg(WRITE__REG + RF_SETUP, 0x0f);    											// 数据传输率2Mbps,发射功率7dBm
	NRF2401_Write_Reg(WRITE__REG + CONFIG, 0x0e);      											// CRC使能,16位CRC校验,上电
	NRF_CE_1;
}

五、应用领域

NRF2401适用于多种无线通信的场合,如无线数据传输系统、无线鼠标、遥控开锁、遥控玩具等。其低功耗、高数据速率和多频道通信的特点使其成为物联网、智能家居和穿戴式设备等领域中备受推崇的无线解决方案之一。

相关推荐
sinat_3607048225 分钟前
STM32 看门狗
stm32·单片机·嵌入式硬件
亿道电子Emdoor27 分钟前
【ARM】MDK如何生成指定大小的bin文件,并指定空区域的填充数据
arm开发·stm32·单片机
mftang33 分钟前
STM32 CAN过滤器配置和应用方法介绍
stm32·单片机·嵌入式硬件
楼台的春风2 小时前
【详细讲解在STM32的UART通信中使用DMA机制】
stm32·单片机·嵌入式硬件·mcu·物联网·嵌入式·信息与通信
Chambor_mak3 小时前
stm32单片机个人学习笔记16(SPI通信协议)
stm32·单片机·学习
电子科技圈3 小时前
在低功耗MCU上实现人工智能和机器学习
人工智能·经验分享·科技·嵌入式硬件·mcu·物联网·机器学习
小白今天也很酷3 小时前
Python与MCU通信:串口数据采集及CSV/Excel存储方法
python·单片机·excel
海的预约4 小时前
51单片机-按键
单片机·嵌入式硬件·51单片机
【云轩】8 小时前
基于STM32与IFX007T的电机驱动全解析(无人机/机器人实战)
stm32·机器人·无人机