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

📄 rf24l01.c

📁 C51单片机驱动程序源代码_RF24L01
💻 C
字号:

//-----------------------------------------------------------------------------
//
// Drive_24L01.c
//
//-----------------------------------------------------------------------------

#include "rf24l01.h"


//-----------------------------------------------------------------------------
//
// 各种全局变量定义
//
//-----------------------------------------------------------------------------


idata unsigned char radio_status;  
static unsigned char gnDataPipeNumber; 


//**********************************************************//
//
//  Function: Rf24L01_Reg_RW
//
//  Description:
//  Writes one byte to nRF24L01, and return the byte read
//  from nRF24L01 during write, according to SPI protocol
//
//  In/Out parameters:
//  In: 'byte', current byte to be written
//  Out: 'SPI0DAT', HW SPI mode, 'byte' SW SPI mode,
//
//**********************************************************//

// Spi函数
static unsigned char Rf24L01_Reg_RW(unsigned char byte)
{
		
  	  
	return 0;
}


//-----------------------------------------------------------------------------
//
//  Function: Rf24L01_WriteByte
//
//  Description:
//  Writes value 'value' to register 'reg'
//
//
//  In/Out parameters:
//  In: 'reg' register to write value 'value' to.
//  Return status byte.
//
//-----------------------------------------------------------------------------

unsigned char Rf24L01_WriteByte(unsigned char reg, unsigned char value)
{
	unsigned char status;

	CSN_LOW();

	status = Rf24L01_Reg_RW(reg);          // select register

	Rf24L01_Reg_RW(value);                 // ..and write value to it..

	CSN_HIGH();

	return(status);                        // return nRF24L01 status byte
}

//-----------------------------------------------------------------------------
//
//  Function: Rf24L01_WriteMultiByte
//
//  Description:
//  Writes contents of buffer '*pBuf' to nRF24L01
//  Typically used to write TX payload, Rx/Tx address
//
//
//  In/Out parameters:
//  In: register 'reg' to write, buffer '*pBuf*' contains
//  data to be written and buffer size 'buf_size' is #of
//  bytes to be written
//  Out: return nRF24L01 status byte.
//
//-----------------------------------------------------------------------------

unsigned char Rf24L01_WriteMultiByte(unsigned char reg, unsigned char *pBuf, unsigned char len)
{
	unsigned char status,i;

	CSN_LOW();

	status = Rf24L01_Reg_RW(reg);               // Select register to write to and read status byte

	for(i=0; i<len; i++)                        // then write all byte in buffer(*pBuf)
	{
		Rf24L01_Reg_RW(*pBuf++);
	}

	CSN_HIGH();

	return(status);                             // return nRF24L01 status byte
}

//-----------------------------------------------------------------------------
//
// Clear nRF24L01 IRQ flag(s)
//
//-----------------------------------------------------------------------------

unsigned char Rf24L01_Clear_IRQ(unsigned char irq_flag)
{
	return Rf24L01_WriteByte(WRITE_REG + STATUS, irq_flag);
}

//-----------------------------------------------------------------------------
//
// Flush TX FIFO
//
//-----------------------------------------------------------------------------

void Rf24L01_Flush_TX(void)
{
	Rf24L01_WriteByte(FLUSH_TX,0);
}

//-----------------------------------------------------------------------------
//
// Flush RX FIFO
//
//-----------------------------------------------------------------------------

void Rf24L01_Flush_RX(void)
{
	Rf24L01_WriteByte(FLUSH_RX,0);
}

//**********************************************************//
//
//  Function: Rf24L01_ReadByte
//
//  Description:
//  Read one byte from nRF24L01 register, 'reg'
//
//
//  In/Out parameters:
//  In: reg, register to read
//  Out: return reg_val, register value.
//
//**********************************************************//

unsigned char Rf24L01_ReadByte(unsigned char reg)
{
	unsigned char reg_val;

	CSN_LOW();

	Rf24L01_Reg_RW(reg);                    // Select register to read from..

	reg_val = Rf24L01_Reg_RW(0);            // ..then read registervalue

	CSN_HIGH();

	return(reg_val);                        // return register value
}

