Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
TestCC1200.cpp
- Committer:
- MultipleMonomials
- Date:
- 2020-08-28
- Revision:
- 1:7e7812669c9c
- Parent:
- 0:ea2678a73bde
- Child:
- 2:ff257762763e
File content as of revision 1:7e7812669c9c:
//
// Test suite for the CC1200 radio driver.
// Provides a menu to configure radio options, and
// attempts to send and receive a signal using two radios connected
// to the processor.
//
#include <mbed.h>
#include <SerialStream.h>
#include <CC1200.h>
#include <cinttypes>
// Pin definitions
// change these to match your board setup
#define PIN_SPI_MOSI P0_9
#define PIN_SPI_MISO P0_8
#define PIN_SPI_SCLK P0_7
#define PIN_TX_CS P0_6
#define PIN_TX_RST P0_29
#define PIN_RX_CS P0_4
#define PIN_RX_RST P0_30
BufferedSerial serial(USBTX, USBRX, 115200);
SerialStream<BufferedSerial> pc(serial);
CC1200 txRadio(PIN_SPI_MOSI, PIN_SPI_MISO, PIN_SPI_SCLK, PIN_TX_CS, PIN_TX_RST, &pc);
CC1200 rxRadio(PIN_SPI_MOSI, PIN_SPI_MISO, PIN_SPI_SCLK, PIN_RX_CS, PIN_RX_RST, &pc);
void checkExistance()
{
pc.printf("Checking TX radio.....\n");
bool txSuccess = txRadio.begin();
pc.printf("TX radio initialized: %s\n", txSuccess ? "true" : "false");
pc.printf("Checking RX radio.....\n");
bool rxSuccess = rxRadio.begin();
pc.printf("RX radio initialized: %s\n", rxSuccess ? "true" : "false");
}
void checkSignalTransmit()
{
pc.printf("Initializing CC1200s.....\n");
txRadio.begin();
rxRadio.begin();
pc.printf("Configuring RF settings.....\n");
int config=-1;
//MENU. ADD AN OPTION FOR EACH TEST.
pc.printf("Select a config: \n");
// This is similar to the SmartRF "100ksps ARIB Standard" configuration, except it doesn't use zero-if
pc.printf("1. 915MHz 100ksps 2-GFSK DEV=50kHz CHF=208kHz\n");
// This should be identical to the SmartRF "500ksps 4-GFSK Max Throughput ARIB Standard" configuration
pc.printf("2. 915MHz 500ksps 4-GFSK DEV=400kHz CHF=1666kHz Zero-IF\n");
pc.printf("3. 915MHz 38.4ksps 2-GFSK DEV=20kHz CHF=833kHz\n");
pc.printf("4. 915MHz 100ksps 2-GFSK DEV=50kHz CHF=208kHz Fixed Length\n");
pc.scanf("%d", &config);
printf("Running test with config %d:\n\n", config);
CC1200::PacketMode mode = CC1200::PacketMode::VARIABLE_LENGTH;
CC1200::Band band = CC1200::Band::BAND_820_960MHz;
float frequency = 915e6;
const float txPower = 0;
float fskDeviation;
float symbolRate;
float rxFilterBW;
CC1200::ModFormat modFormat;
uint8_t ifCfg = 0b101; // max IF
bool imageCompEnabled = true;
bool dcOffsetCorrEnabled = true;
uint8_t agcRefLevel;
uint8_t dcFiltSettingCfg = 1; // default chip setting
uint8_t dcFiltCutoffCfg = 4; // default chip setting
CC1200::SyncMode syncMode = CC1200::SyncMode::SYNC_32_BITS;
uint32_t syncWord = 0x930B51DE; // default sync word
uint8_t syncThreshold = 8; // TI seems to recommend this threshold for most configs above 100ksps
uint8_t preableLengthCfg = 5; // default chip setting
uint8_t preambleFormatCfg = 0; // default chip setting
if(config == 1)
{
fskDeviation = 49896;
symbolRate = 100000;
rxFilterBW = 208300;
modFormat = CC1200::ModFormat::GFSK_2;
agcRefLevel = 0x2A;
}
else if(config == 2)
{
// SmartRF "500ksps 4-GFSK ARIB standard" config
fskDeviation = 399169;
symbolRate = 500000;
rxFilterBW = 1666700;
ifCfg = 0;
imageCompEnabled = false;
dcOffsetCorrEnabled = true;
modFormat = CC1200::ModFormat::GFSK_4;
agcRefLevel = 0x2F;
}
else if(config == 3)
{
fskDeviation = 19989;
symbolRate = 38400;
rxFilterBW = 104200;
modFormat = CC1200::ModFormat::GFSK_2;
agcRefLevel = 0x27;
}
else if(config == 4)
{
fskDeviation = 49896;
symbolRate = 100000;
rxFilterBW = 208300;
modFormat = CC1200::ModFormat::GFSK_2;
agcRefLevel = 0x2A;
mode = CC1200::PacketMode::FIXED_LENGTH;
}
else
{
pc.printf("Invalid config number!");
return;
}
for(CC1200 & radio : {std::ref(txRadio), std::ref(rxRadio)})
{
radio.configureFIFOMode();
radio.setPacketMode(mode);
radio.setModulationFormat(modFormat);
radio.setFSKDeviation(fskDeviation);
radio.setSymbolRate(symbolRate);
radio.setOutputPower(txPower);
radio.setRadioFrequency(band, frequency);
radio.setIFMixCFG(ifCfg);
radio.configureDCFilter(dcOffsetCorrEnabled, dcFiltSettingCfg, dcFiltCutoffCfg);
radio.setIQMismatchCompensationEnabled(imageCompEnabled);
radio.setRXFilterBandwidth(rxFilterBW);
radio.configureSyncWord(syncWord, syncMode, syncThreshold);
radio.configurePreamble(preableLengthCfg, preambleFormatCfg);
// AGC configuration (straight from SmartRF)
radio.setAGCReferenceLevel(agcRefLevel);
radio.setAGCSyncBehavior(CC1200::SyncBehavior::FREEZE_NONE);
if(ifCfg == 0)
{
radio.setAGCGainTable(CC1200::GainTable::ZERO_IF, 11, 0);
}
else
{
// enable all AGC steps for NORMAL mode
radio.setAGCGainTable(CC1200::GainTable::NORMAL, 17, 0);
}
radio.setAGCHysteresis(0b10);
radio.setAGCSlewRate(0);
}
// configure on-transmit actions
txRadio.setOnTransmitState(CC1200::State::TX);
rxRadio.setOnReceiveState(CC1200::State::RX, CC1200::State::RX);
pc.printf("Starting transmission.....\n");
txRadio.startTX();
rxRadio.startRX();
const char message[] = "Hello world!";
char receiveBuffer[sizeof(message)];
if(mode == CC1200::PacketMode::FIXED_LENGTH)
{
txRadio.setPacketLength(sizeof(message) - 1);
rxRadio.setPacketLength(sizeof(message) - 1);
}
while(true)
{
ThisThread::sleep_for(1s);
pc.printf("\n---------------------------------\n");
pc.printf("<<SENDING: %s\n", message);
txRadio.enqueuePacket(message, sizeof(message) - 1);
// update TX radio
pc.printf("TX radio: state = 0x%" PRIx8 ", TX FIFO len = %zu, FS lock = 0x%u\n",
static_cast<uint8_t>(txRadio.getState()), txRadio.getTXFIFOLen(), txRadio.readRegister(CC1200::ExtRegister::FSCAL_CTRL) & 1);
// wait a while for the packet to come in.
ThisThread::sleep_for(10ms);
// wait the time we expect the message to take, with a safety factor of 2
auto timeoutTime = std::chrono::microseconds(static_cast<int64_t>((1/symbolRate) * 1e-6f * sizeof(message) * 2));
Timer packetReceiveTimeout;
packetReceiveTimeout.start();
bool hasPacket;
do
{
hasPacket = rxRadio.hasReceivedPacket();
}
while(packetReceiveTimeout.elapsed_time() < timeoutTime && !hasPacket);
pc.printf("RX radio: state = 0x%" PRIx8 ", RX FIFO len = %zu\n",
static_cast<uint8_t>(rxRadio.getState()), rxRadio.getRXFIFOLen());
if(hasPacket)
{
rxRadio.receivePacket(receiveBuffer, sizeof(message) - 1);
receiveBuffer[sizeof(message)-1] = '\0';
pc.printf(">>RECEIVED: %s\n", receiveBuffer);
}
else
{
pc.printf(">>No packet received!\n");
}
}
}
int main()
{
pc.printf("\nCC1200 Radio Test Suite:\n");
while(1){
int test=-1;
//MENU. ADD AN OPTION FOR EACH TEST.
pc.printf("Select a test: \n");
pc.printf("1. Exit Test Suite\n");
pc.printf("2. Check Existence\n");
pc.printf("3. Check Transmitting Signal\n");
pc.scanf("%d", &test);
printf("Running test %d:\n\n", test);
//SWITCH. ADD A CASE FOR EACH TEST.
switch(test) {
case 1: pc.printf("Exiting test suite.\n"); return 0;
case 2: checkExistance(); break;
case 3: checkSignalTransmit(); break;
default: pc.printf("Invalid test number. Please run again.\n"); continue;
}
pc.printf("done.\r\n");
}
return 0;
}
CC1200