[DemoCode下载] cc1101的详解及单片机程序

[复制链接]
6147|13
 楼主| Mancherstun 发表于 2015-8-9 20:21 | 显示全部楼层 |阅读模式
1.初始化SPI,MCU各引脚。
   
        当有数据接收或发送状态声明时,有中断和查询两种方式。GDO0与GDO2引脚输出至MCU引脚,若要用中断则要接至MCU外部中断引脚,查询时则可用GPIO。

    2.复位CC1101。

    3.初始化CC1101。(写操作时可从SO中读出CC1101状态)

        初始化后CC1100为IDLE状态.
   
    4.状态机转换,写/读FIFO数据。

        每次写操作时SO返回的值为写操作前的CC1100状态值,具体值见Table20;读状态命令为当前CC1100状态值,具体值见寄存器0X35说明;注意两者区别。

快速认识Cc1100

             Cc1100可以工作在同步模式下,代价是:MCU自己控制前导码。本系统中,Cc1100将工作在异步模式下。

知识点

             Head Byte:在 引脚 Cc1100.Csn 有效后,通过SPI总线写入 Cc1100的第一个字节。

             Status Byte: 在写入 HeadByte 的同时,MCU 得到 Status Byte。

             Burst Bit:在 Head Byte 中的一个 Bit, 有效值=="1",无效值=="0"

GDO0:
             GDO0可用作FIFO状态输出,载波感应(CS),时钟输出,GDO0 脚也能用作集成于芯片的模拟温度传感器(未用).配置寄存器为IOCFG0(0X02),现在配置为RX模式下数据状态反应输出.

GDO1:
             GDO1与SPI的SO共用引脚,默认状态下为3态,当CSn为低电平时,此引脚SPI的SO功能生效。配置寄存器为IOCFG0(0X01),现在配置为空闲状态下3态,SPI模式下SO.

GDO2:

             GDO2可用作FIFO状态输出,载波感应(CS),时钟输出,配置寄存器为IOCFG0(0X00),现在配置为载波感应(CS)输出.

TXOFF_MODE/RXOFF_MODE:

             注意,此配置为在数据包被发送/接收后状态机状态决定位,仅是在发生发送或者接收后动作;当为IDLE时发SRX/STX后状态机不按此配置运行。TX/RX后要校准。

功率放大控制(PATABLE):

             0X3E为功率写入地址,0X22为为功率配置寄存器。PATABLE 是一个8字节表,定义了8个PA 功率值。这个表从最低位(0)到最高位(7)可读和写,一次一位。一个索引计数器用来控制对这个表的访问。

             每读出或写入表中的一个字节,计数器就加 1。当 CSn 为高时,计数值置为最小值。当达到最大值时,计数器由零重新开始计数。

             FREND0.PA_POWER(2:0)从8个功率值中选择1个,且振幅为相应数等级。


异步模式:
             在此模式下,CC1101中的MCU的若干支持机制会停用,包括数据包硬件处理,FIFO 缓冲,数据白化,交错(interleaver)和前向纠错(FEC) ,曼彻斯特编码(Manchester encoding);

             MSK不支持异步模式;

             PKTCTRL0.PKT_FORMAT == 3 使能异步模式,GDO0为input,GDO0, GDO1或GDO2为output 相应配置位为IOCFG0.GDO0_CFG, IOCFG1.GDO1_CFG IOCFG2.GDO2_CFG;

电磁波激活(WOR):

             在WOR滤波使用之前RC振荡器必须启用,RC振荡器是 WOR 定时器的时钟源.在WOR下,收到信号后会自动进入RX模式.

载波感应(CS)与RSSI:

             因此两配置相互有连系,所以一起论述.

             RSSI 只能在RX模式下才能有效,作用为对当前信号质量评估,信号质量可从RSSI寄存器读出.RSSI信号强度可从0X34取出.

             RSSI(信号强度)计算公式: 注:此为433M下,结果为负数,

                                            RSSI_dBm=(RSSI-256)/2-74 (RSSI>=128)

                                            RSSI_dBm= (RSSI/2)-74      (RSSI<128)

             CS 只在RX模式下才能有效,当信号质量高于设定门限值时,CS状态将会被声明。现在配置为GDO2输出感应状态.

             CS门限值由以下4个寄存器决定

             ?? AGCCTRL2.MAX_LNA_GAIN  
             ?? AGCCTRL2.MAX_DVGA_GAIN
             ?? AGCCTRL1.CARRIER_SENSE_ABS_THR
             ?? AGCCTRL2.MAGN_TARGET

             CS门限值计算公式:     表默认门限值 + (MAGN_TARGET-33) + CARRIER_SENSE_ABS_THR.

                                           表默认门限值见table29,table30. 由AGCCTRL2.MAX_LNA_GAIN   AGCCTRL2.MAX_DVGA_GAIN 决定.

                                          默认门限值表只给了两个数据速率下的值,其余由自己测.我们对此要求不是太高,可以参考用这个表.

                                           CARRIER_SENSE_ABS_THR为对应表中-7~7的值,最后单位为dBm.

                                           Example:

                                                         在250K下AGCCTRL2.MAX_LNA_GAIN = 00   AGCCTRL2.MAX_DVGA_GAIN = 00 得出表中为-90.5

                                                          MAGN_TARGET = 7(42), CARRIER_SENSE_ABS_THR = 1(1)

                                                         门限为-90.5 + (42-33) + 1= -82.5dBm            

清理信道访问(CCA):

             清理信道访问用来指示当前信号是空闲还是忙。当忙时是否丢弃当前数据,寄存器MCSM1.CCA_MODE决定是否丢弃.默认配置为保留当前寄存器中数据,丢弃下一步要处理数据.