//-----------------------------------------------------------------------------
//
// switch PTX/PRX
//
//-----------------------------------------------------------------------------

void Rf24L01_RxTx_Switch(unsigned char bMode)
{
	unsigned char bConfig;

	CE_LOW();

	Rf24L01_Flush_RX();                //set TX/RX FIFO to be empty
	Rf24L01_Flush_TX();                //
	Rf24L01_Clear_IRQ(MASK_IRQ_FLAGS); //clear IRQ STATUS register

	bConfig = Rf24L01_ReadByte(CONFIG);

	if(bMode == PRX)
	{
		if((bConfig&0x01))
		{
			CE_HIGH();
			return;
		}

		bConfig &= 0xfe;
		bConfig |= 0x01;

		Rf24L01_WriteByte(WRITE_REG + CONFIG, bConfig);

		CE_HIGH();
	}
	else if(bMode == PTX)
	{
		if(!(bConfig&0x01))
		{
			return;
		}

		bConfig &= 0xfe;

		Rf24L01_WriteByte(WRITE_REG + CONFIG, bConfig);
	}
}



//**********************************************************//
//
//  Function: Rf24L01_ReadMultiByte
//
//  Description:
//  Reads 'bytes' #of bytes from register 'reg'
//  Typically used to read RX payload, Rx/Tx address
//
//
//  In/Out parameters:
//  In: 'reg', register to read from, '*pBuf' are buffer
//  the read bytes are stored to and 'bytes' are #of bytes
//  to read.
//  Out: return nRF24L01 status byte.
//
//**********************************************************//

static unsigned char Rf24L01_ReadMultiByte(unsigned char reg, unsigned char *pBuf, unsigned char len)
{
	unsigned char status,i;

	CSN_LOW();

	status = Rf24L01_Reg_RW(reg);           // Select register to write to and read status byte

	for (i=0;i<len;i++)
	{
		pBuf[i] = Rf24L01_Reg_RW(0);        // Perform Rf24L01_Reg_RW to read byte from nRF24L01
	}

	CSN_HIGH();

	return(status);                         // return nRF24L01 status byte
}

//-----------------------------------------------------------------------------
//
// Used in RX mode.
//
//-----------------------------------------------------------------------------

static void Rf24L01_RX(unsigned char *prx_buf)
{ 
	unsigned char gnRF_RecvLen;
	gnRF_RecvLen=Rf24L01_ReadByte(READ_PAYLAODLEN);
		
	if (prx_buf != NULL) Rf24L01_ReadMultiByte(RD_RX_PLOAD, prx_buf, gnRF_RecvLen); 
}

//-----------------------------------------------------------------------------



//-----------------------------------------------------------------------------

void Rf24L01_TX(unsigned char *ptx_buf,unsigned char nLen)
{

	Rf24L01_RxTx_Switch(PTX);

	Rf24L01_Flush_TX();		//clear 24L01 tx buffer

	Rf24L01_WriteMultiByte(WR_TX_PLOAD, ptx_buf, nLen);

	CE_PULSE();
} 
 


//-----------------------------------------------------------------------------
//
//  Function: Rf24L01_Polling_IRQ
//
//  Description:
//  Deal with IQR event with polling mode
//
//-----------------------------------------------------------------------------	 

static void rf_rdy_ov_interrupt(void) interrupt INTERRUPT_RFRDY {}

//---------------------------------------------------------------------------
static void rfirq_ov_interrupt(void) interrupt INTERRUPT_RFIRQ
{
	radio_status =0xFF;
}
//---------------------------------------------------------------------------

