Skip to content

Instantly share code, notes, and snippets.

@devendranaga
Created October 3, 2019 17:01
Show Gist options
  • Save devendranaga/12fd047d41ce16d4a64bc576f0f1e0ef to your computer and use it in GitHub Desktop.
Save devendranaga/12fd047d41ce16d4a64bc576f0f1e0ef to your computer and use it in GitHub Desktop.
deriving keys with HKDF
#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>
#include <fcntl.h>
#include <mbedtls/hkdf.h>
#include <stdint.h>
#include <string.h>
// salt is shared between server and client
uint8_t salt[32];
void server()
{
// input key .. must be setup during one time provisioning or OTP
uint8_t input[] = {
0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08
};
// info can be a device identifier / some stored ids within device from EEPROM etc
uint8_t info[] = {
0xde, 0xad, 0xbe, 0xef
};
// generate a salt
memset(salt, 0, sizeof(salt));
{
int fd;
fd = open("/dev/urandom", O_RDONLY);
if (fd < 0) {
printf("failed to generate a random\n");
return;
}
read(fd, salt, sizeof(salt));
close(fd);
}
// below series of steps derive the key
uint8_t okm[32];
memset(okm, 0, sizeof(okm));
// choose SHA256 for MD
const mbedtls_md_info_t *mdinfo = mbedtls_md_info_from_type(MBEDTLS_MD_SHA256);
if (!mdinfo) {
return;
}
int ret;
ret = mbedtls_hkdf(mdinfo, salt, sizeof(salt), input, sizeof(input), info, sizeof(info), okm, sizeof(okm));
if (ret != 0) {
printf("failed to hkdf\n");
return;
}
printf("HKDF derived at server: ");
int i;
for (i = 0; i < sizeof(okm); i ++) {
printf("%02x ", okm[i]);
}
printf("\n");
}
void client()
{
// input key .. must be setup during manufacturing
uint8_t input[] = {
0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08
};
// info can be a device identifier / some stored ids within device from EEPROM etc
uint8_t info[] = {
0xde, 0xad, 0xbe, 0xef
};
uint8_t okm[32];
memset(okm, 0, sizeof(okm));
// choose SHA256 as MD
const mbedtls_md_info_t *mdinfo = mbedtls_md_info_from_type(MBEDTLS_MD_SHA256);
if (!mdinfo) {
return;
}
int ret;
ret = mbedtls_hkdf(mdinfo, salt, sizeof(salt), input, sizeof(input), info, sizeof(info), okm, sizeof(okm));
if (ret != 0) {
printf("failed to hkdf\n");
return;
}
printf("HKDF derived at client: ");
int i;
for (i = 0; i < sizeof(okm); i ++) {
printf("%02x ", okm[i]);
}
printf("\n");
}
int main()
{
// server creates a salt and shares it with client
//
// server assumes the input key material is commonly known and setup
// between server and client within their hardware / read only memory
//
// salt is shared
//
// device identifier is used as info field for a device specific key generation
server();
client();
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment