Add cryptoauthlib as a component with mbedtls integration

* Add options to mbedtls for hardware acceleration
* Disable mbedtls EC curves if hardware acceleration is selected
since the hardware will have to define the curves supported
* Add a hardware ecdsa example
pull/5408/head
Bryan Hunt 2019-02-10 12:38:11 -07:00 zatwierdzone przez Aditya Patwardhan
rodzic 7099c2b444
commit 4553f6c95d
12 zmienionych plików z 427 dodań i 11 usunięć

4
.gitmodules vendored
Wyświetl plik

@ -82,3 +82,7 @@
[submodule "components/tinyusb/tinyusb"]
path = components/tinyusb/tinyusb
url = ../../espressif/tinyusb.git
[submodule "components/cryptoauthlib/cryptoauthlib"]
path = components/cryptoauthlib/cryptoauthlib
url = https://github.com/MicrochipTech/cryptoauthlib.git

Wyświetl plik

@ -0,0 +1,29 @@
menu "Cryptoauthlib"
config ATCA_MBEDTLS_ECDH
bool "Enable Hardware ECDH with ATECC608A"
depends on MBEDTLS_ECDH_C
select MBEDTLS_HARDWARE_ECDH
select MBEDTLS_ECP_DP_SECP256R1_ENABLED
help
Enable hardware ECDH operations on an ATECC608A device
config ATCA_MBEDTLS_ECDSA
bool "Enable Hardware ECDSA keys for mbedTLS"
depends on MBEDTLS_ECDSA_C
help
Enable Hardware ECDSA
config ATCA_MBEDTLS_ECDSA_SIGN
bool "Enable ATECC608A sign operations in mbedTLS"
depends on ATCA_MBEDTLS_ECDSA
select MBEDTLS_HARDWARE_ECDSA_SIGN
select MBEDTLS_ECP_DP_SECP256R1_ENABLED
config ATCA_MBEDTLS_ECDSA_VERIFY
bool "Enable ATECC608A verify operations in mbedTLS"
depends on ATCA_MBEDTLS_ECDSA
select MBEDTLS_HARDWARE_ECDSA_VERIFY
select MBEDTLS_ECP_DP_SECP256R1_ENABLED
endmenu # cryptoauthlib

Wyświetl plik

