基于ARM的nRF905发送和接收。
此代码运行在LPC系列单片机上。
nRF905.c
#include <stdint.h>
#include "nRF905.h"
#define nRF905_DR 1UL << 10 /* P2.10 DR */
#define nRF905_TX_EN 1UL << 3 /* P2.3 TXE */
#define nRF905_TRX_CE 1UL << 4 /* P2.4 CE */
#define nRF905_PWR_UP 1UL << 5 /* P2.5 PW */
#define nRF905_CSN 1UL << 6 /* P2.6 CSN */
/
#define ByteLength 32
extern uint8_t RecBuf[100];
/
void GPIO_Init(void)
{
LPC_PINCON->PINSEL4 = LPC_PINCON->PINSEL4 | (0x01 << 20); /* GPIO_P2.10(DR) PIN is EINT3 */
LPC_PINCON->PINSEL4 = LPC_PINCON->PINSEL4 & (~(0x03 << 6)); /* GPIO_P2.3 (TXE) PIN */
LPC_PINCON->PINSEL4 = LPC_PINCON->PINSEL4 & (~(0x03 << 8)); /* GPIO_P2.4 (CE) PIN */
LPC_PINCON->PINSEL4 = LPC_PINCON->PINSEL4 & (~(0x03 << 10)); /* GPIO_P2.5 (PW) PIN */
LPC_PINCON->PINSEL4 = LPC_PINCON->PINSEL4 & (~(0x03 << 12)); /* GPIO_P2.6 (CSN) PIN */
LPC_GPIO2->FIODIR |= nRF905_TX_EN|nRF905_TRX_CE|nRF905_CSN|nRF905_PWR_UP; /* GPIO as Output */
LPC_GPIO2->FIODIR &= ~(nRF905_DR); /* GPIO as Input */
}
///
/*********************************************************************************************************
** Function name: DelayNS
** Descriptions: 长软件延时
** input parameters: uiDly延时控制值,值越大,延时越长
** output parameters: 无
** Returned value: 无
*********************************************************************************************************/
void DelayNS (uint32_t uiDly)
{
uint32_t i;
for(; uiDly > 0; uiDly--){
for(i = 0; i < 50000; i++);
}
}
///
void nRF905_PowDown_SPI(void) /* Enter Power down and SPI programming. */
{
LPC_GPIO2->FIOCLR = LPC_GPIO2->FIOCLR | nRF905_PWR_UP;
DelayNS(1);
}
///
void nRF905_StandBy_SPI(void) /* Enter Standby and SPI programming. */
{
LPC_GPIO2->FIOSET = LPC_GPIO2->FIOSET | nRF905_PWR_UP;
LPC_GPIO2->FIOCLR = LPC_GPIO2->FIOCLR | nRF905_TRX_CE;
DelayNS(1);
}
void nRF905_ShockBurstRx(void) /* Enter ShockBurst RX. */
{
LPC_GPIO2->FIOSET = LPC_GPIO2->FIOSET | nRF905_PWR_UP;
LPC_GPIO2->FIOSET = LPC_GPIO2->FIOSET | nRF905_TRX_CE;
LPC_GPIO2->FIOCLR = LPC_GPIO2->FIOCLR | nRF905_TX_EN;
DelayNS(1);
}
void nRF905_ShockBurstTx(void) /* Enter ShockBurst TX. */
{
LPC_GPIO2->FIOSET = LPC_GPIO2->FIOSET | nRF905_PWR_UP;
LPC_GPIO2->FIOSET = LPC_GPIO2->FIOSET | nRF905_TRX_CE;
LPC_GPIO2->FIOSET = LPC_GPIO2->FIOSET | nRF905_TX_EN;
DelayNS(1);
}
//
void EINT3_IRQHandler()
{ /* 进入中断取反LED */
//IRQDisable();
LPC_GPIOINT->IO2IntClr = (1UL << 19);
Receiver(RecBuf);
LPC_SC->EXTINT = 0x08; /* 清中断标志 */
LPC_GPIOINT->IO2IntEnF = (1UL << 19);
//IRQEnable();
// VICVectAddr = 0x00; /* 通知VIC中断处理结束 */
}
//
void Config905() //配置905寄存器
{
uint8_t i;
uint8_t Init905Buf[10]={
0x6C, //CH_NO,配置频段在433.2MHZ
0x0C, //输出功率为10db,重发,节电为正常模式
0x44, //地址宽度设置,为4字节
ByteLength,ByteLength, //接收发送有效数据长度为32字节
0xE7,0xE7,0xE7,0xE7, //接收地址
0xDE, //CRC充许,16位CRC校验,外部时钟信号使能,16M晶振
};
uint8_t *Str;
Str = Init905Buf;
nRF905_StandBy_SPI(); // 进入StandBy和SPI编程模式
LPC_GPIO2->FIOCLR |= nRF905_CSN; // Spi enable for write a spi command
DelayNS(1);
nRF905_SpiRW(0x00); // Write config command
for(i=0;i<10;i++)
{
nRF905_SpiRW(*Str++);
}
DelayNS(1);
LPC_GPIO2->FIOSET |= nRF905_CSN; // Disable Spi
nRF905_ShockBurstRx();
//UART0_SendStr ("Config905 OK");
}
/
void nRF905Init(void) ///905初始化
{
GPIO_Init();
Config905();
Config905();
//InterruptInit();
}
/*
;写config命令 :00H
;读config命令 ;10H
;写发射数据命令:20H
;读发射数据命令:21H
;写发射地址命令:22H
;读发射地址命令:23H
;读接收数据命令:24H
*/
///
uint8_t nRF905_SpiRW(uint8_t data) //SPI读写一体化函数
{
LPC_SPI->SPDR = data;
while((LPC_SPI->SPSR & 0x80)==0);
return (LPC_SPI->SPDR);
}
/
void nRF905_SpiSendStr (uint8_t *str) //SPI0发送字符串
{
uint8_t i = 0;
while(i < ByteLength)
{
nRF905_SpiRW(*str++); // 发送数据
i++;
}
}
//
void nRF905_SpiTest(void) //测试:通过读配置,判断SPI操作是否正确
{
uint8_t i;
uint8_t ConfigBuf[11];
LPC_GPIO2->FIOCLR |= nRF905_CSN;
nRF905_SpiRW(0x10); //读配置
for (i=0;i<10;i++)
{
ConfigBuf[i]= nRF905_SpiRW(0);//read from nrf905
//UART0SendByte(ConfigBuf[i]);
}
LPC_GPIO2->FIOSET |= nRF905_CSN;
}
/
void nRF905_ReadData(uint8_t *Str)
{
uint8_t i = 0;
LPC_GPIO2->FIOCLR |= nRF905_CSN;
nRF905_SpiRW(0x24); //读RxPayload //RRP=0x24
while(i < ByteLength)
{
(*Str++) = nRF905_SpiRW(0);//read...
i++;
}
LPC_GPIO2->FIOSET |= nRF905_CSN;
}
///
void nRF905_SendData(uint8_t *Str)
{
nRF905_StandBy_SPI() ;
LPC_GPIO2->FIOCLR |= nRF905_CSN;
nRF905_SpiRW(0x20); //写TxPayload //0x20
nRF905_SpiSendStr(Str);
LPC_GPIO2->FIOSET |= nRF905_CSN;
DelayNS(1);
LPC_GPIO2->FIOCLR |= nRF905_CSN;
nRF905_SpiRW(0x22); //写Tx地址 //0x22
nRF905_SpiRW(0xE7);
nRF905_SpiRW(0xE7);
nRF905_SpiRW(0xE7);
nRF905_SpiRW(0xE7);
LPC_GPIO2->FIOSET |= nRF905_CSN;
nRF905_ShockBurstTx();
DelayNS(1);
}
//
void Receiver(uint8_t *Str)
{
uint8_t Flag[ByteLength] = "OK";
static uint8_t i = 0;
nRF905_StandBy_SPI();
nRF905_ReadData(Str);//读出...
//UART0SendStr(Str);
if (i == 0)
{
if (*Str == 'A' &&*(Str+1)=='T')
{
DelayNS(500);
Transmitter( Flag);
}
}
i = 1;
nRF905_ShockBurstRx();
}
//
void Transmitter(uint8_t *Str)
{
uint8_t i;
//IRQDisable();
nRF905_SendData(Str);//发送数据
while((LPC_GPIO2->FIOPIN&nRF905_DR)== 0);
DelayNS(1);
nRF905_ShockBurstRx();//重新回到接收状态
//IRQEnable();
NVIC_EnableIRQ(EINT3_IRQn);
}
nRF905.h
#ifndef __NRF905_H__
#define __NRF905_H__
#include <stdint.h>
void GPIO_Init(void);
void nRF905_PowDown_SPI(void);
void nRF905_StandBy_SPI(void);
void nRF905_ShockBurstRx(void);
void nRF905_ShockBurstTx(void);
uint8_t nRF905_SpiRW(uint8_t data);
void Config905(void);
void nRF905_SpiSendStr (uint8_t *str);
void nRF905_SpiTest(void);
void nRF905_ReadData(uint8_t *Str);
void nRF905_SendData(uint8_t *Str);
void Receiver(uint8_t *Str);
void Transmitter(uint8_t *Str);
void nRF905Init(void);
void InterruptInit(void);
#endif //__NRF905_H__