WIP: returning from secp rectification on master and preparing for

rebase and merge.
This commit is contained in:
Paul Driver 2020-09-24 10:57:04 -07:00
parent f5449204e1
commit 7870add409
9 changed files with 241 additions and 39 deletions

View File

@ -619,7 +619,6 @@ main(c3_i argc,
if ( c3y == u3_Host.ops_u.tex ) {
u3_Host.bot_f = _stop_on_boot_completed_cb;
}
#if 0
if ( 0 == getuid() ) {
chroot(u3_Host.dir_c);
@ -748,12 +747,17 @@ main(c3_i argc,
}
}
/* FIXME
// Initialize OpenSSL for client and server
//
{
SSL_library_init();
SSL_load_error_strings();
}
*/
// openssl won't init after this libcurl call, probably because it links
// against openssl and does allocations with it.
// initialize curl
//

View File

@ -14,6 +14,10 @@
c3_d
u3m_boot_lite(void);
/* u3m_stop(): graceful shutdown cleanup. */
void
u3m_stop(void);
/* u3m_bail(): bail out. Does not return.
**
** Bail motes:

View File

@ -8,7 +8,7 @@
*/
static c3_t
_cqear_unpack_type(urcrypt_argon2_type *out, u3_atom in)
_cqear_unpack_type(c3_y* out, u3_atom in)
{
switch ( in ) {
default:
@ -39,7 +39,7 @@
// input params
u3_atom wid, u3_atom dat, u3_atom wis, u3_atom sat )
{
urcrypt_argon2_type typ_u;
c3_y typ_u;
c3_w out_w, wik_w, wix_w, wid_w, wis_w, ver_w, ted_w, mem_w, tim_w;
if ( !(u3r_word_fit(&out_w, out) &&

View File

@ -32,6 +32,9 @@ _cqe_is_8(const c3_w words[8], u3_noun non)
* +secp256k1 passes these constants to it. This should be restructured so
* that the constants are matched as part of the batteries in the core stack
* of the jetted gates.
*
* The hoon also doesn't, in general, check the size of any of its arguments;
* we return u3_none when they are mis-sized.
*/
static c3_t
_cqe_256k1_veri(u3_noun cor)
@ -211,6 +214,28 @@ u3we_reco(u3_noun cor)
}
}
static u3_noun
_cqe_reco(u3_atom has,
u3_atom siv, /* signature: v */
u3_atom sir, /* signature: r */
u3_atom sis) /* signature: s */
{
c3_y has_y[32], sir_y[32], sis_y[32], x_y[32], y_y[32];
if ( !((siv < 4) &&
u3r_bytes_fit(32, has_y, has) &&
u3r_bytes_fit(32, sir_y, sir) &&
u3r_bytes_fit(32, sis_y, sis) &&
(0 == urcrypt_secp_reco(has_y, (c3_y) siv, sir_y, sis_y, x_y, y_y))) )
{
return u3_none;
}
else {
return u3nc(u3i_bytes(32, x_y),
u3i_bytes(32, y_y));
}
}
u3_noun
u3qe_reco(u3_atom has,
u3_atom siv, /* signature: v */
@ -318,15 +343,11 @@ _cqe_make(u3_atom has,
{
c3_y has_y[32], prv_y[32], out_y[32];
if ( ( u3r_met(3, has) > 32 ) ||
( u3r_met(3, prv) > 32 ) ) {
// hoon doesn't check size
if ( !(u3r_bytes_fit(32, has_y, has) &&
u3r_bytes_fit(32, prv_y, prv)) ) {
return u3_none;
}
else {
u3r_bytes(0, 32, has_y, has);
u3r_bytes(0, 32, prv_y, prv);
return ( 0 == urcrypt_secp_make(has_y, prv_y, out_y) )
? u3i_bytes(32, out_y)
: u3_none;

View File

@ -1,6 +1,7 @@
/* n/m.c
**
*/
#include <ent.h>
#include <errno.h>
#include <fcntl.h>
#include <sys/stat.h>
@ -1601,6 +1602,41 @@ _cm_signals(void)
}
}
static void
_cm_crypto_init()
{
/* Initialize OpenSSL with loom allocation functions.
* IMPORTANT: this should come before the urcrypt_set_openssl [...]
* call, because in usual circumstances that will override the functions
* we set here, but weird linking situations we don't currently encounter
* could mean we need to set both, and it doesn't hurt.
*/
if ( 0 == CRYPTO_set_mem_functions(&u3a_malloc_ssl,
&u3a_realloc_ssl,
&u3a_free_ssl) ) {
u3l_log("%s\r\n", "openssl initialization failed");
exit(1);
}
/* Initialize cryptography suite */
if ( 0 != urcrypt_set_openssl_mem_functions(&u3a_malloc,
&u3a_realloc,
&u3a_free) ) {
u3l_log("%s\r\n", "urcrypt-openssl initialization failed");
exit(1);
}
{
c3_y ent_y[32];
ent_getentropy(ent_y, 32);
if ( 0 != urcrypt_secp_init(ent_y) ) {
u3l_log("%s\r\n", "urcrypt-secp initialization failed");
exit(1);
}
}
}
/* u3m_init(): start the environment.
*/
void
@ -1608,6 +1644,7 @@ u3m_init(void)
{
_cm_limits();
_cm_signals();
_cm_crypto_init();
/* Make sure GMP uses our malloc.
*/
@ -1646,6 +1683,13 @@ u3m_init(void)
}
}
/* u3m_stop(): graceful shutdown cleanup. */
void
u3m_stop()
{
urcrypt_secp_cleanup();
}
/* u3m_boot(): start the u3 system. return next event, starting from 1.
*/
c3_d
@ -1657,28 +1701,6 @@ u3m_boot(c3_c* dir_c)
*/
u3m_init();
/* Initialize OpenSSL with loom allocation functions.
* IMPORTANT: this should come before the urcrypt_set_openssl [...]
* call, because in usual circumstances that will override the functions
* we set here, but weird linking situations we don't currently encounter
* could mean we need to set both, and it doesn't hurt.
*/
if ( 0 == CRYPTO_set_mem_functions(&u3a_malloc_ssl,
&u3a_realloc_ssl,
&u3a_free_ssl) ) {
u3l_log("%s\r\n", "openssl initialization failed");
exit(1);
}
/* Initialize cryptography suite with loom allocation functions.
*/
if ( 0 != urcrypt_set_openssl_mem_functions(&u3a_malloc,
&u3a_realloc,
&u3a_free) ) {
u3l_log("%s\r\n", "urcrypt initialization failed");
exit(1);
}
/* Activate the storage system.
*/
nuu_o = u3e_live(c3n, dir_c);

View File

@ -710,6 +710,11 @@ u3_king_commence()
u3C.wag_w |= u3o_hashless;
u3m_boot_lite();
{
#include <openssl/ssl.h>
SSL_library_init();
SSL_load_error_strings();
}
// wire up signal controls
//
@ -761,6 +766,7 @@ u3_king_commence()
_king_loop_init();
uv_run(u3L, UV_RUN_DEFAULT);
_king_loop_exit();
u3m_stop();
}
/* u3_king_stub(): get the One Pier for unreconstructed code.

View File

@ -213,6 +213,7 @@ _cw_serf_commence(c3_i argc, c3_c* argv[])
// enter loop
//
uv_run(lup_u, UV_RUN_DEFAULT);
u3m_stop();
}
/* _cw_info(); print pier info
@ -226,6 +227,7 @@ _cw_info(c3_i argc, c3_c* argv[])
c3_d eve_d = u3m_boot(dir_c);
fprintf(stderr, "urbit-worker: %s at event %" PRIu64 "\r\n", dir_c, eve_d);
u3m_stop();
}
/* _cw_grab(); gc pier.
@ -238,6 +240,7 @@ _cw_grab(c3_i argc, c3_c* argv[])
c3_c* dir_c = argv[2];
u3m_boot(dir_c);
u3_serf_grab();
u3m_stop();
}
/* _cw_cram(); jam persistent state (rock), and exit.
@ -258,6 +261,7 @@ _cw_cram(c3_i argc, c3_c* argv[])
}
fprintf(stderr, "urbit-worker: cram: rock saved at event %" PRIu64 "\r\n", eve_d);
u3m_stop();
}
/* _cw_queu(); cue rock, save, and exit.
@ -285,6 +289,7 @@ _cw_queu(c3_i argc, c3_c* argv[])
u3e_save();
fprintf(stderr, "urbit-worker: queu: rock loaded at event %" PRIu64 "\r\n", eve_d);
u3m_stop();
}
}
@ -301,6 +306,7 @@ _cw_pack(c3_i argc, c3_c* argv[])
u3a_print_memory(stderr, "urbit-worker: pack: gained", u3m_pack());
u3e_save();
u3m_stop();
}
/* _cw_usage(): print urbit-worker usage.

View File

@ -807,7 +807,7 @@ _urcrypt_argon2_free(uint8_t* memory, size_t bytes)
#define SZ_32(s) ( sizeof(size_t) <= sizeof(uint32_t) || s <= 0xFFFFFFFF )
const char*
urcrypt_argon2(urcrypt_argon2_type type,
urcrypt_argon2(uint8_t type,
uint32_t version,
uint32_t threads,
uint32_t memory_cost,
@ -920,6 +920,37 @@ urcrypt_blake2(size_t message_length,
}
}
static secp256k1_context* _urcrypt_secp_ctx = NULL;
int
urcrypt_secp_init(uint8_t entropy[32])
{
if ( NULL != _urcrypt_secp_ctx ) {
return -1;
}
else {
_urcrypt_secp_ctx = secp256k1_context_create(
SECP256K1_CONTEXT_VERIFY | SECP256K1_CONTEXT_SIGN);
if ( 1 == secp256k1_context_randomize(_urcrypt_secp_ctx, entropy) ) {
return 0;
}
else {
secp256k1_context_destroy(_urcrypt_secp_ctx);
_urcrypt_secp_ctx = NULL;
return -2;
}
}
}
void
urcrypt_secp_cleanup(void)
{
if ( NULL != _urcrypt_secp_ctx) {
secp256k1_context_destroy(_urcrypt_secp_ctx);
_urcrypt_secp_ctx = NULL;
}
}
int
urcrypt_secp_make(uint8_t hash[32], uint8_t key[32], uint8_t out[32])
{
@ -940,3 +971,88 @@ urcrypt_secp_make(uint8_t hash[32], uint8_t key[32], uint8_t out[32])
return 0;
}
}
int
urcrypt_secp_reco(uint8_t hash[32],
uint8_t key_v,
const uint8_t key_r[32],
const uint8_t key_s[32],
uint8_t out_x[32],
uint8_t out_y[32])
{
if ( (NULL == _urcrypt_secp_ctx) ||
(NULL == hash) ||
(NULL == key_r) ||
(NULL == key_s) ) {
return -1;
}
else if ( key_v > 3 ) {
return -2;
}
else {
secp256k1_ecdsa_recoverable_signature signature;
uint8_t private[64];
size_t i, j;
// make big private key out of two smaller parts, reversing endianness
for ( j = 31, i = 0; i < 32; ++i, --j) {
private[i] = key_r[j];
}
for ( j = 31; i < 64; ++i, --j ) {
private[i] = key_s[j];
}
memset(&signature, 0, sizeof(secp256k1_ecdsa_recoverable_signature));
if ( 1 != secp256k1_ecdsa_recoverable_signature_parse_compact(
_urcrypt_secp_ctx, /* IN: context */
&signature, /* OUT: sig */
private, /* IN: r/s */
key_v) ) { /* IN: v */
return -3;
}
else {
secp256k1_pubkey public;
memset(&public, 0, sizeof(secp256k1_pubkey));
// the code we ported from looks like it intended to reverse hash
// at some point, but doesn't actually.
if ( 1 != secp256k1_ecdsa_recover(
_urcrypt_secp_ctx, /* IN: context */
&public, /* OUT: pub key */
&signature, /* IN: signature */
hash) ) { /* IN: message hash */
return -4;
}
else {
/* convert pub into serialized form that we can get x, y out of */
uint8_t serialized[65];
size_t outputlen = 65;
memset(serialized, 0, outputlen);
if ( 1 != secp256k1_ec_pubkey_serialize(
_urcrypt_secp_ctx, /* IN: context */
serialized, /* OUT: output */
&outputlen, /* IN/OUT: outputlen */
&public, /* IN: pubkey*/
SECP256K1_EC_UNCOMPRESSED) ) { /* IN: flags */
return -5;
}
else {
/* in file
subprojects/secp256k1/src/eckey_impl.h
func
secp256k1_eckey_pubkey_parse()
we can see
byte 0: signal bits (???)
bytes 1-32: x
bytes 33-64: y
convert endianness while we're at it */
for (j = 32, i = 0; i < 32; ++i, --j) {
out_x[i] = serialized[j];
}
for (j = 64, i = 0; i < 32; ++i, --j) {
out_y[i] = serialized[j];
}
return 0;
}
}
}
}
}

