Skip to content

Commit

Permalink
[radio] fix for key rotation in enhAck (#879)
Browse files Browse the repository at this point in the history
Not all devices do the key rotation at the same time.
This scenario fixes the issue when Router rotates sooner than SSED.
In such case SSED still requires enhAcks to use previous key id and counter.
Added storing last value of FC when keyId changes.
If SSED uses keyId-1 ack uses the stored value instead of current mac counter value.

Signed-off-by: Marek Porwisz <[email protected]>
  • Loading branch information
pkwiek authored Aug 30, 2024
1 parent 7a90219 commit 30ede08
Showing 1 changed file with 17 additions and 8 deletions.
25 changes: 17 additions & 8 deletions src/src/radio.c
Original file line number Diff line number Diff line change
Expand Up @@ -140,6 +140,7 @@ static uint32_t sPendingEvents;

#if OPENTHREAD_CONFIG_THREAD_VERSION >= OT_THREAD_VERSION_1_2
static uint32_t sMacFrameCounter;
static uint32_t sPrevMacFrameCounter;
static uint8_t sKeyId;
static otMacKeyMaterial sPrevKey;
static otMacKeyMaterial sCurrKey;
Expand Down Expand Up @@ -189,6 +190,8 @@ static void dataInit(void)
}

memset(&sAckFrame, 0, sizeof(sAckFrame));

sPrevMacFrameCounter = 0;
}

static void convertShortAddress(uint8_t *aTo, uint16_t aFrom)
Expand Down Expand Up @@ -273,29 +276,34 @@ static void txAckProcessSecurity(uint8_t *aAckFrame)

if (keyId == sKeyId)
{
key = &sCurrKey;
key = &sCurrKey;
sAckFrameCounter = sMacFrameCounter++;
}
else if (keyId == sKeyId - 1)
{
key = &sPrevKey;
key = &sPrevKey;
sAckFrameCounter = sPrevMacFrameCounter++;
}
else if (keyId == sKeyId + 1)
{
key = &sNextKey;
// Openthread does not maintain future frame counter.
// Mac frame counter would be overwritten after key rotation leading to
// frames being dropped due to counter value lower than in acks.
sAckFrameCounter = 0;
}
else
{
otEXPECT(false);
}

sAckFrameCounter = sMacFrameCounter;
sAckKeyId = keyId;
sAckedWithSecEnhAck = true;

ackFrame.mInfo.mTxInfo.mAesKey = key;

otMacFrameSetKeyId(&ackFrame, keyId);
otMacFrameSetFrameCounter(&ackFrame, sMacFrameCounter++);
otMacFrameSetFrameCounter(&ackFrame, sAckFrameCounter);

otMacFrameProcessTransmitAesCcm(&ackFrame, &sExtAddress);

Expand Down Expand Up @@ -1308,10 +1316,11 @@ void otPlatRadioSetMacKey(otInstance *aInstance,

CRITICAL_REGION_ENTER();

sKeyId = aKeyId;
sPrevKey = *aPrevKey;
sCurrKey = *aCurrKey;
sNextKey = *aNextKey;
sKeyId = aKeyId;
sPrevKey = *aPrevKey;
sCurrKey = *aCurrKey;
sNextKey = *aNextKey;
sPrevMacFrameCounter = sMacFrameCounter;

CRITICAL_REGION_EXIT();
}
Expand Down

0 comments on commit 30ede08

Please sign in to comment.