Skip to content

Commit

Permalink
Merge pull request #360 from LedgerHQ/xch/cherry-pick-11
Browse files Browse the repository at this point in the history
Cherry pick for API_LEVEL_11
  • Loading branch information
xchapron-ledger authored Jun 23, 2023
2 parents cd27cc9 + 42c9b84 commit 6b2d5ec
Show file tree
Hide file tree
Showing 27 changed files with 636 additions and 1,556 deletions.
10 changes: 9 additions & 1 deletion Makefile.standard_app
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,14 @@ ifeq ($(TARGET_NAME),$(filter $(TARGET_NAME), TARGET_STAX))
endif
endif

#####################################################################
# SWAP #
#####################################################################
ifeq ($(ENABLE_SWAP), 1)
HAVE_APPLICATION_FLAG_LIBRARY = 1
DEFINES += HAVE_SWAP
endif

#####################################################################
# DEBUG #
#####################################################################
Expand Down Expand Up @@ -85,7 +93,7 @@ ifneq ($(DISABLE_STANDARD_SNPRINTF), 1)
endif

ifneq ($(DISABLE_STANDARD_USB), 1)
DEFINES += HAVE_IO_USB HAVE_L4_USBLIB IO_USB_MAX_ENDPOINTS=6 HAVE_USB_APDU
DEFINES += HAVE_IO_USB HAVE_L4_USBLIB IO_USB_MAX_ENDPOINTS=4 HAVE_USB_APDU
DEFINES += USB_SEGMENT_SIZE=64
SDK_SOURCE_PATH += lib_stusb lib_stusb_impl
endif
Expand Down
4 changes: 4 additions & 0 deletions include/decorators.h
Original file line number Diff line number Diff line change
Expand Up @@ -62,3 +62,7 @@
#ifndef WARN_UNUSED_RESULT
#define WARN_UNUSED_RESULT __attribute__ ((warn_unused_result))
#endif

