#include "myRadio.h" #include "myRadio_gpio.h" #include "common.h" #include "SN_TIM1_INIT.h" /**-------------------------radio include----------------------------------**/ #include "pan_rf.h" /**-------------------------radio include end----------------------------------**/ static int8_t rfTxPower; static uint32_t rfFrequence; static uint32_t rfBaudrate; static uint8_t rfSyncword; static uint8_t rf_sf; static uint8_t rf_bw; static uint8_t rf_cr; static rfRxCallBack rxCb; static uint8_t rfRxBuffer[64]; static uint32_t rf_handle; static uint8_t rf_workProcess = RF_PRC_IDLE; static uint8_t chipType; static uint32_t cadCheckWindow_ms = 0; static uint32_t cadCheckInterval_ms = 0; static uint32_t cadCheckWindowCount_ms = 0; static uint32_t cadCheckIntervalCount_ms = 0; /**-------------------------radio params----------------------------------**/ typedef struct { int8_t power; uint8_t regValue; }rfPowerReg_ts; rfPowerReg_ts rfPowerRegTab[RF_TX_PWR_MAX_COUNT] = { { .power = -26, .regValue = 1, }, { .power = -17, .regValue = 2, }, { .power = -5, .regValue = 3, }, { .power = -3, .regValue = 4, }, { .power = -2, .regValue = 5, }, { .power = -1, .regValue = 6, }, { .power = 2, .regValue = 7, }, { .power = 4, .regValue = 8, }, { .power = 5, .regValue = 9, }, { .power = 7, .regValue = 10, }, { .power = 8, .regValue = 11, }, { .power = 9, .regValue = 12, }, { .power = 10, .regValue = 13, }, { .power = 11, .regValue = 14, }, { .power = 12, .regValue = 15, }, { .power = 13, .regValue = 16, }, { .power = 14, .regValue = 17, }, { .power = 15, .regValue = 18, }, { .power = 16, .regValue = 19, }, { .power = 17, .regValue = 20, }, { .power = 18, .regValue = 21, }, { .power = 19, .regValue = 22, }, { .power = 20, .regValue = 22, } }; const loraBaudrateFrame_ts loraBaudrateFrame[MAX_RF_BAUDRATE_COUNT] = { {//244.14bps,SF=12,BW=62.5kHz(6),CR=2 .SpreadingFactor = 12, .SignalBw = 6, .ErrorCoding = 2, }, {//627.79 bps,SF=9,BW=62.5kHz(6),CR=3 .SpreadingFactor = 9, .SignalBw = 6, .ErrorCoding = 4, }, {//1,255.58 bps,SF=9,BW=125kHz(7),CR=3 .SpreadingFactor = 9, .SignalBw = 7, .ErrorCoding = 3, }, {//2,511.16 bps,SF=8,BW=125kHz(7),CR=2 .SpreadingFactor = 8, .SignalBw = 7, .ErrorCoding = 2, }, {//5022.32bps,SF=8,BW=250kHz(8),CR=2 .SpreadingFactor = 8, .SignalBw = 8, .ErrorCoding = 2, }, {//12500bps,SF=8,BW=500kHz(9),CR=1 .SpreadingFactor = 8, .SignalBw = 9, .ErrorCoding = 1, }, {//20400bps,SF=8,BW=500kHz(9),CR=1 .SpreadingFactor = 7, .SignalBw = 9, .ErrorCoding = 1, }, {//62500bps,SF=5,BW=500kHz(9),CR=1 .SpreadingFactor = 7, .SignalBw = 9, .ErrorCoding = 1, }, }; bool rf_ifq; uint8_t regulatorMode = USE_LDO; extern struct RxDoneMsg RxDoneParams; uint8_t getRfPowerTabIndex(int8_t power); /**-------------------------radio params end----------------------------------**/ void myRadio_delay(uint32_t time_ms) { std_delayms(time_ms); } /** * @brief IO口中断回调 * IO口产生中断后会执行该函数 * 用于接收射频工作的中断响应 * * @param index */ void myRadio_gpioCallback(uint8_t index) { rf_ifq = true; } /** * @brief IO口中断回调 * IO口产生中断后会执行该函数 * 用于接收射频工作的中断响应 * * @param index */ void myRadio_gpioCadCallback(uint8_t index) { if (rf_workProcess != RF_PRC_CAD_RX) { return; } printf("cad = %d= %d\r\n", rf_workProcess, SN_GPIO_PIN_get(RF_PAN3029_IO11)); rf_workProcess = RF_PRC_IDLE; if (SN_GPIO_PIN_get(RF_PAN3029_IO11)) { cadCheckWindowCount_ms = 0; // cadCheckIntervalCount_ms = 0; printf("gpioCad\n"); // RF_StopCad(); // myRadio_receiver(); rf_workProcess = RF_PRC_RX; } else { } } void myRadio_timCallback(uint8_t index) { static uint32_t tiout = 0; tiout++; if (tiout > 1000) { tiout = 0; } if (cadCheckWindowCount_ms) { cadCheckWindowCount_ms--; if (cadCheckWindowCount_ms == 0) { RF_StopCad(); rf_workProcess = RF_PRC_IDLE; // RF_EnterSleepState(); printf("Window Window=%d Interval=%d\n", cadCheckWindowCount_ms, cadCheckIntervalCount_ms); } } if (cadCheckIntervalCount_ms) { cadCheckIntervalCount_ms--; if (cadCheckIntervalCount_ms == 0) { printf("Interval Window=%d Interval=%d\n", cadCheckWindowCount_ms, cadCheckIntervalCount_ms); // RF_ExitSleepState(); myRadio_restartCadReceiver(); } } } /** * @brief 射频初始化 * * @param agr0 * @param agr1_ptr 无线工作状态响应回调 * 产生回调给外部使用,@rfRxCallBack */ void myRadio_init(int agr0, void *agr1_ptr) { myRadio_gpio_init(myRadio_gpioCallback); SN_EXIT_set(RF_PAN3029_IO11,GPIO_NOPULL,myRadio_gpioCadCallback,EXTI_TRIGGER_RISING_FALLING,NVIC_PRIO_3); /**-------------------------radio init----------------------------------**/ int ret = 0; #ifdef SPI_SOFT_3LINE RF_WriteReg(0x00, 0x03); /* 选择寄存器页3 */ RF_WriteReg(0x1A, 0x83); /* 使能3ine SPI */ #endif ret = RF_Init(); if(ret != RF_OK) { // printf(" RF Init Fail"); while(1); } RF_ConfigUserParams(); /* 配置 frequency、SF、BW、Preamble、CRC等参数 */ // RF_SetRegulatorMode(regulatorMode); /* 设置芯片为LDO电源模式 */ SN_TIM1_CALL_set(1000 ,TIM1_AGAIN_WORK ,myRadio_timCallback ,NVIC_PRIO_2); /**-------------------------radio init end----------------------------------**/ myRadio_delay(10); RF_EXT_PA_TO_IDLE(); if ((rfRxCallBack )agr1_ptr) { rxCb = (rfRxCallBack )agr1_ptr; } rf_handle = 0xe5; } void RadioSetregulatorMode(uint8_t mode) { regulatorMode = mode; } /** * @brief 射频底层执行程序 * 要放在主循环中执行 * */ void myRadio_process(void) { rfRxPacket_ts rfRxPacket; if (rf_handle == 0) { return; } if (rf_ifq == false) { return; } rf_ifq = false; printf("rf_process=%d\n", rf_workProcess); if (!((rf_workProcess == RF_PRC_TX) || (rf_workProcess == RF_PRC_RX) )) { return; } uint8_t IRQFlag; IRQFlag = RF_GetIRQFlag(); /* 获取中断标志位 */ printf("IRQFlag=0x%X\n", IRQFlag); if (IRQFlag & RF_IRQ_TX_DONE) /* 发送完成中断 */ { RF_TurnoffLdoPA(); /* 发送完成后须关闭内部PA */ RF_ClrIRQFlag(RF_IRQ_TX_DONE); /* 清除发送完成中断标志位 */ IRQFlag &= ~RF_IRQ_TX_DONE; RF_EnterStandbyState(); /* 发送完成后须设置为RF_STATE_STB3状态 */ // printf(">>RF_IRQ_TX_DONE!\r\n"); RF_EXT_PA_TO_IDLE(); if (rxCb) { rxCb(TX_STA_SECCESS, rfRxPacket); } } if (IRQFlag & RF_IRQ_RX_DONE) /* 接收完成中断 */ { // g_RfRxPkt.Snr = RF_GetPktSnr(); /* 获取接收数据包的SNR值 */ rfRxPacket.rssi = RF_GetPktRssi(); /* 获取接收数据包的RSSI值 */ rfRxPacket.len = RF_GetRecvPayload(rfRxPacket.payload); /* 获取接收数据和长度 */ // printf(">>RF_IRQ_RX_DONE!\r\n"); // printf("+RxLen=%d, Rx Count=%d\n", g_RfRxPkt.RxLen, ++g_RxCount); // printf("+RxHexData:\r\n"); // print_hex(g_RfRxPkt.RxBuf, g_RfRxPkt.RxLen); /* 以十六进制方式打印接收数据 */ // printf("SNR:%ddB, RSSI:%ddBm \r\n", (int)g_RfRxPkt.Snr, (int)g_RfRxPkt.Rssi); RF_ClrIRQFlag(RF_IRQ_RX_DONE); /* 清除接收完成中断标志位 */ IRQFlag &= ~RF_IRQ_RX_DONE; RF_EXT_PA_TO_IDLE(); if (rxCb) { rxCb(RX_STA_SECCESS, rfRxPacket); } } if (IRQFlag & RF_IRQ_CRC_ERR) /* CRC错误中断 */ { RF_ClrIRQFlag(RF_IRQ_CRC_ERR); /* 清除CRC错误中断标志位 */ IRQFlag &= ~RF_IRQ_CRC_ERR; // printf(">>RF_IRQ_CRC_ERR\r\n"); RF_EXT_PA_TO_IDLE(); if (rxCb) { rxCb(RX_STA_PAYLOAD_ERROR, rfRxPacket); } } if (IRQFlag & RF_IRQ_RX_TIMEOUT) /* 接收超时中断 */ { RF_ClrIRQFlag(RF_IRQ_RX_TIMEOUT); /* 清除接收超时中断标志位 */ IRQFlag &= ~RF_IRQ_RX_TIMEOUT; // printf(">>RF_IRQ_RX_TIMEOUT\r\n"); RF_EXT_PA_TO_IDLE(); if (rxCb) { rxCb(RX_STA_TIMEOUT, rfRxPacket); } } if (IRQFlag) { RF_ClrIRQFlag(IRQFlag); /* 清除未处理的中断标志位 */ } } /** * @brief 退出射频进入休眠 * */ void myRadio_abort(void) { if (rf_handle == 0) { return; } RF_EXT_PA_TO_IDLE(); // rf_deepsleep(); RF_EnterSleepState(); rf_workProcess = RF_PRC_SLEEP; } /** * @brief 获取射频工作中心频率 * * @return uint32_t */ uint32_t myRadio_getFrequency(void) { if (rf_handle == 0) { return 0; } return rfFrequence; } /** * @brief 设置射频工作中心频率 * * @param freq * 具体频点,单位:Hz */ void myRadio_setFrequency(uint32_t freq) { if (rf_handle == 0) { return; } rfFrequence = freq; RF_SetFreq(rfFrequence); } /** * @brief 获取发射功率 * * @return int8_t */ int8_t myRadio_getTxPower(void) { if (rf_handle == 0) { return 0; } return rfTxPower; } /** * @brief 设置发射功率 * * @param power * 单位:dbm */ void myRadio_setTxPower(int8_t power) { if (rf_handle == 0) { return; } rfTxPower = power; RF_SetTxPower(rfPowerRegTab[getRfPowerTabIndex(rfTxPower)].regValue); } /** * 获取射频波特率 * @param : br-> */ uint32_t myRadio_getBaudrate(void) { if (rf_handle == 0) { return 0; } return rfBaudrate; } /** * 设置射频波特率 * @param : br-> */ void myRadio_setBaudrate(uint32_t br) { if (rf_handle == 0) { return; } rfBaudrate = br; RF_SetCR(loraBaudrateFrame[br].ErrorCoding); RF_SetBW(loraBaudrateFrame[br].SignalBw); RF_SetSF(loraBaudrateFrame[br].SpreadingFactor); } void myRadio_setSyncWord(uint8_t syncword) { if (rf_handle == 0) { return; } rfSyncword = syncword; RF_SetSyncWord(syncword); } void myRadio_setRfParams(uint8_t sf, uint8_t bw, uint8_t cr) { if (rf_handle == 0) { return; } rf_sf = sf; rf_bw = bw; rf_cr = cr; RF_SetCR(cr); RF_SetBW(bw); RF_SetSF(sf); } /** * @brief 设置模组型号 * * @param type */ void myRadio_setChipType(uint8_t type) { chipType = type; } /** * @brief 获取模组型号 * * @return uint8_t */ uint8_t myRadio_getChipType(void) { return chipType; } int16_t myRadio_getRssi(void) { return (int16_t)RF_GetRealTimeRssi(); } /** * @brief 无线发送数据包 * * @param packet */ void myRadio_transmit(rfTxPacket_ts *packet) { if (rf_handle == 0) { return; } RF_EXT_PA_TO_TX(); // uint32_t getTxtime; if (RF_GetOperateState() == RF_STATE_DEEPSLEEP) { myRadio_init(0, NULL); myRadio_setFrequency(rfFrequence); myRadio_setTxPower(rfTxPower); myRadio_setRfParams(rf_sf, rf_bw, rf_cr); myRadio_delay(10); } if (RF_GetOperateState() == RF_STATE_SLEEP) { RF_ExitSleepState(); myRadio_delay(10); } RF_TxSinglePkt(packet->payload, packet->len); rf_workProcess = RF_PRC_TX; } /** * @brief 无线发送数据包 * * @param packet */ void myRadio_transmitArray(uint8_t *packet, uint16_t len) { if (rf_handle == 0) { return; } RF_EXT_PA_TO_TX(); // uint32_t getTxtime; if (RF_GetOperateState() == RF_STATE_DEEPSLEEP) { myRadio_init(0, NULL); myRadio_setFrequency(rfFrequence); myRadio_setTxPower(rfTxPower); myRadio_setRfParams(rf_sf, rf_bw, rf_cr); myRadio_delay(10); } if (RF_GetOperateState() == RF_STATE_SLEEP) { RF_ExitSleepState(); myRadio_delay(10); } RF_SetTx(packet, len); rf_workProcess = RF_PRC_TX; } /** * @brief 进入无线接收 * */ void myRadio_receiver(void) { if (rf_handle == 0) { return; } RF_EXT_PA_TO_RX(); if (RF_GetOperateState() == RF_STATE_DEEPSLEEP) { myRadio_init(0, NULL); myRadio_setFrequency(rfFrequence); myRadio_setTxPower(rfTxPower); myRadio_setRfParams(rf_sf, rf_bw, rf_cr); myRadio_delay(10); } if (RF_GetOperateState() == RF_STATE_SLEEP) { RF_ExitSleepState(); myRadio_delay(10); } RF_EnterSingleRxWithTimeout(3000); rf_workProcess = RF_PRC_RX; } /** * @brief 进入无线接收 * */ void myRadio_cadReceiver(uint32_t window_ms, uint32_t interval_ms) { if (rf_handle == 0) { return; } RF_EXT_PA_TO_RX(); if (RF_GetOperateState() == RF_STATE_DEEPSLEEP) { myRadio_init(0, NULL); myRadio_setFrequency(rfFrequence); myRadio_setTxPower(rfTxPower); myRadio_setRfParams(rf_sf, rf_bw, rf_cr); myRadio_delay(10); } if (RF_GetOperateState() == RF_STATE_SLEEP) { RF_ExitSleepState(); myRadio_delay(10); } cadCheckWindow_ms = window_ms; cadCheckInterval_ms = interval_ms; cadCheckWindowCount_ms = window_ms; cadCheckIntervalCount_ms = interval_ms; RF_StartCad(RF_CAD_THRESHOLD_20, RF_CAD_03_SYMBOL); printf("start to cad\n"); rf_workProcess = RF_PRC_CAD_RX; } void myRadio_restartCadReceiver(void) { if (rf_handle == 0) { return; } if (rf_workProcess == RF_PRC_CAD_RX) { return; } RF_EXT_PA_TO_RX(); RF_StartCad(RF_CAD_THRESHOLD_20, RF_CAD_03_SYMBOL); cadCheckWindowCount_ms = cadCheckWindow_ms; cadCheckIntervalCount_ms = cadCheckInterval_ms; rf_workProcess = RF_PRC_CAD_RX; printf("restart cad Window=%d Interval=%d\n", cadCheckWindow_ms, cadCheckInterval_ms); } void myRadio_stopCadReceiver(void) { if (rf_handle == 0) { return; } RF_EXT_PA_TO_IDLE(); cadCheckWindow_ms = 0; cadCheckInterval_ms = 0; cadCheckWindowCount_ms = 0; cadCheckIntervalCount_ms = 0; RF_StopCad(); rf_workProcess = RF_PRC_IDLE; printf("stop cad Window=%d Interval=%d\n", cadCheckWindow_ms, cadCheckInterval_ms); } void myRadio_setCtrl(controlMode_te mode, uint32_t value) { if (rf_handle == 0) { return; } rf_workProcess = RF_PRC_TEST_TX; myRadio_init(0, 0); myRadio_setSyncWord(0x45); switch (mode) { case RADIO_EXT_CONTROL_TX_UNMODULATED: { RF_EXT_PA_TO_TX(); myRadio_setTxPower(rfTxPower); myRadio_setFrequency(rfFrequence); RF_StartTxContinuousWave(); rf_workProcess = RF_PRC_TEST_TX; } break; case RADIO_EXT_CONTROL_TX_MODULATED: { RF_EXT_PA_TO_TX(); myRadio_setTxPower(rfTxPower); myRadio_setFrequency(rfFrequence); RF_StartTxContinuousWave(); rf_workProcess = RF_PRC_TEST_TX; } break; case RADIO_EXT_CONTROL_RX_SENSITIVITY: { RF_EXT_PA_TO_RX(); myRadio_receiver(); rf_workProcess = RF_PRC_RX; } break; default: break; } } /**-------------------------radio funtion end----------------------------------**/ uint8_t getRfPowerTabIndex(int8_t power) { for (int i = 0; i < sizeof(rfPowerRegTab)/2; i++) { if (rfPowerRegTab[i].power >= power) { return i; } } return sizeof(rfPowerRegTab)/2 - 1; }