数据FIFO:


             当TX操作时,由MCU控制,溢出时CC1101出错;当RX操作时,读空时CC1101出错

             RX FIFO 和 TX FIFO 中的字节数也能分别从状态寄存器 RXBYTES.NUM_RXBYTES和TXBYTES.NUM_TXBYTES 中读出

             4 位 FIFOTHR.FIFO_THR 设置用来控制FIFO 门限点

             读单字节时,,CSn继续保持低;。突发访问方式允许一地址字节,然后是连续的数据字节,直到通过设置 CSn 为高来断访问

             当写操作时,最后一个字节被传送至 SI 脚后, 被 SO脚接收的状态位会表明在 TX FIFO中只有一个字节是空闲,

寄存器分类
Configration Registers            共47个,可读,可写
            0x00~0x2E
            
Status Registers            共14个,只读
            0x30~0x3D
            
Command Strobe            共14个,只写
            寻址空间:0x30~0x3D
            
                        14个地址,对相应的地址进行写,
            就相当于激活了对应的命令
            
            本系统是用到的Strobe:
            CC1100_STROBE_RESET
            CC1100_STROBE_ENTER_RX_MODE
            CC1100_STROBE_ENTER_TX_MODE
            CC1100_COMMAND_STROBE_SIDLE
            CC1100_COMMAND_STROBE_SFRX
            
TX FIFO共64个,只写
RX FIFO共64个,只读




Status(Command)Registers操作:

     当地址为0X30~0X3D时

     burst为1:对Status Registers的操作

                   Status Registers只可读,且只能一次读一个字节,不可写                 
     burst为0:对Command Registers操作

                 寄存器的访问和一个寄存器的操作一样,但没有数据被传输.写完毕后,CC1100便执行相应操作.

     读写FIFO,有两种模式:单字节读写;Burst读写。         单字节读写时序:
             1 Cc1100.Csn有效。
             2 写入Head Byte。
              3 读、写一个1字节。
             4 Cc1100.Csn无效。

 楼主| Mancherstun 发表于 2015-8-9 20:23 | 显示全部楼层
