mbed_controller / Mbed 2 deprecated CC1101_Transceiver_STM32F4

Dependencies:   mbed

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers main.cpp Source File

main.cpp

00001 /**
00002  * This program prints input text to serial port of each other side.
00003  * Test result: TX, RX work well with 433MHz on STM32-F407 platform.
00004  * Two features are improved from the original source code.
00005  * - Synchronous implementation of CC1101::SendPacket()
00006  * For subsequent packet transmission, now this function returns after packet transmission.
00007  * - FIFO checking routine changed.
00008  * Original code uses timer to check FIFO, it may cause resource corruption by timer interrupt.
00009  */
00010 #include "mbed.h"
00011 #include "CC1101.h"
00012 #include "RingBuffer.h"
00013 
00014 #if 0
00015 #define PRINTF pc.printf
00016 #else
00017 #define PRINTF(...)
00018 #endif
00019 
00020 #define FIFO_CHECK_INTERVAL_US  500000
00021 
00022 ///////////////////////////////////////////////////
00023 const PinName mosi = PB_5;
00024 const PinName miso = PB_4;
00025 const PinName clk = PB_3;
00026 const PinName csn = PA_15;
00027 // RDmiso --> pin to detect MISO low.
00028 const PinName RDmiso = PD_7;
00029 
00030 // pin connected to GDO0 pin of CC1101 for checking that received a new packet
00031 // It related with CC1101 IOCFG0 register.
00032 const PinName gdo0 = PE_0;
00033 
00034 // pin for checking that sent a packet
00035 // It related with CC1101 IOCFG02register.
00036 const PinName gdo2 = PE_1;
00037 
00038 CC1101 cc1101(mosi, miso, clk, csn, RDmiso, gdo0, gdo2);
00039 
00040 #if 1
00041 Serial pc(PD_8, PD_9); // tx, rx
00042 DigitalOut led1(PD_12);  // FIFO led
00043 DigitalOut led2(PD_13);  // RX led
00044 DigitalOut led3(PD_14);  // TX led
00045 #else
00046 Serial pc(USBTX, USBRX);
00047 DigitalOut led1(LED1);  // FIFO led
00048 DigitalOut led2(LED2);  // RX led
00049 DigitalOut led3(LED3);  // TX led
00050 #endif
00051 RingBuffer pcRX(512);   // ring buffer for the pc RX data
00052 RingBuffer pcTX(512);   // ring buffer for the pc TX data
00053 Timeout pcRXtimeout;
00054 Timeout led2timeout;
00055 Timeout led3timeout;
00056 unsigned char buffer[64];
00057 
00058 ///////////////////////////////////////////////////
00059 static uint32_t compute_elapse_us(uint32_t prev_tick, uint32_t cur_tick)
00060 {
00061     if (prev_tick <= cur_tick)
00062         return cur_tick - prev_tick;
00063 
00064     // tick wrap around happens, it assumes tick start from 0.
00065     return cur_tick;
00066 }
00067 ///////////////////////////////////////////////////
00068 void led2timeout_func()
00069 {
00070     led2 = 0;
00071     led2timeout.detach();
00072 }
00073 ///////////////////////////////////////////////////
00074 void led3timeout_func()
00075 {
00076     led3 = 0;
00077     led3timeout.detach();
00078 }
00079 ///////////////////////////////////////////////////
00080 void pcRXtimeout_func()         // function for transmiting the RF packets - empty the pcRX ring buffer
00081 {
00082     unsigned char txlength;
00083 
00084     txlength = 0;
00085     while(pcRX.use() > 0) {
00086         led2 = 1;
00087         buffer[txlength] = pcRX.getc();
00088         txlength++;
00089         led2timeout.attach(&led2timeout_func, 0.050);  // for switch off the led
00090     }
00091     if (txlength) {
00092         cc1101.SendPacket(buffer, txlength);    // tx packet
00093     }
00094 
00095     pcRXtimeout.detach();
00096 }
00097 ///////////////////////////////////////////////////
00098 void check_FIFO()           // check the status of the CC1101 to see FIFO error
00099 {
00100     unsigned char chip_status_rx, chip_status_tx;
00101 
00102     led1 = !led1;
00103     chip_status_rx = cc1101.ReadChipStatusRX();  // check the rx status
00104     if ((chip_status_rx & CHIP_STATE_MASK) == CHIP_STATE_RXFIFO_OVERFLOW)  { // if rx overflow flush the rx fifo
00105         PRINTF("*RXFIFO_OVERFLOW->Flush\r\n");
00106         cc1101.FlushRX();
00107     }
00108     if ((chip_status_rx & CHIP_STATE_MASK) == CHIP_STATE_IDLE) {             // if state is idle go to rx state again
00109         // Basically we don't need to set RXMode here because RXOFF_MODE and TXOFF_MODE of CC1101 are RX mode.
00110         // But we still need to check IDLE because it can be IDEL by flushing FIFO.
00111         PRINTF("*RX MODE\r\n");
00112         cc1101.RXMode();
00113     }
00114     chip_status_tx = cc1101.ReadChipStatusTX();  // check the tx status
00115     if ((chip_status_tx & CHIP_STATE_MASK) == CHIP_STATE_TXFIFO_UNDERFLOW) { // if tx underflow flush the tx fifo
00116         PRINTF("*XFIFO_UNDERFLOW->Flush\r\n");
00117         cc1101.FlushTX();
00118     }
00119     PRINTF("[%8u]Chip RX=%02x TX=%02x\r\n", us_ticker_read()/1000, chip_status_rx, chip_status_tx);
00120 }
00121 ///////////////////////////////////////////////////
00122 int main()
00123 {
00124     unsigned char rxlength, i;
00125     uint32_t saved_tick = 0, cur_tick;
00126 
00127     pc.baud(115200);
00128     printf("build at " __TIME__ "\r\n");
00129     pcRX.clear();
00130     pcTX.clear();
00131     cc1101.init();
00132     while(1) {
00133         cur_tick = us_ticker_read();
00134         if (compute_elapse_us(saved_tick, cur_tick) > FIFO_CHECK_INTERVAL_US) {
00135             check_FIFO();
00136             saved_tick = cur_tick;
00137         }
00138 
00139         if(cc1101.GetGDO0()) {    // rx finished and CRC OK read the new packet
00140             rxlength = sizeof(buffer);
00141             if (cc1101.ReceivePacket(buffer, &rxlength) == 1) { // read the rx packet
00142                 led3 = 1;
00143                 for (i = 0; i < rxlength; i++)
00144                     pcTX.putc(buffer[i]);                       // store the packet to the pcTX ring buffer
00145                 led3timeout.attach(&led3timeout_func, 0.050);   // for switch off the led
00146             }
00147         }
00148         if (pcTX.use() > 0)         // check if we have data to transmit to pc
00149             pc.putc(pcTX.getc());   // get the data from the ring buffer and transmit it to the pc
00150         if (pc.readable()) {        // check if we received new data from the pc
00151             pcRX.putc(pc.getc());   // put the data to the pcRX buffer and wait until 20ms passed till the last byte before tx the packet in RF
00152             if (pcRX.use() > 20)        // if more than 20 bytes received then tx the packet in RF
00153                 pcRXtimeout_func();
00154             else
00155                 pcRXtimeout.attach(&pcRXtimeout_func, 0.020);
00156         }
00157     }
00158 }
00159 ///////////////////////////////////////////////////
00160