View File

@ -158,15 +158,13 @@ void urcrypt_shas(uint8_t *salt, size_t salt_length,
const uint8_t *message, size_t message_length,
uint8_t out[32]);
typedef enum urcrypt_argon2_type {
urcrypt_argon2_d = 0,
urcrypt_argon2_i = 1,
urcrypt_argon2_id = 2,
urcrypt_argon2_u = 10,
} urcrypt_argon2_type;
#define urcrypt_argon2_d 0
#define urcrypt_argon2_i 1
#define urcrypt_argon2_id 2
#define urcrypt_argon2_u 10
/* returns a constant error message string or NULL for success */
const char* urcrypt_argon2(urcrypt_argon2_type type,
const char* urcrypt_argon2(uint8_t type, // one of the urcrpyt_argon2_*
uint32_t version,
uint32_t threads,
uint32_t memory_cost,
@ -191,6 +189,31 @@ int urcrypt_blake2(size_t message_length,
size_t out_length,
uint8_t *out);
/* there is some long-term context associated with the secp library
* (precomputed tables, etc). Because the context itself is thread-safe,
* we have opted to manage it statically and present a simple calling
* interface that doesn't mention it.
*/
/* initialize static secp context (not thread-safe). Recommmendation:
* call this once at main thread startup before calling other secp functions.
* Use a high quality source of entropy.
*/
int urcrypt_secp_init(uint8_t entropy[32]);
/* restore initial secp context conditons (not thread-safe). Recommendation:
* call this just before that main thread exits to make valgrind etc. happy
*/
void urcrypt_secp_cleanup(void);
// technically usable without the secp context
int urcrypt_secp_make(uint8_t hash[32], uint8_t key[32], uint8_t out[32]);
int urcrypt_secp_reco(uint8_t hash[32],
uint8_t key_v, // 0, 1, 2, 3
const uint8_t key_r[32],
const uint8_t key_s[32],
uint8_t out_x[32],
uint8_t out_y[32]);
#endif