@ -0,0 +1,41 @@
#
# Component Makefile
#
COMPONENT_SUBMODULES += cryptoauthlib
CRYPTOAUTHLIB_DIR := cryptoauthlib/lib
COMPONENT_SRCDIRS := $(CRYPTOAUTHLIB_DIR)/atcacert \
$(CRYPTOAUTHLIB_DIR)/basic \
$(CRYPTOAUTHLIB_DIR)/crypto \
$(CRYPTOAUTHLIB_DIR)/crypto/hashes \
$(CRYPTOAUTHLIB_DIR)/host \
$(CRYPTOAUTHLIB_DIR)/mbedtls \
$(CRYPTOAUTHLIB_DIR) \
port
COMPONENT_OBJS := $(foreach compsrcdir,$(COMPONENT_SRCDIRS),$(patsubst %.c,%.o,$(wildcard $(COMPONENT_PATH)/$(compsrcdir)/*.c))) \
$(CRYPTOAUTHLIB_DIR)/hal/atca_hal.o \
$(CRYPTOAUTHLIB_DIR)/hal/hal_freertos.o \
$(CRYPTOAUTHLIB_DIR)/hal/hal_esp32_i2c.o \
$(CRYPTOAUTHLIB_DIR)/hal/hal_esp32_timer.o
# Make relative by removing COMPONENT_PATH from all found object paths
COMPONENT_OBJS := $(patsubst $(COMPONENT_PATH)/%,%,$(COMPONENT_OBJS))
# Don't include the default interface configurations from cryptoauthlib
COMPONENT_OBJEXCLUDE := $(CRYPTOAUTHLIB_DIR)/atca_cfgs.o
# Add the hal directory back in for source search paths
COMPONENT_SRCDIRS += $(CRYPTOAUTHLIB_DIR)/hal
COMPONENT_ADD_INCLUDEDIRS := $(CRYPTOAUTHLIB_DIR) $(CRYPTOAUTHLIB_DIR)/hal
# Library requires some global defines
CFLAGS+=-DESP32 -DATCA_HAL_I2C -DATCA_USE_RTOS_TIMER
$(CRYPTOAUTHLIB_DIR)/hal/hal_freertos.o: CFLAGS+= -I$(IDF_PATH)/components/freertos/include/freertos
# Turn off some warnings for some files that have been checked
$(CRYPTOAUTHLIB_DIR)/hal/hal_esp32_i2c.o: CFLAGS+= -Wno-unused-but-set-variable -Wno-unused-variable
$(CRYPTOAUTHLIB_DIR)/basic/atca_helpers.o: CFLAGS+= -Wno-type-limits

@ -0,0 +1 @@
Subproject commit 3bc5e245c68ca9f25e8fada393d059304b4adecb

Wyświetl plik

@ -0,0 +1,50 @@
/**
* \file
* \brief a set of default configurations for various ATCA devices and interfaces
*
* \copyright (c) 2015-2018 Microchip Technology Inc. and its subsidiaries.
*
* \page License
*
* Subject to your compliance with these terms, you may use Microchip software
* and any derivatives exclusively with Microchip products. It is your
* responsibility to comply with third party license terms applicable to your
* use of third party software (including open source software) that may
* accompany Microchip software.
*
* THIS SOFTWARE IS SUPPLIED BY MICROCHIP "AS IS". NO WARRANTIES, WHETHER
* EXPRESS, IMPLIED OR STATUTORY, APPLY TO THIS SOFTWARE, INCLUDING ANY IMPLIED
* WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY, AND FITNESS FOR A
* PARTICULAR PURPOSE. IN NO EVENT WILL MICROCHIP BE LIABLE FOR ANY INDIRECT,
* SPECIAL, PUNITIVE, INCIDENTAL OR CONSEQUENTIAL LOSS, DAMAGE, COST OR EXPENSE
* OF ANY KIND WHATSOEVER RELATED TO THE SOFTWARE, HOWEVER CAUSED, EVEN IF
* MICROCHIP HAS BEEN ADVISED OF THE POSSIBILITY OR THE DAMAGES ARE
* FORESEEABLE. TO THE FULLEST EXTENT ALLOWED BY LAW, MICROCHIP'S TOTAL
* LIABILITY ON ALL CLAIMS IN ANY WAY RELATED TO THIS SOFTWARE WILL NOT EXCEED
* THE AMOUNT OF FEES, IF ANY, THAT YOU HAVE PAID DIRECTLY TO MICROCHIP FOR
* THIS SOFTWARE.
*/
#include <stddef.h>
#include "atca_cfgs.h"
#include "atca_iface.h"
#include "atca_device.h"
/** \defgroup config Configuration (cfg_)
* \brief Logical device configurations describe the CryptoAuth device type and logical interface.
@{ */
/* if the number of these configurations grows large, we can #ifdef them based on required device support */
/** \brief default configuration for an ECCx08A device */
ATCAIfaceCfg cfg_ateccx08a_i2c_default = {
.iface_type = ATCA_I2C_IFACE,
.devtype = ATECC608A,
.atcai2c.slave_address = 0xC0,
.atcai2c.bus = 0,
.atcai2c.baud = 100000,
.wake_delay = 1500,
.rx_retries = 20
};
/** @} */

Wyświetl plik

@ -280,6 +280,27 @@ menu "mbedTLS"
SHA hardware acceleration is faster than software in some situations but
slower in others. You should benchmark to find the best setting for you.
config MBEDTLS_ATCA_HARDWARE_ECDH
bool "Enable hardware ECDH acceleration when using ATECC608A cryptoauth chip"
default n
help
This option enables hardware acceleration for ECDH, only when using
ATECC608A cryptoauth chip (integrated with ESP32-WROOM-32SE)
config MBEDTLS_ATCA_HARDWARE_ECDSA_SIGN
bool "Enable hardware ECDSA sign acceleration when using ATECC608A"
default n
help
This option enables hardware acceleration for ECDSA sign function, only
when using ATECC608A cryptoauth chip (integrated with ESP32-WROOM-32SE)
config MBEDTLS_ATCA_HARDWARE_ECDSA_VERIFY
bool "Enable hardware ECDSA verify acceleration when using ATECC608A"
default n
help
This option enables hardware acceleration for ECDSA sign function, only
when using ATECC608A cryptoauth chip (integrated with ESP32-WROOM-32SE)
config MBEDTLS_HAVE_TIME
bool "Enable mbedtls time"
depends on !ESP32_TIME_SYSCALL_USE_NONE
@ -650,14 +671,14 @@ menu "mbedTLS"
config MBEDTLS_ECP_DP_SECP192R1_ENABLED
bool "Enable SECP192R1 curve"
depends on MBEDTLS_ECP_C
default y
default y if !(MBEDTLS_ATCA_HARDWARE_ECDH || MBEDTLS_ATCA_HARDWARE_ECDSA_SIGN || MBEDTLS_ATCA_HARDWARE_ECDSA_VERIFY)
help
Enable support for SECP192R1 Elliptic Curve.
config MBEDTLS_ECP_DP_SECP224R1_ENABLED
bool "Enable SECP224R1 curve"
depends on MBEDTLS_ECP_C
default y
default y if !(MBEDTLS_ATCA_HARDWARE_ECDH || MBEDTLS_ATCA_HARDWARE_ECDSA_SIGN || MBEDTLS_ATCA_HARDWARE_ECDSA_VERIFY)
help
Enable support for SECP224R1 Elliptic Curve.
@ -671,63 +692,63 @@ menu "mbedTLS"
config MBEDTLS_ECP_DP_SECP384R1_ENABLED
bool "Enable SECP384R1 curve"
depends on MBEDTLS_ECP_C
default y
default y if !(MBEDTLS_ATCA_HARDWARE_ECDH || MBEDTLS_ATCA_HARDWARE_ECDSA_SIGN || MBEDTLS_ATCA_HARDWARE_ECDSA_VERIFY)
help
Enable support for SECP384R1 Elliptic Curve.
config MBEDTLS_ECP_DP_SECP521R1_ENABLED
bool "Enable SECP521R1 curve"
depends on MBEDTLS_ECP_C
default y
default y if !(MBEDTLS_ATCA_HARDWARE_ECDH || MBEDTLS_ATCA_HARDWARE_ECDSA_SIGN || MBEDTLS_ATCA_HARDWARE_ECDSA_VERIFY)
help
Enable support for SECP521R1 Elliptic Curve.
config MBEDTLS_ECP_DP_SECP192K1_ENABLED
bool "Enable SECP192K1 curve"
depends on MBEDTLS_ECP_C
default y
default y if !(MBEDTLS_ATCA_HARDWARE_ECDH || MBEDTLS_ATCA_HARDWARE_ECDSA_SIGN || MBEDTLS_ATCA_HARDWARE_ECDSA_VERIFY)
help
Enable support for SECP192K1 Elliptic Curve.
config MBEDTLS_ECP_DP_SECP224K1_ENABLED
bool "Enable SECP224K1 curve"
depends on MBEDTLS_ECP_C
default y
default y if !(MBEDTLS_ATCA_HARDWARE_ECDH || MBEDTLS_ATCA_HARDWARE_ECDSA_SIGN || MBEDTLS_ATCA_HARDWARE_ECDSA_VERIFY)
help
Enable support for SECP224K1 Elliptic Curve.
config MBEDTLS_ECP_DP_SECP256K1_ENABLED
bool "Enable SECP256K1 curve"
depends on MBEDTLS_ECP_C
default y
default y if !(MBEDTLS_ATCA_HARDWARE_ECDH || MBEDTLS_ATCA_HARDWARE_ECDSA_SIGN || MBEDTLS_ATCA_HARDWARE_ECDSA_VERIFY)
help
Enable support for SECP256K1 Elliptic Curve.
config MBEDTLS_ECP_DP_BP256R1_ENABLED
bool "Enable BP256R1 curve"
depends on MBEDTLS_ECP_C
default y
default y if !(MBEDTLS_ATCA_HARDWARE_ECDH || MBEDTLS_ATCA_HARDWARE_ECDSA_SIGN || MBEDTLS_ATCA_HARDWARE_ECDSA_VERIFY)
help
support for DP Elliptic Curve.
config MBEDTLS_ECP_DP_BP384R1_ENABLED
bool "Enable BP384R1 curve"
depends on MBEDTLS_ECP_C
default y
default y if !(MBEDTLS_ATCA_HARDWARE_ECDH || MBEDTLS_ATCA_HARDWARE_ECDSA_SIGN || MBEDTLS_ATCA_HARDWARE_ECDSA_VERIFY)
help
support for DP Elliptic Curve.
config MBEDTLS_ECP_DP_BP512R1_ENABLED
bool "Enable BP512R1 curve"
depends on MBEDTLS_ECP_C
default y
default y if !(MBEDTLS_ATCA_HARDWARE_ECDH || MBEDTLS_ATCA_HARDWARE_ECDSA_SIGN || MBEDTLS_ATCA_HARDWARE_ECDSA_VERIFY)
help
support for DP Elliptic Curve.
config MBEDTLS_ECP_DP_CURVE25519_ENABLED
bool "Enable CURVE25519 curve"
depends on MBEDTLS_ECP_C
default y
default y if !(MBEDTLS_ATCA_HARDWARE_ECDH || MBEDTLS_ATCA_HARDWARE_ECDSA_SIGN || MBEDTLS_ATCA_HARDWARE_ECDSA_VERIFY)
help
Enable support for CURVE25519 Elliptic Curve.

Wyświetl plik

@ -149,6 +149,19 @@
#undef MBEDTLS_MPI_MUL_MPI_ALT
#endif
#ifdef CONFIG_MBEDTLS_ATCA_HARDWARE_ECDH
#define MBEDTLS_ECDH_GEN_PUBLIC_ALT
#define MBEDTLS_ECDH_COMPUTE_SHARED_ALT
#endif
#ifdef CONFIG_MBEDTLS_ATCA_HARDWARE_ECDSA_SIGN
#define MBEDTLS_ECDSA_SIGN_ALT
#endif
#ifdef CONFIG_MBEDTLS_ATCA_HARDWARE_ECDSA_VERIFY
#define MBEDTLS_ECDSA_VERIFY_ALT
#endif
/**
* \def MBEDTLS_ENTROPY_HARDWARE_ALT
*

Wyświetl plik

@ -0,0 +1,6 @@
# The following lines of boilerplate have to be in your project's CMakeLists
# in this exact order for cmake to work correctly
cmake_minimum_required(VERSION 3.5)
include($ENV{IDF_PATH}/tools/cmake/project.cmake)
project(atecc608a_ecdsa)

Wyświetl plik

@ -0,0 +1,9 @@
#
# This is a project Makefile. It is assumed the directory this Makefile resides in is a
# project subdirectory.
#
PROJECT_NAME := atecc608a_ecdsa
include $(IDF_PATH)/make/project.mk

Wyświetl plik

@ -0,0 +1,5 @@
#
# "main" pseudo-component makefile.
#
# (Uses default behaviour of compiling all source files in directory, adding 'include' to include path.)

Wyświetl plik

@ -0,0 +1,233 @@
/* Hello World Example
This example code is in the Public Domain (or CC0 licensed, at your option.)
Unless required by applicable law or agreed to in writing, this
software is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
CONDITIONS OF ANY KIND, either express or implied.
*/
/* This is mbedtls boilerplate for library configuration */
#if !defined(MBEDTLS_CONFIG_FILE)
#include "mbedtls/config.h"
#else
#include MBEDTLS_CONFIG_FILE
#endif
/* System Includes*/
#include <stdio.h>
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "esp_system.h"
#include "esp_spi_flash.h"
/* Cryptoauthlib includes */
#include "cryptoauthlib.h"
#include "mbedtls/atca_mbedtls_wrap.h"
/* mbedTLS includes */
#include "mbedtls/platform.h"
#include "mbedtls/debug.h"
#include "mbedtls/ssl.h"
#include "mbedtls/entropy.h"
#include "mbedtls/ctr_drbg.h"
#include "mbedtls/pk.h"
/* globals for mbedtls RNG */
static mbedtls_entropy_context entropy;
static mbedtls_ctr_drbg_context ctr_drbg;
static int configure_mbedtls_rng(void)
{
int ret;
const char * seed = "some random seed string";
mbedtls_ctr_drbg_init(&ctr_drbg);
printf("\n . Seeding the random number generator...");
mbedtls_entropy_init(&entropy);
if ((ret = mbedtls_ctr_drbg_seed(&ctr_drbg, mbedtls_entropy_func, &entropy,
(const unsigned char *)seed, strlen(seed))) != 0)
{
printf(" failed\n ! mbedtls_ctr_drbg_seed returned %d\n", ret);
}
else
{
printf(" ok\n");
}
return ret;
}
static void close_mbedtls_rng(void)
{
mbedtls_ctr_drbg_free(&ctr_drbg);
mbedtls_entropy_free(&entropy);
}
/* An example hash */
static unsigned char hash[32] = {
0xba, 0x78, 0x16, 0xbf, 0x8f, 0x01, 0xcf, 0xea, 0x41, 0x41, 0x40, 0xde, 0x5d, 0xae, 0x22, 0x23,
0xb0, 0x03, 0x61, 0xa3, 0x96, 0x17, 0x7a, 0x9c, 0xb4, 0x10, 0xff, 0x61, 0xf2, 0x00, 0x15, 0xad
};
static const uint8_t public_key_x509_header[] = {
0x30, 0x59, 0x30, 0x13, 0x06, 0x07, 0x2A, 0x86, 0x48, 0xCE, 0x3D, 0x02, 0x01, 0x06, 0x08, 0x2A,
0x86, 0x48, 0xCE, 0x3D, 0x03, 0x01, 0x07, 0x03, 0x42, 0x00, 0x04
};
static void print_public_key(uint8_t pubkey[ATCA_PUB_KEY_SIZE])
{
uint8_t buf[128];
uint8_t * tmp;
size_t buf_len = sizeof(buf);
/* Calculate where the raw data will fit into the buffer */
tmp = buf + sizeof(buf) - ATCA_PUB_KEY_SIZE - sizeof(public_key_x509_header);
/* Copy the header */
memcpy(tmp, public_key_x509_header, sizeof(public_key_x509_header));
/* Copy the key bytes */
memcpy(tmp + sizeof(public_key_x509_header), pubkey, ATCA_PUB_KEY_SIZE);
/* Convert to base 64 */
(void)atcab_base64encode(tmp, ATCA_PUB_KEY_SIZE + sizeof(public_key_x509_header), (char*)buf, &buf_len);
/* Add a null terminator */
buf[buf_len] = 0;
/* Print out the key */
printf("-----BEGIN PUBLIC KEY-----\r\n%s\r\n-----END PUBLIC KEY-----\r\n", buf);
}
extern int atca_connect(const char * endpoint, const char * port);
extern int atca_provision(void);
static int atca_ecdsa_test(void)
{
mbedtls_pk_context pkey;
int ret;
unsigned char buf[MBEDTLS_MPI_MAX_SIZE];
size_t olen = 0;
/* ECDSA Sign/Verify */
#ifdef MBEDTLS_ECDSA_SIGN_ALT
/* Convert to an mbedtls key */
printf( "\n . Using a hardware private key ..." );
if (0 != (ret = atca_mbedtls_pk_init(&pkey, 0)))
{
printf(" failed\n ! atca_mbedtls_pk_init returned %02x\n", ret);
goto exit;
}
printf(" ok\n");
#else
printf( "\n . Generating a software private key ..." );
mbedtls_pk_init(&pkey);
if( ( ret = mbedtls_pk_setup( &pkey,
mbedtls_pk_info_from_type( MBEDTLS_PK_ECDSA ) ) ) != 0 )
{
printf( " failed\n ! mbedtls_pk_setup returned -0x%04x", -ret );
goto exit;
}
ret = mbedtls_ecp_gen_key( MBEDTLS_ECP_DP_SECP256R1,
mbedtls_pk_ec( pkey ),
mbedtls_ctr_drbg_random, &ctr_drbg );
if( ret != 0 )
{
printf( " failed\n ! mbedtls_ecp_gen_key returned -0x%04x", -ret );
goto exit;
}
printf(" ok\n");
#endif
printf(" . Generating ECDSA Signature...");
if ((ret = mbedtls_pk_sign(&pkey, MBEDTLS_MD_SHA256, hash, 0, buf, &olen,
mbedtls_ctr_drbg_random, &ctr_drbg)) != 0)
{
printf(" failed\n ! mbedtls_pk_sign returned -0x%04x\n", -ret);
goto exit;
}
printf(" ok\n");
printf(" . Verifying ECDSA Signature...");
if ((ret = mbedtls_pk_verify(&pkey, MBEDTLS_MD_SHA256, hash, 0,
buf, olen)) != 0)
{
printf(" failed\n ! mbedtls_pk_verify returned -0x%04x\n", -ret);
goto exit;
}
printf(" ok\n");
exit:
fflush(stdout);
return ret;
}
void app_main(void)
{
int ret = 0;
bool lock;
uint8_t buf[ATCA_ECC_CONFIG_SIZE];
uint8_t pubkey[ATCA_PUB_KEY_SIZE];
/* Initialize the mbedtls library */
if (!ret)
{
ret = configure_mbedtls_rng();
}
printf(" . Initialize the ATECC interface...");
if(0 != (ret = atcab_init(&cfg_ateccx08a_i2c_default)))
{
printf(" failed\n ! atcab_init returned %02x\n", ret);
goto exit;
}
printf(" ok\n");
lock = 0;
printf(" . Check the data zone lock status...");
if (0 != (ret = atcab_is_locked(LOCK_ZONE_DATA, &lock)))
{
printf(" failed\n ! atcab_is_locked returned %02x\n", ret);
goto exit;
}
printf(" ok: %s\n", lock ? "locked" : "unlocked");
printf(" . Get the device info (type)...");
if (0 != (ret = atcab_info(buf)))
{
printf(" failed\n ! atcab_info returned %02x\n", ret);
goto exit;
}
printf(" ok: %02x %02x\n", buf[2], buf[3]);
/* If the data zone is not locked (i.e. the configuration is not activated
then if these were run they would simply return execution errors */
if (!ret && lock)
{
printf(" . Get the public key...");
if (0 != (ret = atcab_get_pubkey(0, pubkey)))
{
printf(" failed\n ! atcab_get_pubkey returned %02x\n", ret);
goto exit;
}
printf(" ok\n\n");
print_public_key(pubkey);
if(!ret)
{
/* Perform a Sign/Verify Test */
ret = atca_ecdsa_test();
}
}
exit:
fflush(stdout);
close_mbedtls_rng();
}

Wyświetl plik

@ -0,0 +1,4 @@
# Enable Cryptoauthlib hardware acceleration of mbedtls
CONFIG_ATCA_MBEDTLS_ECDSA=y
CONFIG_ATCA_MBEDTLS_ECDSA_SIGN=y
CONFIG_ATCA_MBEDTLS_ECDSA_VERIFY=y