3558e9e64659ac7e7b13e8684c24948a2afc3ef0.svn-base 10 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262
  1. #ifndef __NRF24L01_H
  2. #define __NRF24L01_H
  3. //#include <reg52.h>
  4. #include <intrins.h>
  5. //#include "typedef.h"
  6. #include "Common.h"
  7. #include "Delay.h"
  8. typedef unsigned char uchar;
  9. //typedef unsigned char uint8;
  10. typedef unsigned char u8;
  11. typedef unsigned int uint;
  12. //typedef unsigned int uint16;
  13. typedef unsigned int u16;
  14. /****************************************NRF24L01端口定义***************************************/
  15. #if 0
  16. sbit CE = P2 ^ 3;
  17. sbit CSN = P2 ^ 4;
  18. sbit SCK = P2 ^ 5;
  19. sbit MOSI = P2 ^ 6;
  20. sbit MISO = P2 ^ 7;
  21. sbit IRQ = P3 ^ 3; //外部中断1
  22. #else
  23. #define CE P11
  24. #define CSN P15
  25. #define SCK P10
  26. #define MOSI P00
  27. #define MISO P01
  28. #define IRQ P03
  29. #endif
  30. /*********************************************NRF24L01*************************************/
  31. #define TX_ADR_WIDTH 5 // 接收地址宽度,一般设置为 5 不要动它
  32. #define RX_ADR_WIDTH 5 // 接收地址宽度,一般设置为 5 不要动它
  33. #define TX_PLOAD_WIDTH 32 //接收数据的 数据宽度(最大为 32 字节),这里我设置为最小的 1 字节,方便调试
  34. #define RX_PLOAD_WIDTH 32 //发送数据的 数据宽度(最大为 32 字节),这里我设置为最小的 1 字节,方便调试
  35. //uchar const TX_ADDRESS[TX_ADR_WIDTH]= {0x35,0x43,0x10,0x10,0x03}; // 这里就是设置了 5 个字节的 本地地址
  36. const u8 TX_ADDRESS[RX_ADR_WIDTH] = {0x34, 0x43, 0x10, 0x10, 0x01}; //发送地址
  37. /*
  38. 此处的地址:在IC内部真实地址是 反过来的。即:address = 0310104334
  39. 在数据发送时,发送到对方去的数据包括:数据本身+本地地址。与接收地址无关。
  40. */
  41. uchar const RX_ADDRESS[RX_ADR_WIDTH] = {0xEF, 0xEF, 0xEF, 0xEF, 0xEF}; //接收地址
  42. /*
  43. 是指接受来自于发送方的地址(指发送方的本地地址),但在自动模式下,得到的应答信息中,包含的不是返回应答信息的对方的(本地地址)
  44. 而是 由 发送方(也就是发送原信息的机子一方) 的本地地址
  45. */
  46. //
  47. //***************************************NRF24L01寄存器指令*******************************************************
  48. #define READ_REG 0x00 // 读寄存器指令
  49. #define WRITE_REG 0x20 // 写寄存器指令
  50. #define RD_RX_PLOAD 0x61 // 读取接收数据指令
  51. #define WR_TX_PLOAD 0xA0 // 写待发数据指令
  52. #define FLUSH_TX 0xE1 // 冲洗发送 FIFO指令
  53. #define FLUSH_RX 0xE2 // 冲洗接收 FIFO指令
  54. #define REUSE_TX_PL 0xE3 // 定义重复装载数据指令
  55. #define NOP 0xFF // 保留
  56. //*************************************SPI(nRF24L01)寄存器地址****************************************************
  57. #define CONFIG 0x00 // 配置收发状态,CRC校验模式以及收发状态响应方式
  58. #define EN_AA 0x01 // 自动应答功能设置
  59. #define EN_RXADDR 0x02 // 可用信道设置
  60. #define SETUP_AW 0x03 // 收发地址宽度设置
  61. #define SETUP_RETR 0x04 // 自动重发功能设置
  62. #define RF_CH 0x05 // 工作频率设置
  63. #define RF_SETUP 0x06 // 发射速率、功耗功能设置
  64. #define STATUS 0x07 // 状态寄存器
  65. #define OBSERVE_TX 0x08 // 发送监测功能
  66. #define CD 0x09 // 地址检测
  67. #define RX_ADDR_P0 0x0A // 频道0接收数据地址
  68. #define RX_ADDR_P1 0x0B // 频道1接收数据地址
  69. #define RX_ADDR_P2 0x0C // 频道2接收数据地址
  70. #define RX_ADDR_P3 0x0D // 频道3接收数据地址
  71. #define RX_ADDR_P4 0x0E // 频道4接收数据地址
  72. #define RX_ADDR_P5 0x0F // 频道5接收数据地址
  73. #define TX_ADDR 0x10 // 发送地址寄存器
  74. #define RX_PW_P0 0x11 // 接收频道0接收数据长度
  75. #define RX_PW_P1 0x12 // 接收频道0接收数据长度
  76. #define RX_PW_P2 0x13 // 接收频道0接收数据长度
  77. #define RX_PW_P3 0x14 // 接收频道0接收数据长度
  78. #define RX_PW_P4 0x15 // 接收频道0接收数据长度
  79. #define RX_PW_P5 0x16 // 接收频道0接收数据长度
  80. #define FIFO_STATUS 0x17 // FIFO栈入栈出状态寄存器设置
  81. //**************************************************************************************
  82. //void Delay(unsigned int s);
  83. void inerDelay_us ( unsigned char n );
  84. void init_NRF24L01 ( void );
  85. uint SPI_RW ( uint uchar );
  86. uchar SPI_Read ( uchar reg );
  87. void SetRX_Mode ( void );
  88. uint SPI_RW_Reg ( uchar reg, uchar value );
  89. uint SPI_Read_Buf ( uchar reg, uchar *pBuf, uchar uchars );
  90. uint SPI_Write_Buf ( uchar reg, uchar *pBuf, uchar uchars );
  91. uchar nRF24L01_RxPacket ( unsigned char* rx_buf );
  92. void nRF24L01_TxPacket ( unsigned char * tx_buf );
  93. //******************************************************************************************
  94. uchar bdata sta; //状态标志
  95. sbit RX_DR = sta ^ 6;
  96. sbit TX_DS = sta ^ 5;
  97. sbit MAX_RT = sta ^ 4;
  98. /******************************************************************************************
  99. /*延时函数
  100. /******************************************************************************************/
  101. void inerDelay_us ( unsigned char n )
  102. {
  103. for ( ; n > 0; n-- )
  104. _nop_();
  105. }
  106. //****************************************************************************************
  107. /*NRF24L01初始化
  108. //***************************************************************************************/
  109. void init_NRF24L01 ( void )
  110. {
  111. inerDelay_us ( 100 );
  112. CE = 0;
  113. CSN = 1;
  114. SCK = 0;
  115. SPI_Write_Buf ( WRITE_REG + TX_ADDR, TX_ADDRESS, TX_ADR_WIDTH ); // 写本地地址
  116. SPI_Write_Buf ( WRITE_REG + RX_ADDR_P0, TX_ADDRESS, RX_ADR_WIDTH ); // 写接收端地址
  117. SPI_RW_Reg ( WRITE_REG + EN_AA, 0x01 ); // 频道0自动 ACK应答允许
  118. SPI_RW_Reg ( WRITE_REG + EN_RXADDR, 0x01 ); // 允许接收地址只有频道0
  119. SPI_RW_Reg ( WRITE_REG + SETUP_RETR, 0x1a ); //设置自动重发间隔时间:500us + 86us;最大自动重发次数:10次
  120. SPI_RW_Reg ( WRITE_REG + RF_CH, 40 ); //
  121. SPI_RW_Reg ( WRITE_REG + RX_PW_P0, RX_PLOAD_WIDTH ); //设置接收数据长度,本次设置为32字节
  122. SPI_RW_Reg ( WRITE_REG + RF_SETUP, 0x0f ); //设置发射速率为1MHZ,发射功率为最大值0dB
  123. CE = 1; // 网上很多地方 这里的 CE=1 都没有设置,不过也能正常工作。
  124. }
  125. /****************************************************************************************************
  126. /*函数:uint SPI_RW(uint uchar)
  127. /*功能:NRF24L01的SPI写时序
  128. /****************************************************************************************************/
  129. uint SPI_RW ( uint uchar )
  130. {
  131. uint bit_ctr;
  132. for ( bit_ctr = 0; bit_ctr < 8; bit_ctr++ )
  133. {
  134. MOSI = ( uchar & 0x80 );
  135. uchar = ( uchar << 1 );
  136. SCK = 1;
  137. uchar |= MISO;
  138. SCK = 0;
  139. }
  140. return ( uchar );
  141. }
  142. /****************************************************************************************************
  143. /*函数:uchar SPI_Read(uchar reg)
  144. /*功能:NRF24L01的SPI时序
  145. /****************************************************************************************************/
  146. uchar SPI_Read ( uchar reg )
  147. {
  148. uchar reg_val;
  149. CSN = 0;
  150. SPI_RW ( reg );
  151. reg_val = SPI_RW ( 0 );
  152. CSN = 1;
  153. return ( reg_val );
  154. }
  155. /****************************************************************************************************/
  156. /*功能:NRF24L01读写寄存器函数
  157. /****************************************************************************************************/
  158. uint SPI_RW_Reg ( uchar reg, uchar value )
  159. {
  160. uint status;
  161. CSN = 0;
  162. status = SPI_RW ( reg );
  163. SPI_RW ( value );
  164. CSN = 1;
  165. return ( status );
  166. }
  167. /****************************************************************************************************/
  168. /*函数:uint SPI_Read_Buf(uchar reg, uchar *pBuf, uchar uchars)
  169. /*功能: 用于读数据,reg:为寄存器地址,pBuf:为待读出数据地址,uchars:读出数据的个数
  170. /****************************************************************************************************/
  171. uint SPI_Read_Buf ( uchar reg, uchar *pBuf, uchar uchars )
  172. {
  173. uint status, uchar_ctr;
  174. CSN = 0; // Set CSN low, init SPI tranaction
  175. status = SPI_RW ( reg ); // Select register to write to and read status uchar
  176. for ( uchar_ctr = 0; uchar_ctr < uchars; uchar_ctr++ )
  177. pBuf[uchar_ctr] = SPI_RW ( 0 ); //
  178. CSN = 1;
  179. return ( status ); // return nRF24L01 status uchar
  180. }
  181. /*********************************************************************************************************
  182. /*函数:uint SPI_Write_Buf(uchar reg, uchar *pBuf, uchar uchars)
  183. /*功能: 用于写数据:reg为寄存器地址,pBuf:为待写入数据地址,uchars:写入数据的个数
  184. /*********************************************************************************************************/
  185. uint SPI_Write_Buf ( uchar reg, uchar *pBuf, uchar uchars )
  186. {
  187. uint status, uchar_ctr;
  188. CSN = 0; //SPI使能
  189. status = SPI_RW ( reg );
  190. for ( uchar_ctr = 0; uchar_ctr < uchars; uchar_ctr++ ) //
  191. SPI_RW ( *pBuf++ );
  192. CSN = 1; //关闭SPI
  193. return ( status ); //
  194. }
  195. /****************************************************************************************************/
  196. /*函数:void SetRX_Mode(void)
  197. /*功能:数据接收配置
  198. /****************************************************************************************************/
  199. void SetRX_Mode ( void )
  200. {
  201. CE = 0;
  202. SPI_RW_Reg ( WRITE_REG + CONFIG, 0x0f ); // IRQ收发完成中断响应,16位CRC ,主接收
  203. CE = 1;
  204. inerDelay_us ( 130 );
  205. }
  206. /******************************************************************************************************/
  207. /*函数:unsigned char nRF24L01_RxPacket(unsigned char* rx_buf)
  208. /*功能:数据读取后放如rx_buf接收缓冲区中
  209. /******************************************************************************************************/
  210. uchar nRF24L01_RxPacket ( unsigned char* rx_buf )
  211. {
  212. unsigned char revale = 0;
  213. sta = SPI_Read ( STATUS ); // 读取状态寄存其来判断数据接收状况
  214. if ( RX_DR ) // 判断是否接收到数据
  215. {
  216. CE = 0; //SPI使能
  217. SPI_Read_Buf ( RD_RX_PLOAD, rx_buf, TX_PLOAD_WIDTH ); // read receive payload from RX_FIFO buffer
  218. revale = 1; //读取数据完成标志
  219. }
  220. SPI_RW_Reg ( WRITE_REG + STATUS, sta ); //接收到数据后RX_DR,TX_DS,MAX_PT都置高为1,通过写1来清楚中断标志
  221. return revale;
  222. }
  223. /***********************************************************************************************************
  224. /*函数:void nRF24L01_TxPacket(unsigned char * tx_buf)
  225. /*功能:发送 tx_buf中数据
  226. /**********************************************************************************************************/
  227. void nRF24L01_TxPacket ( unsigned char * tx_buf )
  228. {
  229. CE = 0; //StandBy I模式
  230. SPI_Write_Buf ( WRITE_REG + RX_ADDR_P0, TX_ADDRESS, TX_ADR_WIDTH ); // 装载接收端地址
  231. SPI_Write_Buf ( WR_TX_PLOAD, tx_buf, TX_PLOAD_WIDTH ); // 装载数据
  232. SPI_RW_Reg ( WRITE_REG + CONFIG, 0x0e ); // IRQ收发完成中断响应,16位CRC,主发送
  233. SPI_RW_Reg ( WRITE_REG + STATUS, 0X7E ); // 清 除中断,以便开始发送数据
  234. CE = 1; //置高CE,激发数据发送
  235. inerDelay_us ( 10 );
  236. }
  237. #endif