unsigned char Rf24L01_Polling_IRQ(unsigned char * rev_buf)
{
    unsigned char irq_status;

	if(radio_status == 0x00) 
	{
		if(Rf24L01_ReadByte(FIFO_STATUS) & MASK_RX_EMPTY) return IDLE;

        Rf24L01_RX(rev_buf);
        
        irq_status=Rf24L01_ReadByte(STATUS);

        gnDataPipeNumber=(irq_status>>1)&0x7;

        return (unsigned char)RX_DR;
	}

	radio_status = 0x00;

    irq_status=Rf24L01_ReadByte(STATUS);

    switch(irq_status&MASK_IRQ_FLAGS)
    {
        case MASK_RX_DR_FLAG:			//rf receive data
        {
            if(Rf24L01_ReadByte(FIFO_STATUS) & MASK_RX_EMPTY)
            {
                irq_status =IDLE;
            }
            else
            { 				
                Rf24L01_RX(rev_buf);
                gnDataPipeNumber=(irq_status>>1)&0x7;
                irq_status = (unsigned char)RX_DR;
            }

            break;
        }

        case MASK_TX_DS_FLAG: 			//send rf data success (with ack response)
        {
            irq_status = (unsigned char)TX_DS;            
            break;
        }

        case MASK_MAX_RT_FLAG:			//Maximum number of TX retries interrupt  If MAX_RT is set it must be cleared to enable further communication.
        {
            irq_status = (unsigned char)MAX_RT;	
            break;
        }

        case IDLE:
        {
            irq_status = (unsigned char)IDLE;
            break;
        }

	}

    if(Rf24L01_ReadByte(FIFO_STATUS) & MASK_RX_EMPTY)
        Rf24L01_Clear_IRQ(MASK_IRQ_FLAGS);

    return irq_status;

}


//-----------------------------------------------------------------------------