#ifndef DEPRECATED
#define DEPRECATED __attribute__ ((deprecated))
#endif
119 changes: 90 additions & 29 deletions include/os_seed.h
Original file line number Diff line number Diff line change
Expand Up @@ -28,30 +28,49 @@ typedef enum {
/**
* Set the persisted seed if none yet, else override the volatile seed (in RAM)
*/
SYSCALL PERMISSION(APPLICATION_FLAG_BOLOS_UX) void os_perso_set_seed(unsigned int identity, unsigned int algorithm, unsigned char* seed PLENGTH(length), unsigned int length);
SYSCALL PERMISSION(APPLICATION_FLAG_BOLOS_UX) void os_perso_set_seed(
unsigned int identity,
unsigned int algorithm,
unsigned char *seed PLENGTH(length),
unsigned int length);

SYSCALL PERMISSION(APPLICATION_FLAG_BOLOS_UX) void os_perso_derive_and_set_seed(unsigned char identity,
const char* prefix PLENGTH(prefix_length), unsigned int prefix_length,
const char* passphrase PLENGTH(passphrase_length), unsigned int passphrase_length,
const char* words PLENGTH(words_length), unsigned int words_length);
SYSCALL PERMISSION(APPLICATION_FLAG_BOLOS_UX) void os_perso_derive_and_set_seed(
unsigned char identity,
const char *prefix PLENGTH(prefix_length),
unsigned int prefix_length,
const char *passphrase PLENGTH(passphrase_length),
unsigned int passphrase_length,
const char *words PLENGTH(words_length),
unsigned int words_length);

#if defined(HAVE_VAULT_RECOVERY_ALGO)
SYSCALL PERMISSION(APPLICATION_FLAG_BOLOS_UX) void os_perso_derive_and_prepare_seed(const char* words, unsigned int words_length, uint8_t *vault_recovery_work_buffer);
SYSCALL PERMISSION(APPLICATION_FLAG_BOLOS_UX) void os_perso_derive_and_xor_seed(uint8_t *vault_recovery_work_buffer);
SYSCALL PERMISSION(APPLICATION_FLAG_BOLOS_UX) unsigned char os_perso_get_seed_algorithm(void);
SYSCALL PERMISSION(APPLICATION_FLAG_BOLOS_UX) void os_perso_derive_and_prepare_seed(
const char * words,
unsigned int words_length,
uint8_t *vault_recovery_work_buffer);
SYSCALL PERMISSION(APPLICATION_FLAG_BOLOS_UX) void os_perso_derive_and_xor_seed(
uint8_t *vault_recovery_work_buffer);
SYSCALL PERMISSION(APPLICATION_FLAG_BOLOS_UX) unsigned char os_perso_get_seed_algorithm(void);
#endif // HAVE_VAULT_RECOVERY_ALGO

SYSCALL PERMISSION(APPLICATION_FLAG_BOLOS_UX) void os_perso_set_words(const unsigned char* words PLENGTH(length), unsigned int length);
SYSCALL PERMISSION(APPLICATION_FLAG_BOLOS_UX) void os_perso_finalize(void);
SYSCALL PERMISSION(APPLICATION_FLAG_BOLOS_UX) void os_perso_set_words(
const unsigned char *words PLENGTH(length),
unsigned int length);
SYSCALL PERMISSION(APPLICATION_FLAG_BOLOS_UX) void os_perso_finalize(void);
#if defined(HAVE_RECOVER)
SYSCALL PERMISSION(APPLICATION_FLAG_BOLOS_UX) void os_perso_master_seed(uint8_t* master_seed PLENGTH(length), size_t length, os_action_t action);
SYSCALL PERMISSION(APPLICATION_FLAG_BOLOS_UX) void os_perso_recover_state(uint8_t* state, os_action_t action);
SYSCALL PERMISSION(APPLICATION_FLAG_BOLOS_UX) void os_perso_master_seed(
uint8_t *master_seed PLENGTH(length),
size_t length,
os_action_t action);
SYSCALL PERMISSION(APPLICATION_FLAG_BOLOS_UX) void os_perso_recover_state(
uint8_t *state,
os_action_t action);
#endif // HAVE_RECOVER

// checked in the ux flow to avoid asking the pin for example
// NBA : could also be checked by applications running in insecure mode - thus unprivilegied
// @return BOLOS_UX_OK when perso is onboarded.
SYSCALL bolos_bool_t os_perso_isonboarded(void);
SYSCALL bolos_bool_t os_perso_isonboarded(void);

enum {
ONBOARDING_STATUS_WELCOME = 0,
Expand All @@ -71,22 +90,48 @@ enum {
ONBOARDING_STATUS_SETUP_CHOICE_RESTORE_SEED,
ONBOARDING_STATUS_CHECKING
};
SYSCALL void os_perso_set_onboarding_status(unsigned int state, unsigned int count, unsigned int total);
SYSCALL void os_perso_set_onboarding_status(unsigned int state,
unsigned int count,
unsigned int total);

// derive the seed for the requested BIP32 path
SYSCALL void os_perso_derive_node_bip32(cx_curve_t curve, const unsigned int* path PLENGTH(4 * (pathLength&0x0FFFFFFFu)), unsigned int pathLength, unsigned char *privateKey PLENGTH(64), unsigned char* chain PLENGTH(32));
// Deprecated : see "os_derive_bip32_no_throw"
#ifndef HAVE_BOLOS
DEPRECATED
#endif
SYSCALL void os_perso_derive_node_bip32(cx_curve_t curve,
const unsigned int *path PLENGTH(4 * (pathLength & 0x0FFFFFFFu)),
unsigned int pathLength,
unsigned char *privateKey PLENGTH(64),
unsigned char *chain PLENGTH(32));

#define HDW_NORMAL 0
#define HDW_ED25519_SLIP10 1
// symmetric key derivation according to SLIP-0021
// this only supports derivation of the master node (level 1)
// the beginning of the authorized path is to be provided in the authorized derivation tag of the registry
// starting with a \x00
// Note: for SLIP21, the path is a string and the pathLength is the number of chars including the starting \0 byte. However, firewall checks are processing a number of integers, therefore, take care not to locate the buffer too far in memory to pass the firewall check.
// Note: for SLIP21, the path is a string and the pathLength is the number of chars including the starting \0 byte.
// However, firewall checks are processing a number of integers, therefore, take care not to locate the buffer too far
// in memory to pass the firewall check.
#define HDW_SLIP21 2
// derive the seed for the requested BIP32 path, with the custom provided seed_key for the sha512 hmac ("Bitcoin Seed", "Nist256p1 Seed", "ed25519 seed", ...)
SYSCALL void os_perso_derive_node_with_seed_key(unsigned int mode, cx_curve_t curve, const unsigned int* path PLENGTH(4 * (pathLength&0x0FFFFFFFu)), unsigned int pathLength, unsigned char *privateKey PLENGTH(64), unsigned char* chain PLENGTH(32), unsigned char* seed_key PLENGTH(seed_key_length), unsigned int seed_key_length);
#define os_perso_derive_node_bip32_seed_key(mode, curve, path, pathLength, privateKey, chain, seed_key, seed_key_length) os_perso_derive_node_with_seed_key(mode, curve, path, pathLength, privateKey, chain, seed_key, seed_key_length)

// derive the seed for the requested BIP32 path, with the custom provided seed_key for the sha512 hmac ("Bitcoin Seed",
// "Nist256p1 Seed", "ed25519 seed", ...)
// Deprecated : see "os_derive_bip32_with_seed_no_throw"
#ifndef HAVE_BOLOS
DEPRECATED
#endif
SYSCALL void os_perso_derive_node_with_seed_key(unsigned int mode,
cx_curve_t curve,
const unsigned int *path PLENGTH(4 * (pathLength & 0x0FFFFFFFu)),
unsigned int pathLength,
unsigned char *privateKey PLENGTH(64),
unsigned char *chain PLENGTH(32),
unsigned char *seed_key PLENGTH(seed_key_length),
unsigned int seed_key_length);

#define os_perso_derive_node_bip32_seed_key os_perso_derive_node_with_seed_key

/**
* @brief Gets the private key from the device seed using the specified bip32 path and seed key.
Expand All @@ -112,18 +157,21 @@ SYSCALL void os_perso_derive_nod
* - CX_INTERNAL_ERROR
*/
WARN_UNUSED_RESULT static inline cx_err_t os_derive_bip32_with_seed_no_throw(
unsigned int derivation_mode,
cx_curve_t curve,
const unsigned int *path,
unsigned int path_len,
unsigned char raw_privkey[static 64],
unsigned char *chain_code,
unsigned char *seed,
unsigned int seed_len) {
unsigned int derivation_mode,
cx_curve_t curve,
const unsigned int *path,
unsigned int path_len,
unsigned char raw_privkey[static 64],
unsigned char * chain_code,
unsigned char * seed,
unsigned int seed_len) {
cx_err_t error = CX_OK;

BEGIN_TRY {
TRY {
// ignore the deprecated warning, pragma to remove when the "no throw" OS function will be available
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wdeprecated-declarations"
// Derive the seed with path
os_perso_derive_node_bip32_seed_key(derivation_mode,
curve,
Expand All @@ -133,6 +181,7 @@ WARN_UNUSED_RESULT static inline cx_err_t os_derive_bip32_with_seed_no_throw(
chain_code,
seed,
seed_len);
#pragma GCC diagnostic pop
}
CATCH_OTHER(e) {
error = e;
Expand Down Expand Up @@ -182,7 +231,15 @@ WARN_UNUSED_RESULT static inline cx_err_t os_derive_bip32_no_throw(
0);
}

SYSCALL void os_perso_derive_eip2333(cx_curve_t curve, const unsigned int* path PLENGTH(4 * (pathLength&0x0FFFFFFFu)), unsigned int pathLength, unsigned char *privateKey PLENGTH(32));
// Deprecated : see "os_derive_eip2333_no_throw"
#ifndef HAVE_BOLOS
DEPRECATED
#endif
SYSCALL void os_perso_derive_eip2333(
cx_curve_t curve,
const unsigned int *path PLENGTH(4 * (pathLength & 0x0FFFFFFFu)),
unsigned int pathLength,
unsigned char *privateKey PLENGTH(32));

/**
* @brief Gets the private key from the device seed using the specified eip2333 path.
Expand All @@ -208,8 +265,12 @@ WARN_UNUSED_RESULT static inline cx_err_t os_derive_eip2333_no_throw(

BEGIN_TRY {
TRY {
// ignore the deprecated warning, pragma to remove when the "no throw" OS function will be available
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wdeprecated-declarations"
// Derive the seed with path
os_perso_derive_eip2333(curve, path, path_len, raw_privkey);
#pragma GCC diagnostic pop
}
CATCH_OTHER(e) {
error = e;
Expand All @@ -234,5 +295,5 @@ WARN_UNUSED_RESULT static inline cx_err_t os_derive_eip2333_no_throw(
#if defined(HAVE_SEED_COOKIE)
// seed_cookie length has to be CX_SHA512_SIZE.
// return BOLOS_TRUE if the seed has been generated, return BOLOS_FALSE otherwise.
SYSCALL bolos_bool_t os_perso_seed_cookie(unsigned char * seed_cookie PLENGTH(CX_SHA512_SIZE));
SYSCALL bolos_bool_t os_perso_seed_cookie(unsigned char *seed_cookie PLENGTH(CX_SHA512_SIZE));
#endif // HAVE_SEED_COOKIE
8 changes: 4 additions & 4 deletions include/os_utils.h
Original file line number Diff line number Diff line change
Expand Up @@ -79,10 +79,10 @@ char os_secure_memcmp(const void *src1, const void* src2, size_t length);
#define offsetof(type, field) ((unsigned int)&(((type*)NULL)->field))
#endif

void *os_memmove(void *dest, const void *src, size_t n) __attribute__((deprecated));
void *os_memcpy(void *dest, const void *src, size_t n) __attribute__((deprecated));
int os_memcmp(const void *s1, const void *s2, size_t n) __attribute__((deprecated));
void *os_memset(void *s, int c, size_t n) __attribute__((deprecated));
void *os_memmove(void *dest, const void *src, size_t n) DEPRECATED;
void *os_memcpy(void *dest, const void *src, size_t n) DEPRECATED;
int os_memcmp(const void *s1, const void *s2, size_t n) DEPRECATED;
void *os_memset(void *s, int c, size_t n) DEPRECATED;

// This call will reset the value of the entire BSS segment
void os_explicit_zero_BSS_segment(void);
122 changes: 10 additions & 112 deletions lib_cxng/include/lcx_aes.h
Original file line number Diff line number Diff line change
Expand Up @@ -56,27 +56,12 @@
*/
cx_err_t cx_aes_init_key_no_throw(const uint8_t *rawkey, size_t key_len, cx_aes_key_t *key);


/**
* @brief Initializes an AES Key.
*
* @details Once initialized, the key can be stored in non-volatile memory
* and directly used for any AES processing.
* This function throws an exception if the initialization fails.
*
* @warning It is recommended to use #cx_aes_init_key_no_throw rather
* than this function.
*
* @param[in] rawkey Pointer to the supplied key.
*
* @param[in] key_len Length of the key: 16, 24 or 32 octets.
*
* @param[out] key Pointer to the key structure. This must not be NULL.
*
* @return Length of the key.
*
* @throw CX_INVALID_PARAMETER
* @deprecated
* See #cx_aes_init_key_no_throw
*/
static inline size_t cx_aes_init_key ( const unsigned char * rawkey, unsigned int key_len, cx_aes_key_t * key )
DEPRECATED static inline size_t cx_aes_init_key ( const unsigned char * rawkey, unsigned int key_len, cx_aes_key_t * key )
{
CX_THROW(cx_aes_init_key_no_throw(rawkey, key_len, key));
return key_len;
Expand Down Expand Up @@ -136,56 +121,10 @@ cx_err_t cx_aes_iv_no_throw(const cx_aes_key_t *key,
size_t * out_len);

/**
* @brief Encrypts, decrypts, signs or verifies data with AES algorithm.
*
* @details This function throws an exception if the computation
* doesn't succeed.
*
* @warning It is recommended to use #cx_aes_iv_no_throw rather than
* this function.
*
* @param[in] key Pointer to the key initialized with #cx_aes_init_key_no_throw.
*
* @param[in] mode Crypto mode flags
* Supported flags:
* - CX_LAST
* - CX_ENCRYPT
* - CX_DECRYPT
* - CX_SIGN
* - CX_VERIFY
* - CX_PAD_NONE
* - CX_PAD_ISO9797M1
* - CX_PAD_ISO9797M2
* - CX_CHAIN_ECB
* - CX_CHAIN_CBC
* - CX_CHAIN_CTR
*
* When using the CTR mode with AES, CX_ENCRYPT must be used for encryption
* and decryption.
*
* @param[in] iv Initialization vector.
*
* @param[in] iv_len Length of the initialization vector.
*
* @param[in] in Input data.
*
* @param[in] in_len Length of the input data.
* If CX_LAST is set, padding is automatically done according to the *mode*.
* Otherwise, *in_len* shall be a multiple of AES_BLOCK_SIZE.
*
* @param[out] out Output data according to the mode:
* - encrypted/decrypted output data
* - generated signature
* - signature to be verified
*
* @param[in] out_len Length of the output data.
*
* @return Length of the output.
*
* @throws CX_INVALID_PARAMETER
* @throws INVALID_PARAMETER
* @deprecated
* See #cx_aes_iv_no_throw
*/
static inline size_t cx_aes_iv ( const cx_aes_key_t * key, uint32_t mode, unsigned char * iv, unsigned int iv_len, const unsigned char * in, unsigned int in_len, unsigned char * out, unsigned int out_len )
DEPRECATED static inline size_t cx_aes_iv ( const cx_aes_key_t * key, uint32_t mode, unsigned char * iv, unsigned int iv_len, const unsigned char * in, unsigned int in_len, unsigned char * out, unsigned int out_len )
{
size_t out_len_ = out_len;
CX_THROW(cx_aes_iv_no_throw(key, mode, iv, iv_len, in, in_len, out, &out_len_));
Expand Down Expand Up @@ -235,51 +174,10 @@ static inline size_t cx_aes_iv ( const cx_aes_key_t * key, uint32_t mode, unsign
cx_err_t cx_aes_no_throw(const cx_aes_key_t *key, uint32_t mode, const uint8_t *in, size_t in_len, uint8_t *out, size_t *out_len);

/**
* @brief Encrypts, decrypts, signs or verifies data with AES algorithm.
*
* @details Same as #cx_aes_iv_no_throw with initial IV assumed to be sixteen zeros.
* This function throws an exception if the computation
* doesn't succeed.
*
* @warning It is recommended to use #cx_aes_no_throw rather than this
* function.
*
* @param[in] key Pointer to the key initialized with
* #cx_aes_init_key_no_throw.
*
* @param[in] mode Crypto mode flags
* Supported flags:
* - CX_LAST
* - CX_ENCRYPT
* - CX_DECRYPT
* - CX_SIGN
* - CX_VERIFY
* - CX_PAD_NONE
* - CX_PAD_ISO9797M1
* - CX_PAD_ISO9797M2
* - CX_CHAIN_ECB
* - CX_CHAIN_CBC
* - CX_CHAIN_CTR
*
* @param[in] in Input data.
*
* @param[in] in_len Length of the input data.
* If CX_LAST is set, padding is automatically done according to the *mode*.
* Otherwise, *in_len* shall be a multiple of AES_BLOCK_SIZE.
*
* @param[out] out Output data according to the mode:
* - encrypted/decrypted output data
* - generated signature
* - signature to be verified
*
* @param[in] out_len Length of the output data.
*
* @return Length of the output.
*
* @throws CX_INVALID_PARAMETER
* @throws INVALID_PARAMETER
* @deprecated
* See #cx_aes_no_throw
*/
static inline size_t cx_aes ( const cx_aes_key_t * key, uint32_t mode, const unsigned char * in, unsigned int in_len, unsigned char * out, unsigned int out_len )
DEPRECATED static inline size_t cx_aes ( const cx_aes_key_t * key, uint32_t mode, const unsigned char * in, unsigned int in_len, unsigned char * out, unsigned int out_len )
{
size_t out_len_ = out_len;
CX_THROW(cx_aes_no_throw(key, mode, in, in_len, out, &out_len_));
Expand Down
Loading

0 comments on commit 6b2d5ec

Please sign in to comment.