Berry crypto add `SPAKE2P_Matter` for Matter support (#17497)

This commit is contained in:
s-hadinger 2022-12-23 19:40:12 +01:00 committed by GitHub
parent f5f7ff4fb8
commit 1832c4b2f0
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
5 changed files with 885 additions and 0 deletions

View File

@ -9,6 +9,7 @@ All notable changes to this project will be documented in this file.
- Berry crypto add ``random`` to generate series of random bytes
- Berry crypto add ``HKDF_HMAC_SHA256``
- Support for up to 3 single phase modbus energy monitoring device using generic Energy Modbus driver
- Berry crypto add ``SPAKE2P_Matter`` for Matter support
### Breaking Changed

View File

@ -45,6 +45,7 @@ extern int m_hkdf_sha256_derive(bvm *vm);
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_aes_gcm.h"
#include "be_fixed_be_class_aes_ctr.h"
@ -56,6 +57,16 @@ extern const bclass be_class_md5;
#include "be_fixed_be_class_hkdf_sha256.h"
#include "be_fixed_crypto.h"
// Enable all the crypto required by Matter
#ifdef USE_BERRY_CRYPTO_SPAKE2P_MATTER
#undef USE_BERRY_CRYPTO_EC_P256
#define USE_BERRY_CRYPTO_EC_P256
#undef USE_BERRY_CRYPTO_HMAC_SHA256
#define USE_BERRY_CRYPTO_HMAC_SHA256
#undef USE_BERRY_CRYPTO_HKDF_SHA256
#define USE_BERRY_CRYPTO_HKDF_SHA256
#endif
const be_const_member_t be_crypto_members[] = {
// name with prefix '/' indicates a Berry class
// entries need to be sorted (ignoring the prefix char)
@ -92,6 +103,11 @@ const be_const_member_t be_crypto_members[] = {
#ifdef USE_BERRY_CRYPTO_SHA256
{ "/SHA256", (intptr_t) &be_class_sha256 },
#endif // USE_BERRY_CRYPTO_SHA256
#ifdef USE_BERRY_CRYPTO_SPAKE2P_MATTER
{ "/SPAKE2P_Matter", (intptr_t) &be_class_SPAKE2P_Matter },
#endif // USE_BERRY_CRYPTO_SPAKE2P_MATTER
};
const size_t be_crypto_members_size = sizeof(be_crypto_members)/sizeof(be_crypto_members[0]);

View File

@ -0,0 +1,210 @@
# SPAKE2+ with Matter 1.0 specification
#
# Real name is SPAKE2+-P256-SHA256-HKDF-SHA256-HMAC-SHA256
# but we'll use SPAKE2P_Matter as a shorter name
#
# To start SPAKE2+, we need either w0/w1 for the prover (Matter Gateway)
# or w0/L for the verifier (end-device).
# The end-device can store in flash pre-computed values for w0/L.
#
# In this class we consider w0/w1/L to be computerd before using this class
#@ solidify:SPAKE2P_Matter,weak
class SPAKE2P_Matter
# computed values from above
var w0 # w0
var w1
var L
var pA, pB, Z, V
var x, y
# var TT
var Kmain
var KcA, KcB, K_shared
var cA, cB
# Matter values for key generation
var A, B, Context
# values from the Matter specification
static var CRYPTO_GROUP_SIZE_BYTES = 32
static var CRYPTO_W_SIZE_BYTES = 40 # CRYPTO_GROUP_SIZE_BYTES + 8
static var spake_M_hex = "04886e2f97ace46e55ba9dd7242579f2993b64e16ef3dcab95afd497333d8fa12f5ff355163e43ce224e0b0e65ff02ac8e5c7be09419c785e0ca547d55a12e2d20"
static var spake_N_hex = "04d8bbd6c639c62937b04d997f38c3770719c629d7014d49a24b4f98baa1292b4907d60aa6bfade45008a636337f5168c64d9bd36034808cd564490b1e656edbe7"
var M, N # due to the nature of solification, we can't solidify the bytes versions nor store as static variable
# Initialize the SPAKE2+ class with required value.
# We need either w0/w1 for the gateway or w0/L for the end-device
def init(w0, w1, L)
self.M = bytes().fromhex(self.spake_M_hex)
self.N = bytes().fromhex(self.spake_N_hex)
# set w0/w1/L
self.w0 = w0
self.w1 = w1
self.L = L
end
# compute the shared values pA (done by Matter gateway)
# w0 must be known
# x is a random 32 bytes vector. It does not need to be lower than the order (we take the modulus anyways)
#
# if `x` is nil, we take a random vector, otherwise it must be byytes(32)
def compute_pA(x)
import crypto
if x == nil x = crypto.random(32) end
var ec = crypto.EC_P256()
self.x = ec.mod(x)
self.pA = ec.muladd(self.w0, self.M, self.x, bytes() #- empty means generator -#) # compute x*P+w0*M
end
# compute the shared values pB (done by Matter end-device)
# w0 must be known
# y is a random 32 bytes vector. It does not need to be lower than the order (we take the modulus anyways)
def compute_pB(y)
import crypto
if y == nil y = crypto.random(32) end
var ec = crypto.EC_P256()
self.y = ec.mod(y)
self.pB = ec.muladd(self.w0, self.N, self.y, bytes() #- empty means generator -#) # compute y*P+w0*M
end
# compute Z and V for the Prover (Gateway), receiving pB from the verifier (end-device)
# pB must be bytes(65)
# x must be known
def compute_ZV_prover(pB)
import crypto
var ec = crypto.EC_P256()
self.pB = pB
# we are supposed to check that the point is on the curve -- TODO
# we need a substraction so we negate w0
var w0_neg = ec.neg(self.w0)
var t_inner = ec.muladd(bytes("01"), self.pB, w0_neg, self.N) # compute 1*pB-w0*N
self.Z = ec.mul(self.x, t_inner)
self.V = ec.mul(self.w1, t_inner)
end
# compute Z and V for the Verifier (end-device), receiving pA from the prover (Gateway)
# pA must be bytes(65)
# y must be known
def compute_ZV_verifier(pA)
import crypto
var ec = crypto.EC_P256()
self.pA = pA
# we are supposed to check that the point is on the curve -- TODO
# we need a substraction so we negate w0
var w0_neg = ec.neg(self.w0)
var t_inner = ec.muladd(bytes("01"), self.pA, w0_neg, self.M) # compute 1*pA-w0*M
self.Z = ec.mul(self.y, t_inner)
self.V = ec.mul(self.y, self.L)
end
# Set context, prover and verifier identitites (last 2 can be empty)
def set_context(context, prover, verifier)
if prover == nil prover = bytes() end
if verifier == nil verifier = bytes() end
self.Context = context
self.A = prover
self.B = verifier
end
# Need to know "Context, pA, pB, Z, V, w0"
#
def compute_TT_hash()
class SPAKE_Hasher
var hash
# var complete # complete value for the bytes -- will be removed in production code
def init()
import crypto
self.hash = crypto.SHA256()
# self.complete = bytes()
end
# add v (bytes) to the hash
def add_item(v)
var len = v.size()
var len_bin = bytes().add(len, 4).add(0, 4)
# self.complete += len_bin
# self.complete += v
self.hash.update(len_bin)
self.hash.update(v)
end
def out()
return self.hash.out()
end
end
import crypto
var hasher = SPAKE_Hasher()
# Context
hasher.add_item(self.Context)
hasher.add_item(self.A)
hasher.add_item(self.B)
hasher.add_item(self.M)
hasher.add_item(self.N)
hasher.add_item(self.pA)
hasher.add_item(self.pB)
hasher.add_item(self.Z)
hasher.add_item(self.V)
hasher.add_item(self.w0)
# self.TT = hasher.complete
self.Kmain = hasher.out()
# compute KcA and KcB
var kdf = crypto.HKDF_SHA256()
var KPV = kdf.derive(self.Kmain, bytes(), bytes().fromstring("ConfirmationKeys"), 64)
self.KcA = KPV[0..31]
self.KcB = KPV[32..63]
self.K_shared = kdf.derive(self.Kmain, bytes(), bytes().fromstring("SharedKey"), 32)
self.cA = crypto.HMAC_SHA256(self.KcA).update(self.pB).out()
self.cB = crypto.HMAC_SHA256(self.KcB).update(self.pA).out()
end
end
#-
# ======================================================================
# Example from SPAKE2P test vectors
# https://chris-wood.github.io/draft-bar-cfrg-spake2plus/draft-bar-cfrg-spake2plus.html
import crypto
var w0 = bytes("bb8e1bbcf3c48f62c08db243652ae55d3e5586053fca77102994f23ad95491b3")
var w1 = bytes("7e945f34d78785b8a3ef44d0df5a1a97d6b3b460409a345ca7830387a74b1dba")
var L = bytes("04eb7c9db3d9a9eb1f8adab81b5794c1f13ae3e225efbe91ea487425854c7fc00f00bfedcbd09b2400142d40a14f2064ef31dfaa903b91d1faea7093d835966efd")
var spake_matter = crypto.SPAKE2P_Matter(w0, w1, L)
# context values
var Context = bytes().fromstring('SPAKE2+-P256-SHA256-HKDF-SHA256-HMAC-SHA256 Test Vectors')
var Prover = bytes().fromstring('client')
var Verifier = bytes().fromstring('server')
spake_matter.set_context(Context, Prover, Verifier)
# x is supposed to be random 32 bytes, test vector sets it
var x = bytes("d1232c8e8693d02368976c174e2088851b8365d0d79a9eee709c6a05a2fad539")
spake_matter.compute_pA(x)
assert(spake_matter.pA == bytes('04EF3BD051BF78A2234EC0DF197F7828060FE9856503579BB1733009042C15C0C1DE127727F418B5966AFADFDD95A6E4591D171056B333DAB97A79C7193E341727'))
# y is supposed to be random 32 bytes, test vector sets it
var y = bytes("717a72348a182085109c8d3917d6c43d59b224dc6a7fc4f0483232fa6516d8b3")
spake_matter.compute_pB(y)
assert(spake_matter.pB == bytes('04C0F65DA0D11927BDF5D560C69E1D7D939A05B0E88291887D679FCADEA75810FB5CC1CA7494DB39E82FF2F50665255D76173E09986AB46742C798A9A68437B048'))
spake_matter.compute_ZV_prover(spake_matter.pB)
assert(spake_matter.Z == bytes('04BBFCE7DD7F277819C8DA21544AFB7964705569BDF12FB92AA388059408D50091A0C5F1D3127F56813B5337F9E4E67E2CA633117A4FBD559946AB474356C41839'))
assert(spake_matter.V == bytes('0458BF27C6BCA011C9CE1930E8984A797A3419797B936629A5A937CF2F11C8B9514B82B993DA8A46E664F23DB7C01EDC87FAA530DB01C2EE405230B18997F16B68'))
spake_matter.compute_ZV_verifier(spake_matter.pA)
assert(spake_matter.Z == bytes('04BBFCE7DD7F277819C8DA21544AFB7964705569BDF12FB92AA388059408D50091A0C5F1D3127F56813B5337F9E4E67E2CA633117A4FBD559946AB474356C41839'))
assert(spake_matter.V == bytes('0458BF27C6BCA011C9CE1930E8984A797A3419797B936629A5A937CF2F11C8B9514B82B993DA8A46E664F23DB7C01EDC87FAA530DB01C2EE405230B18997F16B68'))
spake_matter.compute_TT_hash()
assert(spake_matter.Kmain == bytes('4c59e1ccf2cfb961aa31bd9434478a1089b56cd11542f53d3576fb6c2a438a29'))
assert(spake_matter.KcA == bytes('871ae3f7b78445e34438fb284504240239031c39d80ac23eb5ab9be5ad6db58a'))
assert(spake_matter.KcB == bytes('ccd53c7c1fa37b64a462b40db8be101cedcf838950162902054e644b400f1680'))
assert(spake_matter.cA == bytes('926cc713504b9b4d76c9162ded04b5493e89109f6d89462cd33adc46fda27527'))
assert(spake_matter.cB == bytes('9747bcc4f8fe9f63defee53ac9b07876d907d55047e6ff2def2e7529089d3e68'))
assert(spake_matter.K_shared == bytes('0c5f8ccd1413423a54f6c1fb26ff01534a87f893779c6e68666d772bfd91f3e7'))
print("SPAKE2P Matter all tests passed")
-#

View File

@ -0,0 +1,657 @@
/* Solidification of crypto_spake2p_matter.h */
/********************************************************************\
* Generated code, don't edit *
\********************************************************************/
#include "be_constobj.h"
/********************************************************************
** Solidified function: set_context
********************************************************************/
be_local_closure(SPAKE2P_Matter_set_context, /* name */
be_nested_proto(
5, /* nstack */
4, /* argc */
2, /* varg */
0, /* has upvals */
NULL, /* no upvals */
0, /* has sup protos */
NULL, /* no sub protos */
1, /* has constants */
( &(const bvalue[ 3]) { /* constants */
/* K0 */ be_nested_str_weak(Context),
/* K1 */ be_nested_str_weak(A),
/* K2 */ be_nested_str_weak(B),
}),
be_str_weak(set_context),
&be_const_str_solidified,
( &(const binstruction[16]) { /* code */
0x4C100000, // 0000 LDNIL R4
0x1C100404, // 0001 EQ R4 R2 R4
0x78120002, // 0002 JMPF R4 #0006
0x60100015, // 0003 GETGBL R4 G21
0x7C100000, // 0004 CALL R4 0
0x5C080800, // 0005 MOVE R2 R4
0x4C100000, // 0006 LDNIL R4
0x1C100604, // 0007 EQ R4 R3 R4
0x78120002, // 0008 JMPF R4 #000C
0x60100015, // 0009 GETGBL R4 G21
0x7C100000, // 000A CALL R4 0
0x5C0C0800, // 000B MOVE R3 R4
0x90020001, // 000C SETMBR R0 K0 R1
0x90020202, // 000D SETMBR R0 K1 R2
0x90020403, // 000E SETMBR R0 K2 R3
0x80000000, // 000F RET 0
})
)
);
/*******************************************************************/
/********************************************************************
** Solidified function: compute_ZV_prover
********************************************************************/
be_local_closure(SPAKE2P_Matter_compute_ZV_prover, /* name */
be_nested_proto(
11, /* nstack */
2, /* argc */
2, /* varg */
0, /* has upvals */
NULL, /* no upvals */
0, /* has sup protos */
NULL, /* no sub protos */
1, /* has constants */
( &(const bvalue[13]) { /* constants */
/* K0 */ be_nested_str_weak(crypto),
/* K1 */ be_nested_str_weak(EC_P256),
/* K2 */ be_nested_str_weak(pB),
/* K3 */ be_nested_str_weak(neg),
/* K4 */ be_nested_str_weak(w0),
/* K5 */ be_nested_str_weak(muladd),
/* K6 */ be_nested_str_weak(01),
/* K7 */ be_nested_str_weak(N),
/* K8 */ be_nested_str_weak(Z),
/* K9 */ be_nested_str_weak(mul),
/* K10 */ be_nested_str_weak(x),
/* K11 */ be_nested_str_weak(V),
/* K12 */ be_nested_str_weak(w1),
}),
be_str_weak(compute_ZV_prover),
&be_const_str_solidified,
( &(const binstruction[26]) { /* code */
0xA40A0000, // 0000 IMPORT R2 K0
0x8C0C0501, // 0001 GETMET R3 R2 K1
0x7C0C0200, // 0002 CALL R3 1
0x90020401, // 0003 SETMBR R0 K2 R1
0x8C100703, // 0004 GETMET R4 R3 K3
0x88180104, // 0005 GETMBR R6 R0 K4
0x7C100400, // 0006 CALL R4 2
0x8C140705, // 0007 GETMET R5 R3 K5
0x601C0015, // 0008 GETGBL R7 G21
0x58200006, // 0009 LDCONST R8 K6
0x7C1C0200, // 000A CALL R7 1
0x88200102, // 000B GETMBR R8 R0 K2
0x5C240800, // 000C MOVE R9 R4
0x88280107, // 000D GETMBR R10 R0 K7
0x7C140A00, // 000E CALL R5 5
0x8C180709, // 000F GETMET R6 R3 K9
0x8820010A, // 0010 GETMBR R8 R0 K10
0x5C240A00, // 0011 MOVE R9 R5
0x7C180600, // 0012 CALL R6 3
0x90021006, // 0013 SETMBR R0 K8 R6
0x8C180709, // 0014 GETMET R6 R3 K9
0x8820010C, // 0015 GETMBR R8 R0 K12
0x5C240A00, // 0016 MOVE R9 R5
0x7C180600, // 0017 CALL R6 3
0x90021606, // 0018 SETMBR R0 K11 R6
0x80000000, // 0019 RET 0
})
)
);
/*******************************************************************/
/********************************************************************
** Solidified function: init
********************************************************************/
be_local_closure(SPAKE_Hasher_init, /* name */
be_nested_proto(
4, /* nstack */
1, /* argc */
2, /* varg */
0, /* has upvals */
NULL, /* no upvals */
0, /* has sup protos */
NULL, /* no sub protos */
1, /* has constants */
( &(const bvalue[ 3]) { /* constants */
/* K0 */ be_nested_str_weak(crypto),
/* K1 */ be_nested_str_weak(hash),
/* K2 */ be_nested_str_weak(SHA256),
}),
be_str_weak(init),
&be_const_str_solidified,
( &(const binstruction[ 5]) { /* code */
0xA4060000, // 0000 IMPORT R1 K0
0x8C080302, // 0001 GETMET R2 R1 K2
0x7C080200, // 0002 CALL R2 1
0x90020202, // 0003 SETMBR R0 K1 R2
0x80000000, // 0004 RET 0
})
)
);
/*******************************************************************/
/********************************************************************
** Solidified function: add_item
********************************************************************/
be_local_closure(SPAKE_Hasher_add_item, /* name */
be_nested_proto(
7, /* nstack */
2, /* argc */
2, /* varg */
0, /* has upvals */
NULL, /* no upvals */
0, /* has sup protos */
NULL, /* no sub protos */
1, /* has constants */
( &(const bvalue[ 5]) { /* constants */
/* K0 */ be_nested_str_weak(size),
/* K1 */ be_nested_str_weak(add),
/* K2 */ be_const_int(0),
/* K3 */ be_nested_str_weak(hash),
/* K4 */ be_nested_str_weak(update),
}),
be_str_weak(add_item),
&be_const_str_solidified,
( &(const binstruction[21]) { /* code */
0x8C080300, // 0000 GETMET R2 R1 K0
0x7C080200, // 0001 CALL R2 1
0x600C0015, // 0002 GETGBL R3 G21
0x7C0C0000, // 0003 CALL R3 0
0x8C0C0701, // 0004 GETMET R3 R3 K1
0x5C140400, // 0005 MOVE R5 R2
0x541A0003, // 0006 LDINT R6 4
0x7C0C0600, // 0007 CALL R3 3
0x8C0C0701, // 0008 GETMET R3 R3 K1
0x58140002, // 0009 LDCONST R5 K2
0x541A0003, // 000A LDINT R6 4
0x7C0C0600, // 000B CALL R3 3
0x88100103, // 000C GETMBR R4 R0 K3
0x8C100904, // 000D GETMET R4 R4 K4
0x5C180600, // 000E MOVE R6 R3
0x7C100400, // 000F CALL R4 2
0x88100103, // 0010 GETMBR R4 R0 K3
0x8C100904, // 0011 GETMET R4 R4 K4
0x5C180200, // 0012 MOVE R6 R1
0x7C100400, // 0013 CALL R4 2
0x80000000, // 0014 RET 0
})
)
);
/*******************************************************************/
/********************************************************************
** Solidified function: out
********************************************************************/
be_local_closure(SPAKE_Hasher_out, /* name */
be_nested_proto(
3, /* nstack */
1, /* argc */
2, /* varg */
0, /* has upvals */
NULL, /* no upvals */
0, /* has sup protos */
NULL, /* no sub protos */
1, /* has constants */
( &(const bvalue[ 2]) { /* constants */
/* K0 */ be_nested_str_weak(hash),
/* K1 */ be_nested_str_weak(out),
}),
be_str_weak(out),
&be_const_str_solidified,
( &(const binstruction[ 4]) { /* code */
0x88040100, // 0000 GETMBR R1 R0 K0
0x8C040301, // 0001 GETMET R1 R1 K1
0x7C040200, // 0002 CALL R1 1
0x80040200, // 0003 RET 1 R1
})
)
);
/*******************************************************************/
/********************************************************************
** Solidified class: SPAKE_Hasher
********************************************************************/
be_local_class(SPAKE_Hasher,
1,
NULL,
be_nested_map(4,
( (struct bmapnode*) &(const bmapnode[]) {
{ be_const_key_weak(out, -1), be_const_closure(SPAKE_Hasher_out_closure) },
{ be_const_key_weak(hash, -1), be_const_var(0) },
{ be_const_key_weak(add_item, -1), be_const_closure(SPAKE_Hasher_add_item_closure) },
{ be_const_key_weak(init, 0), be_const_closure(SPAKE_Hasher_init_closure) },
})),
be_str_weak(SPAKE_Hasher)
);
/********************************************************************
** Solidified function: compute_TT_hash
********************************************************************/
be_local_closure(SPAKE2P_Matter_compute_TT_hash, /* name */
be_nested_proto(
13, /* nstack */
1, /* argc */
2, /* varg */
0, /* has upvals */
NULL, /* no upvals */
0, /* has sup protos */
NULL, /* no sub protos */
1, /* has constants */
( &(const bvalue[28]) { /* constants */
/* K0 */ be_const_class(be_class_SPAKE_Hasher),
/* K1 */ be_nested_str_weak(crypto),
/* K2 */ be_nested_str_weak(add_item),
/* K3 */ be_nested_str_weak(Context),
/* K4 */ be_nested_str_weak(A),
/* K5 */ be_nested_str_weak(B),
/* K6 */ be_nested_str_weak(M),
/* K7 */ be_nested_str_weak(N),
/* K8 */ be_nested_str_weak(pA),
/* K9 */ be_nested_str_weak(pB),
/* K10 */ be_nested_str_weak(Z),
/* K11 */ be_nested_str_weak(V),
/* K12 */ be_nested_str_weak(w0),
/* K13 */ be_nested_str_weak(Kmain),
/* K14 */ be_nested_str_weak(out),
/* K15 */ be_nested_str_weak(HKDF_SHA256),
/* K16 */ be_nested_str_weak(derive),
/* K17 */ be_nested_str_weak(fromstring),
/* K18 */ be_nested_str_weak(ConfirmationKeys),
/* K19 */ be_nested_str_weak(KcA),
/* K20 */ be_const_int(0),
/* K21 */ be_nested_str_weak(KcB),
/* K22 */ be_nested_str_weak(K_shared),
/* K23 */ be_nested_str_weak(SharedKey),
/* K24 */ be_nested_str_weak(cA),
/* K25 */ be_nested_str_weak(HMAC_SHA256),
/* K26 */ be_nested_str_weak(update),
/* K27 */ be_nested_str_weak(cB),
}),
be_str_weak(compute_TT_hash),
&be_const_str_solidified,
( &(const binstruction[91]) { /* code */
0x58040000, // 0000 LDCONST R1 K0
0xB4000000, // 0001 CLASS K0
0xA40A0200, // 0002 IMPORT R2 K1
0x5C0C0200, // 0003 MOVE R3 R1
0x7C0C0000, // 0004 CALL R3 0
0x8C100702, // 0005 GETMET R4 R3 K2
0x88180103, // 0006 GETMBR R6 R0 K3
0x7C100400, // 0007 CALL R4 2
0x8C100702, // 0008 GETMET R4 R3 K2
0x88180104, // 0009 GETMBR R6 R0 K4
0x7C100400, // 000A CALL R4 2
0x8C100702, // 000B GETMET R4 R3 K2
0x88180105, // 000C GETMBR R6 R0 K5
0x7C100400, // 000D CALL R4 2
0x8C100702, // 000E GETMET R4 R3 K2
0x88180106, // 000F GETMBR R6 R0 K6
0x7C100400, // 0010 CALL R4 2
0x8C100702, // 0011 GETMET R4 R3 K2
0x88180107, // 0012 GETMBR R6 R0 K7
0x7C100400, // 0013 CALL R4 2
0x8C100702, // 0014 GETMET R4 R3 K2
0x88180108, // 0015 GETMBR R6 R0 K8
0x7C100400, // 0016 CALL R4 2
0x8C100702, // 0017 GETMET R4 R3 K2
0x88180109, // 0018 GETMBR R6 R0 K9
0x7C100400, // 0019 CALL R4 2
0x8C100702, // 001A GETMET R4 R3 K2
0x8818010A, // 001B GETMBR R6 R0 K10
0x7C100400, // 001C CALL R4 2
0x8C100702, // 001D GETMET R4 R3 K2
0x8818010B, // 001E GETMBR R6 R0 K11
0x7C100400, // 001F CALL R4 2
0x8C100702, // 0020 GETMET R4 R3 K2
0x8818010C, // 0021 GETMBR R6 R0 K12
0x7C100400, // 0022 CALL R4 2
0x8C10070E, // 0023 GETMET R4 R3 K14
0x7C100200, // 0024 CALL R4 1
0x90021A04, // 0025 SETMBR R0 K13 R4
0x8C10050F, // 0026 GETMET R4 R2 K15
0x7C100200, // 0027 CALL R4 1
0x8C140910, // 0028 GETMET R5 R4 K16
0x881C010D, // 0029 GETMBR R7 R0 K13
0x60200015, // 002A GETGBL R8 G21
0x7C200000, // 002B CALL R8 0
0x60240015, // 002C GETGBL R9 G21
0x7C240000, // 002D CALL R9 0
0x8C241311, // 002E GETMET R9 R9 K17
0x582C0012, // 002F LDCONST R11 K18
0x7C240400, // 0030 CALL R9 2
0x542A003F, // 0031 LDINT R10 64
0x7C140A00, // 0032 CALL R5 5
0x541A001E, // 0033 LDINT R6 31
0x401A2806, // 0034 CONNECT R6 K20 R6
0x94180A06, // 0035 GETIDX R6 R5 R6
0x90022606, // 0036 SETMBR R0 K19 R6
0x541A001F, // 0037 LDINT R6 32
0x541E003E, // 0038 LDINT R7 63
0x40180C07, // 0039 CONNECT R6 R6 R7
0x94180A06, // 003A GETIDX R6 R5 R6
0x90022A06, // 003B SETMBR R0 K21 R6
0x8C180910, // 003C GETMET R6 R4 K16
0x8820010D, // 003D GETMBR R8 R0 K13
0x60240015, // 003E GETGBL R9 G21
0x7C240000, // 003F CALL R9 0
0x60280015, // 0040 GETGBL R10 G21
0x7C280000, // 0041 CALL R10 0
0x8C281511, // 0042 GETMET R10 R10 K17
0x58300017, // 0043 LDCONST R12 K23
0x7C280400, // 0044 CALL R10 2
0x542E001F, // 0045 LDINT R11 32
0x7C180A00, // 0046 CALL R6 5
0x90022C06, // 0047 SETMBR R0 K22 R6
0x8C180519, // 0048 GETMET R6 R2 K25
0x88200113, // 0049 GETMBR R8 R0 K19
0x7C180400, // 004A CALL R6 2
0x8C180D1A, // 004B GETMET R6 R6 K26
0x88200109, // 004C GETMBR R8 R0 K9
0x7C180400, // 004D CALL R6 2
0x8C180D0E, // 004E GETMET R6 R6 K14
0x7C180200, // 004F CALL R6 1
0x90023006, // 0050 SETMBR R0 K24 R6
0x8C180519, // 0051 GETMET R6 R2 K25
0x88200115, // 0052 GETMBR R8 R0 K21
0x7C180400, // 0053 CALL R6 2
0x8C180D1A, // 0054 GETMET R6 R6 K26
0x88200108, // 0055 GETMBR R8 R0 K8
0x7C180400, // 0056 CALL R6 2
0x8C180D0E, // 0057 GETMET R6 R6 K14
0x7C180200, // 0058 CALL R6 1
0x90023606, // 0059 SETMBR R0 K27 R6
0x80000000, // 005A RET 0
})
)
);
/*******************************************************************/
/********************************************************************
** Solidified function: compute_pA
********************************************************************/
be_local_closure(SPAKE2P_Matter_compute_pA, /* name */
be_nested_proto(
10, /* nstack */
2, /* argc */
2, /* varg */
0, /* has upvals */
NULL, /* no upvals */
0, /* has sup protos */
NULL, /* no sub protos */
1, /* has constants */
( &(const bvalue[ 9]) { /* constants */
/* K0 */ be_nested_str_weak(crypto),
/* K1 */ be_nested_str_weak(random),
/* K2 */ be_nested_str_weak(EC_P256),
/* K3 */ be_nested_str_weak(x),
/* K4 */ be_nested_str_weak(mod),
/* K5 */ be_nested_str_weak(pA),
/* K6 */ be_nested_str_weak(muladd),
/* K7 */ be_nested_str_weak(w0),
/* K8 */ be_nested_str_weak(M),
}),
be_str_weak(compute_pA),
&be_const_str_solidified,
( &(const binstruction[23]) { /* code */
0xA40A0000, // 0000 IMPORT R2 K0
0x4C0C0000, // 0001 LDNIL R3
0x1C0C0203, // 0002 EQ R3 R1 R3
0x780E0003, // 0003 JMPF R3 #0008
0x8C0C0501, // 0004 GETMET R3 R2 K1
0x5416001F, // 0005 LDINT R5 32
0x7C0C0400, // 0006 CALL R3 2
0x5C040600, // 0007 MOVE R1 R3
0x8C0C0502, // 0008 GETMET R3 R2 K2
0x7C0C0200, // 0009 CALL R3 1
0x8C100704, // 000A GETMET R4 R3 K4
0x5C180200, // 000B MOVE R6 R1
0x7C100400, // 000C CALL R4 2
0x90020604, // 000D SETMBR R0 K3 R4
0x8C100706, // 000E GETMET R4 R3 K6
0x88180107, // 000F GETMBR R6 R0 K7
0x881C0108, // 0010 GETMBR R7 R0 K8
0x88200103, // 0011 GETMBR R8 R0 K3
0x60240015, // 0012 GETGBL R9 G21
0x7C240000, // 0013 CALL R9 0
0x7C100A00, // 0014 CALL R4 5
0x90020A04, // 0015 SETMBR R0 K5 R4
0x80000000, // 0016 RET 0
})
)
);
/*******************************************************************/
/********************************************************************
** Solidified function: init
********************************************************************/
be_local_closure(SPAKE2P_Matter_init, /* name */
be_nested_proto(
7, /* nstack */
4, /* argc */
2, /* varg */
0, /* has upvals */
NULL, /* no upvals */
0, /* has sup protos */
NULL, /* no sub protos */
1, /* has constants */
( &(const bvalue[ 8]) { /* constants */
/* K0 */ be_nested_str_weak(M),
/* K1 */ be_nested_str_weak(fromhex),
/* K2 */ be_nested_str_weak(spake_M_hex),
/* K3 */ be_nested_str_weak(N),
/* K4 */ be_nested_str_weak(spake_N_hex),
/* K5 */ be_nested_str_weak(w0),
/* K6 */ be_nested_str_weak(w1),
/* K7 */ be_nested_str_weak(L),
}),
be_str_weak(init),
&be_const_str_solidified,
( &(const binstruction[16]) { /* code */
0x60100015, // 0000 GETGBL R4 G21
0x7C100000, // 0001 CALL R4 0
0x8C100901, // 0002 GETMET R4 R4 K1
0x88180102, // 0003 GETMBR R6 R0 K2
0x7C100400, // 0004 CALL R4 2
0x90020004, // 0005 SETMBR R0 K0 R4
0x60100015, // 0006 GETGBL R4 G21
0x7C100000, // 0007 CALL R4 0
0x8C100901, // 0008 GETMET R4 R4 K1
0x88180104, // 0009 GETMBR R6 R0 K4
0x7C100400, // 000A CALL R4 2
0x90020604, // 000B SETMBR R0 K3 R4
0x90020A01, // 000C SETMBR R0 K5 R1
0x90020C02, // 000D SETMBR R0 K6 R2
0x90020E03, // 000E SETMBR R0 K7 R3
0x80000000, // 000F RET 0
})
)
);
/*******************************************************************/
/********************************************************************
** Solidified function: compute_ZV_verifier
********************************************************************/
be_local_closure(SPAKE2P_Matter_compute_ZV_verifier, /* name */
be_nested_proto(
11, /* nstack */
2, /* argc */
2, /* varg */
0, /* has upvals */
NULL, /* no upvals */
0, /* has sup protos */
NULL, /* no sub protos */
1, /* has constants */
( &(const bvalue[13]) { /* constants */
/* K0 */ be_nested_str_weak(crypto),
/* K1 */ be_nested_str_weak(EC_P256),
/* K2 */ be_nested_str_weak(pA),
/* K3 */ be_nested_str_weak(neg),
/* K4 */ be_nested_str_weak(w0),
/* K5 */ be_nested_str_weak(muladd),
/* K6 */ be_nested_str_weak(01),
/* K7 */ be_nested_str_weak(M),
/* K8 */ be_nested_str_weak(Z),
/* K9 */ be_nested_str_weak(mul),
/* K10 */ be_nested_str_weak(y),
/* K11 */ be_nested_str_weak(V),
/* K12 */ be_nested_str_weak(L),
}),
be_str_weak(compute_ZV_verifier),
&be_const_str_solidified,
( &(const binstruction[26]) { /* code */
0xA40A0000, // 0000 IMPORT R2 K0
0x8C0C0501, // 0001 GETMET R3 R2 K1
0x7C0C0200, // 0002 CALL R3 1
0x90020401, // 0003 SETMBR R0 K2 R1
0x8C100703, // 0004 GETMET R4 R3 K3
0x88180104, // 0005 GETMBR R6 R0 K4
0x7C100400, // 0006 CALL R4 2
0x8C140705, // 0007 GETMET R5 R3 K5
0x601C0015, // 0008 GETGBL R7 G21
0x58200006, // 0009 LDCONST R8 K6
0x7C1C0200, // 000A CALL R7 1
0x88200102, // 000B GETMBR R8 R0 K2
0x5C240800, // 000C MOVE R9 R4
0x88280107, // 000D GETMBR R10 R0 K7
0x7C140A00, // 000E CALL R5 5
0x8C180709, // 000F GETMET R6 R3 K9
0x8820010A, // 0010 GETMBR R8 R0 K10
0x5C240A00, // 0011 MOVE R9 R5
0x7C180600, // 0012 CALL R6 3
0x90021006, // 0013 SETMBR R0 K8 R6
0x8C180709, // 0014 GETMET R6 R3 K9
0x8820010A, // 0015 GETMBR R8 R0 K10
0x8824010C, // 0016 GETMBR R9 R0 K12
0x7C180600, // 0017 CALL R6 3
0x90021606, // 0018 SETMBR R0 K11 R6
0x80000000, // 0019 RET 0
})
)
);
/*******************************************************************/
/********************************************************************
** Solidified function: compute_pB
********************************************************************/
be_local_closure(SPAKE2P_Matter_compute_pB, /* name */
be_nested_proto(
10, /* nstack */
2, /* argc */
2, /* varg */
0, /* has upvals */
NULL, /* no upvals */
0, /* has sup protos */
NULL, /* no sub protos */
1, /* has constants */
( &(const bvalue[ 9]) { /* constants */
/* K0 */ be_nested_str_weak(crypto),
/* K1 */ be_nested_str_weak(random),
/* K2 */ be_nested_str_weak(EC_P256),
/* K3 */ be_nested_str_weak(y),
/* K4 */ be_nested_str_weak(mod),
/* K5 */ be_nested_str_weak(pB),
/* K6 */ be_nested_str_weak(muladd),
/* K7 */ be_nested_str_weak(w0),
/* K8 */ be_nested_str_weak(N),
}),
be_str_weak(compute_pB),
&be_const_str_solidified,
( &(const binstruction[23]) { /* code */
0xA40A0000, // 0000 IMPORT R2 K0
0x4C0C0000, // 0001 LDNIL R3
0x1C0C0203, // 0002 EQ R3 R1 R3
0x780E0003, // 0003 JMPF R3 #0008
0x8C0C0501, // 0004 GETMET R3 R2 K1
0x5416001F, // 0005 LDINT R5 32
0x7C0C0400, // 0006 CALL R3 2
0x5C040600, // 0007 MOVE R1 R3
0x8C0C0502, // 0008 GETMET R3 R2 K2
0x7C0C0200, // 0009 CALL R3 1
0x8C100704, // 000A GETMET R4 R3 K4
0x5C180200, // 000B MOVE R6 R1
0x7C100400, // 000C CALL R4 2
0x90020604, // 000D SETMBR R0 K3 R4
0x8C100706, // 000E GETMET R4 R3 K6
0x88180107, // 000F GETMBR R6 R0 K7
0x881C0108, // 0010 GETMBR R7 R0 K8
0x88200103, // 0011 GETMBR R8 R0 K3
0x60240015, // 0012 GETGBL R9 G21
0x7C240000, // 0013 CALL R9 0
0x7C100A00, // 0014 CALL R4 5
0x90020A04, // 0015 SETMBR R0 K5 R4
0x80000000, // 0016 RET 0
})
)
);
/*******************************************************************/
/********************************************************************
** Solidified class: SPAKE2P_Matter
********************************************************************/
be_local_class(SPAKE2P_Matter,
20,
NULL,
be_nested_map(31,
( (struct bmapnode*) &(const bmapnode[]) {
{ be_const_key_weak(pA, 23), be_const_var(3) },
{ be_const_key_weak(set_context, 28), be_const_closure(SPAKE2P_Matter_set_context_closure) },
{ be_const_key_weak(KcA, -1), be_const_var(10) },
{ be_const_key_weak(cA, -1), be_const_var(13) },
{ be_const_key_weak(K_shared, -1), be_const_var(12) },
{ be_const_key_weak(A, 9), be_const_var(15) },
{ be_const_key_weak(V, -1), be_const_var(6) },
{ be_const_key_weak(compute_TT_hash, -1), be_const_closure(SPAKE2P_Matter_compute_TT_hash_closure) },
{ be_const_key_weak(Kmain, -1), be_const_var(9) },
{ be_const_key_weak(w0, -1), be_const_var(0) },
{ be_const_key_weak(N, -1), be_const_var(19) },
{ be_const_key_weak(x, -1), be_const_var(7) },
{ be_const_key_weak(Context, 20), be_const_var(17) },
{ be_const_key_weak(compute_pA, -1), be_const_closure(SPAKE2P_Matter_compute_pA_closure) },
{ be_const_key_weak(w1, -1), be_const_var(1) },
{ be_const_key_weak(B, 22), be_const_var(16) },
{ be_const_key_weak(L, 25), be_const_var(2) },
{ be_const_key_weak(cB, 10), be_const_var(14) },
{ be_const_key_weak(spake_M_hex, -1), be_nested_str_weak(04886e2f97ace46e55ba9dd7242579f2993b64e16ef3dcab95afd497333d8fa12f5ff355163e43ce224e0b0e65ff02ac8e5c7be09419c785e0ca547d55a12e2d20) },
{ be_const_key_weak(spake_N_hex, -1), be_nested_str_weak(04d8bbd6c639c62937b04d997f38c3770719c629d7014d49a24b4f98baa1292b4907d60aa6bfade45008a636337f5168c64d9bd36034808cd564490b1e656edbe7) },
{ be_const_key_weak(CRYPTO_GROUP_SIZE_BYTES, 7), be_const_int(32) },
{ be_const_key_weak(CRYPTO_W_SIZE_BYTES, 6), be_const_int(40) },
{ be_const_key_weak(pB, 8), be_const_var(4) },
{ be_const_key_weak(M, -1), be_const_var(18) },
{ be_const_key_weak(compute_ZV_verifier, -1), be_const_closure(SPAKE2P_Matter_compute_ZV_verifier_closure) },
{ be_const_key_weak(KcB, 19), be_const_var(11) },
{ be_const_key_weak(y, -1), be_const_var(8) },
{ be_const_key_weak(Z, -1), be_const_var(5) },
{ be_const_key_weak(compute_ZV_prover, 2), be_const_closure(SPAKE2P_Matter_compute_ZV_prover_closure) },
{ be_const_key_weak(init, 5), be_const_closure(SPAKE2P_Matter_init_closure) },
{ be_const_key_weak(compute_pB, -1), be_const_closure(SPAKE2P_Matter_compute_pB_closure) },
})),
be_str_weak(SPAKE2P_Matter)
);
/*******************************************************************/
void be_load_SPAKE2P_Matter_class(bvm *vm) {
be_pushntvclass(vm, &be_class_SPAKE2P_Matter);
be_setglobal(vm, "SPAKE2P_Matter");
be_pop(vm, 1);
}
/********************************************************************/
/* End of solidification */

View File

@ -1113,6 +1113,7 @@
#define USE_BERRY_CRYPTO_HMAC_SHA256 // enable HMAC SHA256 hash function
// #define USE_BERRY_CRYPTO_PBKDF2_HMAC_SHA256 // PBKDF2 with HMAC SHA256, used in Matter protocol
// #define USE_BERRY_CRYPTO_HKDF_SHA256 // HKDF with HMAC SHA256, used in Matter protocol
// #define USE_BERRY_CRYPTO_SPAKE2P_MATTER // SPAKE2+ used in Matter 1.0, complete name is SPAKE2+-P256-SHA256-HKDF-SHA256-HMAC-SHA256
#define USE_CSE7761 // Add support for CSE7761 Energy monitor as used in Sonoff Dual R3
// -- LVGL Graphics Library ---------------------------------