1
0
mirror of https://github.com/RIOT-OS/RIOT.git synced 2024-12-29 04:50:03 +01:00
RIOT/sys/include/fido2/ctap/ctap_crypto.h
2021-09-08 15:22:40 +02:00

302 lines
9.5 KiB
C

/*
* Copyright (C) 2021 Freie Universität Berlin
*
* This file is subject to the terms and conditions of the GNU Lesser
* General Public License v2.1. See the file LICENSE in the top level
* directory for more details.
*/
/**
* @defgroup fido2_ctap_crypto FIDO2 CTAP crypto
* @ingroup fido2_ctap
* @brief FIDO2 CTAP crypto helper
*
* @{
*
* @file
* @brief FIDO2 CTAP crypto helper defines, structures and function
* declarations.
*
* @author Nils Ollrogge <nils.ollrogge@fu-berlin.de>
*/
#ifndef FIDO2_CTAP_CTAP_CRYPTO_H
#define FIDO2_CTAP_CTAP_CRYPTO_H
#include <stdint.h>
#include "hashes/sha256.h"
#ifdef __cplusplus
extern "C" {
#endif
/**
* @brief Size in bytes of cryptographic keys used
*/
#define CTAP_CRYPTO_KEY_SIZE 32
/**
* @brief Max size of ES256 signature in ASN.1 DER format
*/
#define CTAP_CRYPTO_ES256_DER_MAX_SIZE 72
/**
* @brief Elliptic curve public key
*/
typedef struct {
uint8_t x[CTAP_CRYPTO_KEY_SIZE]; /**< x coordinate of curve point */
uint8_t y[CTAP_CRYPTO_KEY_SIZE]; /**< y coordinate of curve point */
} ctap_crypto_pub_key_t;
/**
* @brief Key agreement key
*
* CTAP specification (version 20190130) section 5.5.4
*/
typedef struct {
ctap_crypto_pub_key_t pub; /**< public key */
uint8_t priv[CTAP_CRYPTO_KEY_SIZE]; /**< private key */
} ctap_crypto_key_agreement_key_t;
/**
* @brief Initialize crypto helper
*
* Initializes crypto libs and creates key_agreement key pair
*
* @return @ref ctap_status_codes_t
*/
int fido2_ctap_crypto_init(void);
/**
* @brief Wrapper function for @ref random_bytes
*
* @param[in] buf buffer to hold random bytes
* @param[in] len length of @p buf
*
* @return @ref ctap_status_codes_t
*/
int fido2_ctap_crypto_prng(uint8_t *buf, size_t len);
/**
* @brief Wrapper function for @ref sha256_init
*
* @param ctx sha256_context_t handle to init
*
* @return @ref ctap_status_codes_t
*/
int fido2_ctap_crypto_sha256_init(sha256_context_t *ctx);
/**
* @brief Wrapper function for @ref sha256_update
*
* @param ctx sha256_context_t handle to use
* @param[in] data Input data
* @param[in] len Length of @p data
*
* @return @ref ctap_status_codes_t
*/
int fido2_ctap_crypto_sha256_update(sha256_context_t *ctx, const void *data, size_t len);
/**
* @brief Wrapper for @ref sha256_final
*
* @param ctx sha256_context_t handle to use
* @param digest resulting digest, this is the hash of all the bytes
*
* @return @ref ctap_status_codes_t
*/
int fido2_ctap_crypto_sha256_final(sha256_context_t *ctx, void *digest);
/**
* @brief Wrapper function for @ref sha256
*
* @param[in] data pointer to the buffer to generate hash from
* @param[in] len length of @p data
* @param[out] digest optional pointer to an array for the result, length must
* be SHA256_DIGEST_LENGTH
*
* @note discards the pointer returned by @ref sha256
*
* @return @ref ctap_status_codes_t
*/
int fido2_ctap_crypto_sha256(const void *data, size_t len,
void *digest);
/**
* @brief Wrapper function for @ref hmac_sha256_init
*
* @param[in] ctx hmac_context_t handle to use
* @param[in] key key used in the hmac-sha256 computation
* @param[in] key_length length of @p key
*
* @return @ref ctap_status_codes_t
*/
int fido2_ctap_crypto_hmac_sha256_init(hmac_context_t *ctx, const void *key,
size_t key_length);
/**
* @brief Wrapper function for @ref hmac_sha256_update
*
* @param[in] ctx hmac_context_t handle to use
* @param[in] data pointer to the buffer to generate hash from
* @param[in] len length of @p data
*
* @return @ref ctap_status_codes_t
*/
int fido2_ctap_crypto_hmac_sha256_update(hmac_context_t *ctx, const void *data, size_t len);
/**
* @brief Wrapper function for @ref hmac_sha256_final
*
* @param[in] ctx hmac_context_t handle to use
* @param[out] digest the computed hmac-sha256,
* length MUST be SHA256_DIGEST_LENGTH
*
* @return @ref ctap_status_codes_t
*/
int fido2_ctap_crypto_hmac_sha256_final(hmac_context_t *ctx, void *digest);
/**
* @brief Wrapper function for @ref hmac_sha256
*
* @param[in] key key used in the hmac-sha256 computation
* @param[in] key_length length of @p key
* @param[in] data pointer to the buffer to generate the hmac-sha256
* @param[in] len length of @p data
* @param[out] digest the computed hmac-sha256,
* length MUST be SHA256_DIGEST_LENGTH
*
* @note discards the pointer returned by @ref hmac_sha256
*
* @return @ref ctap_status_codes_t
*/
int fido2_ctap_crypto_hmac_sha256(const void *key,
size_t key_length, const void *data, size_t len,
void *digest);
/**
* @brief Generate cryptographic key pair
*
* @param[in] pub_key public key buffer
* @param[in] priv_key private key buffer
* @param[in] len length of @p priv_key
*
* @return @ref ctap_status_codes_t
*/
int fido2_ctap_crypto_gen_keypair(ctap_crypto_pub_key_t *pub_key, uint8_t *priv_key, size_t len);
/**
* @brief Elliptic-curve Diffie-Hellmann
*
* @param[in] out shared secret buffer
* @param[in] len length of @p out
* @param[in] pub_key public key of other party
* @param[in] priv_key private key
* @param[in] key_len length of @p priv_key
*
* @return @ref ctap_status_codes_t
*/
int fido2_ctap_crypto_ecdh(uint8_t *out, size_t len,
ctap_crypto_pub_key_t *pub_key, uint8_t *priv_key, size_t key_len);
/**
* @brief Create cryptographic signature
*
* @param[in] hash Hash to be signed
* @param[in] hash_len length of @p hash
* @param[in] sig signature buffer
* @param[in] sig_len length of @p sig
* @param[in] key private key to use for signature
* @param[in] key_len length of @p key
*
* @return @ref ctap_status_codes_t
*/
int fido2_ctap_crypto_get_sig(uint8_t *hash, size_t hash_len, uint8_t *sig,
size_t *sig_len, const uint8_t *key, size_t key_len);
/**
* @brief Encrypt data using AES-256-CBC
*
* @param[in] out encrypted data
* @param[in] out_len length of @p out
* @param[in] in data to be encrypted
* @param[in] in_len length of @p in
* @param[in] key symmetric key to use for encryption
* @param[in] key_len length of @p key
*
* @return @ref ctap_status_codes_t
*/
int fido2_ctap_crypto_aes_enc(uint8_t *out, size_t *out_len, uint8_t * in,
size_t in_len, const uint8_t * key, size_t key_len);
/**
* @brief Decrypt data using AES-256-CBC
*
* @param[in] out decrypted data
* @param[in] out_len length of @p out
* @param[in] in encrypted data
* @param[in] in_len len of @p in
* @param[in] key symmetric key to use for decryption
* @param[in] key_len length of @p key
*
* @return @ref ctap_status_codes_t
*/
int fido2_ctap_crypto_aes_dec(uint8_t *out, size_t *out_len, uint8_t * in,
size_t in_len, const uint8_t * key, size_t key_len);
/**
* @brief Encrypt data using AES-128-CCM
*
* @param[in] out encrypted data
* @param[in] out_len length of @p out
* @param[in] in data to be encrypted
* @param[in] in_len length of @p in
* @param[in] auth_data additional data to authenticate in MAC
* @param[in] auth_data_len length of @p auth_data
* @param[in] mac_len length of appended MAC
* @param[in] length_encoding max supported length of plaintext
* @param[in] nonce nonce for ctr mode encryption
* @param[in] nonce_len length of @p nonce
* @param[in] key symmetric key to use for encryption
* @param[in] key_len length of @p key
*
* @return @ref ctap_status_codes_t
*/
int fido2_ctap_crypto_aes_ccm_enc(uint8_t *out, size_t out_len,
const uint8_t *in, size_t in_len,
uint8_t *auth_data, size_t auth_data_len,
uint8_t mac_len, uint8_t length_encoding,
const uint8_t *nonce, size_t nonce_len,
const uint8_t *key, size_t key_len);
/**
* @brief Encrypt data using AES-128-CCM
*
* @param[in] out encrypted data
* @param[in] out_len length of @p out
* @param[in] in data to be encrypted
* @param[in] in_len length of @p in
* @param[in] auth_data additional data to authenticate in MAC
* @param[in] auth_data_len length of @p auth_data
* @param[in] mac_len length of appended MAC
* @param[in] length_encoding max supported length of plaintext
* @param[in] nonce nonce for ctr mode encryption
* @param[in] nonce_len length of @p nonce
* @param[in] key symmetric key to use for encryption
* @param[in] key_len length of @p key
*
* @return @ref ctap_status_codes_t
*/
int fido2_ctap_crypto_aes_ccm_dec(uint8_t *out, size_t out_len,
const uint8_t *in, size_t in_len,
uint8_t *auth_data, size_t auth_data_len,
uint8_t mac_len, uint8_t length_encoding,
const uint8_t *nonce, size_t nonce_len,
const uint8_t *key, size_t key_len);
#ifdef __cplusplus
}
#endif
#endif /* FIDO2_CTAP_CTAP_CRYPTO_H */
/** @} */