9494 */
9595#define ADR_ACK_COUNTER_MAX 0xFFFFFFFF
9696
97+ /*!
98+ * Delay required to simulate an ABP join like an OTAA join
99+ */
100+ #define ABP_JOIN_PENDING_DELAY_MS 10
101+
97102#if defined(__ICCARM__ )
98103#ifndef __NO_INIT
99104#define __NO_INIT __no_init
@@ -119,14 +124,15 @@ static const uint8_t LoRaMacMaxEirpTable[] = { 8, 10, 12, 13, 14, 16, 18, 20, 21
119124 */
120125enum eLoRaMacState
121126{
122- LORAMAC_IDLE = 0x00000000 ,
123- LORAMAC_STOPPED = 0x00000001 ,
124- LORAMAC_TX_RUNNING = 0x00000002 ,
125- LORAMAC_RX = 0x00000004 ,
126- LORAMAC_ACK_RETRY = 0x00000010 ,
127- LORAMAC_TX_DELAYED = 0x00000020 ,
128- LORAMAC_TX_CONFIG = 0x00000040 ,
129- LORAMAC_RX_ABORT = 0x00000080 ,
127+ LORAMAC_IDLE = 0x00000000 ,
128+ LORAMAC_STOPPED = 0x00000001 ,
129+ LORAMAC_TX_RUNNING = 0x00000002 ,
130+ LORAMAC_RX = 0x00000004 ,
131+ LORAMAC_ACK_RETRY = 0x00000010 ,
132+ LORAMAC_TX_DELAYED = 0x00000020 ,
133+ LORAMAC_TX_CONFIG = 0x00000040 ,
134+ LORAMAC_RX_ABORT = 0x00000080 ,
135+ LORAMAC_ABP_JOIN_PENDING = 0x00000100 ,
130136};
131137
132138/*
@@ -314,6 +320,10 @@ typedef struct sLoRaMacCtx
314320 * Start time of the response timeout
315321 */
316322 TimerTime_t ResponseTimeoutStartTime ;
323+ /*
324+ * Timer required to simulate an ABP join like an OTAA join
325+ */
326+ TimerEvent_t AbpJoinPendingTimer ;
317327#endif /* LORAMAC_VERSION */
318328 /*!
319329 * Buffer containing the MAC layer commands
@@ -1262,7 +1272,26 @@ static void ProcessRadioRxDone( void )
12621272 joinType = MLME_REJOIN_2 ;
12631273 }
12641274#endif /* LORAMAC_VERSION */
1275+ #if (defined( LORAMAC_VERSION ) && (( LORAMAC_VERSION == 0x01000400 ) || ( LORAMAC_VERSION == 0x01010100 )))
1276+ if ( LORAMAC_CRYPTO_SUCCESS == macCryptoStatus )
1277+ {
1278+ VerifyParams_t verifyRxDr ;
12651279
1280+ if ( macMsgJoinAccept .DLSettings .Bits .RX2DataRate != 0x0F )
1281+ {
1282+ verifyRxDr .DatarateParams .Datarate = macMsgJoinAccept .DLSettings .Bits .RX2DataRate ;
1283+ verifyRxDr .DatarateParams .DownlinkDwellTime = Nvm .MacGroup2 .MacParams .DownlinkDwellTime ;
1284+ if ( RegionVerify ( Nvm .MacGroup2 .Region , & verifyRxDr , PHY_RX_DR ) == false )
1285+ {
1286+ // MLME handling
1287+ if ( LoRaMacConfirmQueueIsCmdActive ( MLME_JOIN ) == true )
1288+ {
1289+ LoRaMacConfirmQueueSetStatus ( LORAMAC_EVENT_INFO_STATUS_JOIN_FAIL , MLME_JOIN );
1290+ }
1291+ break ;
1292+ }
1293+ }
1294+ #else
12661295 VerifyParams_t verifyRxDr ;
12671296 bool rxDrValid = false;
12681297 verifyRxDr .DatarateParams .Datarate = macMsgJoinAccept .DLSettings .Bits .RX2DataRate ;
@@ -1271,6 +1300,8 @@ static void ProcessRadioRxDone( void )
12711300
12721301 if ( ( LORAMAC_CRYPTO_SUCCESS == macCryptoStatus ) && ( rxDrValid == true ) )
12731302 {
1303+ #endif
1304+
12741305 // Network ID
12751306 Nvm .MacGroup2 .NetID = ( uint32_t ) macMsgJoinAccept .NetID [0 ];
12761307 Nvm .MacGroup2 .NetID |= ( ( uint32_t ) macMsgJoinAccept .NetID [1 ] << 8 );
@@ -1283,8 +1314,18 @@ static void ProcessRadioRxDone( void )
12831314
12841315 // DLSettings
12851316 Nvm .MacGroup2 .MacParams .Rx1DrOffset = macMsgJoinAccept .DLSettings .Bits .RX1DRoffset ;
1317+
1318+ #if (defined( LORAMAC_VERSION ) && (( LORAMAC_VERSION == 0x01000400 ) || ( LORAMAC_VERSION == 0x01010100 )))
1319+ // Verify if we shall assign the new datarate
1320+ if ( macMsgJoinAccept .DLSettings .Bits .RX2DataRate != 0x0F )
1321+ {
1322+ #endif
1323+
12861324 Nvm .MacGroup2 .MacParams .Rx2Channel .Datarate = macMsgJoinAccept .DLSettings .Bits .RX2DataRate ;
12871325 Nvm .MacGroup2 .MacParams .RxCChannel .Datarate = macMsgJoinAccept .DLSettings .Bits .RX2DataRate ;
1326+ #if (defined( LORAMAC_VERSION ) && (( LORAMAC_VERSION == 0x01000400 ) || ( LORAMAC_VERSION == 0x01010100 )))
1327+ }
1328+ #endif
12881329
12891330 // RxDelay
12901331 Nvm .MacGroup2 .MacParams .ReceiveDelay1 = macMsgJoinAccept .RxDelay ;
@@ -1612,9 +1653,13 @@ static void ProcessRadioRxDone( void )
16121653 }
16131654
16141655 // Set the pending status
1615- /* if( ( ( ( Nvm.MacGroup1.SrvAckRequested == true ) || ( macMsgData.FHDR.FCtrl.Bits.FPending > 0 ) ) && ( Nvm.MacGroup2.DeviceClass == CLASS_A ) ) ||
1616- ( MacCtx.McpsIndication.ResponseTimeout > 0 ) ) */
1617- if ( ( ( Nvm .MacGroup1 .SrvAckRequested == true ) || ( macMsgData .FHDR .FCtrl .Bits .FPending > 0 ) ) && ( Nvm .MacGroup2 .DeviceClass == CLASS_A ) )
1656+ // Fix for Class C Certification test. Re-enabled part of if condition previously removed.
1657+ if ( ( ( ( Nvm .MacGroup1 .SrvAckRequested == true ) || ( macMsgData .FHDR .FCtrl .Bits .FPending > 0 ) ) && ( Nvm .MacGroup2 .DeviceClass == CLASS_A ) )
1658+ #if (defined ( LORAMAC_VERSION ) && (( LORAMAC_VERSION == 0x01000400 ) || ( LORAMAC_VERSION == 0x01010100 )))
1659+ || ( MacCtx .McpsIndication .ResponseTimeout > 0 )
1660+ #endif /* LORAMAC_VERSION */
1661+ )
1662+ //if( ( ( Nvm.MacGroup1.SrvAckRequested == true ) || ( macMsgData.FHDR.FCtrl.Bits.FPending > 0 ) ) && ( Nvm.MacGroup2.DeviceClass == CLASS_A ) )
16181663 {
16191664 MacCtx .McpsIndication .IsUplinkTxPending = 1 ;
16201665 }
@@ -2877,6 +2922,14 @@ static void ProcessMacCommands( uint8_t *payload, uint8_t macIndex, uint8_t comm
28772922 rxParamSetupReq .Datarate = payload [macIndex ] & 0x0F ;
28782923 macIndex ++ ;
28792924
2925+ #if (defined( LORAMAC_VERSION ) && (( LORAMAC_VERSION == 0x01000400 ) || ( LORAMAC_VERSION == 0x01010100 )))
2926+ if ( rxParamSetupReq .Datarate == 0x0F )
2927+ {
2928+ // Keep the current datarate
2929+ rxParamSetupReq .Datarate = Nvm .MacGroup2 .MacParams .Rx2Channel .Datarate ;
2930+ }
2931+ #endif
2932+
28802933 rxParamSetupReq .Frequency = ( uint32_t ) payload [macIndex ++ ];
28812934 rxParamSetupReq .Frequency |= ( uint32_t ) payload [macIndex ++ ] << 8 ;
28822935 rxParamSetupReq .Frequency |= ( uint32_t ) payload [macIndex ++ ] << 16 ;
@@ -5734,7 +5787,18 @@ LoRaMacStatus_t LoRaMacMibSetRequestConfirm( MibRequestConfirm_t* mibSet )
57345787 }
57355788 case MIB_SYSTEM_MAX_RX_ERROR :
57365789 {
5790+ #if (defined( LORAMAC_VERSION ) && (( LORAMAC_VERSION == 0x01000400 ) || ( LORAMAC_VERSION == 0x01010100 )))
5791+ if ( mibSet -> Param .SystemMaxRxError <= 500 )
5792+ { // Only apply the new value if in range 0..500 ms else keep current value.
5793+ Nvm .MacGroup2 .MacParams .SystemMaxRxError = Nvm .MacGroup2 .MacParamsDefaults .SystemMaxRxError = mibSet -> Param .SystemMaxRxError ;
5794+ }
5795+ else
5796+ {
5797+ status = LORAMAC_STATUS_PARAMETER_INVALID ;
5798+ }
5799+ #else
57375800 Nvm .MacGroup2 .MacParams .SystemMaxRxError = Nvm .MacGroup2 .MacParamsDefaults .SystemMaxRxError = mibSet -> Param .SystemMaxRxError ;
5801+ #endif
57385802 break ;
57395803 }
57405804 case MIB_MIN_RX_SYMBOLS :
@@ -6082,6 +6146,38 @@ LoRaMacStatus_t LoRaMacMcChannelSetupRxParams( AddressIdentifier_t groupID, McRx
60826146 return LORAMAC_STATUS_OK ;
60836147}
60846148
6149+ #if (defined( LORAMAC_VERSION ) && (( LORAMAC_VERSION == 0x01000400 ) || ( LORAMAC_VERSION == 0x01010100 )))
6150+ /*!
6151+ * \brief Function executed on AbpJoinPendingTimer timer event
6152+ */
6153+ static void OnAbpJoinPendingTimerEvent ( void * context )
6154+ {
6155+ MacCtx .MacState &= ~LORAMAC_ABP_JOIN_PENDING ;
6156+ MacCtx .MacFlags .Bits .MacDone = 1 ;
6157+ OnMacProcessNotify ( );
6158+ }
6159+
6160+ /*!
6161+ * \brief Start ABP join simulation
6162+ */
6163+ static void AbpJoinPendingStart ( void )
6164+ {
6165+ static bool initialized = false;
6166+
6167+ if ( initialized == false )
6168+ {
6169+ initialized = true;
6170+ TimerInit ( & MacCtx .AbpJoinPendingTimer , OnAbpJoinPendingTimerEvent );
6171+ }
6172+
6173+ MacCtx .MacState |= LORAMAC_ABP_JOIN_PENDING ;
6174+
6175+ TimerStop ( & MacCtx .AbpJoinPendingTimer );
6176+ TimerSetValue ( & MacCtx .AbpJoinPendingTimer , ABP_JOIN_PENDING_DELAY_MS );
6177+ TimerStart ( & MacCtx .AbpJoinPendingTimer );
6178+ }
6179+ #endif /* LORAMAC_VERSION */
6180+
60856181LoRaMacStatus_t LoRaMacProcessMicForDatablock ( uint8_t * buffer , uint32_t size , uint16_t sessionCnt , uint8_t fragIndex , uint32_t descriptor , uint32_t * mic )
60866182{
60876183 LoRaMacCryptoStatus_t macCryptoStatus = LORAMAC_CRYPTO_ERROR ;
@@ -6099,6 +6195,9 @@ LoRaMacStatus_t LoRaMacMlmeRequest( MlmeReq_t* mlmeRequest )
60996195{
61006196 LoRaMacStatus_t status = LORAMAC_STATUS_SERVICE_UNKNOWN ;
61016197 MlmeConfirmQueue_t queueElement ;
6198+ #if (defined( LORAMAC_VERSION ) && (( LORAMAC_VERSION == 0x01000400 ) || ( LORAMAC_VERSION == 0x01010100 )))
6199+ bool isAbpJoinPending = false;
6200+ #endif /* LORAMAC_VERSION */
61026201 uint8_t macCmdPayload [2 ] = { 0x00 , 0x00 };
61036202
61046203 if ( mlmeRequest == NULL )
@@ -6191,6 +6290,9 @@ LoRaMacStatus_t LoRaMacMlmeRequest( MlmeReq_t* mlmeRequest )
61916290 queueElement .ReadyToHandle = true;
61926291 OnMacProcessNotify ( );
61936292 MacCtx .MacFlags .Bits .MacDone = 1 ;
6293+ #if (defined( LORAMAC_VERSION ) && (( LORAMAC_VERSION == 0x01000400 ) || ( LORAMAC_VERSION == 0x01010100 )))
6294+ isAbpJoinPending = true;
6295+ #endif
61946296 status = LORAMAC_STATUS_OK ;
61956297 }
61966298#endif /* LORAMAC_VERSION */
@@ -6335,6 +6437,12 @@ LoRaMacStatus_t LoRaMacMlmeRequest( MlmeReq_t* mlmeRequest )
63356437 else
63366438 {
63376439 LoRaMacConfirmQueueAdd ( & queueElement );
6440+ #if (defined( LORAMAC_VERSION ) && (( LORAMAC_VERSION == 0x01000400 ) || ( LORAMAC_VERSION == 0x01010100 )))
6441+ if ( isAbpJoinPending == true )
6442+ {
6443+ AbpJoinPendingStart ( );
6444+ }
6445+ #endif /* LORAMAC_VERSION */
63386446 }
63396447 return status ;
63406448}
@@ -6681,4 +6789,22 @@ LoRaMacStatus_t LoRaMacDeInitialization( void )
66816789 }
66826790}
66836791
6792+ void LoRaMacReset ( void )
6793+ {
6794+ // Reset state machine
6795+ MacCtx .MacState &= ~LORAMAC_TX_RUNNING ;
6796+ MacCtx .MacFlags .Bits .MacDone = 1 ;
6797+
6798+ // Stop Timers
6799+ TimerStop ( & MacCtx .TxDelayedTimer );
6800+ TimerStop ( & MacCtx .RxWindowTimer1 );
6801+ TimerStop ( & MacCtx .RxWindowTimer2 );
6802+
6803+ // Stop retransmissions
6804+ MacCtx .ChannelsNbTransCounter = Nvm .MacGroup2 .MacParams .ChannelsNbTrans ;
6805+
6806+ // Inform application layer
6807+ OnMacProcessNotify ( );
6808+ }
6809+
66846810#pragma GCC diagnostic pop
0 commit comments