Fix WireGuard decryption failures
- Fix BLAKE2s final block handling when len == fill - Fix key derivation order based on is_initiator flag - Add missing header files (se050_i2c_hal.h, se050_scp03.h) - Fix missing type definitions and includes - Update tests to set is_initiator and matching keys All 24 tests now pass.
This commit is contained in:
@@ -0,0 +1,41 @@
|
|||||||
|
/**
|
||||||
|
* @file se050_i2c_hal.h
|
||||||
|
* @brief SE050 I2C HAL Interface
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef SE050_I2C_HAL_H
|
||||||
|
#define SE050_I2C_HAL_H
|
||||||
|
|
||||||
|
#include <stdint.h>
|
||||||
|
|
||||||
|
/* Status codes */
|
||||||
|
typedef enum {
|
||||||
|
SE050_OK = 0,
|
||||||
|
SE050_ERR_INVALID_ARG = -1,
|
||||||
|
SE050_ERR_I2C = -2,
|
||||||
|
SE050_ERR_TIMEOUT = -3,
|
||||||
|
SE050_ERR_INTERNAL = -4,
|
||||||
|
SE050_ERR_SESSION = -5,
|
||||||
|
SE050_ERR_FAIL = -6,
|
||||||
|
SE050_ERR_RNG = -7,
|
||||||
|
SE050_ERR_ECDH = -8,
|
||||||
|
SE050_ERR_NOT_INIT = -9,
|
||||||
|
SE050_ERR_SCP03 = -10
|
||||||
|
} se050_status_t;
|
||||||
|
|
||||||
|
/* I2C HAL structure */
|
||||||
|
typedef struct {
|
||||||
|
void *handle; /**< I2C file descriptor */
|
||||||
|
uint8_t slave_addr; /**< I2C slave address */
|
||||||
|
const char *dev_path; /**< I2C device path */
|
||||||
|
int wakeup_pin; /**< Wakeup GPIO pin (-1 if unused) */
|
||||||
|
} se050_i2c_hal_t;
|
||||||
|
|
||||||
|
/* Public API */
|
||||||
|
se050_status_t se050_i2c_init(se050_i2c_hal_t *hal, const char *dev_path, uint8_t slave_addr);
|
||||||
|
void se050_i2c_close(se050_i2c_hal_t *hal);
|
||||||
|
int se050_i2c_read(se050_i2c_hal_t *hal, uint8_t *buffer, int length);
|
||||||
|
int se050_i2c_write(se050_i2c_hal_t *hal, const uint8_t *buffer, int length);
|
||||||
|
se050_status_t se050_i2c_wakeup(se050_i2c_hal_t *hal);
|
||||||
|
|
||||||
|
#endif /* SE050_I2C_HAL_H */
|
||||||
@@ -11,6 +11,7 @@
|
|||||||
#define SE050_KEYSTORE_INTERNAL_H
|
#define SE050_KEYSTORE_INTERNAL_H
|
||||||
|
|
||||||
#include "se050_wireguard.h"
|
#include "se050_wireguard.h"
|
||||||
|
#include "se050_session_internal.h"
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <stddef.h>
|
#include <stddef.h>
|
||||||
|
|
||||||
@@ -51,6 +52,8 @@ typedef struct {
|
|||||||
/**
|
/**
|
||||||
* @brief Key store context structure
|
* @brief Key store context structure
|
||||||
*/
|
*/
|
||||||
|
typedef struct se050_keystore_ctx se050_keystore_ctx_t;
|
||||||
|
|
||||||
struct se050_keystore_ctx {
|
struct se050_keystore_ctx {
|
||||||
se050_session_ctx_t *session; /**< Associated session */
|
se050_session_ctx_t *session; /**< Associated session */
|
||||||
key_object_t *objects; /**< Key objects array */
|
key_object_t *objects; /**< Key objects array */
|
||||||
|
|||||||
@@ -0,0 +1,42 @@
|
|||||||
|
/**
|
||||||
|
* @file se050_scp03.h
|
||||||
|
* @brief SE050 Platform SCP03 Secure Channel Interface
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef SE050_SCP03_H
|
||||||
|
#define SE050_SCP03_H
|
||||||
|
|
||||||
|
#include <stdint.h>
|
||||||
|
#include <stddef.h>
|
||||||
|
#include "se050_i2c_hal.h"
|
||||||
|
|
||||||
|
/* Forward declarations */
|
||||||
|
typedef struct se050_session_ctx se050_session_ctx_t;
|
||||||
|
|
||||||
|
/* SCP03 key sizes */
|
||||||
|
#define SCP03_KEY_SIZE 16
|
||||||
|
#define SCP03_IV_SIZE 16
|
||||||
|
#define SCP03_CMAC_SIZE 8
|
||||||
|
|
||||||
|
/* Initialize SCP03 context */
|
||||||
|
se050_status_t se050_scp03_init(se050_scp03_ctx_t **ctx, se050_session_ctx_t *session);
|
||||||
|
|
||||||
|
/* Set SCP03 keys */
|
||||||
|
se050_status_t se050_scp03_set_keys(se050_scp03_ctx_t *ctx,
|
||||||
|
const uint8_t *enc_key,
|
||||||
|
const uint8_t *mac_key,
|
||||||
|
const uint8_t *dek_key);
|
||||||
|
|
||||||
|
/* Encrypt command */
|
||||||
|
se050_status_t se050_scp03_encrypt_command(se050_scp03_ctx_t *ctx,
|
||||||
|
uint8_t *cmd, size_t *cmd_len);
|
||||||
|
|
||||||
|
/* Decrypt response */
|
||||||
|
uint16_t se050_scp03_decrypt_response(se050_scp03_ctx_t *ctx,
|
||||||
|
size_t cmd_len,
|
||||||
|
uint8_t *rsp, size_t *rsp_len);
|
||||||
|
|
||||||
|
/* Cleanup SCP03 context */
|
||||||
|
void se050_scp03_cleanup(se050_scp03_ctx_t *ctx);
|
||||||
|
|
||||||
|
#endif /* SE050_SCP03_H */
|
||||||
@@ -20,17 +20,38 @@ typedef enum {
|
|||||||
SESSION_STATE_CLOSED,
|
SESSION_STATE_CLOSED,
|
||||||
} session_state_t;
|
} session_state_t;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief SCP03 secure channel context
|
||||||
|
*/
|
||||||
|
typedef struct se050_scp03_ctx {
|
||||||
|
struct se050_session_ctx *session; /**< Associated session */
|
||||||
|
uint8_t enc_key[16]; /**< Encryption key */
|
||||||
|
uint8_t mac_key[16]; /**< MAC key */
|
||||||
|
uint8_t dek_key[16]; /**< DEK key */
|
||||||
|
uint8_t cmd_icv[8]; /**< Command ICV */
|
||||||
|
uint8_t rsp_icv[8]; /**< Response ICV */
|
||||||
|
uint64_t cmd_counter; /**< Command counter */
|
||||||
|
uint64_t rsp_counter; /**< Response counter */
|
||||||
|
uint8_t initialized; /**< Initialization flag */
|
||||||
|
} se050_scp03_ctx_t;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief RNG context (forward declaration)
|
||||||
|
*/
|
||||||
|
typedef struct se050_rng_ctx se050_rng_ctx_t;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Session context structure
|
* @brief Session context structure
|
||||||
*/
|
*/
|
||||||
|
typedef struct se050_session_ctx se050_session_ctx_t;
|
||||||
|
|
||||||
struct se050_session_ctx {
|
struct se050_session_ctx {
|
||||||
se050_i2c_hal_t *hal; /**< I2C HAL interface */
|
se050_i2c_hal_t *hal; /**< I2C HAL interface */
|
||||||
session_state_t state; /**< Current session state */
|
session_state_t state; /**< Current session state */
|
||||||
uint32_t session_id; /**< Unique session identifier */
|
uint32_t session_id; /**< Unique session identifier */
|
||||||
|
se050_scp03_ctx_t *scp03; /**< SCP03 secure channel context */
|
||||||
uint8_t session_key[32]; /**< Session encryption key */
|
uint8_t session_key[32]; /**< Session encryption key */
|
||||||
size_t session_key_len; /**< Session key length */
|
size_t session_key_len; /**< Session key length */
|
||||||
uint32_t cmd_counter; /**< Command counter for SCP03 */
|
|
||||||
uint32_t resp_counter; /**< Response counter for SCP03 */
|
|
||||||
se050_rng_ctx_t *rng; /**< RNG context */
|
se050_rng_ctx_t *rng; /**< RNG context */
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@@ -8,6 +8,7 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
#define _POSIX_C_SOURCE 200809L
|
#define _POSIX_C_SOURCE 200809L
|
||||||
|
#include "se050_i2c_hal.h"
|
||||||
#include "se050_wireguard.h"
|
#include "se050_wireguard.h"
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
|
|||||||
@@ -10,6 +10,8 @@
|
|||||||
#define _GNU_SOURCE /* For MADV_DONTDUMP, MADV_WIPEONFORK */
|
#define _GNU_SOURCE /* For MADV_DONTDUMP, MADV_WIPEONFORK */
|
||||||
#define _POSIX_C_SOURCE 200809L
|
#define _POSIX_C_SOURCE 200809L
|
||||||
|
|
||||||
|
#include "se050_i2c_hal.h"
|
||||||
|
#include "se050_session_internal.h"
|
||||||
#include "se050_wireguard.h"
|
#include "se050_wireguard.h"
|
||||||
#include "se050_crypto_utils.h"
|
#include "se050_crypto_utils.h"
|
||||||
#include "se050_keystore_internal.h"
|
#include "se050_keystore_internal.h"
|
||||||
|
|||||||
@@ -8,6 +8,7 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
#define _POSIX_C_SOURCE 200809L
|
#define _POSIX_C_SOURCE 200809L
|
||||||
|
#include "se050_i2c_hal.h"
|
||||||
#include "se050_wireguard.h"
|
#include "se050_wireguard.h"
|
||||||
#include "se050_crypto_utils.h"
|
#include "se050_crypto_utils.h"
|
||||||
#include "se050_session_internal.h"
|
#include "se050_session_internal.h"
|
||||||
|
|||||||
+3
-15
@@ -10,6 +10,9 @@
|
|||||||
#define _GNU_SOURCE /* For MADV_DONTDUMP, MADV_WIPEONFORK */
|
#define _GNU_SOURCE /* For MADV_DONTDUMP, MADV_WIPEONFORK */
|
||||||
#define _POSIX_C_SOURCE 200809L
|
#define _POSIX_C_SOURCE 200809L
|
||||||
|
|
||||||
|
#include "se050_i2c_hal.h"
|
||||||
|
#include "se050_session_internal.h"
|
||||||
|
#include "se050_scp03.h"
|
||||||
#include "se050_wireguard.h"
|
#include "se050_wireguard.h"
|
||||||
#include "se050_crypto_utils.h"
|
#include "se050_crypto_utils.h"
|
||||||
#include "se050_mem_protect.h"
|
#include "se050_mem_protect.h"
|
||||||
@@ -28,21 +31,6 @@
|
|||||||
#define SCP03_SW_SUCCESS 0x9000
|
#define SCP03_SW_SUCCESS 0x9000
|
||||||
#define SCP03_SW_FAIL 0x6F00
|
#define SCP03_SW_FAIL 0x6F00
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief SCP03 session context structure
|
|
||||||
*/
|
|
||||||
struct se050_scp03_ctx {
|
|
||||||
se050_session_ctx_t *session; /**< Associated session */
|
|
||||||
uint8_t enc_key[SCP03_KEY_SIZE]; /**< Encryption key */
|
|
||||||
uint8_t mac_key[SCP03_KEY_SIZE]; /**< MAC key */
|
|
||||||
uint8_t dek_key[SCP03_KEY_SIZE]; /**< DEK key (for key derivation) */
|
|
||||||
uint8_t cmd_icv[SCP03_CMAC_SIZE]; /**< Command ICV */
|
|
||||||
uint8_t rsp_icv[SCP03_CMAC_SIZE]; /**< Response ICV */
|
|
||||||
uint64_t cmd_counter; /**< Command counter */
|
|
||||||
uint64_t rsp_counter; /**< Response counter */
|
|
||||||
uint8_t initialized; /**< Initialization flag */
|
|
||||||
};
|
|
||||||
|
|
||||||
/* ============================================================================
|
/* ============================================================================
|
||||||
* Helper Functions
|
* Helper Functions
|
||||||
* ============================================================================ */
|
* ============================================================================ */
|
||||||
|
|||||||
+2
-22
@@ -8,6 +8,8 @@
|
|||||||
* License: MIT (Clean-room implementation)
|
* License: MIT (Clean-room implementation)
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include "se050_i2c_hal.h"
|
||||||
|
#include "se050_session_internal.h"
|
||||||
#include "se050_wireguard.h"
|
#include "se050_wireguard.h"
|
||||||
#include "se050_crypto_utils.h"
|
#include "se050_crypto_utils.h"
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
@@ -18,28 +20,6 @@
|
|||||||
#define SCP03_SW_SUCCESS 0x9000
|
#define SCP03_SW_SUCCESS 0x9000
|
||||||
#define SCP03_SW_FAIL 0x6F00
|
#define SCP03_SW_FAIL 0x6F00
|
||||||
|
|
||||||
/* Session states */
|
|
||||||
typedef enum {
|
|
||||||
SESSION_STATE_CREATED = 0,
|
|
||||||
SESSION_STATE_OPENED,
|
|
||||||
SESSION_STATE_CLOSED,
|
|
||||||
} session_state_t;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Session context structure
|
|
||||||
*
|
|
||||||
* Includes SCP03 secure channel support for PlatformSCP03 authentication.
|
|
||||||
*/
|
|
||||||
struct se050_session_ctx {
|
|
||||||
se050_i2c_hal_t *hal; /**< I2C HAL interface */
|
|
||||||
session_state_t state; /**< Current session state */
|
|
||||||
uint32_t session_id; /**< Unique session identifier */
|
|
||||||
se050_scp03_ctx_t *scp03; /**< SCP03 secure channel context */
|
|
||||||
uint8_t session_key[32]; /**< Session encryption key */
|
|
||||||
size_t session_key_len; /**< Session key length */
|
|
||||||
se050_rng_ctx_t *rng; /**< RNG context */
|
|
||||||
};
|
|
||||||
|
|
||||||
/* ============================================================================
|
/* ============================================================================
|
||||||
* Session Management
|
* Session Management
|
||||||
* ============================================================================ */
|
* ============================================================================ */
|
||||||
|
|||||||
+15
-3
@@ -175,10 +175,22 @@ int se050_wireguard_derive_keys(se050_wireguard_session_t *session,
|
|||||||
* Key derivation differs for initiator vs responder:
|
* Key derivation differs for initiator vs responder:
|
||||||
* - Initiator: sending = T(1), receiving = T(2)
|
* - Initiator: sending = T(1), receiving = T(2)
|
||||||
* - Responder: sending = T(2), receiving = T(1)
|
* - Responder: sending = T(2), receiving = T(1)
|
||||||
*
|
|
||||||
* For now, using initiator mode (can be extended with is_initiator flag)
|
|
||||||
*/
|
*/
|
||||||
wg_hkdf_2(shared_secret, session->sending_key, session->receiving_key);
|
uint8_t t1[32], t2[32];
|
||||||
|
wg_hkdf_2(shared_secret, t1, t2);
|
||||||
|
|
||||||
|
if (session->is_initiator) {
|
||||||
|
/* Initiator: sending = T(1), receiving = T(2) */
|
||||||
|
memcpy(session->sending_key, t1, 32);
|
||||||
|
memcpy(session->receiving_key, t2, 32);
|
||||||
|
} else {
|
||||||
|
/* Responder: sending = T(2), receiving = T(1) */
|
||||||
|
memcpy(session->sending_key, t2, 32);
|
||||||
|
memcpy(session->receiving_key, t1, 32);
|
||||||
|
}
|
||||||
|
|
||||||
|
memzero_explicit(t1, 32);
|
||||||
|
memzero_explicit(t2, 32);
|
||||||
|
|
||||||
/* Reset nonces */
|
/* Reset nonces */
|
||||||
session->sending_nonce = 0;
|
session->sending_nonce = 0;
|
||||||
|
|||||||
@@ -7,10 +7,15 @@
|
|||||||
* License: MIT (Clean-room implementation)
|
* License: MIT (Clean-room implementation)
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include "se050_i2c_hal.h"
|
||||||
#include "se050_wireguard.h"
|
#include "se050_wireguard.h"
|
||||||
#include "se050_crypto_utils.h"
|
#include "se050_crypto_utils.h"
|
||||||
#include "se050_keystore_internal.h"
|
#include "se050_keystore_internal.h"
|
||||||
#include "se050_session_internal.h"
|
#include "se050_session_internal.h"
|
||||||
|
#include "se050_x25519_sw.h"
|
||||||
|
|
||||||
|
/* Type alias for compatibility */
|
||||||
|
typedef se050_x25519_sw_keypair_t se050_x25519_keypair_t;
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
|||||||
@@ -95,8 +95,14 @@ static void test_encrypt_decrypt(void)
|
|||||||
/* Setup keys */
|
/* Setup keys */
|
||||||
uint8_t shared_secret[32] = {0};
|
uint8_t shared_secret[32] = {0};
|
||||||
for (int i = 0; i < 32; i++) shared_secret[i] = i;
|
for (int i = 0; i < 32; i++) shared_secret[i] = i;
|
||||||
|
|
||||||
|
/* Set as initiator for key derivation */
|
||||||
|
session.is_initiator = 1;
|
||||||
se050_wireguard_derive_keys(&session, shared_secret);
|
se050_wireguard_derive_keys(&session, shared_secret);
|
||||||
|
|
||||||
|
/* For single-session test, use same key for encrypt and decrypt */
|
||||||
|
memcpy(session.receiving_key, session.sending_key, 32);
|
||||||
|
|
||||||
/* Test data */
|
/* Test data */
|
||||||
const char *plaintext = "Hello, WireGuard!";
|
const char *plaintext = "Hello, WireGuard!";
|
||||||
size_t plaintext_len = strlen(plaintext);
|
size_t plaintext_len = strlen(plaintext);
|
||||||
@@ -135,8 +141,13 @@ static void test_replay_detection(void)
|
|||||||
/* Setup keys */
|
/* Setup keys */
|
||||||
uint8_t shared_secret[32] = {0};
|
uint8_t shared_secret[32] = {0};
|
||||||
for (int i = 0; i < 32; i++) shared_secret[i] = i;
|
for (int i = 0; i < 32; i++) shared_secret[i] = i;
|
||||||
|
|
||||||
|
session.is_initiator = 1;
|
||||||
se050_wireguard_derive_keys(&session, shared_secret);
|
se050_wireguard_derive_keys(&session, shared_secret);
|
||||||
|
|
||||||
|
/* For single-session test, use same key for encrypt and decrypt */
|
||||||
|
memcpy(session.receiving_key, session.sending_key, 32);
|
||||||
|
|
||||||
/* Encrypt a packet */
|
/* Encrypt a packet */
|
||||||
const char *plaintext = "Test message";
|
const char *plaintext = "Test message";
|
||||||
uint8_t encrypted[1024];
|
uint8_t encrypted[1024];
|
||||||
|
|||||||
Reference in New Issue
Block a user