本帖最后由 Mancherstun 于 2015-8-9 20:26 编辑
  1. [code]#include <reg52.h>
  2. #include <intrins.h>
  3. #define  INT8U  unsigned char
  4. #define  INT16U  unsigned int
  5. #define  WRITE_BURST      0x40      //连续写入
  6. #define  READ_SINGLE      0x80      //读
  7. #define  READ_BURST       0xC0      //连续读
  8. #define  BYTES_IN_RXFIFO     0x7F        //接收缓冲区的有效字节数
  9. #define  CRC_OK              0x80       //CRC校验通过位标志
  10. //*****************************************************************************************
  11. sbit  GDO0 =P1^3;
  12. sbit  GDO2 =P3^2;
  13. sbit MISO =P1^6;
  14. sbit MOSI =P1^5;
  15. sbit SCK =P1^7;
  16. sbit CSN =P1^2;
  17. //*****************************************************************************************
  18. sbit    LED2    =P3^4;
  19. sbit    LED1    =P3^5;
  20. sbit    KEY1    =P3^6;
  21. sbit    KEY2    =P3^7;
  22. //*****************************************************************************************
  23. sbit led3=P2^3;
  24. sbit led2=P2^2;
  25. sbit led1=P2^1;
  26. sbit led0=P2^0;
  27. //*****************************************************************************************
  28. //INT8U PaTabel[8] = {0x60 ,0x60 ,0x60 ,0x60 ,0x60 ,0x60 ,0x60 ,0x60};
  29. INT8U PaTabel[8] = {0xc0 ,0xc0 ,0xc0 ,0xc0 ,0xc0 ,0xc0 ,0xc0 ,0xc0};//修改发射功率
  30. //*****************************************************************************************
  31. void SpiInit(void);
  32. void CpuInit(void);
  33. void RESET_CC1100(void);
  34. void POWER_UP_RESET_CC1100(void);
  35. void halSpiWriteReg(INT8U addr, INT8U value);
  36. void halSpiWriteBurstReg(INT8U addr, INT8U *buffer, INT8U count);
  37. void halSpiStrobe(INT8U strobe);
  38. INT8U halSpiReadReg(INT8U addr);
  39. void halSpiReadBurstReg(INT8U addr, INT8U *buffer, INT8U count);
  40. INT8U halSpiReadStatus(INT8U addr);
  41. void halRfWriteRfSettings(void);
  42. void halRfSendPacket(INT8U *txBuffer, INT8U size);
  43. INT8U halRfReceivePacket(INT8U *rxBuffer, INT8U *length);
  44. //*****************************************************************************************
  45. // CC1100 STROBE, CONTROL AND STATUS REGSITER
  46. #define CCxxx0_IOCFG2       0x00        // GDO2 output pin configuration
  47. #define CCxxx0_IOCFG1       0x01        // GDO1 output pin configuration
  48. #define CCxxx0_IOCFG0       0x02        // GDO0 output pin configuration
  49. #define CCxxx0_FIFOTHR      0x03        // RX FIFO and TX FIFO thresholds
  50. #define CCxxx0_SYNC1        0x04        // Sync word, high INT8U
  51. #define CCxxx0_SYNC0        0x05        // Sync word, low INT8U
  52. #define CCxxx0_PKTLEN       0x06        // Packet length
  53. #define CCxxx0_PKTCTRL1     0x07        // Packet automation control
  54. #define CCxxx0_PKTCTRL0     0x08        // Packet automation control
  55. #define CCxxx0_ADDR         0x09        // Device address
  56. #define CCxxx0_CHANNR       0x0A        // Channel number
  57. #define CCxxx0_FSCTRL1      0x0B        // Frequency synthesizer control
  58. #define CCxxx0_FSCTRL0      0x0C        // Frequency synthesizer control
  59. #define CCxxx0_FREQ2        0x0D        // Frequency control word, high INT8U
  60. #define CCxxx0_FREQ1        0x0E        // Frequency control word, middle INT8U
  61. #define CCxxx0_FREQ0        0x0F        // Frequency control word, low INT8U
  62. #define CCxxx0_MDMCFG4      0x10        // Modem configuration
  63. #define CCxxx0_MDMCFG3      0x11        // Modem configuration
  64. #define CCxxx0_MDMCFG2      0x12        // Modem configuration
  65. #define CCxxx0_MDMCFG1      0x13        // Modem configuration
  66. #define CCxxx0_MDMCFG0      0x14        // Modem configuration
  67. #define CCxxx0_DEVIATN      0x15        // Modem deviation setting
  68. #define CCxxx0_MCSM2        0x16        // Main Radio Control State Machine configuration
  69. #define CCxxx0_MCSM1        0x17        // Main Radio Control State Machine configuration
  70. #define CCxxx0_MCSM0        0x18        // Main Radio Control State Machine configuration
  71. #define CCxxx0_FOCCFG       0x19        // Frequency Offset Compensation configuration
  72. #define CCxxx0_BSCFG        0x1A        // Bit Synchronization configuration
  73. #define CCxxx0_AGCCTRL2     0x1B        // AGC control
  74. #define CCxxx0_AGCCTRL1     0x1C        // AGC control
  75. #define CCxxx0_AGCCTRL0     0x1D        // AGC control
  76. #define CCxxx0_WOREVT1      0x1E        // High INT8U Event 0 timeout
  77. #define CCxxx0_WOREVT0      0x1F        // Low INT8U Event 0 timeout
  78. #define CCxxx0_WORCTRL      0x20        // Wake On Radio control
  79. #define CCxxx0_FREND1       0x21        // Front end RX configuration
  80. #define CCxxx0_FREND0       0x22        // Front end TX configuration
  81. #define CCxxx0_FSCAL3       0x23        // Frequency synthesizer calibration
  82. #define CCxxx0_FSCAL2       0x24        // Frequency synthesizer calibration
  83. #define CCxxx0_FSCAL1       0x25        // Frequency synthesizer calibration
  84. #define CCxxx0_FSCAL0       0x26        // Frequency synthesizer calibration
  85. #define CCxxx0_RCCTRL1      0x27        // RC oscillator configuration
  86. #define CCxxx0_RCCTRL0      0x28        // RC oscillator configuration
  87. #define CCxxx0_FSTEST       0x29        // Frequency synthesizer calibration control
  88. #define CCxxx0_PTEST        0x2A        // Production test
  89. #define CCxxx0_AGCTEST      0x2B        // AGC test
  90. #define CCxxx0_TEST2        0x2C        // Various test settings
  91. #define CCxxx0_TEST1        0x2D        // Various test settings
  92. #define CCxxx0_TEST0        0x2E        // Various test settings
  93. // Strobe commands
  94. #define CCxxx0_SRES         0x30        // Reset chip.
  95. #define CCxxx0_SFSTXON      0x31        // Enable and calibrate frequency synthesizer (if MCSM0.FS_AUTOCAL=1).
  96.                                         // If in RX/TX: Go to a wait state where only the synthesizer is
  97.                                         // running (for quick RX / TX turnaround).
  98. #define CCxxx0_SXOFF        0x32        // Turn off crystal oscillator.
  99. #define CCxxx0_SCAL         0x33        // Calibrate frequency synthesizer and turn it off
  100.                                         // (enables quick start).
  101. #define CCxxx0_SRX          0x34        // Enable RX. Perform calibration first if coming from IDLE and
  102.                                         // MCSM0.FS_AUTOCAL=1.
  103. #define CCxxx0_STX          0x35        // In IDLE state: Enable TX. Perform calibration first if
  104.                                         // MCSM0.FS_AUTOCAL=1. If in RX state and CCA is enabled:
  105.                                         // Only go to TX if channel is clear.
  106. #define CCxxx0_SIDLE        0x36        // Exit RX / TX, turn off frequency synthesizer and exit
  107.                                         // Wake-On-Radio mode if applicable.
  108. #define CCxxx0_SAFC         0x37        // Perform AFC adjustment of the frequency synthesizer
  109. #define CCxxx0_SWOR         0x38        // Start automatic RX polling sequence (Wake-on-Radio)
  110. #define CCxxx0_SPWD         0x39        // Enter power down mode when CSn goes high.
  111. #define CCxxx0_SFRX         0x3A        // Flush the RX FIFO buffer.
  112. #define CCxxx0_SFTX         0x3B        // Flush the TX FIFO buffer.
  113. #define CCxxx0_SWORRST      0x3C        // Reset real time clock.
  114. #define CCxxx0_SNOP         0x3D        // No operation. May be used to pad strobe commands to two
  115.                                         // INT8Us for simpler software.
  116. #define CCxxx0_PARTNUM      0x30
  117. #define CCxxx0_VERSION      0x31
  118. #define CCxxx0_FREQEST      0x32
  119. #define CCxxx0_LQI          0x33
  120. #define CCxxx0_RSSI         0x34
  121. #define CCxxx0_MARCSTATE    0x35
  122. #define CCxxx0_WORTIME1     0x36
  123. #define CCxxx0_WORTIME0     0x37
  124. #define CCxxx0_PKTSTATUS    0x38
  125. #define CCxxx0_VCO_VC_DAC   0x39
  126. #define CCxxx0_TXBYTES      0x3A
  127. #define CCxxx0_RXBYTES      0x3B
  128. #define CCxxx0_PATABLE      0x3E
  129. #define CCxxx0_TXFIFO       0x3F
  130. #define CCxxx0_RXFIFO       0x3F
  131. // RF_SETTINGS is a data structure which contains all relevant CCxxx0 registers
  132. typedef struct S_RF_SETTINGS
  133. {
  134.     INT8U FSCTRL2;   //自已加的
  135.     INT8U FSCTRL1;   // Frequency synthesizer control.
  136.     INT8U FSCTRL0;   // Frequency synthesizer control.
  137.     INT8U FREQ2;     // Frequency control word, high INT8U.
  138.     INT8U FREQ1;     // Frequency control word, middle INT8U.
  139.     INT8U FREQ0;     // Frequency control word, low INT8U.
  140.     INT8U MDMCFG4;   // Modem configuration.
  141.     INT8U MDMCFG3;   // Modem configuration.
  142.     INT8U MDMCFG2;   // Modem configuration.
  143.     INT8U MDMCFG1;   // Modem configuration.
  144.     INT8U MDMCFG0;   // Modem configuration.
  145.     INT8U CHANNR;    // Channel number.
  146.     INT8U DEVIATN;   // Modem deviation setting (when FSK modulation is enabled).
  147.     INT8U FREND1;    // Front end RX configuration.
  148.     INT8U FREND0;    // Front end RX configuration.
  149.     INT8U MCSM0;     // Main Radio Control State Machine configuration.
  150.     INT8U FOCCFG;    // Frequency Offset Compensation Configuration.
  151.     INT8U BSCFG;     // Bit synchronization Configuration.
  152.     INT8U AGCCTRL2;  // AGC control.
  153.     INT8U AGCCTRL1;  // AGC control.
  154.     INT8U AGCCTRL0;  // AGC control.
  155.     INT8U FSCAL3;    // Frequency synthesizer calibration.
  156.     INT8U FSCAL2;    // Frequency synthesizer calibration.
  157.     INT8U FSCAL1;    // Frequency synthesizer calibration.
  158.     INT8U FSCAL0;    // Frequency synthesizer calibration.
  159.     INT8U FSTEST;    // Frequency synthesizer calibration control
  160.     INT8U TEST2;     // Various test settings.
  161.     INT8U TEST1;     // Various test settings.
  162.     INT8U TEST0;     // Various test settings.
  163.     INT8U IOCFG2;    // GDO2 output pin configuration
  164.     INT8U IOCFG0;    // GDO0 output pin configuration
  165.     INT8U PKTCTRL1;  // Packet automation control.
  166.     INT8U PKTCTRL0;  // Packet automation control.
  167.     INT8U ADDR;      // Device address.
  168.     INT8U PKTLEN;    // Packet length.
  169. } RF_SETTINGS;
  170. /////////////////////////////////////////////////////////////////
  171. const RF_SETTINGS rfSettings =
  172. {
  173. 0x00,
  174.     0x08,   // FSCTRL1   Frequency synthesizer control.
  175.     0x00,   // FSCTRL0   Frequency synthesizer control.
  176.     0x10,   // FREQ2     Frequency control word, high byte.
  177.     0xA7,   // FREQ1     Frequency control word, middle byte.
  178.     0x62,   // FREQ0     Frequency control word, low byte.
  179.    
  180. 0x5B,   // MDMCFG4   Modem configuration.
  181. //0xf6, // MDMCFG4 chang by allen
  182.     0xF8,   // MDMCFG3   Modem configuration.
  183. //0x83, // MDMCFG3 chang by allen   data rate = 2.398K
  184.     0x03,   // MDMCFG2   Modem configuration.
  185.     0x22,   // MDMCFG1   Modem configuration.
  186.     0xF8,   // MDMCFG0   Modem configuration.
  187.     0x00,   // CHANNR    Channel number.
  188.     0x47,   // DEVIATN   Modem deviation setting (when FSK modulation is enabled).
  189.     0xB6,   // FREND1    Front end RX configuration.
  190.     0x10,   // FREND0    Front end RX configuration.
  191.     0x18,   // MCSM0     Main Radio Control State Machine configuration.
  192.     0x1D,   // FOCCFG    Frequency Offset Compensation Configuration.
  193.     0x1C,   // BSCFG     Bit synchronization Configuration.
  194.     0xC7,   // AGCCTRL2  AGC control.
  195.     0x00,   // AGCCTRL1  AGC control.
  196.     0xB2,   // AGCCTRL0  AGC control.
  197.     0xEA,   // FSCAL3    Frequency synthesizer calibration.
  198.     0x2A,   // FSCAL2    Frequency synthesizer calibration.
  199.     0x00,   // FSCAL1    Frequency synthesizer calibration.
  200.     0x11,   // FSCAL0    Frequency synthesizer calibration.
  201.     0x59,   // FSTEST    Frequency synthesizer calibration.
  202.     0x81,   // TEST2     Various test settings.
  203.     0x35,   // TEST1     Various test settings.
  204.     0x09,   // TEST0     Various test settings.
  205.     0x0B,   // IOCFG2    GDO2 output pin configuration.
  206.     0x06,   // IOCFG0D   GDO0 output pin configuration. Refer to SmartRF?Studio User Manual for detailed pseudo register explanation.
  207.     0x04,   // PKTCTRL1  Packet automation control.
  208.     //0x05,   // PKTCTRL0  Packet automation control.
  209. 0x01, //PKTCTRL0  crc disable chang by allen at 09.12.24
  210.     0x00,   // ADDR      Device address.
  211.     0x0c    // PKTLEN    Packet length.
  212. };
  213. //*****************************************************************************************
  214. //函数名:delay(unsigned int s)
  215. //输入:时间
  216. //输出:无
  217. //功能描述:普通廷时,内部用
  218. //*****************************************************************************************  
  219. static void delay(unsigned int s)
  220. {
  221. unsigned int i;
  222. for(i=0; i<s; i++);
  223. for(i=0; i<s; i++);
  224. }

  225. void halWait(INT16U timeout) {
  226.     do {
  227.         _nop_();
  228.   _nop_();
  229.   _nop_();
  230.   _nop_();
  231.   _nop_();
  232.   _nop_();
  233.   _nop_();
  234.   _nop_();
  235.   _nop_();
  236.   _nop_();
  237.   _nop_();
  238.   _nop_();
  239.   _nop_();
  240.   _nop_();
  241.   _nop_();
  242.     } while (--timeout);
  243. }

  244. void SpiInit(void)
  245. {
  246. CSN=0;
  247. SCK=0;
  248. CSN=1;
  249. }
  250. /*****************************************************************************************
  251. //函数名:CpuInit()
  252. //输入:无
  253. //输出:无
  254. //功能描述:SPI初始化程序
  255. /*****************************************************************************************/
  256. void CpuInit(void)
  257. {
  258. SpiInit();
  259. delay(5000);
  260. }

  261. //*****************************************************************************************
  262. //函数名:SpisendByte(INT8U dat)
  263. //输入:发送的数据
  264. //输出:无
  265. //功能描述:SPI发送一个字节
  266. //*****************************************************************************************
  267. INT8U SpiTxRxByte(INT8U dat)
  268. {
  269. INT8U i,temp;
  270. temp = 0;

  271. SCK = 0;
  272. for(i=0; i<8; i++)
  273. {
  274.   if(dat & 0x80)
  275.   {
  276.    MOSI = 1;
  277.   }
  278.   else MOSI = 0;
  279.   dat <<= 1;
  280.   SCK = 1;
  281.   _nop_();
  282.   _nop_();
  283.   temp <<= 1;
  284.   if(MISO)temp++;
  285.   SCK = 0;
  286.   _nop_();
  287.   _nop_();
  288. }
  289. return temp;
  290. }
  291. //*****************************************************************************************
  292. //函数名:void RESET_CC1100(void)
  293. //输入:无
  294. //输出:无
  295. //功能描述:复位CC1100
  296. //*****************************************************************************************
  297. void RESET_CC1100(void)
  298. {
  299. CSN = 0;
  300. while (MISO);
  301.     SpiTxRxByte(CCxxx0_SRES);   //写入复位命令
  302. while (MISO);
  303.     CSN = 1;
  304. }
  305. //*****************************************************************************************
  306. //函数名:void POWER_UP_RESET_CC1100(void)
  307. //输入:无
  308. //输出:无
  309. //功能描述:上电复位CC1100
  310. //*****************************************************************************************
  311. void POWER_UP_RESET_CC1100(void)
  312. {
  313. CSN = 1;
  314. halWait(1);
  315. CSN = 0;
  316. halWait(1);
  317. CSN = 1;
  318. halWait(41);
  319. RESET_CC1100();     //复位CC1100
  320. }
  321. //*****************************************************************************************
  322. //函数名:void halSpiWriteReg(INT8U addr, INT8U value)
  323. //输入:地址和配置字
  324. //输出:无
  325. //功能描述:SPI写寄存器
  326. //*****************************************************************************************
  327. void halSpiWriteReg(INT8U addr, INT8U value)
  328. {
  329.     CSN = 0;
  330.     while (MISO);
  331.     SpiTxRxByte(addr);  //写地址
  332.     SpiTxRxByte(value);  //写入配置
  333.     CSN = 1;
  334. }
  335. //*****************************************************************************************
  336. //函数名:void halSpiWriteBurstReg(INT8U addr, INT8U *buffer, INT8U count)
  337. //输入:地址,写入缓冲区,写入个数
  338. //输出:无
  339. //功能描述:SPI连续写配置寄存器
  340. //*****************************************************************************************
  341. void halSpiWriteBurstReg(INT8U addr, INT8U *buffer, INT8U count)
  342. {
  343.     INT8U i, temp;
  344. temp = addr | WRITE_BURST;
  345.     CSN = 0;
  346.     while (MISO);
  347.     SpiTxRxByte(temp);
  348.     for (i = 0; i < count; i++)
  349.   {
  350.         SpiTxRxByte(buffer);    }    CSN = 1;}//*****************************************************************************************//函数名:void halSpiStrobe(INT8U strobe)//输入:命令//输出:无//功能描述:SPI写命令//*****************************************************************************************void halSpiStrobe(INT8U strobe){    CSN = 0;    while (MISO);    SpiTxRxByte(strobe);  //写入命令    CSN = 1;} //*****************************************************************************************//函数名:INT8U halSpiReadReg(INT8U addr)//输入:地址//输出:该寄存器的配置字//功能描述:SPI读寄存器//*****************************************************************************************INT8U halSpiReadReg(INT8U addr){ INT8U temp, value;    temp = addr|READ_SINGLE;//读寄存器命令 CSN = 0; while (MISO); SpiTxRxByte(temp); value = SpiTxRxByte(0); CSN = 1; return value;}
  351. //*****************************************************************************************//函数名:void halSpiReadBurstReg(INT8U addr, INT8U *buffer, INT8U count)//输入:地址,读出数据后暂存的缓冲区,读出配置个数//输出:无//功能描述:SPI连续写配置寄存器//*****************************************************************************************void halSpiReadBurstReg(INT8U addr, INT8U *buffer, INT8U count){    INT8U i,temp; temp = addr | READ_BURST;  //写入要读的配置寄存器地址和读命令    CSN = 0;    while (MISO); SpiTxRxByte(temp);      for (i = 0; i < count; i++) {        buffer = SpiTxRxByte(0);    }    CSN = 1;}
  352. //*****************************************************************************************//函数名:INT8U halSpiReadReg(INT8U addr)//输入:地址//输出:该状态寄存器当前值//功能描述:SPI读状态寄存器//*****************************************************************************************INT8U halSpiReadStatus(INT8U addr){    INT8U value,temp; temp = addr | READ_BURST;  //写入要读的状态寄存器的地址同时写入读命令    CSN = 0;    while (MISO);    SpiTxRxByte(temp); value = SpiTxRxByte(0); CSN = 1; return value;}

 楼主| Mancherstun 发表于 2015-8-9 20:25 | 显示全部楼层
  1. //*****************************************************************************************
  2. //函数名:void halRfWriteRfSettings(RF_SETTINGS *pRfSettings)
  3. //输入:无
  4. //输出:无
  5. //功能描述:配置CC1100的寄存器
  6. //*****************************************************************************************
  7. void halRfWriteRfSettings(void)
  8. {
  9. halSpiWriteReg(CCxxx0_FSCTRL0,  rfSettings.FSCTRL2);//自已加的
  10.     // Write register settings
  11.     halSpiWriteReg(CCxxx0_FSCTRL1,  rfSettings.FSCTRL1);
  12.     halSpiWriteReg(CCxxx0_FSCTRL0,  rfSettings.FSCTRL0);
  13.     halSpiWriteReg(CCxxx0_FREQ2,    rfSettings.FREQ2);
  14.     halSpiWriteReg(CCxxx0_FREQ1,    rfSettings.FREQ1);
  15.     halSpiWriteReg(CCxxx0_FREQ0,    rfSettings.FREQ0);
  16.     halSpiWriteReg(CCxxx0_MDMCFG4,  rfSettings.MDMCFG4);
  17.     halSpiWriteReg(CCxxx0_MDMCFG3,  rfSettings.MDMCFG3);
  18.     halSpiWriteReg(CCxxx0_MDMCFG2,  rfSettings.MDMCFG2);
  19.     halSpiWriteReg(CCxxx0_MDMCFG1,  rfSettings.MDMCFG1);
  20.     halSpiWriteReg(CCxxx0_MDMCFG0,  rfSettings.MDMCFG0);
  21.     halSpiWriteReg(CCxxx0_CHANNR,   rfSettings.CHANNR);
  22.     halSpiWriteReg(CCxxx0_DEVIATN,  rfSettings.DEVIATN);
  23.     halSpiWriteReg(CCxxx0_FREND1,   rfSettings.FREND1);
  24.     halSpiWriteReg(CCxxx0_FREND0,   rfSettings.FREND0);
  25.     halSpiWriteReg(CCxxx0_MCSM0 ,   rfSettings.MCSM0 );
  26.     halSpiWriteReg(CCxxx0_FOCCFG,   rfSettings.FOCCFG);
  27.     halSpiWriteReg(CCxxx0_BSCFG,    rfSettings.BSCFG);
  28.     halSpiWriteReg(CCxxx0_AGCCTRL2, rfSettings.AGCCTRL2);
  29. halSpiWriteReg(CCxxx0_AGCCTRL1, rfSettings.AGCCTRL1);
  30.     halSpiWriteReg(CCxxx0_AGCCTRL0, rfSettings.AGCCTRL0);
  31.     halSpiWriteReg(CCxxx0_FSCAL3,   rfSettings.FSCAL3);
  32. halSpiWriteReg(CCxxx0_FSCAL2,   rfSettings.FSCAL2);
  33. halSpiWriteReg(CCxxx0_FSCAL1,   rfSettings.FSCAL1);
  34.     halSpiWriteReg(CCxxx0_FSCAL0,   rfSettings.FSCAL0);
  35.     halSpiWriteReg(CCxxx0_FSTEST,   rfSettings.FSTEST);
  36.     halSpiWriteReg(CCxxx0_TEST2,    rfSettings.TEST2);
  37.     halSpiWriteReg(CCxxx0_TEST1,    rfSettings.TEST1);
  38.     halSpiWriteReg(CCxxx0_TEST0,    rfSettings.TEST0);
  39.     halSpiWriteReg(CCxxx0_IOCFG2,   rfSettings.IOCFG2);
  40.     halSpiWriteReg(CCxxx0_IOCFG0,   rfSettings.IOCFG0);   
  41.     halSpiWriteReg(CCxxx0_PKTCTRL1, rfSettings.PKTCTRL1);
  42.     halSpiWriteReg(CCxxx0_PKTCTRL0, rfSettings.PKTCTRL0);
  43.     halSpiWriteReg(CCxxx0_ADDR,     rfSettings.ADDR);
  44.     halSpiWriteReg(CCxxx0_PKTLEN,   rfSettings.PKTLEN);
  45. }
  46. //*****************************************************************************************
  47. //函数名:void halRfSendPacket(INT8U *txBuffer, INT8U size)
  48. //输入:发送的缓冲区,发送数据个数
  49. //输出:无
  50. //功能描述:CC1100发送一组数据
  51. //*****************************************************************************************
  52. void halRfSendPacket(INT8U *txBuffer, INT8U size)
  53. {
  54. halSpiWriteReg(CCxxx0_TXFIFO, size);
  55.     halSpiWriteBurstReg(CCxxx0_TXFIFO, txBuffer, size); //写入要发送的数据
  56.     halSpiStrobe(CCxxx0_STX);  //进入发送模式发送数据
  57.     // Wait for GDO0 to be set -> sync transmitted
  58.     while (!GDO0);
  59.     // Wait for GDO0 to be cleared -> end of packet
  60.     while (GDO0);
  61. halSpiStrobe(CCxxx0_SFTX);
  62. delay(20);
  63. }

  64. void setRxMode(void)
  65. {
  66.     halSpiStrobe(CCxxx0_SRX);  //进入接收状态
  67. }
  68. /*
  69. // Bit masks corresponding to STATE[2:0] in the status byte returned on MISO
  70. #define CCxx00_STATE_BM                 0x70
  71. #define CCxx00_FIFO_BYTES_AVAILABLE_BM  0x0F
  72. #define CCxx00_STATE_TX_BM              0x20
  73. #define CCxx00_STATE_TX_UNDERFLOW_BM    0x70
  74. #define CCxx00_STATE_RX_BM              0x10
  75. #define CCxx00_STATE_RX_OVERFLOW_BM     0x60
  76. #define CCxx00_STATE_IDLE_BM            0x00
  77. static INT8U RfGetRxStatus(void)
  78. {
  79. INT8U temp, spiRxStatus1,spiRxStatus2;
  80. INT8U i=4;// 循环测试次数
  81.     temp = CCxxx0_SNOP|READ_SINGLE;//读寄存器命令
  82. CSN = 0;
  83. while (MISO);
  84. SpiTxRxByte(temp);
  85. spiRxStatus1 = SpiTxRxByte(0);
  86. do
  87. {
  88.   SpiTxRxByte(temp);
  89.   spiRxStatus2 = SpiTxRxByte(0);
  90.   if(spiRxStatus1 == spiRxStatus2)
  91.   {
  92.    if( (spiRxStatus1 & CCxx00_STATE_BM) == CCxx00_STATE_RX_OVERFLOW_BM)
  93.    {
  94.                halSpiStrobe(CCxxx0_SFRX);
  95.       return 0;
  96.    }
  97.       return 1;
  98.   }
  99.    spiRxStatus1=spiRxStatus2;
  100. }
  101. while(i--);
  102. CSN = 1;
  103.     return 0;
  104. }
  105. */
  106. INT8U halRfReceivePacket(INT8U *rxBuffer, INT8U *length)
  107. {
  108.     INT8U status[2];
  109.     INT8U packetLength;
  110. INT8U i=(*length)*4;  // 具体多少要根据datarate和length来决定
  111.     halSpiStrobe(CCxxx0_SRX);  //进入接收状态
  112. //delay(5);
  113.     //while (!GDO1);
  114.     //while (GDO1);
  115. delay(2);
  116. while (GDO0)
  117. {
  118.   delay(2);
  119.   --i;
  120.   if(i<1)
  121.      return 0;     
  122. }
  123.     if ((halSpiReadStatus(CCxxx0_RXBYTES) & BYTES_IN_RXFIFO)) //如果接的字节数不为0
  124. {
  125.         //LED2 = 0;
  126.   packetLength = halSpiReadReg(CCxxx0_RXFIFO);//读出第一个字节,此字节为该帧数据长度
  127.         //if (packetLength <= *length)   //如果所要的有效数据长度小于等于接收到的数据包的长度
  128.   if(packetLength == 0x08)
  129.   {
  130.             //halSpiReadBurstReg(CCxxx0_RXFIFO, rxBuffer, packetLength); //读出所有接收到的数据
  131.    halSpiReadBurstReg(CCxxx0_RXFIFO, rxBuffer, 8); //读出所有接收到的数据
  132.             *length = packetLength;    //把接收数据长度的修改为当前数据的长度
  133.       
  134.             // Read the 2 appended status bytes (status[0] = RSSI, status[1] = LQI)
  135.             //halSpiReadBurstReg(CCxxx0_RXFIFO, status, 2);  //读出CRC校验位
  136.    halSpiStrobe(CCxxx0_SFRX);  //清洗接收缓冲区
  137.   // delay(2);
  138.   // halSpiStrobe(CCxxx0_SRX);  //进入接收状态
  139.   // delay(20);
  140.    //delay(200);
  141.    return 1;
  142.             //return (status[1] & CRC_OK);   //如果校验成功返回接收成功
  143.         }
  144.    else
  145.   {
  146.             *length = packetLength;
  147.             halSpiStrobe(CCxxx0_SFRX);  //清洗接收缓冲区
  148.   // delay(2);
  149.   // halSpiStrobe(CCxxx0_SRX);  //进入接收状态
  150.   // delay(20);
  151.   // LED2 = 1;
  152.             return 0;
  153.         }
  154.     }
  155.   return 0;
  156. }

  157. void main(void)
  158. {
  159. unsigned char key1_flag = 0;
  160. bit key2_flag = 0;
  161. unsigned int key1_scan_cnt = 400;
  162. unsigned int key2_scan_cnt = 300;
  163. INT8U i = 0;
  164. INT8U leng =0;
  165. INT8U tf =0;
  166. INT8U TxBuf[8]={1,2,3,4,5,6,7,8};  // 8字节, 如果需要更长的数据包,请正确设置
  167. INT8U RxBuf[8]={0};
  168. CpuInit();
  169. POWER_UP_RESET_CC1100();
  170. halRfWriteRfSettings();
  171. halSpiWriteBurstReg(CCxxx0_PATABLE, PaTabel, 8);
  172. //halSpiStrobe(CCxxx0_SRX);  //进入接收状态
  173. //setRxMode();
  174. while(1)
  175. {
  176.      //setRxMode();
  177.   delay(10);
  178.      if(KEY1 == 0)
  179.     {
  180.    key1_scan_cnt--;
  181.    if(!key1_scan_cnt)
  182.    {   
  183.     key1_scan_cnt = 300;
  184.     if(key1_flag == 0)//判断按键是否第1次按下
  185.     {
  186.      key1_flag = 1;//按键第1次按下标志位
  187.     }
  188.    }
  189.      }
  190.   else
  191.   {
  192.    key1_scan_cnt = 300;
  193.    if(key1_flag == 1)//判断是否第一次按键动作松开
  194.    {
  195.     led1 = 0;
  196.     led0 = 0;
  197.     key1_flag = 2;
  198.     key1_scan_cnt = 3;
  199.     TxBuf[0] = 0x77;//第1个字节为0x77的数据帧,接收方收到后不需要返回应答
  200.     while(1)
  201.     {        
  202.      halRfSendPacket(TxBuf,8); // Transmit Tx buffer data
  203.      delay(100);   
  204.      if(KEY1 == 0)//检测按键是否第2次按下
  205.      {
  206.       key1_scan_cnt--;
  207.       if(!key1_scan_cnt)
  208.       {
  209.        key1_flag = 3;//按键第2次按下
  210.        key1_scan_cnt = 300;
  211.        led1 = 1;
  212.        led0 = 1;
  213.        break;//当按键再次按下时退出长发状态
  214.       }
  215.      }
  216.      else//没有第2次的按键动作
  217.      {
  218.       key1_scan_cnt = 3;
  219.      }
  220.     }
  221.    }
  222.    else if(key1_flag == 3)//是否为第2次的按键动作松开
  223.    {
  224.     key1_flag = 0;
  225.    }
  226.   }

  227.      if(KEY2 == 0)
  228.     {
  229.    key2_scan_cnt--;
  230.    if(!key2_scan_cnt)//确认按键正常按下
  231.    {   
  232.     key2_scan_cnt = 300;   
  233.     key2_flag = 1;//按键第1次按下标志位   
  234.    }
  235.      }
  236.   else
  237.   {
  238.    key2_scan_cnt = 300;
  239.    if(key2_flag)//按键弹起
  240.    {
  241.     LED1 = 0;
  242.     key2_flag = 0;
  243.     delay(1000);
  244.     TxBuf[0] = 0x88;        
  245.     halRfSendPacket(TxBuf,8);// Transmit Tx buffer data   
  246.     LED1 = 1;   
  247.    }
  248.     }
  249.   leng =8; // 预计接受8 bytes
  250.      if(halRfReceivePacket(RxBuf,&leng))
  251. // if(!GDO0)
  252.   {      
  253.   // leng =8; // 预计接受8 bytes
  254.   // if(halRfReceivePacket(RxBuf,&leng))
  255.    {
  256.     if(RxBuf[0] == 0x77)//接收到的数据不需要返回应答
  257.     {
  258.      LED2 = ~LED2;
  259.     }
  260.     else if(RxBuf[0] == 0x88)//判断接收到的数据是否需要返回应答
  261.     {
  262.      LED2 = 0;//接收数据正确,开接收指示灯
  263.      LED1 = 0;//准备发送应答,开发送指示灯
  264.      delay(1000);
  265.      TxBuf[0] = 0x99;
  266.      halRfSendPacket(TxBuf,8); // Transmit Tx buffer data  返回应答
  267.      LED2 = 1;
  268.      LED1 = 1;
  269.     }
  270.     else if(RxBuf[0] == 0x99)//应答数据
  271.     {
  272.      LED2 = 0;
  273.      delay(1000);
  274.      LED2 = 1;
  275.     }
  276.    }
  277.   }
  278. }
  279. }
