mirror of https://github.com/arendst/Tasmota.git
Berry RS256 crypto algorithm (RSASSA-MCKS1_v1-5 with SHA256) used for JWT (#18763)
This commit is contained in:
parent
74f9973b8b
commit
b9d855ef79
|
@ -11,6 +11,7 @@ All notable changes to this project will be documented in this file.
|
|||
- Matter bridge for ESP8266 remote endpoints (experimental)
|
||||
- Display descriptor for ST7735 128x160 display
|
||||
- Matter support for Occupancy via Switch (experimental)
|
||||
- Berry RS256 crypto algorithm (RSASSA-MCKS1_v1-5 with SHA256) used for JWT
|
||||
|
||||
### Breaking Changed
|
||||
- Matter relay number starts at 1 instead of 0 to match Tasmota numbering
|
||||
|
|
|
@ -2597,7 +2597,11 @@ br_cpuid(uint32_t mask_eax, uint32_t mask_ebx,
|
|||
#endif
|
||||
|
||||
#define _debugBearSSL (0)
|
||||
extern void optimistic_yield(uint32_t);
|
||||
#ifdef ESP8266
|
||||
extern void optimistic_yield(uint32_t);
|
||||
#else
|
||||
#define optimistic_yield(ignored)
|
||||
#endif
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
|
|
@ -11,6 +11,8 @@
|
|||
extern int be_class_crypto_member(bvm *vm);
|
||||
extern int m_crypto_random(bvm *vm);
|
||||
|
||||
extern int m_rsa_rsassa_pkcs1_v1_5(bvm *vm);
|
||||
|
||||
extern int m_aes_ccm_init(bvm *vm);
|
||||
extern int m_aes_ccm_encryt(bvm *vm);
|
||||
extern int m_aes_ccm_decryt(bvm *vm);
|
||||
|
@ -56,6 +58,7 @@ extern const bclass be_class_md5;
|
|||
#include "solidify/solidified_crypto_pbkdf2_hmac_sha256.h"
|
||||
#include "solidify/solidified_crypto_spake2p_matter.h"
|
||||
|
||||
#include "be_fixed_be_class_rsa.h"
|
||||
#include "be_fixed_be_class_aes_ccm.h"
|
||||
#include "be_fixed_be_class_aes_gcm.h"
|
||||
#include "be_fixed_be_class_aes_ctr.h"
|
||||
|
@ -104,6 +107,10 @@ const be_const_member_t be_crypto_members[] = {
|
|||
{ "/PBKDF2_HMAC_SHA256", (intptr_t) &be_class_pbkdf2_hmac_sha256 },
|
||||
#endif // USE_BERRY_CRYPTO_PBKDF2_HMAC_SHA256
|
||||
|
||||
#ifdef USE_BERRY_CRYPTO_RSA
|
||||
{ "/RSA", (intptr_t) &be_class_rsa },
|
||||
#endif // USE_BERRY_CRYPTO_PBKDF2_HMAC_SHA256
|
||||
|
||||
#ifdef USE_BERRY_CRYPTO_SHA256
|
||||
{ "/SHA256", (intptr_t) &be_class_sha256 },
|
||||
#endif // USE_BERRY_CRYPTO_SHA256
|
||||
|
@ -118,6 +125,10 @@ const size_t be_crypto_members_size = sizeof(be_crypto_members)/sizeof(be_crypto
|
|||
|
||||
/* @const_object_info_begin
|
||||
|
||||
class be_class_rsa (scope: global, name: RSA) {
|
||||
rs256, static_func(m_rsa_rsassa_pkcs1_v1_5)
|
||||
}
|
||||
|
||||
class be_class_aes_ccm (scope: global, name: AES_CCM) {
|
||||
.p1, var
|
||||
.p2, var
|
||||
|
|
|
@ -65,6 +65,56 @@ extern "C" {
|
|||
}
|
||||
}
|
||||
|
||||
/*********************************************************************************************\
|
||||
* RSA class
|
||||
*
|
||||
\*********************************************************************************************/
|
||||
extern "C" {
|
||||
// crypto.RSA.rsassa_pkcs1_v1_5(private_key:bytes(), msg:bytes()) -> bytes()
|
||||
// Parses RSA private key from DER binary
|
||||
int32_t m_rsa_rsassa_pkcs1_v1_5(bvm *vm);
|
||||
int32_t m_rsa_rsassa_pkcs1_v1_5(bvm *vm) {
|
||||
int32_t argc = be_top(vm); // Get the number of arguments
|
||||
if (argc >= 2 && be_isbytes(vm, 1)) {
|
||||
size_t sk_len = 0;
|
||||
uint8_t * sk_der = (uint8_t*) be_tobytes(vm, 1, &sk_len);
|
||||
|
||||
// 1. decode the DER private key
|
||||
br_skey_decoder_context sdc;
|
||||
br_skey_decoder_init(&sdc);
|
||||
br_skey_decoder_push(&sdc, sk_der, sk_len);
|
||||
if (int ret = br_skey_decoder_last_error(&sdc)) {
|
||||
be_raisef(vm, "value_error", "invalid private key %i", ret);
|
||||
}
|
||||
if (br_skey_decoder_key_type(&sdc) != BR_KEYTYPE_RSA) {
|
||||
be_raise(vm, "value_error", "key is not RSA");
|
||||
}
|
||||
const br_rsa_private_key *sk = br_skey_decoder_get_rsa(&sdc);
|
||||
|
||||
// 2. Hash the message with SHA
|
||||
size_t msg_len = 0;
|
||||
uint8_t * msg = (uint8_t*) be_tobytes(vm, 2, &msg_len);
|
||||
uint8_t hash[32];
|
||||
br_sha256_context ctx;
|
||||
br_sha256_init(&ctx);
|
||||
br_sha256_update(&ctx, msg, msg_len);
|
||||
br_sha256_out(&ctx, hash);
|
||||
|
||||
// 3. sign the message
|
||||
size_t sign_len = (sk->n_bitlen + 7) / 8;
|
||||
uint8_t x[sign_len] = {};
|
||||
int err = br_rsa_i15_pkcs1_sign(BR_HASH_OID_SHA256, hash, sizeof(hash), sk, x);
|
||||
if (err != 1) {
|
||||
be_raisef(vm, "value_error", "signature failed %i", err);
|
||||
}
|
||||
|
||||
be_pushbytes(vm, x, sign_len);
|
||||
be_return(vm);
|
||||
}
|
||||
be_raise(vm, kTypeError, nullptr);
|
||||
}
|
||||
}
|
||||
|
||||
/*********************************************************************************************\
|
||||
* AES_GCM class
|
||||
*
|
||||
|
|
Loading…
Reference in New Issue