llsec: Added AEAD mode to CCM*
This commit is contained in:
parent
c656a4d1c5
commit
0a6b1cb646
@ -146,9 +146,32 @@ set_key(const uint8_t *key)
|
||||
AES_128.set_key(key);
|
||||
}
|
||||
/*---------------------------------------------------------------------------*/
|
||||
void
|
||||
aead(const uint8_t* nonce,
|
||||
uint8_t* m, uint8_t m_len,
|
||||
const uint8_t* a, uint8_t a_len,
|
||||
uint8_t *result, uint8_t mic_len,
|
||||
int forward)
|
||||
{
|
||||
if(!forward) {
|
||||
/* decrypt */
|
||||
ctr(nonce, m, m_len);
|
||||
}
|
||||
|
||||
mic(nonce,
|
||||
m, m_len,
|
||||
a, a_len,
|
||||
result,
|
||||
mic_len);
|
||||
|
||||
if(forward) {
|
||||
/* encrypt */
|
||||
ctr(nonce, m, m_len);
|
||||
}
|
||||
}
|
||||
/*---------------------------------------------------------------------------*/
|
||||
const struct ccm_star_driver ccm_star_driver = {
|
||||
mic,
|
||||
ctr,
|
||||
set_key
|
||||
set_key,
|
||||
aead
|
||||
};
|
||||
/*---------------------------------------------------------------------------*/
|
||||
|
@ -54,34 +54,27 @@
|
||||
* Structure of CCM* drivers.
|
||||
*/
|
||||
struct ccm_star_driver {
|
||||
|
||||
/**
|
||||
* \brief Generates a MIC over the data supplied.
|
||||
* \param nonce The nonce to use. CCM_STAR_NONCE_LENGTH bytes long.
|
||||
* \param m Message to authenticate and encrypt
|
||||
* \param a Additional authenticated data
|
||||
* \param result The generated MIC will be put here
|
||||
* \param mic_len The size of the MIC to be generated. <= 16.
|
||||
*/
|
||||
void (* mic)(const uint8_t* nonce,
|
||||
const uint8_t* m, uint8_t m_len,
|
||||
const uint8_t* a, uint8_t a_len,
|
||||
uint8_t *result,
|
||||
uint8_t mic_len);
|
||||
|
||||
/**
|
||||
* \brief XORs m with the key stream.
|
||||
* \param nonce The nonce to use. CCM_STAR_NONCE_LENGTH bytes long.
|
||||
* \param m Message to authenticate and encrypt
|
||||
*/
|
||||
void (* ctr)(const uint8_t* nonce,
|
||||
uint8_t* m, uint8_t m_len);
|
||||
|
||||
/**
|
||||
* \brief Sets the key in use. Default implementation calls AES_128.set_key().
|
||||
* \param key The key to use.
|
||||
*/
|
||||
void (* set_key)(const uint8_t* key);
|
||||
|
||||
/**
|
||||
* \brief Combines authentication and encryption.
|
||||
* \param nonce The nonce to use. CCM_STAR_NONCE_LENGTH bytes long.
|
||||
* \param m message to encrypt or decrypt
|
||||
* \param a Additional authenticated data
|
||||
* \param result The generated MIC will be put here
|
||||
* \param mic_len The size of the MIC to be generated. <= 16.
|
||||
* \param forward != 0 if used in forward direction.
|
||||
*/
|
||||
void (* aead)(const uint8_t* nonce,
|
||||
uint8_t* m, uint8_t m_len,
|
||||
const uint8_t* a, uint8_t a_len,
|
||||
uint8_t *result, uint8_t mic_len,
|
||||
int forward);
|
||||
};
|
||||
|
||||
extern const struct ccm_star_driver CCM_STAR;
|
||||
|
@ -39,7 +39,7 @@
|
||||
*/
|
||||
|
||||
#include "llsec/ccm-star-packetbuf.h"
|
||||
#include "lib/ccm-star.h"
|
||||
#include "net/linkaddr.h"
|
||||
#include "net/packetbuf.h"
|
||||
#include <string.h>
|
||||
|
||||
@ -62,10 +62,12 @@ get_extended_address(const linkaddr_t *addr)
|
||||
}
|
||||
#endif /* LINKADDR_SIZE == 2 */
|
||||
/*---------------------------------------------------------------------------*/
|
||||
/* Inits the 13-byte CCM* nonce as of 802.15.4-2011. */
|
||||
static void
|
||||
set_nonce(uint8_t *nonce, const linkaddr_t *source_addr)
|
||||
void
|
||||
ccm_star_packetbuf_set_nonce(uint8_t *nonce, int forward)
|
||||
{
|
||||
const linkaddr_t *source_addr;
|
||||
|
||||
source_addr = forward ? &linkaddr_node_addr : packetbuf_addr(PACKETBUF_ADDR_SENDER);
|
||||
memcpy(nonce, get_extended_address(source_addr), 8);
|
||||
nonce[8] = packetbuf_attr(PACKETBUF_ATTR_FRAME_COUNTER_BYTES_2_3) >> 8;
|
||||
nonce[9] = packetbuf_attr(PACKETBUF_ATTR_FRAME_COUNTER_BYTES_2_3) & 0xff;
|
||||
@ -74,43 +76,3 @@ set_nonce(uint8_t *nonce, const linkaddr_t *source_addr)
|
||||
nonce[12] = packetbuf_attr(PACKETBUF_ATTR_SECURITY_LEVEL);
|
||||
}
|
||||
/*---------------------------------------------------------------------------*/
|
||||
void
|
||||
ccm_star_packetbuf_mic(const linkaddr_t *source_addr,
|
||||
uint8_t *result,
|
||||
uint8_t mic_len)
|
||||
{
|
||||
uint8_t nonce[CCM_STAR_NONCE_LENGTH];
|
||||
uint8_t *m;
|
||||
uint8_t m_len;
|
||||
uint8_t *a;
|
||||
uint8_t a_len;
|
||||
|
||||
set_nonce(nonce, source_addr);
|
||||
|
||||
a = packetbuf_hdrptr();
|
||||
if(packetbuf_attr(PACKETBUF_ATTR_SECURITY_LEVEL) & (1 << 2)) {
|
||||
m = packetbuf_dataptr();
|
||||
m_len = packetbuf_datalen();
|
||||
a_len = packetbuf_hdrlen();
|
||||
} else {
|
||||
m = NULL;
|
||||
m_len = 0;
|
||||
a_len = packetbuf_totlen();
|
||||
}
|
||||
|
||||
CCM_STAR.mic(nonce,
|
||||
m, m_len,
|
||||
a, a_len,
|
||||
result,
|
||||
mic_len);
|
||||
}
|
||||
/*---------------------------------------------------------------------------*/
|
||||
void
|
||||
ccm_star_packetbuf_ctr(const linkaddr_t *source_addr)
|
||||
{
|
||||
uint8_t nonce[CCM_STAR_NONCE_LENGTH];
|
||||
|
||||
set_nonce(nonce, source_addr);
|
||||
CCM_STAR.ctr(nonce, packetbuf_dataptr(), packetbuf_datalen());
|
||||
}
|
||||
/*---------------------------------------------------------------------------*/
|
||||
|
@ -41,18 +41,8 @@
|
||||
#ifndef CCM_STAR_PACKETBUF_H_
|
||||
#define CCM_STAR_PACKETBUF_H_
|
||||
|
||||
#include "net/linkaddr.h"
|
||||
#include "lib/ccm-star.h"
|
||||
|
||||
/**
|
||||
* \brief Calls CCM_STAR.mic with parameters appropriate for LLSEC.
|
||||
*/
|
||||
void ccm_star_packetbuf_mic(const linkaddr_t *source_addr,
|
||||
uint8_t *result,
|
||||
uint8_t mic_len);
|
||||
|
||||
/**
|
||||
* \brief Calls CCM_STAR.ctr with parameters appropriate for LLSEC.
|
||||
*/
|
||||
void ccm_star_packetbuf_ctr(const linkaddr_t *source_addr);
|
||||
void ccm_star_packetbuf_set_nonce(uint8_t *nonce, int forward);
|
||||
|
||||
#endif /* CCM_STAR_PACKETBUF_H_ */
|
||||
|
@ -80,6 +80,45 @@
|
||||
static uint8_t key[16] = NONCORESEC_KEY;
|
||||
NBR_TABLE(struct anti_replay_info, anti_replay_table);
|
||||
|
||||
/*---------------------------------------------------------------------------*/
|
||||
static int
|
||||
aead(int forward)
|
||||
{
|
||||
uint8_t nonce[CCM_STAR_NONCE_LENGTH];
|
||||
uint8_t *m;
|
||||
uint8_t m_len;
|
||||
uint8_t *a;
|
||||
uint8_t a_len;
|
||||
uint8_t *result;
|
||||
uint8_t generated_mic[LLSEC802154_MIC_LENGTH];
|
||||
uint8_t *mic;
|
||||
|
||||
ccm_star_packetbuf_set_nonce(nonce, forward);
|
||||
a = packetbuf_hdrptr();
|
||||
m = packetbuf_dataptr();
|
||||
#if WITH_ENCRYPTION
|
||||
a_len = packetbuf_hdrlen();
|
||||
m_len = packetbuf_datalen();
|
||||
#else /* WITH_ENCRYPTION */
|
||||
a_len = packetbuf_totlen();
|
||||
m_len = 0;
|
||||
#endif /* WITH_ENCRYPTION */
|
||||
mic = a + a_len + m_len;
|
||||
result = forward ? mic : generated_mic;
|
||||
|
||||
CCM_STAR.aead(nonce,
|
||||
m, m_len,
|
||||
a, a_len,
|
||||
result, LLSEC802154_MIC_LENGTH,
|
||||
forward);
|
||||
|
||||
if(forward) {
|
||||
packetbuf_set_datalen(packetbuf_datalen() + LLSEC802154_MIC_LENGTH);
|
||||
return 1;
|
||||
} else {
|
||||
return (memcmp(generated_mic, mic, LLSEC802154_MIC_LENGTH) == 0);
|
||||
}
|
||||
}
|
||||
/*---------------------------------------------------------------------------*/
|
||||
static void
|
||||
send(mac_callback_t sent, void *ptr)
|
||||
@ -94,22 +133,13 @@ static int
|
||||
create(void)
|
||||
{
|
||||
int result;
|
||||
uint8_t *dataptr;
|
||||
uint8_t datalen;
|
||||
|
||||
result = framer_802154.create();
|
||||
if(result == FRAMER_FAILED) {
|
||||
return result;
|
||||
}
|
||||
|
||||
dataptr = packetbuf_dataptr();
|
||||
datalen = packetbuf_datalen();
|
||||
|
||||
ccm_star_packetbuf_mic(&linkaddr_node_addr, dataptr + datalen, LLSEC802154_MIC_LENGTH);
|
||||
#if WITH_ENCRYPTION
|
||||
ccm_star_packetbuf_ctr(&linkaddr_node_addr);
|
||||
#endif /* WITH_ENCRYPTION */
|
||||
packetbuf_set_datalen(datalen + LLSEC802154_MIC_LENGTH);
|
||||
aead(1);
|
||||
|
||||
return result;
|
||||
}
|
||||
@ -123,8 +153,6 @@ parse(void)
|
||||
static void
|
||||
input(void)
|
||||
{
|
||||
uint8_t generated_mic[LLSEC802154_MIC_LENGTH];
|
||||
uint8_t *received_mic;
|
||||
const linkaddr_t *sender;
|
||||
struct anti_replay_info* info;
|
||||
|
||||
@ -140,14 +168,8 @@ input(void)
|
||||
|
||||
packetbuf_set_datalen(packetbuf_datalen() - LLSEC802154_MIC_LENGTH);
|
||||
|
||||
#if WITH_ENCRYPTION
|
||||
ccm_star_packetbuf_ctr(sender);
|
||||
#endif /* WITH_ENCRYPTION */
|
||||
ccm_star_packetbuf_mic(sender, generated_mic, LLSEC802154_MIC_LENGTH);
|
||||
|
||||
received_mic = ((uint8_t *) packetbuf_dataptr()) + packetbuf_datalen();
|
||||
if(memcmp(generated_mic, received_mic, LLSEC802154_MIC_LENGTH) != 0) {
|
||||
PRINTF("noncoresec: received nonauthentic frame %"PRIu32"\n",
|
||||
if(!aead(0)) {
|
||||
PRINTF("noncoresec: received unauthentic frame %"PRIu32"\n",
|
||||
anti_replay_get_counter());
|
||||
return;
|
||||
}
|
||||
|
@ -72,11 +72,12 @@ test_sec_lvl_6()
|
||||
0x01 , 0xCE };
|
||||
uint8_t oracle[LLSEC802154_MIC_LENGTH] = { 0x4F , 0xDE , 0x52 , 0x90 ,
|
||||
0x61 , 0xF9 , 0xC6 , 0xF1 };
|
||||
uint8_t nonce[13];
|
||||
frame802154_frame_counter_t counter;
|
||||
uint8_t mic[LLSEC802154_MIC_LENGTH];
|
||||
|
||||
printf("Testing verification ... ");
|
||||
|
||||
linkaddr_copy(&linkaddr_node_addr, &source_address);
|
||||
packetbuf_clear();
|
||||
packetbuf_set_datalen(30);
|
||||
memcpy(packetbuf_hdrptr(), data, 30);
|
||||
@ -87,9 +88,14 @@ test_sec_lvl_6()
|
||||
packetbuf_hdrreduce(29);
|
||||
|
||||
CCM_STAR.set_key(key);
|
||||
ccm_star_packetbuf_mic(&source_address, mic, LLSEC802154_MIC_LENGTH);
|
||||
ccm_star_packetbuf_set_nonce(nonce, 1);
|
||||
CCM_STAR.aead(nonce,
|
||||
packetbuf_dataptr(), packetbuf_datalen(),
|
||||
packetbuf_hdrptr(), packetbuf_hdrlen(),
|
||||
((uint8_t *) packetbuf_hdrptr()) + 30, LLSEC802154_MIC_LENGTH,
|
||||
1);
|
||||
|
||||
if(memcmp(mic, oracle, LLSEC802154_MIC_LENGTH) == 0) {
|
||||
if(memcmp(((uint8_t *) packetbuf_hdrptr()) + 30, oracle, LLSEC802154_MIC_LENGTH) == 0) {
|
||||
printf("Success\n");
|
||||
} else {
|
||||
printf("Failure\n");
|
||||
@ -97,7 +103,6 @@ test_sec_lvl_6()
|
||||
|
||||
printf("Testing encryption ... ");
|
||||
|
||||
ccm_star_packetbuf_ctr(&source_address);
|
||||
if(((uint8_t *) packetbuf_hdrptr())[29] == 0xD8) {
|
||||
printf("Success\n");
|
||||
} else {
|
||||
@ -105,7 +110,13 @@ test_sec_lvl_6()
|
||||
}
|
||||
|
||||
printf("Testing decryption ... ");
|
||||
ccm_star_packetbuf_ctr(&source_address);
|
||||
packetbuf_set_addr(PACKETBUF_ADDR_SENDER, &source_address);
|
||||
ccm_star_packetbuf_set_nonce(nonce, 0);
|
||||
CCM_STAR.aead(nonce,
|
||||
packetbuf_dataptr(), packetbuf_datalen(),
|
||||
packetbuf_hdrptr(), packetbuf_hdrlen(),
|
||||
((uint8_t *) packetbuf_hdrptr()) + 30, LLSEC802154_MIC_LENGTH,
|
||||
0);
|
||||
if(((uint8_t *) packetbuf_hdrptr())[29] == 0xCE) {
|
||||
printf("Success\n");
|
||||
} else {
|
||||
|
@ -101,9 +101,11 @@ test_sec_lvl_2()
|
||||
0x84 , 0x1A , 0xB5 , 0x53 };
|
||||
frame802154_frame_counter_t counter;
|
||||
uint8_t mic[LLSEC802154_MIC_LENGTH];
|
||||
uint8_t nonce[13];
|
||||
|
||||
printf("Testing verification ... ");
|
||||
|
||||
linkaddr_copy(&linkaddr_node_addr, &source_address);
|
||||
packetbuf_clear();
|
||||
packetbuf_set_datalen(26);
|
||||
memcpy(packetbuf_hdrptr(), data, 26);
|
||||
@ -114,9 +116,14 @@ test_sec_lvl_2()
|
||||
packetbuf_hdrreduce(18);
|
||||
|
||||
CCM_STAR.set_key(key);
|
||||
ccm_star_packetbuf_mic(&source_address, mic, LLSEC802154_MIC_LENGTH);
|
||||
ccm_star_packetbuf_set_nonce(nonce, 1);
|
||||
CCM_STAR.aead(nonce,
|
||||
NULL, 0,
|
||||
packetbuf_hdrptr(), packetbuf_totlen(),
|
||||
((uint8_t *) packetbuf_dataptr()) + packetbuf_datalen(), LLSEC802154_MIC_LENGTH,
|
||||
1);
|
||||
|
||||
if(memcmp(mic, oracle, LLSEC802154_MIC_LENGTH) == 0) {
|
||||
if(memcmp(((uint8_t *) packetbuf_dataptr()) + packetbuf_datalen(), oracle, LLSEC802154_MIC_LENGTH) == 0) {
|
||||
printf("Success\n");
|
||||
} else {
|
||||
printf("Failure\n");
|
||||
|
Loading…
Reference in New Issue
Block a user