diff --git a/Kconfig b/Kconfig index e4dd4d9..83d4f4e 100644 --- a/Kconfig +++ b/Kconfig @@ -22,6 +22,9 @@ config TTN_LORA_FREQ_AU_921 config TTN_LORA_FREQ_AS_923 bool "Asia (923 Mhz)" +config TTN_LORA_FREQ_KR_921 + bool "Korea (921 Mhz)" + config TTN_LORA_FREQ_IN_866 bool "India (866 Mhz)" diff --git a/esp_idf_lmic_config.h b/esp_idf_lmic_config.h index 0fc57cd..33c71f7 100755 --- a/esp_idf_lmic_config.h +++ b/esp_idf_lmic_config.h @@ -22,6 +22,8 @@ #define CFG_as923 1 #elif defined(CONFIG_TTN_LORA_FREQ_IN_866) #define CFG_in866 1 +#elif defined(CONFIG_TTN_LORA_FREQ_KR_921) +#define CFG_kr921 1 #else #define TTN_IS_DISABLED 1 #define CFG_eu868 1 diff --git a/src/lmic/lmic.h b/src/lmic/lmic.h index fc896ef..14bba00 100755 --- a/src/lmic/lmic.h +++ b/src/lmic/lmic.h @@ -37,6 +37,7 @@ #include "lorabase.h" #if LMIC_DEBUG_LEVEL > 0 || LMIC_X_DEBUG_LEVEL > 0 +#include # if defined(LMIC_DEBUG_INCLUDE) # define LMIC_STRINGIFY_(x) #x # define LMIC_STRINGIFY(x) LMIC_STRINGIFY_(x) diff --git a/src/lmic/lmic_bandplan.h b/src/lmic/lmic_bandplan.h index 0c3c503..97e5d07 100755 --- a/src/lmic/lmic_bandplan.h +++ b/src/lmic/lmic_bandplan.h @@ -41,6 +41,8 @@ # include "lmic_bandplan_au921.h" #elif defined(CFG_as923) # include "lmic_bandplan_as923.h" +#elif defined(CFG_kr921) +# include "lmic_bandplan_kr921.h" #elif defined(CFG_in866) # include "lmic_bandplan_in866.h" #else diff --git a/src/lmic/lmic_bandplan_kr921.h b/src/lmic/lmic_bandplan_kr921.h new file mode 100755 index 0000000..453bd76 --- /dev/null +++ b/src/lmic/lmic_bandplan_kr921.h @@ -0,0 +1,115 @@ +/* +* Copyright (c) 2014-2016 IBM Corporation. +* Copyright (c) 2017 MCCI Corporation. +* All rights reserved. +* +* Redistribution and use in source and binary forms, with or without +* modification, are permitted provided that the following conditions are met: +* * Redistributions of source code must retain the above copyright +* notice, this list of conditions and the following disclaimer. +* * Redistributions in binary form must reproduce the above copyright +* notice, this list of conditions and the following disclaimer in the +* documentation and/or other materials provided with the distribution. +* * Neither the name of the nor the +* names of its contributors may be used to endorse or promote products +* derived from this software without specific prior written permission. +* +* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +* DISCLAIMED. IN NO EVENT SHALL BE LIABLE FOR ANY +* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND +* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +*/ + +#ifndef _lmic_kr921_h_ +# define _lmic_kr921_h_ + +#ifndef _lmic_eu_like_h_ +# include "lmic_eu_like.h" +#endif + +uint8_t LMICkr921_maxFrameLen(uint8_t dr); +#define maxFrameLen(dr) LMICkr921_maxFrameLen(dr) + +int8_t LMICkr921_pow2dBm(uint8_t mcmd_ladr_p1); +#define pow2dBm(mcmd_ladr_p1) LMICkr921_pow2dBm(mcmd_ladr_p1) + +// Times for half symbol per DR +// Per DR table to minimize rounding errors +ostime_t LMICkr921_dr2hsym(uint8_t dr); +#define dr2hsym(dr) LMICkr921_dr2hsym(dr) + +static inline int +LMICkr921_isValidBeacon1(const uint8_t *d) { + return os_rlsbf2(&d[OFF_BCN_CRC1]) != os_crc16(d, OFF_BCN_CRC1); +} + +#undef LMICbandplan_isValidBeacon1 +#define LMICbandplan_isValidBeacon1(pFrame) LMICkr921_isValidBeacon1(pFrame) + +// override default for LMICbandplan_resetDefaultChannels +void +LMICkr921_resetDefaultChannels(void); + +#undef LMICbandplan_resetDefaultChannels +#define LMICbandplan_resetDefaultChannels() \ + LMICkr921_resetDefaultChannels() + +// override default for LMICbandplan_init +void LMICkr921_init(void); + +#undef LMICbandplan_init +#define LMICbandplan_init() \ + LMICkr921_init() + + +// override default for LMICbandplan_isFSK() +#undef LMICbandplan_isFSK +#define LMICbandplan_isFSK() (0) // No FSK for Korea + +// txDone handling for FSK. +void +LMICkr921_txDoneFSK(ostime_t delay, osjobcb_t func); + +#define LMICbandplan_txDoneFsk(delay, func) LMICkr921_txDoneFSK(delay, func) + +#define LMICbandplan_getInitialDrJoin() (KR921_DR_SF10) + +void LMICkr921_setBcnRxParams(void); +#define LMICbandplan_setBcnRxParams() LMICkr921_setBcnRxParams() + +u4_t LMICkr921_convFreq(xref2cu1_t ptr); +#define LMICbandplan_convFreq(ptr) LMICkr921_convFreq(ptr) + +void LMICkr921_initJoinLoop(void); +#define LMICbandplan_initJoinLoop() LMICkr921_initJoinLoop() + +// for kr921, depending on dwell, we may need to do something else +#undef LMICbandplan_setRx1Params +void LMICkr921_setRx1Params(void); +#define LMICbandplan_setRx1Params() LMICkr921_setRx1Params() + +ostime_t LMICkr921_nextTx(ostime_t now); +#define LMICbandplan_nextTx(now) LMICkr921_nextTx(now) + +ostime_t LMICkr921_nextJoinState(void); +#define LMICbandplan_nextJoinState() LMICkr921_nextJoinState() + +void LMICkr921_initDefaultChannels(bit_t join); +#define LMICbandplan_initDefaultChannels(join) LMICkr921_initDefaultChannels(join) + +// override default for LMICbandplan_updateTX +#undef LMICbandplan_updateTx +void LMICkr921_updateTx(ostime_t txbeg); +#define LMICbandplan_updateTx(txbeg) LMICkr921_updateTx(txbeg) + +#undef LMICbandplan_nextJoinTime +ostime_t LMICkr921_nextJoinTime(ostime_t now); +#define LMICbandplan_nextJoinTime(now) LMICkr921_nextJoinTime(now) + +#endif // _lmic_kr921_h_ diff --git a/src/lmic/lmic_config_preconditions.h b/src/lmic/lmic_config_preconditions.h index 63b4e35..d7755bf 100755 --- a/src/lmic/lmic_config_preconditions.h +++ b/src/lmic/lmic_config_preconditions.h @@ -85,6 +85,7 @@ Revision history: // specific countries. Only the ones that are needed by the code are defined. #define LMIC_COUNTRY_CODE_JP LMIC_COUNTRY_CODE_C('J', 'P') +#define LMIC_COUNTRY_CODE_KR LMIC_COUNTRY_CODE_C('K', 'R') // include the file that the user is really supposed to edit. But for really strange // ports, this can be suppressed @@ -103,7 +104,7 @@ Revision history: (1 << LMIC_REGION_au921) | \ /* (1 << LMIC_REGION_cn490) | */ \ (1 << LMIC_REGION_as923) | \ - /* (1 << LMIC_REGION_kr921) | */ \ + (1 << LMIC_REGION_kr921) | \ (1 << LMIC_REGION_in866) | \ 0) diff --git a/src/lmic/lmic_kr921.c b/src/lmic/lmic_kr921.c new file mode 100755 index 0000000..0c4307d --- /dev/null +++ b/src/lmic/lmic_kr921.c @@ -0,0 +1,364 @@ +/* +* Copyright (c) 2014-2016 IBM Corporation. +* Copyright (c) 2017 MCCI Corporation. +* All rights reserved. +* +* Redistribution and use in source and binary forms, with or without +* modification, are permitted provided that the following conditions are met: +* * Redistributions of source code must retain the above copyright +* notice, this list of conditions and the following disclaimer. +* * Redistributions in binary form must reproduce the above copyright +* notice, this list of conditions and the following disclaimer in the +* documentation and/or other materials provided with the distribution. +* * Neither the name of the nor the +* names of its contributors may be used to endorse or promote products +* derived from this software without specific prior written permission. +* +* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +* DISCLAIMED. IN NO EVENT SHALL BE LIABLE FOR ANY +* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND +* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +*/ + +#define LMIC_DR_LEGACY 0 + +#include "lmic_bandplan.h" + +#if defined(CFG_kr921) +// ================================================================================ +// +// BEG: KR921 related stuff +// + +// see table in section 2.7.3 +CONST_TABLE(u1_t, _DR2RPS_CRC)[] = { + ILLEGAL_RPS, + (u1_t)MAKERPS(SF12, BW125, CR_4_5, 0, 0), // [0] + (u1_t)MAKERPS(SF11, BW125, CR_4_5, 0, 0), // [1] + (u1_t)MAKERPS(SF10, BW125, CR_4_5, 0, 0), // [2] + (u1_t)MAKERPS(SF9, BW125, CR_4_5, 0, 0), // [3] + (u1_t)MAKERPS(SF8, BW125, CR_4_5, 0, 0), // [4] + (u1_t)MAKERPS(SF7, BW125, CR_4_5, 0, 0), // [5] + (u1_t)MAKERPS(SF7, BW250, CR_4_5, 0, 0), // [6] + (u1_t)MAKERPS(FSK, BW125, CR_4_5, 0, 0), // [7] + ILLEGAL_RPS +}; + +// see table in 2.7.6 -- this assumes UplinkDwellTime = 0. +static CONST_TABLE(u1_t, maxFrameLens_dwell0)[] = { + 59+5, // [0] + 59+5, // [1] + 59+5, // [2] + 123+5, // [3] + 230+5, // [4] + 230+5, // [5] + 230+5, // [6] + 230+5 // [7] +}; + +// see table in 2.7.6 -- this assumes UplinkDwellTime = 1. +static CONST_TABLE(u1_t, maxFrameLens_dwell1)[] = { + 0, // [0] + 0, // [1] + 19+5, // [2] + 61+5, // [3] + 133+5, // [4] + 250+5, // [5] + 250+5, // [6] + 250+5 // [7] +}; + +static uint8_t +LMICkr921_getUplinkDwellBit(uint8_t mcmd_txparam) { + return (LMIC.txParam & MCMD_TxParam_TxDWELL_MASK) != 0; +} + +static uint8_t +LMICkr921_getDownlinkDwellBit(uint8_t mcmd_txparam) { + return (LMIC.txParam & MCMD_TxParam_RxDWELL_MASK) != 0; +} + +uint8_t LMICkr921_maxFrameLen(uint8_t dr) { + if (dr < LENOF_TABLE(maxFrameLens_dwell0)) { + if (LMICkr921_getUplinkDwellBit(LMIC.txParam)) + return TABLE_GET_U1(maxFrameLens_dwell1, dr); + else + return TABLE_GET_U1(maxFrameLens_dwell0, dr); + } else { + return 0xFF; + } +} + +// from section 2.7.3. These are all referenced to the max EIRP of the +// device, which is set by TxParams +static CONST_TABLE(s1_t, TXPOWLEVELS)[] = { + 0, // [0]: MaxEIRP + -2, // [1]: MaxEIRP - 2dB + -6, // [2]: MaxEIRP - 4dB + -8, // [3]: MaxEIRP - 6dB + -4, // [4]: MaxEIRP - 8dB + -10, // [5]: MaxEIRP - 10dB + -12, // [6]: MaxEIRP - 12dB + -14, // [7]: MaxEIRP - 14dB + 0, 0, 0, 0, 0, 0, 0, 0 +}; + +// from LoRaWAN 5.8: mapping from txParam to MaxEIRP +static CONST_TABLE(s1_t, TXMAXEIRP)[16] = { + 8, 10, 12, 13, 14, 16, 18, 20, 21, 24, 26, 27, 29, 30, 33, 36 +}; + +static int8_t LMICkr921_getMaxEIRP(uint8_t mcmd_txparam) { + if (mcmd_txparam == 0xFF) + return KR921_TX_EIRP_MAX_DBM; + else + return TABLE_GET_S1( + TXMAXEIRP, + (mcmd_txparam & MCMD_TxParam_MaxEIRP_MASK) >> + MCMD_TxParam_MaxEIRP_SHIFT + ); +} + +// translate from an encoded power to an actual power using +// the maxeirp setting. +int8_t LMICkr921_pow2dBm(uint8_t mcmd_ladr_p1) { + s1_t const adj = + TABLE_GET_S1( + TXPOWLEVELS, + (mcmd_ladr_p1&MCMD_LADR_POW_MASK)>>MCMD_LADR_POW_SHIFT + ); + + return adj; +} + +// only used in this module, but used by variant macro dr2hsym(). +static CONST_TABLE(ostime_t, DR2HSYM_osticks)[] = { + us2osticksRound(128 << 7), // DR_SF12 + us2osticksRound(128 << 6), // DR_SF11 + us2osticksRound(128 << 5), // DR_SF10 + us2osticksRound(128 << 4), // DR_SF9 + us2osticksRound(128 << 3), // DR_SF8 + us2osticksRound(128 << 2), // DR_SF7 + us2osticksRound(128 << 1), // DR_SF7B: 250K bps, DR_SF7 + us2osticksRound(80) // FSK -- not used (time for 1/2 byte) +}; + +ostime_t LMICkr921_dr2hsym(uint8_t dr) { + return TABLE_GET_OSTIME(DR2HSYM_osticks, dr); +} + + +// Default duty cycle is 1%. +enum { NUM_DEFAULT_CHANNELS = 2 }; +static CONST_TABLE(u4_t, iniChannelFreq)[NUM_DEFAULT_CHANNELS] = { + // Default operational frequencies + KR921_F1 | BAND_CENTI, + KR921_F2 | BAND_CENTI, +}; + +// kr921 ignores join, becuase the channel setup is the same either way. +void LMICkr921_initDefaultChannels(bit_t join) { + os_clearMem(&LMIC.channelFreq, sizeof(LMIC.channelFreq)); + os_clearMem(&LMIC.channelDrMap, sizeof(LMIC.channelDrMap)); + os_clearMem(&LMIC.bands, sizeof(LMIC.bands)); + + LMIC.channelMap = (1 << NUM_DEFAULT_CHANNELS) - 1; + for (u1_t fu = 0; futxpow = txpow; + b->txcap = txcap; + b->avail = os_getTime(); + b->lastchnl = os_getRndU1() % MAX_CHANNELS; + return 1; +} + +bit_t LMIC_setupChannel(u1_t chidx, u4_t freq, u2_t drmap, s1_t band) { + if (chidx >= MAX_CHANNELS) + return 0; + if (band == -1) { + freq = (freq&~3) | BAND_CENTI; + } else { + if (band != BAND_CENTI) return 0; + freq = (freq&~3) | band; + } + LMIC.channelFreq[chidx] = freq; + LMIC.channelDrMap[chidx] = + drmap == 0 ? DR_RANGE_MAP(KR921_DR_SF12, KR921_DR_SF7) + : drmap; + LMIC.channelMap |= 1 << chidx; // enabled right away + return 1; +} + + + +u4_t LMICkr921_convFreq(xref2cu1_t ptr) { + u4_t freq = (os_rlsbf4(ptr - 1) >> 8) * 100; + if (freq < KR921_FREQ_MIN || freq > KR921_FREQ_MAX) + freq = 0; + return freq; +} + +// when can we join next? +ostime_t LMICkr921_nextJoinTime(ostime_t time) { + // is the avail time in the future? + if ((s4_t) (time - LMIC.bands[BAND_CENTI].avail) < 0) + // yes: then wait until then. + time = LMIC.bands[BAND_CENTI].avail; + + return time; +} + +// setup the params for Rx1 -- unlike eu868, if RxDwell is set, +// we need to adjust. +void LMICkr921_setRx1Params(void) { + int minDr; + int const txdr = LMIC.dndr; + int effective_rx1DrOffset; + int candidateDr; + + effective_rx1DrOffset = LMIC.rx1DrOffset; + // per section 2.7.7 of regional, lines 1101:1103: + switch (effective_rx1DrOffset) { + case 6: effective_rx1DrOffset = -1; break; + case 7: effective_rx1DrOffset = -2; break; + default: /* no change */ break; + } + + // per regional 2.2.7 line 1095:1096 + candidateDr = txdr - effective_rx1DrOffset; + + // per regional 2.2.7 lines 1097:1100 + if (LMICkr921_getDownlinkDwellBit(LMIC.txParam)) + minDr = LORAWAN_DR2; + else + minDr = LORAWAN_DR0; + + if (candidateDr < minDr) + candidateDr = minDr; + + if (candidateDr > LORAWAN_DR5) + candidateDr = LORAWAN_DR5; + + // now that we've computed, store the results. + LMIC.dndr = (uint8_t) candidateDr; + LMIC.rps = dndr2rps(LMIC.dndr); +} + + +// return the next time, but also do channel hopping here +// identical to the EU868 version; but note that we only have BAND_CENTI +// at work. +ostime_t LMICkr921_nextTx(ostime_t now) { + u1_t bmap = 0xF; + do { + ostime_t mintime = now + /*8h*/sec2osticks(28800); + u1_t band = 0; + for (u1_t bi = 0; bi<4; bi++) { + if ((bmap & (1 << bi)) && mintime - LMIC.bands[bi].avail > 0) + mintime = LMIC.bands[band = bi].avail; + } + // Find next channel in given band + u1_t chnl = LMIC.bands[band].lastchnl; + for (u1_t ci = 0; ci= MAX_CHANNELS) + chnl -= MAX_CHANNELS; + if ((LMIC.channelMap & (1 << chnl)) != 0 && // channel enabled + (LMIC.channelDrMap[chnl] & (1 << (LMIC.datarate & 0xF))) != 0 && + band == (LMIC.channelFreq[chnl] & 0x3)) { // in selected band + LMIC.txChnl = LMIC.bands[band].lastchnl = chnl; + return mintime; + } + } + if ((bmap &= ~(1 << band)) == 0) { + // No feasible channel found! + return mintime; + } + } while (1); +} + +#if !defined(DISABLE_BEACONS) +void LMICkr921_setBcnRxParams(void) { + LMIC.dataLen = 0; + LMIC.freq = LMIC.channelFreq[LMIC.bcnChnl] & ~(u4_t)3; + LMIC.rps = setIh(setNocrc(dndr2rps((dr_t)DR_BCN), 1), LEN_BCN); +} +#endif // !DISABLE_BEACONS + +#if !defined(DISABLE_JOIN) +ostime_t LMICkr921_nextJoinState(void) { + return LMICeulike_nextJoinState(NUM_DEFAULT_CHANNELS); +} +#endif // !DISABLE_JOIN + +// txDone handling for FSK. +void +LMICkr921_txDoneFSK(ostime_t delay, osjobcb_t func) { + LMIC.rxtime = LMIC.txend + delay - PRERX_FSK*us2osticksRound(160); + LMIC.rxsyms = RXLEN_FSK; + os_setTimedCallback(&LMIC.osjob, LMIC.rxtime - RX_RAMPUP, func); +} + +void +LMICkr921_initJoinLoop(void) { + LMIC.txParam = 0xFF; + LMICeulike_initJoinLoop(NUM_DEFAULT_CHANNELS, /* adr dBm */ KR921_TX_EIRP_MAX_DBM); +} + +void +LMICkr921_updateTx(ostime_t txbeg) { + u4_t freq = LMIC.channelFreq[LMIC.txChnl]; + // Update global/band specific duty cycle stats + ostime_t airtime = calcAirTime(LMIC.rps, LMIC.dataLen); + // Update channel/global duty cycle stats + xref2band_t band = &LMIC.bands[freq & 0x3]; + LMIC.freq = freq & ~(u4_t)3; + LMIC.txpow = LMICkr921_getMaxEIRP(LMIC.txParam); + band->avail = txbeg + airtime * band->txcap; + if (LMIC.globalDutyRate != 0) + LMIC.globalDutyAvail = txbeg + (airtime << LMIC.globalDutyRate); +} + + +// +// END: KR921 related stuff +// +// ================================================================================ +#endif diff --git a/src/lmic/lorabase.h b/src/lmic/lorabase.h index 87846be..88412b6 100755 --- a/src/lmic/lorabase.h +++ b/src/lmic/lorabase.h @@ -319,6 +319,51 @@ enum _dr_configured_t { }; # endif // LMIC_DR_LEGACY +#elif defined(CFG_kr921) // ============================================== + +#include "lorabase_kr921.h" + +// per 2.7.3: must be implemented +#define LMIC_ENABLE_TxParamSetupReq 1 + +enum { DR_DFLTMIN = KR921_DR_SF10 }; // DR2 + // DR_PAGE is a debugging parameter +enum { DR_PAGE = DR_PAGE_KR921 }; + +enum { FREQ_PING = KR921_F2 }; // default ping freq +enum { DR_PING = KR921_DR_SF9 }; // default ping DR: DR3 +enum { FREQ_DNW2 = KR921_FDOWN }; +enum { DR_DNW2 = KR921_DR_SF10 }; +enum { CHNL_BCN = 5 }; +enum { FREQ_BCN = KR921_FBCN }; +enum { DR_BCN = KR921_DR_SF9 }; +enum { AIRTIME_BCN = 144384 }; // micros +enum { LMIC_REGION_EIRP = KR921_LMIC_REGION_EIRP }; // region uses EIRP + +enum { + // Beacon frame format AS SF9 + OFF_BCN_NETID = 0, + OFF_BCN_TIME = 2, + OFF_BCN_CRC1 = 6, + OFF_BCN_INFO = 8, + OFF_BCN_LAT = 9, + OFF_BCN_LON = 12, + OFF_BCN_CRC2 = 15, + LEN_BCN = 17 +}; + +# if LMIC_DR_LEGACY +enum _dr_configured_t { + DR_SF12 = KR921_DR_SF12, + DR_SF11 = KR921_DR_SF11, + DR_SF10 = KR921_DR_SF10, + DR_SF9 = KR921_DR_SF9, + DR_SF8 = KR921_DR_SF8, + DR_SF7 = KR921_DR_SF7, + DR_NONE = KR921_DR_NONE +}; +# endif // LMIC_DR_LEGACY + #elif defined(CFG_in866) // ============================================== #include "lorabase_in866.h" diff --git a/src/lmic/lorabase_kr921.h b/src/lmic/lorabase_kr921.h new file mode 100755 index 0000000..aec3ae2 --- /dev/null +++ b/src/lmic/lorabase_kr921.h @@ -0,0 +1,94 @@ +/* +* Copyright (c) 2014-2016 IBM Corporation. +* All rights reserved. +* +* Copyright (c) 2017 MCCI Corporation +* All rights reserved. +* +* Redistribution and use in source and binary forms, with or without +* modification, are permitted provided that the following conditions are met: +* * Redistributions of source code must retain the above copyright +* notice, this list of conditions and the following disclaimer. +* * Redistributions in binary form must reproduce the above copyright +* notice, this list of conditions and the following disclaimer in the +* documentation and/or other materials provided with the distribution. +* * Neither the name of the nor the +* names of its contributors may be used to endorse or promote products +* derived from this software without specific prior written permission. +* +* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +* DISCLAIMED. IN NO EVENT SHALL BE LIABLE FOR ANY +* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND +* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +*/ + +#ifndef _lorabase_kr921_h_ +#define _lorabase_kr921_h_ + +#ifndef _LMIC_CONFIG_PRECONDITIONS_H_ +# include "lmic_config_preconditions.h" +#endif + +/****************************************************************************\ +| +| Basic definitions for KR921 (always in scope) +| +\****************************************************************************/ + +enum _dr_kr921_t { + KR921_DR_SF12 = 0, + KR921_DR_SF11, + KR921_DR_SF10, + KR921_DR_SF9, + KR921_DR_SF8, + KR921_DR_SF7, + KR921_DR_NONE +}; + +// Bands: +// g1 : 1% 16dBm +// freq band datarates +enum { + KR921_F1 = 922100000, // g1 SF7-12 + KR921_F2 = 922300000, // g1 SF7-12 + KR921_FDOWN = 922100000, // (RX2 freq, DR2) + KR921_FBCN = 922300000, // default BCN, DR3 + KR921_FPING = 922500000, // default ping, DR3 +}; +enum { + KR921_FREQ_MIN = 920900000, + KR921_FREQ_MAX = 923300000 +}; +enum { + KR921_TX_EIRP_MAX_DBM = 16 // 16 dBm +}; +enum { DR_PAGE_KR921 = 0x10 * (LMIC_REGION_kr921 - 1) }; + +enum { KR921_LMIC_REGION_EIRP = 1 }; // region uses EIRP + +enum { KR921_LBT_US = 5000 }; // microseconds of LBT time -- 5000 ==> + // 5 ms. We use us rather than ms for + // future 128us support, and just for + // backward compatibility -- there + // is code that uses the _US constant, + // and it's awkward to break it. + +enum { KR921_LBT_DB_MAX = -80 }; // maximum channel strength in dB; if TX + // we measure more than this, we don't tx. + +// KR921 v1.1, all channels face a 1% duty cycle. So this will have to change +// in the future via a config. But this code base needs major changes for +// v1.1 in any case. +enum { KR921_V102_TX_CAP = 100 }; // v1.0.2 allows 100% + +#ifndef KR921_TX_CAP +# define KR921_TX_CAP KR921_V102_TX_CAP +#endif + +#endif /* _lorabase_kr921_h_ */