43 #include "dev/watchdog.h" 47 #include "sys/clock.h" 48 #include "sys/critical.h" 60 #include "hw_rfc_dbell.h" 61 #include "hw_rfc_pwr.h" 64 #include "driverlib/rf_mailbox.h" 65 #include "driverlib/rf_common_cmd.h" 66 #include "driverlib/rf_data_entry.h" 67 #include "driverlib/rf_prop_mailbox.h" 68 #include "driverlib/rf_prop_cmd.h" 71 #include "rf_patches/rf_patch_cpe_genfsk.h" 72 #include "rf_patches/rf_patch_rfe_genfsk.h" 74 #include "rf-core/smartrf-settings.h" 83 #define PRINTF(...) printf(__VA_ARGS__) 89 #define DATA_ENTRY_STATUS_PENDING 0x00 90 #define DATA_ENTRY_STATUS_ACTIVE 0x01 91 #define DATA_ENTRY_STATUS_BUSY 0x02 92 #define DATA_ENTRY_STATUS_FINISHED 0x03 93 #define DATA_ENTRY_STATUS_UNFINISHED 0x04 96 #ifdef PROP_MODE_CONF_DW 97 #define PROP_MODE_DW PROP_MODE_CONF_DW 99 #define PROP_MODE_DW 0 102 #ifdef PROP_MODE_CONF_USE_CRC16 103 #define PROP_MODE_USE_CRC16 PROP_MODE_CONF_USE_CRC16 105 #define PROP_MODE_USE_CRC16 0 116 #define RF_RADIO_OP_GET_STATUS(a) GET_FIELD_V(a, radioOp, status) 118 #ifdef PROP_MODE_CONF_RSSI_THRESHOLD 119 #define PROP_MODE_RSSI_THRESHOLD PROP_MODE_CONF_RSSI_THRESHOLD 121 #define PROP_MODE_RSSI_THRESHOLD 0xA6 124 static int8_t rssi_threshold = PROP_MODE_RSSI_THRESHOLD;
126 #if MAC_CONF_WITH_TSCH 127 static volatile uint8_t is_receiving_packet;
131 static int off(
void);
133 static rfc_propRxOutput_t rx_stats;
136 #define DOT_4G_MAX_FRAME_LEN 2047 137 #define DOT_4G_PHR_LEN 2 140 #define DOT_4G_PHR_CRC16 0x10 141 #define DOT_4G_PHR_DW 0x08 143 #if PROP_MODE_USE_CRC16 145 #define DOT_4G_PHR_CRC_BIT DOT_4G_PHR_CRC16 149 #define DOT_4G_PHR_CRC_BIT 0 154 #define DOT_4G_PHR_DW_BIT DOT_4G_PHR_DW 156 #define DOT_4G_PHR_DW_BIT 0 160 #ifdef PROP_MODE_CONF_TX_POWER_431_527 161 #define PROP_MODE_TX_POWER_431_527 PROP_MODE_CONF_TX_POWER_431_527 163 #define PROP_MODE_TX_POWER_431_527 prop_mode_tx_power_431_527 167 #ifdef PROP_MODE_CONF_TX_POWER_779_930 168 #define PROP_MODE_TX_POWER_779_930 PROP_MODE_CONF_TX_POWER_779_930 170 #define PROP_MODE_TX_POWER_779_930 prop_mode_tx_power_779_930 174 #if DOT_15_4G_FREQUENCY_BAND_ID==DOT_15_4G_FREQUENCY_BAND_470 175 #define TX_POWER_DRIVER PROP_MODE_TX_POWER_431_527 177 #define TX_POWER_DRIVER PROP_MODE_TX_POWER_779_930 180 extern const prop_mode_tx_power_config_t TX_POWER_DRIVER[];
183 #define OUTPUT_POWER_MAX (TX_POWER_DRIVER[0].dbm) 184 #define OUTPUT_POWER_UNKNOWN 0xFFFF 187 static const prop_mode_tx_power_config_t *tx_power_current = &TX_POWER_DRIVER[1];
189 #ifdef PROP_MODE_CONF_LO_DIVIDER 190 #define PROP_MODE_LO_DIVIDER PROP_MODE_CONF_LO_DIVIDER 192 #define PROP_MODE_LO_DIVIDER 0x05 195 #ifdef PROP_MODE_CONF_RX_BUF_CNT 196 #define PROP_MODE_RX_BUF_CNT PROP_MODE_CONF_RX_BUF_CNT 198 #define PROP_MODE_RX_BUF_CNT 4 201 #define DATA_ENTRY_LENSZ_NONE 0 202 #define DATA_ENTRY_LENSZ_BYTE 1 203 #define DATA_ENTRY_LENSZ_WORD 2 206 #define RX_BUF_METADATA_SIZE \ 207 (CRC_LEN * RF_CORE_RX_BUF_INCLUDE_CRC \ 208 + RF_CORE_RX_BUF_INCLUDE_RSSI \ 209 + RF_CORE_RX_BUF_INCLUDE_CORR \ 210 + 4 * RF_CORE_RX_BUF_INCLUDE_TIMESTAMP) 213 #define RX_BUF_LENGTH_OFFSET sizeof(rfc_dataEntry_t) 215 #define RX_BUF_DATA_OFFSET (RX_BUF_LENGTH_OFFSET + DOT_4G_PHR_LEN) 217 #define ALIGN_TO_4(size) (((size) + 3) & ~3) 219 #define RX_BUF_SIZE ALIGN_TO_4(RX_BUF_DATA_OFFSET \ 220 + NETSTACK_RADIO_MAX_PAYLOAD_LEN \ 221 + RX_BUF_METADATA_SIZE) 228 static uint8_t rx_buf[PROP_MODE_RX_BUF_CNT][RX_BUF_SIZE] CC_ALIGN(4);
231 static dataQueue_t rx_data_queue = { 0 };
234 volatile static uint8_t *rx_read_entry;
240 #define RAT_TIMESTAMP_OFFSET_SUB_GHZ USEC_TO_RADIO(160 * 6 - 240) 243 #define TX_BUF_PAYLOAD_LEN 180 244 #define TX_BUF_HDR_LEN 2 246 static uint8_t tx_buf[TX_BUF_HDR_LEN + TX_BUF_PAYLOAD_LEN] CC_ALIGN(4);
255 return smartrf_settings_cmd_prop_rx_adv.status == RF_CORE_RADIO_OP_STATUS_ACTIVE;
261 return smartrf_settings_cmd_prop_tx_adv.status == RF_CORE_RADIO_OP_STATUS_ACTIVE;
269 uint8_t attempts = 0;
271 rfc_CMD_GET_RSSI_t cmd;
276 if(
on() != RF_CORE_CMD_OK) {
277 PRINTF(
"get_rssi: on() failed\n");
278 return RF_CORE_CMD_CCA_REQ_RSSI_UNKNOWN;
282 rssi = RF_CORE_CMD_CCA_REQ_RSSI_UNKNOWN;
284 while((rssi == RF_CORE_CMD_CCA_REQ_RSSI_UNKNOWN || rssi == 0) && ++attempts < 10) {
285 memset(&cmd, 0x00,
sizeof(cmd));
286 cmd.commandNo = CMD_GET_RSSI;
289 PRINTF(
"get_rssi: CMDSTA=0x%08lx\n", cmd_status);
293 rssi = (cmd_status >> 16) & 0xFF;
310 freq_khz = smartrf_settings_cmd_fs.frequency * 1000;
318 freq_khz += (((smartrf_settings_cmd_fs.fractFreq * 1000) + 65535) / 65536);
320 return (freq_khz - DOT_15_4G_CHAN0_FREQUENCY) / DOT_15_4G_CHANNEL_SPACING;
329 new_freq = DOT_15_4G_CHAN0_FREQUENCY + (channel * DOT_15_4G_CHANNEL_SPACING);
331 freq = (uint16_t)(new_freq / 1000);
332 frac = (new_freq - (freq * 1000)) * 65536 / 1000;
334 PRINTF(
"set_channel: %u = 0x%04x.0x%04x (%lu)\n", channel, freq, frac,
337 smartrf_settings_cmd_prop_radio_div_setup.centerFreq = freq;
338 smartrf_settings_cmd_fs.frequency = freq;
339 smartrf_settings_cmd_fs.fractFreq = frac;
343 get_tx_power_array_last_element(
void)
345 const prop_mode_tx_power_config_t *array = TX_POWER_DRIVER;
348 while(array->tx_power != OUTPUT_POWER_UNKNOWN) {
359 return tx_power_current->dbm;
371 for(i = get_tx_power_array_last_element(); i >= 0; --i) {
372 if(power <= TX_POWER_DRIVER[i].dbm) {
378 tx_power_current = &TX_POWER_DRIVER[i];
386 prop_div_radio_setup(
void)
389 rfc_radioOp_t *cmd = (rfc_radioOp_t *)&smartrf_settings_cmd_prop_radio_div_setup;
391 rf_switch_select_path(RF_SWITCH_PATH_SUBGHZ);
394 smartrf_settings_cmd_prop_radio_div_setup.loDivider = PROP_MODE_LO_DIVIDER;
397 smartrf_settings_cmd_prop_radio_div_setup.txPower = tx_power_current->tx_power;
400 smartrf_settings_cmd_prop_radio_div_setup.config.frontEndMode =
401 RF_CORE_PROP_FRONT_END_MODE;
402 smartrf_settings_cmd_prop_radio_div_setup.config.biasMode =
403 RF_CORE_PROP_BIAS_MODE;
407 PRINTF(
"prop_div_radio_setup: DIV_SETUP, CMDSTA=0x%08lx, status=0x%04x\n",
408 cmd_status, cmd->status);
409 return RF_CORE_CMD_ERROR;
414 PRINTF(
"prop_div_radio_setup: DIV_SETUP wait, CMDSTA=0x%08lx," 415 "status=0x%04x\n", cmd_status, cmd->status);
416 return RF_CORE_CMD_ERROR;
419 return RF_CORE_CMD_OK;
426 volatile rfc_CMD_PROP_RX_ADV_t *cmd_rx_adv;
429 cmd_rx_adv = (rfc_CMD_PROP_RX_ADV_t *)&smartrf_settings_cmd_prop_rx_adv;
430 cmd_rx_adv->status = RF_CORE_RADIO_OP_STATUS_IDLE;
432 cmd_rx_adv->rxConf.bIncludeCrc = RF_CORE_RX_BUF_INCLUDE_CRC;
433 cmd_rx_adv->rxConf.bAppendRssi = RF_CORE_RX_BUF_INCLUDE_RSSI;
434 cmd_rx_adv->rxConf.bAppendTimestamp = RF_CORE_RX_BUF_INCLUDE_TIMESTAMP;
435 cmd_rx_adv->rxConf.bAppendStatus = RF_CORE_RX_BUF_INCLUDE_CORR;
441 cmd_rx_adv->maxPktLen = DOT_4G_MAX_FRAME_LEN - cmd_rx_adv->lenOffset;
445 if(ret != RF_CORE_CMD_OK) {
446 PRINTF(
"rf_cmd_prop_rx: send_cmd ret=%d, CMDSTA=0x%08lx, status=0x%04x\n",
447 ret, cmd_status, cmd_rx_adv->status);
448 return RF_CORE_CMD_ERROR;
452 RF_CORE_ENTER_RX_TIMEOUT);
455 if(cmd_rx_adv->status != RF_CORE_RADIO_OP_STATUS_ACTIVE) {
456 PRINTF(
"rf_cmd_prop_rx: CMDSTA=0x%08lx, status=0x%04x\n",
457 cmd_status, cmd_rx_adv->status);
458 return RF_CORE_CMD_ERROR;
465 init_rx_buffers(
void)
467 rfc_dataEntry_t *entry;
470 for(i = 0; i < PROP_MODE_RX_BUF_CNT; i++) {
471 entry = (rfc_dataEntry_t *)rx_buf[i];
472 entry->status = DATA_ENTRY_STATUS_PENDING;
473 entry->config.type = DATA_ENTRY_TYPE_GEN;
474 entry->config.lenSz = DATA_ENTRY_LENSZ_WORD;
475 entry->length = RX_BUF_SIZE - 8;
476 entry->pNextEntry = rx_buf[i + 1];
479 ((rfc_dataEntry_t *)rx_buf[PROP_MODE_RX_BUF_CNT - 1])->pNextEntry = rx_buf[0];
488 PRINTF(
"rx_on_prop: We were on. PD=%u, RX=0x%04x\n",
490 return RF_CORE_CMD_OK;
494 ret = rf_cmd_prop_rx();
497 ENERGEST_ON(ENERGEST_TYPE_LISTEN);
511 return RF_CORE_CMD_OK;
518 if(
rf_core_send_cmd(CMDR_DIR_CMD(CMD_ABORT), &cmd_status) != RF_CORE_CMD_OK) {
519 PRINTF(
"rx_off_prop: CMD_ABORT status=0x%08lx\n", cmd_status);
525 if(smartrf_settings_cmd_prop_rx_adv.status == PROP_DONE_STOPPED ||
526 smartrf_settings_cmd_prop_rx_adv.status == PROP_DONE_ABORT) {
528 ENERGEST_OFF(ENERGEST_TYPE_LISTEN);
529 ret = RF_CORE_CMD_OK;
531 PRINTF(
"rx_off_prop: status=0x%04x\n",
532 smartrf_settings_cmd_prop_rx_adv.status);
533 ret = RF_CORE_CMD_ERROR;
547 return LPM_MODE_SLEEP;
550 return LPM_MODE_MAX_SUPPORTED;
553 LPM_MODULE(prop_lpm_module, request, NULL, NULL, LPM_DOMAIN_NONE);
559 rfc_radioOp_t *cmd = (rfc_radioOp_t *)&smartrf_settings_cmd_fs;
563 PRINTF(
"prop_fs: CMD_FS, CMDSTA=0x%08lx, status=0x%04x\n",
564 cmd_status, cmd->status);
565 return RF_CORE_CMD_ERROR;
570 PRINTF(
"prop_fs: CMD_FS wait, CMDSTA=0x%08lx, status=0x%04x\n",
571 cmd_status, cmd->status);
572 return RF_CORE_CMD_ERROR;
575 return RF_CORE_CMD_OK;
589 if(
rf_core_send_cmd(CMDR_DIR_CMD(CMD_ABORT), &cmd_status) != RF_CORE_CMD_OK) {
590 PRINTF(
"soft_off_prop: CMD_ABORT status=0x%08lx\n", cmd_status);
595 RF_CORE_RADIO_OP_MASKED_STATUS_RUNNING, RF_CORE_TURN_OFF_TIMEOUT);
601 if(prop_div_radio_setup() != RF_CORE_CMD_OK) {
602 PRINTF(
"soft_on_prop: prop_div_radio_setup() failed\n");
603 return RF_CORE_CMD_ERROR;
606 if(prop_fs() != RF_CORE_CMD_OK) {
607 PRINTF(
"soft_on_prop: prop_fs() failed\n");
608 return RF_CORE_CMD_ERROR;
618 RAT_TIMESTAMP_OFFSET_SUB_GHZ
626 if(ti_lib_chipinfo_chip_family_is_cc13xx() ==
false) {
627 return RF_CORE_CMD_ERROR;
631 memset(rx_buf, 0,
sizeof(rx_buf));
634 rx_data_queue.pCurrEntry = rx_buf[0];
635 rx_data_queue.pLastEntry = NULL;
638 rx_read_entry = rx_buf[0];
640 smartrf_settings_cmd_prop_rx_adv.pQueue = &rx_data_queue;
641 smartrf_settings_cmd_prop_rx_adv.pOutput = (uint8_t *)&rx_stats;
645 if(
on() != RF_CORE_CMD_OK) {
646 PRINTF(
"init: on() failed\n");
647 return RF_CORE_CMD_ERROR;
650 ENERGEST_ON(ENERGEST_TYPE_LISTEN);
662 prepare(
const void *payload,
unsigned short payload_len)
664 if(payload_len > TX_BUF_PAYLOAD_LEN || payload_len > NETSTACK_RADIO_MAX_PAYLOAD_LEN) {
668 memcpy(&tx_buf[TX_BUF_HDR_LEN], payload, payload_len);
673 transmit(
unsigned short transmit_len)
678 volatile rfc_CMD_PROP_TX_ADV_t *cmd_tx_adv;
681 uint16_t total_length;
683 if(transmit_len > NETSTACK_RADIO_MAX_PAYLOAD_LEN) {
684 PRINTF(
"transmit: too long\n");
690 if(
on() != RF_CORE_CMD_OK) {
691 PRINTF(
"transmit: on() failed\n");
704 total_length = transmit_len + CRC_LEN;
706 tx_buf[0] = total_length & 0xFF;
707 tx_buf[1] = (total_length >> 8) + DOT_4G_PHR_DW_BIT + DOT_4G_PHR_CRC_BIT;
710 cmd_tx_adv = (rfc_CMD_PROP_TX_ADV_t *)&smartrf_settings_cmd_prop_tx_adv;
716 cmd_tx_adv->pktLen = transmit_len + DOT_4G_PHR_LEN;
717 cmd_tx_adv->pPkt = tx_buf;
729 ENERGEST_SWITCH(ENERGEST_TYPE_LISTEN, ENERGEST_TYPE_TRANSMIT);
732 while((cmd_tx_adv->status & RF_CORE_RADIO_OP_MASKED_STATUS)
733 == RF_CORE_RADIO_OP_MASKED_STATUS_RUNNING) {
739 if(!rf_core_poll_mode) {
744 if(cmd_tx_adv->status == RF_CORE_RADIO_OP_STATUS_PROP_DONE_OK) {
749 PRINTF(
"transmit: Not Sent OK status=0x%04x\n",
755 PRINTF(
"transmit: PROP_TX_ERR ret=%d, CMDSTA=0x%08lx, status=0x%04x\n",
756 ret, cmd_status, cmd_tx_adv->status);
764 ENERGEST_SWITCH(ENERGEST_TYPE_TRANSMIT, ENERGEST_TYPE_LISTEN);
773 cmd_tx_adv->status = RF_CORE_RADIO_OP_STATUS_IDLE;
785 send(
const void *payload,
unsigned short payload_len)
792 release_data_entry(
void)
794 rfc_dataEntryGeneral_t *entry = (rfc_dataEntryGeneral_t *)rx_read_entry;
795 uint8_t *data_ptr = &entry->data;
803 entry->status = DATA_ENTRY_STATUS_PENDING;
804 rx_read_entry = entry->pNextEntry;
807 if(rf_core_rx_is_full) {
808 rf_core_rx_is_full =
false;
809 PRINTF(
"RXQ was full, re-enabling radio!\n");
817 read_frame(
void *buf,
unsigned short buf_len)
819 rfc_dataEntryGeneral_t *entry = (rfc_dataEntryGeneral_t *)rx_read_entry;
820 uint8_t *data_ptr = &entry->data;
822 uint32_t rat_timestamp;
826 while(entry->status == DATA_ENTRY_STATUS_BUSY
827 && RTIMER_CLOCK_LT(
RTIMER_NOW(), t0 + (RTIMER_SECOND / 50)));
829 #if MAC_CONF_WITH_TSCH 831 is_receiving_packet = 0;
834 if(entry->status != DATA_ENTRY_STATUS_FINISHED) {
845 len = (*(uint16_t *)data_ptr);
847 if(len <= RX_BUF_METADATA_SIZE) {
848 PRINTF(
"RF: too short!");
850 release_data_entry();
855 len -= RX_BUF_METADATA_SIZE;
858 PRINTF(
"RF: too long\n");
860 release_data_entry();
864 memcpy(buf, data_ptr, len);
867 rf_core_last_rssi = (int8_t)data_ptr[len];
868 rf_core_last_corr_lqi = data_ptr[len + 5];
871 memcpy(&rat_timestamp, data_ptr + len + 1, 4);
875 if(!rf_core_poll_mode) {
879 packetbuf_set_attr(PACKETBUF_ATTR_RSSI, rf_core_last_rssi);
880 packetbuf_set_attr(PACKETBUF_ATTR_LINK_QUALITY, rf_core_last_corr_lqi);
883 release_data_entry();
893 int8_t rssi = RF_CORE_CMD_CCA_REQ_RSSI_UNKNOWN;
900 return RF_CORE_CCA_CLEAR;
905 if(
on() != RF_CORE_CMD_OK) {
906 PRINTF(
"channel_clear: on() failed\n");
910 return RF_CORE_CCA_CLEAR;
914 PRINTF(
"channel_clear: called while in TX\n");
915 return RF_CORE_CCA_CLEAR;
919 while(rssi == RF_CORE_CMD_CCA_REQ_RSSI_UNKNOWN || rssi == 0) {
925 rssi = (cmd_status >> 16) & 0xFF;
932 if(rssi >= rssi_threshold) {
933 return RF_CORE_CCA_BUSY;
936 return RF_CORE_CCA_CLEAR;
946 #if MAC_CONF_WITH_TSCH 954 if(!is_receiving_packet) {
958 if(HWREG(RFC_DBELL_BASE + RFC_DBELL_O_RFHWIFG) & RFC_DBELL_RFHWIFG_MDMSOFT) {
959 is_receiving_packet = 1;
964 if(!is_receiving_packet) {
966 ti_lib_rfc_hw_int_clear(RFC_DBELL_RFHWIFG_MDMSOFT);
970 return is_receiving_packet;
1005 volatile rfc_dataEntry_t *entry = (rfc_dataEntry_t *)rx_data_queue.pCurrEntry;
1009 if(entry->status == DATA_ENTRY_STATUS_FINISHED
1010 || entry->status == DATA_ENTRY_STATUS_BUSY) {
1012 if(!rf_core_poll_mode) {
1017 entry = (rfc_dataEntry_t *)entry->pNextEntry;
1018 }
while(entry != (rfc_dataEntry_t *)rx_data_queue.pCurrEntry);
1032 return RF_CORE_CMD_OK;
1037 smartrf_settings_cmd_prop_rx_adv.status);
1038 return RF_CORE_CMD_OK;
1049 PRINTF(
"on: rf_core_power_up() failed\n");
1053 return RF_CORE_CMD_ERROR;
1060 rf_patch_cpe_genfsk();
1061 while(!HWREG(RFC_DBELL_BASE + RFC_DBELL_O_RFACKIFG));
1062 HWREG(RFC_DBELL_BASE + RFC_DBELL_O_RFACKIFG) = 0;
1063 rf_patch_rfe_genfsk();
1066 HWREG(RFC_DBELL_BASE + RFC_DBELL_O_RFACKIFG) = 0;
1067 HWREG(RFC_DBELL_BASE + RFC_DBELL_O_CMDR) =
1068 CMDR_DIR_CMD_1BYTE(CMD_BUS_REQUEST, 1);
1071 ti_lib_rfc_adi3vco_ldo_voltage_mode(
true);
1074 ti_lib_rfc_rtrim((rfc_radioOp_t *)&smartrf_settings_cmd_prop_radio_div_setup);
1077 while(!HWREG(RFC_DBELL_BASE + RFC_DBELL_O_RFACKIFG));
1078 HWREG(RFC_DBELL_BASE + RFC_DBELL_O_RFACKIFG) = 0;
1081 PRINTF(
"on: rf_core_start_rat() failed\n");
1085 return RF_CORE_CMD_ERROR;
1100 if(prop_div_radio_setup() != RF_CORE_CMD_OK) {
1101 PRINTF(
"on: prop_div_radio_setup() failed\n");
1102 return RF_CORE_CMD_ERROR;
1105 if(prop_fs() != RF_CORE_CMD_OK) {
1106 PRINTF(
"on: prop_fs() failed\n");
1107 return RF_CORE_CMD_ERROR;
1110 return rx_on_prop();
1117 rfc_dataEntry_t *entry;
1124 return RF_CORE_CMD_OK;
1130 ENERGEST_OFF(ENERGEST_TYPE_LISTEN);
1132 #if !CC2650_FAST_RADIO_STARTUP 1138 smartrf_settings_cmd_prop_rx_adv.status = RF_CORE_RADIO_OP_STATUS_IDLE;
1144 for(i = 0; i < PROP_MODE_RX_BUF_CNT; i++) {
1145 entry = (rfc_dataEntry_t *)rx_buf[i];
1146 if(entry->status == DATA_ENTRY_STATUS_BUSY) {
1147 entry->status = DATA_ENTRY_STATUS_PENDING;
1151 return RF_CORE_CMD_OK;
1155 static radio_result_t
1156 set_send_on_cca(uint8_t enable)
1160 return RADIO_RESULT_NOT_SUPPORTED;
1162 return RADIO_RESULT_OK;
1165 static radio_result_t
1169 return RADIO_RESULT_INVALID_VALUE;
1173 case RADIO_PARAM_POWER_MODE:
1175 *value =
rf_is_on() ? RADIO_POWER_MODE_ON : RADIO_POWER_MODE_OFF;
1176 return RADIO_RESULT_OK;
1177 case RADIO_PARAM_CHANNEL:
1179 return RADIO_RESULT_OK;
1180 case RADIO_PARAM_RX_MODE:
1182 if(rf_core_poll_mode) {
1183 *value |= RADIO_RX_MODE_POLL_MODE;
1185 return RADIO_RESULT_OK;
1186 case RADIO_PARAM_TX_MODE:
1188 return RADIO_RESULT_OK;
1189 case RADIO_PARAM_TXPOWER:
1190 *value = get_tx_power();
1191 return RADIO_RESULT_OK;
1192 case RADIO_PARAM_CCA_THRESHOLD:
1193 *value = rssi_threshold;
1194 return RADIO_RESULT_OK;
1195 case RADIO_PARAM_RSSI:
1196 *value = get_rssi();
1198 if(*value == RF_CORE_CMD_CCA_REQ_RSSI_UNKNOWN) {
1199 return RADIO_RESULT_ERROR;
1201 return RADIO_RESULT_OK;
1203 case RADIO_CONST_CHANNEL_MIN:
1205 return RADIO_RESULT_OK;
1206 case RADIO_CONST_CHANNEL_MAX:
1207 *value = DOT_15_4G_CHANNEL_MAX;
1208 return RADIO_RESULT_OK;
1209 case RADIO_CONST_TXPOWER_MIN:
1210 *value = TX_POWER_DRIVER[get_tx_power_array_last_element()].dbm;
1211 return RADIO_RESULT_OK;
1212 case RADIO_CONST_TXPOWER_MAX:
1213 *value = OUTPUT_POWER_MAX;
1214 return RADIO_RESULT_OK;
1215 case RADIO_PARAM_LAST_RSSI:
1216 *value = rf_core_last_rssi;
1217 return RADIO_RESULT_OK;
1218 case RADIO_PARAM_LAST_LINK_QUALITY:
1219 *value = rf_core_last_corr_lqi;
1220 return RADIO_RESULT_OK;
1221 case RADIO_CONST_PHY_OVERHEAD:
1224 return RADIO_RESULT_OK;
1225 case RADIO_CONST_BYTE_AIR_TIME:
1227 return RADIO_RESULT_OK;
1228 case RADIO_CONST_DELAY_BEFORE_TX:
1230 return RADIO_RESULT_OK;
1231 case RADIO_CONST_DELAY_BEFORE_RX:
1233 return RADIO_RESULT_OK;
1234 case RADIO_CONST_DELAY_BEFORE_DETECT:
1236 return RADIO_RESULT_OK;
1238 return RADIO_RESULT_NOT_SUPPORTED;
1242 static radio_result_t
1245 radio_result_t rv = RADIO_RESULT_OK;
1246 uint8_t old_poll_mode;
1249 case RADIO_PARAM_POWER_MODE:
1250 if(value == RADIO_POWER_MODE_ON) {
1251 if(
on() != RF_CORE_CMD_OK) {
1252 PRINTF(
"set_value: on() failed (1)\n");
1253 return RADIO_RESULT_ERROR;
1255 return RADIO_RESULT_OK;
1257 if(value == RADIO_POWER_MODE_OFF) {
1259 return RADIO_RESULT_OK;
1261 return RADIO_RESULT_INVALID_VALUE;
1262 case RADIO_PARAM_CHANNEL:
1264 value > DOT_15_4G_CHANNEL_MAX) {
1265 return RADIO_RESULT_INVALID_VALUE;
1271 return RADIO_RESULT_OK;
1277 case RADIO_PARAM_RX_MODE:
1278 if(value & ~(RADIO_RX_MODE_POLL_MODE)) {
1279 return RADIO_RESULT_INVALID_VALUE;
1282 old_poll_mode = rf_core_poll_mode;
1283 rf_core_poll_mode = (value & RADIO_RX_MODE_POLL_MODE) != 0;
1284 if(rf_core_poll_mode == old_poll_mode) {
1285 return RADIO_RESULT_OK;
1289 case RADIO_PARAM_TX_MODE:
1291 return RADIO_RESULT_INVALID_VALUE;
1295 case RADIO_PARAM_TXPOWER:
1296 if(value < TX_POWER_DRIVER[get_tx_power_array_last_element()].dbm ||
1297 value > OUTPUT_POWER_MAX) {
1298 return RADIO_RESULT_INVALID_VALUE;
1303 set_tx_power(value);
1305 if(soft_on_prop() != RF_CORE_CMD_OK) {
1306 PRINTF(
"set_value: soft_on_prop() failed\n");
1307 rv = RADIO_RESULT_ERROR;
1310 return RADIO_RESULT_OK;
1312 case RADIO_PARAM_CCA_THRESHOLD:
1313 rssi_threshold = (int8_t)value;
1316 return RADIO_RESULT_NOT_SUPPORTED;
1321 return RADIO_RESULT_OK;
1325 if(rx_off_prop() != RF_CORE_CMD_OK) {
1326 PRINTF(
"set_value: rx_off_prop() failed\n");
1327 rv = RADIO_RESULT_ERROR;
1333 PRINTF(
"set_value: rf_core_restart_rat() failed\n");
1339 if(soft_on_prop() != RF_CORE_CMD_OK) {
1340 PRINTF(
"set_value: soft_on_prop() failed\n");
1341 rv = RADIO_RESULT_ERROR;
1347 static radio_result_t
1348 get_object(radio_param_t param,
void *dest,
size_t size)
1350 if(param == RADIO_PARAM_LAST_PACKET_TIMESTAMP) {
1351 if(size !=
sizeof(rtimer_clock_t) || !dest) {
1352 return RADIO_RESULT_INVALID_VALUE;
1354 *(rtimer_clock_t *)dest = rf_core_last_packet_timestamp;
1356 return RADIO_RESULT_OK;
1359 return RADIO_RESULT_NOT_SUPPORTED;
1362 static radio_result_t
1363 set_object(radio_param_t param,
const void *src,
size_t size)
1365 return RADIO_RESULT_NOT_SUPPORTED;
radio_result_t(* get_object)(radio_param_t param, void *dest, size_t size)
Get a radio parameter object.
void oscillators_request_hf_xosc(void)
Requests the HF XOSC as the source for the HF clock, but does not perform the actual switch...
static uint8_t transmitting(void)
Check the RF's TX status.
int(* prepare)(const void *payload, unsigned short payload_len)
Prepare the radio with a packet to be sent.
Header file with macros which rename TI CC26xxware functions.
static uint8_t rf_is_on(void)
Checks whether the RFC domain is accessible and the RFC is in IEEE RX.
Header file for the energy estimation mechanism
rfc_radioOp_t * rf_core_get_last_radio_op()
Returns a pointer to the most recent proto-dependent Radio Op.
Header file for the radio API
static void critical_exit(int_master_status_t status)
Exit a critical section and restore the master interrupt.
int rf_core_power_up()
Turn on power to the RFC and boot it.
void rf_core_power_down()
Disable RFCORE clock domain in the MCU VD and turn off the RFCORE PD.
int(* receiving_packet)(void)
Check if the radio driver is currently receiving a packet.
radio_result_t(* set_value)(radio_param_t param, radio_value_t value)
Set a radio parameter value.
int(* pending_packet)(void)
Check if the radio driver has just received a packet.
uint8_t rf_core_set_modesel()
Initialise RF APIs in the RF core.
The structure of a device driver for a radio in Contiki.
#define RTIMER_BUSYWAIT_UNTIL(cond, max_time)
Busy-wait until a condition for at most max_time.
static void set_channel(uint8_t channel)
Set the current operating channel.
void lpm_sleep(void)
Enter sleep mode.
int(* channel_clear)(void)
Perform a Clear-Channel Assessment (CCA) to find out if there is a packet in the air or not...
Header file for the CC13xx/CC26xx RF core driver.
int radio_value_t
Each radio has a set of parameters that designate the current configuration and state of the radio...
#define IEEE802154_DEFAULT_CHANNEL
The default channel for IEEE 802.15.4 networks.
static int_master_status_t critical_enter()
Enter a critical section.
#define RTIMER_NOW()
Get the current clock time.
Header file for the CC13xx/CC26xx oscillator control.
uint32_t rf_core_convert_rat_to_rtimer(uint32_t rat_timestamp)
Convert from RAT timestamp to rtimer ticks.
Header file with descriptors for the various modes of operation defined in IEEE 802.15.4g.
void oscillators_switch_to_hf_rc(void)
Switches MF and HF clock source to be the HF RC OSC.
INT_MASTER_STATUS_DATATYPE int_master_status_t
Master interrupt state representation data type.
void rf_core_primary_mode_register(const rf_core_primary_mode_t *mode)
Register a primary mode for radio operation.
Header file for the CC13xx prop mode NETSTACK_RADIO driver.
int(* send)(const void *payload, unsigned short payload_len)
Prepare & transmit a packet.
A data strcuture representing the radio's primary mode of operation.
int(* transmit)(unsigned short transmit_len)
Send the packet that has previously been prepared.
void process_poll(struct process *p)
Request a process to be polled.
int(* off)(void)
Turn the radio off.
Header file for the real-time timer module.
uint8_t rf_core_rat_init(void)
Initialize the RAT to RTC conversion machinery.
void rf_core_cmd_done_dis(void)
Disable the LAST_CMD_DONE and LAST_FG_CMD_DONE interrupts.
uint8_t rf_ble_is_active()
Check whether the BLE beacond is currently active.
Header file for the CC13xx/CC26xx BLE driver.
Header file with definitions related to RF switch support.
#define RADIO_TX_MODE_SEND_ON_CCA
The radio transmission mode controls whether transmissions should be done using clear channel assessm...
uint8_t rf_core_is_accessible()
Check whether the RF core is accessible.
Header file for the CC13xx/CC26xx UART driver.
void oscillators_switch_to_hf_xosc(void)
Performs the switch to the XOSC.
uint_fast8_t rf_core_send_cmd(uint32_t cmd, uint32_t *status)
Sends a command to the RF core.
Header file for the Packet buffer (packetbuf) management
#define LPM_MODULE(n, m, s, w, l)
Declare a variable to be used in order to get notifications from LPM.
void rf_core_setup_interrupts(void)
Setup RF core interrupts.
Include file for the Contiki low-layer network stack (NETSTACK)
uint8_t rf_core_start_rat(void)
Start the CM0 RAT.
uint8_t rf_core_restart_rat(void)
Restart the CM0 RAT.
radio_result_t(* get_value)(radio_param_t param, radio_value_t *value)
Get a radio parameter value.
Default definitions of C compiler quirk work-arounds.
radio_result_t(* set_object)(radio_param_t param, const void *src, size_t size)
Set a radio parameter object.
void rf_core_cmd_done_en(bool fg)
Enable interrupt on command done.
uint8_t rf_core_check_rat_overflow(void)
Check if RAT overflow has occured and increment the overflow counter if so.
int(* on)(void)
Turn the radio on.
void process_start(struct process *p, process_data_t data)
Start a process.
void lpm_register_module(lpm_registered_module_t *module)
Register a module for LPM notifications.
uint_fast8_t rf_core_wait_cmd_done(void *cmd)
Block and wait for a Radio op to complete.
static uint8_t get_channel()
Get the current operating channel.