unsigned char Rf24L01_Set_Init(SetupData *drc)
{
    	unsigned char btemp; 	

	RFCKEN = 1;                                     // enable L01 clock
  	RF = 0;
	CE_LOW();

	Rf24L01_Flush_RX();                				//flush TX/RX FIFO to be empty
	Rf24L01_Flush_TX();                				//
	Rf24L01_Clear_IRQ(MASK_IRQ_FLAGS); 				//clear IRQ STATUS register

	//------------------------------------------------------
	//1 set config
	//------------------------------------------------------  
		//'comm config' default value:0000 1000
    	//bit7 must be 0;
   		//bit6,0--enable,RX interrupt enable,IRQ pin active low
    	//bit5,0--enable TX Succeed interrupt enable,IRQ pin active low
      	//bit4,0--eanble TX time over interrupt enable,IRQ pin active low
    	//bit3,CRC enable,if EN_AA be set,this bit will be forced to high
      	//bit2,CRC width,0--one byte,1--two bytes
       	//bit1,RF POWER ON/OFF,1--ON, 0--OFF
      	//bit0,transmmit mode: 1--PTX,0--PRX
	btemp =0x0e;	
	if (drc->nOn == Dev_Normal) btemp +=0x01; 		
	Rf24L01_WriteByte(WRITE_REG + CONFIG, btemp);

	//------------------------------------------------------
	//2 set ee_aa
	//------------------------------------------------------	
		//'Enable Auto Acknowledgment'
		// bit76 must be 00;
		// bit 5-0 response to Pip5-0; bit: 1-en, 0-disen
		// bit0 = 1;only enble pipe0   	
		// Enable Auto.Ack:Pipe0  

	Rf24L01_WriteByte(WRITE_REG + EN_AA, drc->nAutoAck);            

	//------------------------------------------------------
	//3 set en_rxaddr
	//------------------------------------------------------ 		  
		//'Enabled RX addresses', default 0000 0011
      	//bit76 must be 00;
   		//bit 5-0 response to Pip5-0, bit: 1-en, 0-disen
		//pipe rx enble,bit0 = 1,only enable pipe0 RX
	Rf24L01_WriteByte(WRITE_REG + EN_RXADDR, drc->nRecvAddr);  

	//------------------------------------------------------
	//4 set setup_aw
	//------------------------------------------------------
		//'address width',default 0000 0011
    	//bit765432 must be 000000;
      	//bit10,value must be 1~3, 1--3Bytes width,2--4Bytes,3--5Bytes
		//address width is 5 bytes;bit10: 00--illegal,01--3bytes,10--4bytes,11--5bytes
	Rf24L01_WriteByte(WRITE_REG + SETUP_AW, 0x03);

	//------------------------------------------------------
	//5 set setup_retr
	//------------------------------------------------------  
		//'Auto. Retransmite delay time and count', default 0000 0011
       	//delay time(bit7~3):(bit7~3+1)*250+86us;
     	//retran count(bit2~0):0--disenable retran,otherwise 1~15 times
		//0x10;    
		//retran delay time:250us+86us
		//drc->Retran;
	btemp = (drc->nART_Factor&0x0f)<<4;	 		
	btemp += (drc->nRetran > 15 ? 15 : drc->nRetran); 			
	Rf24L01_WriteByte(WRITE_REG + SETUP_RETR, btemp);

	//------------------------------------------------------
	//6 set rf_ch
	//------------------------------------------------------  
		//'rf frequency channel' 2400+rf_ch,default:0000 0010
		// bit7 must be 0
     	// bit6~0 rf frequency channel,one step deputy 1MHZ
    	// we use frequency at less than 2.49GHZ,beause WLAN use frequency band 2.4G~2.4835Ghz
      	// we choice rf_ch = 100; thats 2.5GHZ
		// default we choice frequency range 2.495GHz~2.513GHZ  channel
	if (drc->nChannel>122)
	{
		drc->nChannel = 0;
	} 	
		
 	Rf24L01_WriteByte(WRITE_REG + RF_CH, drc->nChannel);

	//------------------------------------------------------
	//7 set rf_setup
	//------------------------------------------------------ 
		//'RF setup' default 0000 1111
    	// bit7~4 must be 00000
      	// bit 3 data rate :0--1Mbps,1--2Mbps;
       	// bit 2~1 rf power:00,-18dbm,,01,-12dbm,,10,-6dbm,,11,0dbm
      	// bit 0 must be 1
	btemp =((drc->nPower&0x0f)>3 ? 3:(drc->nPower&0x0f))<<1;  
	btemp +=0x01;
	if((drc->nPower&0xf0)>0) btemp += 0x08;
	
	//btemp |= 0x20;	 
	Rf24L01_WriteByte(WRITE_REG + RF_SETUP, btemp);

	//------------------------------------------------------
	//8 set rx_addr_p0
	//------------------------------------------------------ 
		//pipe0 rx address buf 
	Rf24L01_WriteMultiByte(WRITE_REG + RX_ADDR_P0,drc->aAddr1,5);

	//------------------------------------------------------
	//9 set rx_addr_p1
	//------------------------------------------------------ 
		//'pipe1 rx payload width' 		
		//'pipe0 rx payload width' 0000 0000
     	//bit76 must be 00
      	//bit5~0,at less than must be one byte
     	//the most width is 32 bytes 
	if (drc->nLen>32)
	{
		drc->nLen = 32;
	}
	else if (drc->nLen == 0)
	{
		drc->nLen = 1;
	} 

	Rf24L01_WriteByte(WRITE_REG + RX_PW_P0, drc->nLen);	  

	btemp = drc->nRecvAddr;
	btemp = btemp>>1;
	if (btemp&1)
	{
		//81 get rx_addr_p1
		Rf24L01_WriteMultiByte(WRITE_REG + RX_ADDR_P1,drc->aAddr2,5);

		//91 get rx_pw_p1
		Rf24L01_WriteByte(WRITE_REG + RX_PW_P1, drc->nLen);
	}

	//------------------------------------------------------
	//10 set tx_addr
	//------------------------------------------------------ 
		//tx address buf	
	Rf24L01_WriteMultiByte(WRITE_REG + TX_ADDR,drc->aAddr1,5);

	
	//------------------------------------------------------
	//11 ACTIVATE
	//------------------------------------------------------ 
 	Rf24L01_WriteByte(ACTIVATE, 0x73); 

	//------------------------------------------------------
	//12 get FEATURE 
	//------------------------------------------------------
	Rf24L01_WriteByte(WRITE_REG + FEATURE, 0x05); 
	
	//------------------------------------------------------
	//13 get DYNPD
	//------------------------------------------------------
	Rf24L01_WriteByte(WRITE_REG + DYNPD, drc->nRecvAddr);


	RF = 1;	
	if(drc->nOn == Dev_Normal) 
	{
		CE_HIGH();
	}

	return 0;
}
//---------------------------------------------------------------------------
//
// End file
//
//---------------------------------------------------------------------------

⌨️ 快捷键说明

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