Fork of SX1276 library, with setLowDataRateOptimize() function added to configure "Low Datarate Optimize" setting of chip.

Dependents:   SX1276_terminal SX1276_Semtech_GUI

Fork of SX127x by wayne roberts

Committer:
dudmuck
Date:
Wed Apr 30 22:49:43 2014 +0000
Revision:
2:fdae76e1215e
Child:
3:3bf2515b1eed
separated LoRa code from FSK code from common code

Who changed what in which revision?

UserRevisionLine numberNew contents of line
dudmuck 2:fdae76e1215e 1 #include "sx127x_lora.h"
dudmuck 2:fdae76e1215e 2
dudmuck 2:fdae76e1215e 3 /* SX127x driver
dudmuck 2:fdae76e1215e 4 * Copyright (c) 2013 Semtech
dudmuck 2:fdae76e1215e 5 *
dudmuck 2:fdae76e1215e 6 * Licensed under the Apache License, Version 2.0 (the "License");
dudmuck 2:fdae76e1215e 7 * you may not use this file except in compliance with the License.
dudmuck 2:fdae76e1215e 8 * You may obtain a copy of the License at
dudmuck 2:fdae76e1215e 9 *
dudmuck 2:fdae76e1215e 10 * http://www.apache.org/licenses/LICENSE-2.0
dudmuck 2:fdae76e1215e 11 *
dudmuck 2:fdae76e1215e 12 * Unless required by applicable law or agreed to in writing, software
dudmuck 2:fdae76e1215e 13 * distributed under the License is distributed on an "AS IS" BASIS,
dudmuck 2:fdae76e1215e 14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
dudmuck 2:fdae76e1215e 15 * See the License for the specific language governing permissions and
dudmuck 2:fdae76e1215e 16 * limitations under the License.
dudmuck 2:fdae76e1215e 17 */
dudmuck 2:fdae76e1215e 18
dudmuck 2:fdae76e1215e 19 //SX127x_lora::SX127x_lora(PinName mosi, PinName miso, PinName sclk, PinName cs, PinName rst, PinName dio_0, PinName dio_1, PinName fem_ctx, PinName fem_cps) : SX127x(mosi, miso, sclk, cs, rst, dio_0, dio_1, fem_ctx, fem_cps)
dudmuck 2:fdae76e1215e 20 SX127x_lora::SX127x_lora(SX127x r) : m_xcvr(r)
dudmuck 2:fdae76e1215e 21 {
dudmuck 2:fdae76e1215e 22 RegModemConfig.octet = m_xcvr.read_reg(REG_LR_MODEMCONFIG);
dudmuck 2:fdae76e1215e 23 RegModemConfig2.octet = m_xcvr.read_reg(REG_LR_MODEMCONFIG2);
dudmuck 2:fdae76e1215e 24 RegTest31.octet = m_xcvr.read_reg(REG_LR_TEST31);
dudmuck 2:fdae76e1215e 25
dudmuck 2:fdae76e1215e 26 // CRC for TX is disabled by default
dudmuck 2:fdae76e1215e 27 setRxPayloadCrcOn(true);
dudmuck 2:fdae76e1215e 28 }
dudmuck 2:fdae76e1215e 29
dudmuck 2:fdae76e1215e 30 SX127x_lora::~SX127x_lora()
dudmuck 2:fdae76e1215e 31 {
dudmuck 2:fdae76e1215e 32 }
dudmuck 2:fdae76e1215e 33
dudmuck 2:fdae76e1215e 34 void SX127x_lora::write_fifo(uint8_t len)
dudmuck 2:fdae76e1215e 35 {
dudmuck 2:fdae76e1215e 36 int i;
dudmuck 2:fdae76e1215e 37
dudmuck 2:fdae76e1215e 38 m_xcvr.m_cs = 0;
dudmuck 2:fdae76e1215e 39 m_xcvr.m_spi.write(REG_FIFO | 0x80); // bit7 is high for writing to radio
dudmuck 2:fdae76e1215e 40
dudmuck 2:fdae76e1215e 41 for (i = 0; i < len; i++) {
dudmuck 2:fdae76e1215e 42 m_xcvr.m_spi.write(m_xcvr.tx_buf[i]);
dudmuck 2:fdae76e1215e 43 }
dudmuck 2:fdae76e1215e 44 m_xcvr.m_cs = 1;
dudmuck 2:fdae76e1215e 45 }
dudmuck 2:fdae76e1215e 46
dudmuck 2:fdae76e1215e 47 void SX127x_lora::read_fifo(uint8_t len)
dudmuck 2:fdae76e1215e 48 {
dudmuck 2:fdae76e1215e 49 int i;
dudmuck 2:fdae76e1215e 50
dudmuck 2:fdae76e1215e 51 m_xcvr.m_cs = 0;
dudmuck 2:fdae76e1215e 52 m_xcvr.m_spi.write(REG_FIFO); // bit7 is low for reading from radio
dudmuck 2:fdae76e1215e 53 for (i = 0; i < len; i++) {
dudmuck 2:fdae76e1215e 54 m_xcvr.rx_buf[i] = m_xcvr.m_spi.write(0);
dudmuck 2:fdae76e1215e 55 }
dudmuck 2:fdae76e1215e 56 m_xcvr.m_cs = 1;
dudmuck 2:fdae76e1215e 57 }
dudmuck 2:fdae76e1215e 58
dudmuck 2:fdae76e1215e 59 void SX127x_lora::enable()
dudmuck 2:fdae76e1215e 60 {
dudmuck 2:fdae76e1215e 61 m_xcvr.set_opmode(RF_OPMODE_SLEEP);
dudmuck 2:fdae76e1215e 62
dudmuck 2:fdae76e1215e 63 m_xcvr.RegOpMode.bits.LongRangeMode = 1;
dudmuck 2:fdae76e1215e 64 m_xcvr.write_reg(REG_OPMODE, m_xcvr.RegOpMode.octet);
dudmuck 2:fdae76e1215e 65
dudmuck 2:fdae76e1215e 66 /*RegOpMode.octet = read_reg(REG_OPMODE);
dudmuck 2:fdae76e1215e 67 printf("setloraon:%02x\r\n", RegOpMode.octet);*/
dudmuck 2:fdae76e1215e 68
dudmuck 2:fdae76e1215e 69
dudmuck 2:fdae76e1215e 70 /* // RxDone RxTimeout FhssChangeChannel CadDone
dudmuck 2:fdae76e1215e 71 SX1272LR->RegDioMapping1 = RFLR_DIOMAPPING1_DIO0_00 | RFLR_DIOMAPPING1_DIO1_00 | RFLR_DIOMAPPING1_DIO2_00 | RFLR_DIOMAPPING1_DIO3_00;
dudmuck 2:fdae76e1215e 72 // CadDetected ModeReady
dudmuck 2:fdae76e1215e 73 SX1272LR->RegDioMapping2 = RFLR_DIOMAPPING2_DIO4_00 | RFLR_DIOMAPPING2_DIO5_00;
dudmuck 2:fdae76e1215e 74 SX1272WriteBuffer( REG_LR_DIOMAPPING1, &SX1272LR->RegDioMapping1, 2 );*/
dudmuck 2:fdae76e1215e 75 m_xcvr.RegDioMapping1.bits.Dio0Mapping = 0; // DIO0 to RxDone
dudmuck 2:fdae76e1215e 76 m_xcvr.RegDioMapping1.bits.Dio1Mapping = 0;
dudmuck 2:fdae76e1215e 77 m_xcvr.write_reg(REG_DIOMAPPING1, m_xcvr.RegDioMapping1.octet);
dudmuck 2:fdae76e1215e 78
dudmuck 2:fdae76e1215e 79 // todo: read LoRa regsiters
dudmuck 2:fdae76e1215e 80 //SX1272ReadBuffer( REG_LR_OPMODE, SX1272Regs + 1, 0x70 - 1 );
dudmuck 2:fdae76e1215e 81
dudmuck 2:fdae76e1215e 82 m_xcvr.set_opmode(RF_OPMODE_STANDBY);
dudmuck 2:fdae76e1215e 83 }
dudmuck 2:fdae76e1215e 84
dudmuck 2:fdae76e1215e 85 uint8_t SX127x_lora::getCodingRate(bool from_rx)
dudmuck 2:fdae76e1215e 86 {
dudmuck 2:fdae76e1215e 87 if (from_rx) {
dudmuck 2:fdae76e1215e 88 // expected RegModemStatus was read on RxDone interrupt
dudmuck 2:fdae76e1215e 89 return RegModemStatus.bits.RxCodingRate;
dudmuck 2:fdae76e1215e 90 } else { // transmitted coding rate...
dudmuck 2:fdae76e1215e 91 if (m_xcvr.type == SX1276)
dudmuck 2:fdae76e1215e 92 return RegModemConfig.sx1276bits.CodingRate;
dudmuck 2:fdae76e1215e 93 else if (m_xcvr.type == SX1272)
dudmuck 2:fdae76e1215e 94 return RegModemConfig.sx1272bits.CodingRate;
dudmuck 2:fdae76e1215e 95 else
dudmuck 2:fdae76e1215e 96 return 0;
dudmuck 2:fdae76e1215e 97 }
dudmuck 2:fdae76e1215e 98 }
dudmuck 2:fdae76e1215e 99
dudmuck 2:fdae76e1215e 100
dudmuck 2:fdae76e1215e 101
dudmuck 2:fdae76e1215e 102 void SX127x_lora::setCodingRate(uint8_t cr)
dudmuck 2:fdae76e1215e 103 {
dudmuck 2:fdae76e1215e 104 if (!m_xcvr.RegOpMode.bits.LongRangeMode)
dudmuck 2:fdae76e1215e 105 return;
dudmuck 2:fdae76e1215e 106
dudmuck 2:fdae76e1215e 107 if (m_xcvr.type == SX1276)
dudmuck 2:fdae76e1215e 108 RegModemConfig.sx1276bits.CodingRate = cr;
dudmuck 2:fdae76e1215e 109 else if (m_xcvr.type == SX1272)
dudmuck 2:fdae76e1215e 110 RegModemConfig.sx1272bits.CodingRate = cr;
dudmuck 2:fdae76e1215e 111 else
dudmuck 2:fdae76e1215e 112 return;
dudmuck 2:fdae76e1215e 113
dudmuck 2:fdae76e1215e 114 m_xcvr.write_reg(REG_LR_MODEMCONFIG, RegModemConfig.octet);
dudmuck 2:fdae76e1215e 115 }
dudmuck 2:fdae76e1215e 116
dudmuck 2:fdae76e1215e 117
dudmuck 2:fdae76e1215e 118
dudmuck 2:fdae76e1215e 119 bool SX127x_lora::getHeaderMode(void)
dudmuck 2:fdae76e1215e 120 {
dudmuck 2:fdae76e1215e 121 if (m_xcvr.type == SX1276)
dudmuck 2:fdae76e1215e 122 return RegModemConfig.sx1276bits.ImplicitHeaderModeOn;
dudmuck 2:fdae76e1215e 123 else if (m_xcvr.type == SX1272)
dudmuck 2:fdae76e1215e 124 return RegModemConfig.sx1272bits.ImplicitHeaderModeOn;
dudmuck 2:fdae76e1215e 125 else
dudmuck 2:fdae76e1215e 126 return false;
dudmuck 2:fdae76e1215e 127 }
dudmuck 2:fdae76e1215e 128
dudmuck 2:fdae76e1215e 129 void SX127x_lora::setHeaderMode(bool hm)
dudmuck 2:fdae76e1215e 130 {
dudmuck 2:fdae76e1215e 131 if (m_xcvr.type == SX1276)
dudmuck 2:fdae76e1215e 132 RegModemConfig.sx1276bits.ImplicitHeaderModeOn = hm;
dudmuck 2:fdae76e1215e 133 else if (m_xcvr.type == SX1272)
dudmuck 2:fdae76e1215e 134 RegModemConfig.sx1272bits.ImplicitHeaderModeOn = hm;
dudmuck 2:fdae76e1215e 135 else
dudmuck 2:fdae76e1215e 136 return;
dudmuck 2:fdae76e1215e 137
dudmuck 2:fdae76e1215e 138 m_xcvr.write_reg(REG_LR_MODEMCONFIG, RegModemConfig.octet);
dudmuck 2:fdae76e1215e 139 }
dudmuck 2:fdae76e1215e 140
dudmuck 2:fdae76e1215e 141
dudmuck 2:fdae76e1215e 142 uint8_t SX127x_lora::getBw(void)
dudmuck 2:fdae76e1215e 143 {
dudmuck 2:fdae76e1215e 144 if (m_xcvr.type == SX1276)
dudmuck 2:fdae76e1215e 145 return RegModemConfig.sx1276bits.Bw;
dudmuck 2:fdae76e1215e 146 else if (m_xcvr.type == SX1272)
dudmuck 2:fdae76e1215e 147 return RegModemConfig.sx1272bits.Bw;
dudmuck 2:fdae76e1215e 148 else
dudmuck 2:fdae76e1215e 149 return 0;
dudmuck 2:fdae76e1215e 150 }
dudmuck 2:fdae76e1215e 151
dudmuck 2:fdae76e1215e 152 void SX127x_lora::setBw(uint8_t bw)
dudmuck 2:fdae76e1215e 153 {
dudmuck 2:fdae76e1215e 154 if (!m_xcvr.RegOpMode.bits.LongRangeMode)
dudmuck 2:fdae76e1215e 155 return;
dudmuck 2:fdae76e1215e 156
dudmuck 2:fdae76e1215e 157 if (m_xcvr.type == SX1276)
dudmuck 2:fdae76e1215e 158 RegModemConfig.sx1276bits.Bw = bw;
dudmuck 2:fdae76e1215e 159 else if (m_xcvr.type == SX1272) {
dudmuck 2:fdae76e1215e 160 RegModemConfig.sx1272bits.Bw = bw;
dudmuck 2:fdae76e1215e 161 if (RegModemConfig2.sx1272bits.SpreadingFactor > 10)
dudmuck 2:fdae76e1215e 162 RegModemConfig.sx1272bits.LowDataRateOptimize = 1;
dudmuck 2:fdae76e1215e 163 else
dudmuck 2:fdae76e1215e 164 RegModemConfig.sx1272bits.LowDataRateOptimize = 0;
dudmuck 2:fdae76e1215e 165 } else
dudmuck 2:fdae76e1215e 166 return;
dudmuck 2:fdae76e1215e 167
dudmuck 2:fdae76e1215e 168 m_xcvr.write_reg(REG_LR_MODEMCONFIG, RegModemConfig.octet);
dudmuck 2:fdae76e1215e 169 }
dudmuck 2:fdae76e1215e 170
dudmuck 2:fdae76e1215e 171
dudmuck 2:fdae76e1215e 172
dudmuck 2:fdae76e1215e 173 uint8_t SX127x_lora::getSf(void)
dudmuck 2:fdae76e1215e 174 {
dudmuck 2:fdae76e1215e 175 // spreading factor same between sx127[26]
dudmuck 2:fdae76e1215e 176 return RegModemConfig2.sx1276bits.SpreadingFactor;
dudmuck 2:fdae76e1215e 177 }
dudmuck 2:fdae76e1215e 178
dudmuck 2:fdae76e1215e 179 void SX127x_lora::set_nb_trig_peaks(int n)
dudmuck 2:fdae76e1215e 180 {
dudmuck 2:fdae76e1215e 181 RegTest31.bits.detect_trig_same_peaks_nb = n;
dudmuck 2:fdae76e1215e 182 m_xcvr.write_reg(REG_LR_TEST31, RegTest31.octet);
dudmuck 2:fdae76e1215e 183 }
dudmuck 2:fdae76e1215e 184
dudmuck 2:fdae76e1215e 185
dudmuck 2:fdae76e1215e 186 void SX127x_lora::setSf(uint8_t sf)
dudmuck 2:fdae76e1215e 187 {
dudmuck 2:fdae76e1215e 188 if (!m_xcvr.RegOpMode.bits.LongRangeMode)
dudmuck 2:fdae76e1215e 189 return;
dudmuck 2:fdae76e1215e 190
dudmuck 2:fdae76e1215e 191 // false detections vs missed detections tradeoff
dudmuck 2:fdae76e1215e 192 switch (sf) {
dudmuck 2:fdae76e1215e 193 case 6:
dudmuck 2:fdae76e1215e 194 set_nb_trig_peaks(3);
dudmuck 2:fdae76e1215e 195 break;
dudmuck 2:fdae76e1215e 196 case 7:
dudmuck 2:fdae76e1215e 197 set_nb_trig_peaks(4);
dudmuck 2:fdae76e1215e 198 break;
dudmuck 2:fdae76e1215e 199 default:
dudmuck 2:fdae76e1215e 200 set_nb_trig_peaks(5);
dudmuck 2:fdae76e1215e 201 break;
dudmuck 2:fdae76e1215e 202 }
dudmuck 2:fdae76e1215e 203
dudmuck 2:fdae76e1215e 204 // write register at 0x37 with value 0xc if at SF6
dudmuck 2:fdae76e1215e 205 if (sf < 7)
dudmuck 2:fdae76e1215e 206 m_xcvr.write_reg(REG_LR_DETECTION_THRESHOLD, 0x0c);
dudmuck 2:fdae76e1215e 207 else
dudmuck 2:fdae76e1215e 208 m_xcvr.write_reg(REG_LR_DETECTION_THRESHOLD, 0x0a);
dudmuck 2:fdae76e1215e 209
dudmuck 2:fdae76e1215e 210 RegModemConfig2.sx1276bits.SpreadingFactor = sf; // spreading factor same between sx127[26]
dudmuck 2:fdae76e1215e 211 m_xcvr.write_reg(REG_LR_MODEMCONFIG2, RegModemConfig2.octet);
dudmuck 2:fdae76e1215e 212
dudmuck 2:fdae76e1215e 213 if (m_xcvr.type == SX1272) {
dudmuck 2:fdae76e1215e 214 if (sf > 10 && RegModemConfig.sx1272bits.Bw == 0) // if bw=125KHz and sf11 or sf12
dudmuck 2:fdae76e1215e 215 RegModemConfig.sx1272bits.LowDataRateOptimize = 1;
dudmuck 2:fdae76e1215e 216 else
dudmuck 2:fdae76e1215e 217 RegModemConfig.sx1272bits.LowDataRateOptimize = 0;
dudmuck 2:fdae76e1215e 218 m_xcvr.write_reg(REG_LR_MODEMCONFIG, RegModemConfig.octet);
dudmuck 2:fdae76e1215e 219 } else if (m_xcvr.type == SX1276) {
dudmuck 2:fdae76e1215e 220 if (sf > 10 && RegModemConfig.sx1272bits.Bw == 0) // if bw=125KHz and sf11 or sf12
dudmuck 2:fdae76e1215e 221 RegModemConfig3.sx1276bits.LowDataRateOptimize = 1;
dudmuck 2:fdae76e1215e 222 else
dudmuck 2:fdae76e1215e 223 RegModemConfig3.sx1276bits.LowDataRateOptimize = 0;
dudmuck 2:fdae76e1215e 224 m_xcvr.write_reg(REG_LR_MODEMCONFIG3, RegModemConfig3.octet);
dudmuck 2:fdae76e1215e 225 }
dudmuck 2:fdae76e1215e 226 }
dudmuck 2:fdae76e1215e 227
dudmuck 2:fdae76e1215e 228
dudmuck 2:fdae76e1215e 229
dudmuck 2:fdae76e1215e 230 bool SX127x_lora::getRxPayloadCrcOn(void)
dudmuck 2:fdae76e1215e 231 {
dudmuck 2:fdae76e1215e 232 if (m_xcvr.type == SX1276)
dudmuck 2:fdae76e1215e 233 return RegModemConfig2.sx1276bits.RxPayloadCrcOn;
dudmuck 2:fdae76e1215e 234 else if (m_xcvr.type == SX1272)
dudmuck 2:fdae76e1215e 235 return RegModemConfig.sx1272bits.RxPayloadCrcOn;
dudmuck 2:fdae76e1215e 236 else
dudmuck 2:fdae76e1215e 237 return 0;
dudmuck 2:fdae76e1215e 238 }
dudmuck 2:fdae76e1215e 239
dudmuck 2:fdae76e1215e 240
dudmuck 2:fdae76e1215e 241 void SX127x_lora::setRxPayloadCrcOn(bool on)
dudmuck 2:fdae76e1215e 242 {
dudmuck 2:fdae76e1215e 243 if (m_xcvr.type == SX1276) {
dudmuck 2:fdae76e1215e 244 RegModemConfig2.sx1276bits.RxPayloadCrcOn = on;
dudmuck 2:fdae76e1215e 245 m_xcvr.write_reg(REG_LR_MODEMCONFIG2, RegModemConfig2.octet);
dudmuck 2:fdae76e1215e 246 } else if (m_xcvr.type == SX1272) {
dudmuck 2:fdae76e1215e 247 RegModemConfig.sx1272bits.RxPayloadCrcOn = on;
dudmuck 2:fdae76e1215e 248 m_xcvr.write_reg(REG_LR_MODEMCONFIG, RegModemConfig.octet);
dudmuck 2:fdae76e1215e 249 }
dudmuck 2:fdae76e1215e 250 }
dudmuck 2:fdae76e1215e 251
dudmuck 2:fdae76e1215e 252
dudmuck 2:fdae76e1215e 253
dudmuck 2:fdae76e1215e 254 bool SX127x_lora::getAgcAutoOn(void)
dudmuck 2:fdae76e1215e 255 {
dudmuck 2:fdae76e1215e 256 if (m_xcvr.type == SX1276) {
dudmuck 2:fdae76e1215e 257 RegModemConfig3.octet = m_xcvr.read_reg(REG_LR_MODEMCONFIG3);
dudmuck 2:fdae76e1215e 258 return RegModemConfig3.sx1276bits.AgcAutoOn;
dudmuck 2:fdae76e1215e 259 } else if (m_xcvr.type == SX1272) {
dudmuck 2:fdae76e1215e 260 RegModemConfig2.octet = m_xcvr.read_reg(REG_LR_MODEMCONFIG2);
dudmuck 2:fdae76e1215e 261 return RegModemConfig2.sx1272bits.AgcAutoOn;
dudmuck 2:fdae76e1215e 262 } else
dudmuck 2:fdae76e1215e 263 return 0;
dudmuck 2:fdae76e1215e 264 }
dudmuck 2:fdae76e1215e 265
dudmuck 2:fdae76e1215e 266 void SX127x_lora::setAgcAutoOn(bool on)
dudmuck 2:fdae76e1215e 267 {
dudmuck 2:fdae76e1215e 268 if (m_xcvr.type == SX1276) {
dudmuck 2:fdae76e1215e 269 RegModemConfig3.sx1276bits.AgcAutoOn = on;
dudmuck 2:fdae76e1215e 270 m_xcvr.write_reg(REG_LR_MODEMCONFIG3, RegModemConfig3.octet);
dudmuck 2:fdae76e1215e 271 } else if (m_xcvr.type == SX1272) {
dudmuck 2:fdae76e1215e 272 RegModemConfig2.sx1272bits.AgcAutoOn = on;
dudmuck 2:fdae76e1215e 273 m_xcvr.write_reg(REG_LR_MODEMCONFIG2, RegModemConfig2.octet);
dudmuck 2:fdae76e1215e 274 }
dudmuck 2:fdae76e1215e 275
dudmuck 2:fdae76e1215e 276 }
dudmuck 2:fdae76e1215e 277
dudmuck 2:fdae76e1215e 278
dudmuck 2:fdae76e1215e 279
dudmuck 2:fdae76e1215e 280 void SX127x_lora::start_tx(uint8_t len)
dudmuck 2:fdae76e1215e 281 {
dudmuck 2:fdae76e1215e 282 if (m_xcvr.type == SX1276) {
dudmuck 2:fdae76e1215e 283 // PA_BOOST on LF, RFO on HF
dudmuck 2:fdae76e1215e 284 if (m_xcvr.HF) {
dudmuck 2:fdae76e1215e 285 if (m_xcvr.RegPaConfig.bits.PaSelect) {
dudmuck 2:fdae76e1215e 286 m_xcvr.RegPaConfig.bits.PaSelect = 0;
dudmuck 2:fdae76e1215e 287 m_xcvr.write_reg(REG_PACONFIG, m_xcvr.RegPaConfig.octet);
dudmuck 2:fdae76e1215e 288 }
dudmuck 2:fdae76e1215e 289 } else { // LF...
dudmuck 2:fdae76e1215e 290 if (!m_xcvr.RegPaConfig.bits.PaSelect) {
dudmuck 2:fdae76e1215e 291 m_xcvr.RegPaConfig.bits.PaSelect = 1;
dudmuck 2:fdae76e1215e 292 m_xcvr.write_reg(REG_PACONFIG, m_xcvr.RegPaConfig.octet);
dudmuck 2:fdae76e1215e 293 }
dudmuck 2:fdae76e1215e 294 }
dudmuck 2:fdae76e1215e 295 } else if (m_xcvr.type == SX1272) {
dudmuck 2:fdae76e1215e 296 // always PA_BOOST
dudmuck 2:fdae76e1215e 297 if (!m_xcvr.RegPaConfig.bits.PaSelect) {
dudmuck 2:fdae76e1215e 298 m_xcvr.RegPaConfig.bits.PaSelect = 1;
dudmuck 2:fdae76e1215e 299 m_xcvr.write_reg(REG_PACONFIG, m_xcvr.RegPaConfig.octet);
dudmuck 2:fdae76e1215e 300 }
dudmuck 2:fdae76e1215e 301 }
dudmuck 2:fdae76e1215e 302
dudmuck 2:fdae76e1215e 303
dudmuck 2:fdae76e1215e 304 // DIO0 to TxDone
dudmuck 2:fdae76e1215e 305 if (m_xcvr.RegDioMapping1.bits.Dio0Mapping != 1) {
dudmuck 2:fdae76e1215e 306 m_xcvr.RegDioMapping1.bits.Dio0Mapping = 1;
dudmuck 2:fdae76e1215e 307 m_xcvr.write_reg(REG_DIOMAPPING1, m_xcvr.RegDioMapping1.octet);
dudmuck 2:fdae76e1215e 308 }
dudmuck 2:fdae76e1215e 309
dudmuck 2:fdae76e1215e 310 // set FifoPtrAddr to FifoTxPtrBase
dudmuck 2:fdae76e1215e 311 m_xcvr.write_reg(REG_LR_FIFOADDRPTR, m_xcvr.read_reg(REG_LR_FIFOTXBASEADDR));
dudmuck 2:fdae76e1215e 312
dudmuck 2:fdae76e1215e 313 // write PayloadLength bytes to fifo
dudmuck 2:fdae76e1215e 314 write_fifo(len);
dudmuck 2:fdae76e1215e 315
dudmuck 2:fdae76e1215e 316 if (m_xcvr.HF)
dudmuck 2:fdae76e1215e 317 m_xcvr.femctx = 1;
dudmuck 2:fdae76e1215e 318 else
dudmuck 2:fdae76e1215e 319 m_xcvr.femcps = 0;
dudmuck 2:fdae76e1215e 320
dudmuck 2:fdae76e1215e 321 // radio doesnt provide FhssChangeChannel with channel=0 for TX
dudmuck 2:fdae76e1215e 322 if (RegHopPeriod > 0)
dudmuck 2:fdae76e1215e 323 m_xcvr.write_reg_u24(REG_FRFMSB, m_xcvr.frfs[0]);
dudmuck 2:fdae76e1215e 324
dudmuck 2:fdae76e1215e 325 m_xcvr.set_opmode(RF_OPMODE_TRANSMITTER);
dudmuck 2:fdae76e1215e 326 }
dudmuck 2:fdae76e1215e 327
dudmuck 2:fdae76e1215e 328 void SX127x_lora::start_rx()
dudmuck 2:fdae76e1215e 329 {
dudmuck 2:fdae76e1215e 330 if (!m_xcvr.RegOpMode.bits.LongRangeMode)
dudmuck 2:fdae76e1215e 331 return;
dudmuck 2:fdae76e1215e 332
dudmuck 2:fdae76e1215e 333 if (m_xcvr.HF)
dudmuck 2:fdae76e1215e 334 m_xcvr.femctx = 0;
dudmuck 2:fdae76e1215e 335 else
dudmuck 2:fdae76e1215e 336 m_xcvr.femcps = 1;
dudmuck 2:fdae76e1215e 337
dudmuck 2:fdae76e1215e 338 if (m_xcvr.RegDioMapping1.bits.Dio0Mapping != 0) {
dudmuck 2:fdae76e1215e 339 m_xcvr.RegDioMapping1.bits.Dio0Mapping = 0; // DIO0 to RxDone
dudmuck 2:fdae76e1215e 340 m_xcvr.write_reg(REG_DIOMAPPING1, m_xcvr.RegDioMapping1.octet);
dudmuck 2:fdae76e1215e 341 }
dudmuck 2:fdae76e1215e 342
dudmuck 2:fdae76e1215e 343 m_xcvr.write_reg(REG_LR_FIFOADDRPTR, m_xcvr.read_reg(REG_LR_FIFORXBASEADDR));
dudmuck 2:fdae76e1215e 344
dudmuck 2:fdae76e1215e 345 // shouldn't be necessary, radio should provide FhssChangeChannel with channel=0 for RX
dudmuck 2:fdae76e1215e 346 if (RegHopPeriod > 0)
dudmuck 2:fdae76e1215e 347 m_xcvr.write_reg_u24(REG_FRFMSB, m_xcvr.frfs[0]);
dudmuck 2:fdae76e1215e 348
dudmuck 2:fdae76e1215e 349 m_xcvr.set_opmode(RF_OPMODE_RECEIVER);
dudmuck 2:fdae76e1215e 350 }
dudmuck 2:fdae76e1215e 351
dudmuck 2:fdae76e1215e 352 float SX127x_lora::get_pkt_rssi()
dudmuck 2:fdae76e1215e 353 {
dudmuck 2:fdae76e1215e 354 /* TODO: calculating with pktSNR to give meaningful result below noise floor */
dudmuck 2:fdae76e1215e 355 if (m_xcvr.type == SX1276)
dudmuck 2:fdae76e1215e 356 return RegPktRssiValue - 137;
dudmuck 2:fdae76e1215e 357 else
dudmuck 2:fdae76e1215e 358 return RegPktRssiValue - 125;
dudmuck 2:fdae76e1215e 359 }
dudmuck 2:fdae76e1215e 360
dudmuck 2:fdae76e1215e 361 service_action_e SX127x_lora::service()
dudmuck 2:fdae76e1215e 362 {
dudmuck 2:fdae76e1215e 363 if (m_xcvr.RegOpMode.bits.Mode == RF_OPMODE_RECEIVER) {
dudmuck 2:fdae76e1215e 364 if (poll_vh) {
dudmuck 2:fdae76e1215e 365 RegIrqFlags.octet = m_xcvr.read_reg(REG_LR_IRQFLAGS);
dudmuck 2:fdae76e1215e 366 if (RegIrqFlags.bits.ValidHeader) {
dudmuck 2:fdae76e1215e 367 RegIrqFlags.octet = 0;
dudmuck 2:fdae76e1215e 368 RegIrqFlags.bits.ValidHeader = 1;
dudmuck 2:fdae76e1215e 369 m_xcvr.write_reg(REG_LR_IRQFLAGS, RegIrqFlags.octet);
dudmuck 2:fdae76e1215e 370 printf("VH\r\n");
dudmuck 2:fdae76e1215e 371 }
dudmuck 2:fdae76e1215e 372 }
dudmuck 2:fdae76e1215e 373 }
dudmuck 2:fdae76e1215e 374
dudmuck 2:fdae76e1215e 375 // FhssChangeChannel
dudmuck 2:fdae76e1215e 376 if (m_xcvr.RegDioMapping1.bits.Dio1Mapping == 1) {
dudmuck 2:fdae76e1215e 377 if (m_xcvr.dio1) {
dudmuck 2:fdae76e1215e 378 RegHopChannel.octet = m_xcvr.read_reg(REG_LR_HOPCHANNEL);
dudmuck 2:fdae76e1215e 379 m_xcvr.write_reg_u24(REG_FRFMSB, m_xcvr.frfs[RegHopChannel.bits.FhssPresentChannel]);
dudmuck 2:fdae76e1215e 380 printf("hopch:%d\r\n", RegHopChannel.bits.FhssPresentChannel);
dudmuck 2:fdae76e1215e 381 RegIrqFlags.octet = 0;
dudmuck 2:fdae76e1215e 382 RegIrqFlags.bits.FhssChangeChannel = 1;
dudmuck 2:fdae76e1215e 383 m_xcvr. write_reg(REG_LR_IRQFLAGS, RegIrqFlags.octet);
dudmuck 2:fdae76e1215e 384
dudmuck 2:fdae76e1215e 385 }
dudmuck 2:fdae76e1215e 386 }
dudmuck 2:fdae76e1215e 387
dudmuck 2:fdae76e1215e 388 if (m_xcvr.dio0 == 0)
dudmuck 2:fdae76e1215e 389 return SERVICE_NONE;
dudmuck 2:fdae76e1215e 390
dudmuck 2:fdae76e1215e 391 switch (m_xcvr.RegDioMapping1.bits.Dio0Mapping) {
dudmuck 2:fdae76e1215e 392 case 0: // RxDone
dudmuck 2:fdae76e1215e 393 /* user checks for CRC error in IrqFlags */
dudmuck 2:fdae76e1215e 394 RegIrqFlags.octet = m_xcvr.read_reg(REG_LR_IRQFLAGS); // save flags
dudmuck 2:fdae76e1215e 395 RegHopChannel.octet = m_xcvr.read_reg(REG_LR_HOPCHANNEL);
dudmuck 2:fdae76e1215e 396 if (RegIrqFlags.bits.FhssChangeChannel) {
dudmuck 2:fdae76e1215e 397 m_xcvr.write_reg_u24(REG_FRFMSB, m_xcvr.frfs[RegHopChannel.bits.FhssPresentChannel]);
dudmuck 2:fdae76e1215e 398 }
dudmuck 2:fdae76e1215e 399 //printf("[%02x]", RegIrqFlags.octet);
dudmuck 2:fdae76e1215e 400 m_xcvr.write_reg(REG_LR_IRQFLAGS, RegIrqFlags.octet); // clear flags in radio
dudmuck 2:fdae76e1215e 401
dudmuck 2:fdae76e1215e 402 /* any register of interest on received packet is read(saved) here */
dudmuck 2:fdae76e1215e 403 RegModemStatus.octet = m_xcvr.read_reg(REG_LR_MODEMSTAT);
dudmuck 2:fdae76e1215e 404 RegPktSnrValue = m_xcvr.read_reg(REG_LR_PKTSNRVALUE);
dudmuck 2:fdae76e1215e 405 RegPktRssiValue = m_xcvr.read_reg(REG_LR_PKTRSSIVALUE);
dudmuck 2:fdae76e1215e 406 RegRxNbBytes = m_xcvr.read_reg(REG_LR_RXNBBYTES);
dudmuck 2:fdae76e1215e 407
dudmuck 2:fdae76e1215e 408 m_xcvr.write_reg(REG_LR_FIFOADDRPTR, m_xcvr.read_reg(REG_LR_FIFORXCURRENTADDR));
dudmuck 2:fdae76e1215e 409 read_fifo(RegRxNbBytes);
dudmuck 2:fdae76e1215e 410 return SERVICE_READ_FIFO;
dudmuck 2:fdae76e1215e 411 case 1: // TxDone
dudmuck 2:fdae76e1215e 412 if (m_xcvr.HF)
dudmuck 2:fdae76e1215e 413 m_xcvr.femctx = 0;
dudmuck 2:fdae76e1215e 414 else
dudmuck 2:fdae76e1215e 415 m_xcvr.femcps = 1;
dudmuck 2:fdae76e1215e 416
dudmuck 2:fdae76e1215e 417 RegIrqFlags.octet = 0;
dudmuck 2:fdae76e1215e 418 RegIrqFlags.bits.TxDone = 1;
dudmuck 2:fdae76e1215e 419 m_xcvr.write_reg(REG_LR_IRQFLAGS, RegIrqFlags.octet);
dudmuck 2:fdae76e1215e 420 return SERVICE_TX_DONE;
dudmuck 2:fdae76e1215e 421 } // ...switch (RegDioMapping1.bits.Dio0Mapping)
dudmuck 2:fdae76e1215e 422
dudmuck 2:fdae76e1215e 423 return SERVICE_ERROR;
dudmuck 2:fdae76e1215e 424 }