734774645 发表于 2015-8-9 20:57 | 显示全部楼层
代码完整,收藏了,楼主真是用心。
643757107 发表于 2015-8-9 22:15 | 显示全部楼层
  Status Byte: 在写入 HeadByte 的同时,MCU 得到 Status Byte。
玛尼玛尼哄 发表于 2015-8-9 22:28 | 显示全部楼层
CS门限值计算公式:     表默认门限值 + (MAGN_TARGET-33) + CARRIER_SENSE_ABS_THR.
稳稳の幸福 发表于 2015-8-9 22:34 | 显示全部楼层
1101是短距离无线应用吧,鼠标了,遥控器了
捉虫天师 发表于 2015-8-10 09:02 | 显示全部楼层
1101是51核心吗?没用过这个,还以为是430核心的。
C洛达尔多 发表于 2015-8-10 13:39 | 显示全部楼层
都是状态机的程序,这是精髓
luoqiang10605 发表于 2015-8-10 14:33 | 显示全部楼层
:handshake
mtd527 发表于 2015-12-15 14:04 | 显示全部楼层
谢谢分享,学习一下
春风的暖暖 发表于 2015-12-15 19:56 | 显示全部楼层
这个也是用的SPI接口啊,那就好学了,天线什么的不用了解就应该能用吧
 楼主| Mancherstun 发表于 2015-12-16 20:12 | 显示全部楼层
春风的暖暖 发表于 2015-12-15 19:56
这个也是用的SPI接口啊,那就好学了,天线什么的不用了解就应该能用吧

其实无非SPI,iic,uart等这些接口,很好学的
HAO123456025F 发表于 2017-8-21 18:29 | 显示全部楼层
楼主可以上传整个工程包吗
您需要登录后才可以回帖 登录 | 注册

本版积分规则

35

主题

294

帖子

2

粉丝
快速回复 在线客服 返回列表 返回顶部