From 460bc7525b7ca623dea8980eea76ef313d0c4403 Mon Sep 17 00:00:00 2001 From: evoskuil Date: Wed, 18 May 2016 23:51:18 -0700 Subject: [PATCH] Problem: no function to derive curve public key from secret key. --- include/zmq.h | 6 +++++- src/tweetnacl.h | 1 + src/zmq_utils.cpp | 37 ++++++++++++++++++++++++++++++++++++- 3 files changed, 42 insertions(+), 2 deletions(-) diff --git a/include/zmq.h b/include/zmq.h index f6eec923..06e456bc 100644 --- a/include/zmq.h +++ b/include/zmq.h @@ -465,10 +465,14 @@ ZMQ_EXPORT char *zmq_z85_encode (char *dest, const uint8_t *data, size_t size); /* Decode data with Z85 encoding. Returns decoded data */ ZMQ_EXPORT uint8_t *zmq_z85_decode (uint8_t *dest, const char *string); -/* Generate z85-encoded public and private keypair with libsodium. */ +/* Generate z85-encoded public and private keypair with tweetnacl/libsodium. */ /* Returns 0 on success. */ ZMQ_EXPORT int zmq_curve_keypair (char *z85_public_key, char *z85_secret_key); +/* Derive the z85-encoded public key from the z85-encoded secret key. */ +/* Returns 0 on success. */ +ZMQ_EXPORT int zmq_curve_public (char *z85_public_key, const char *z85_secret_key); + /******************************************************************************/ /* Atomic utility methods */ /******************************************************************************/ diff --git a/src/tweetnacl.h b/src/tweetnacl.h index a49264ba..eedcc999 100644 --- a/src/tweetnacl.h +++ b/src/tweetnacl.h @@ -60,6 +60,7 @@ int crypto_box_open_afternm(u8 *m,const u8 *c,u64 d,const u8 *n,const u8 *k); int crypto_box(u8 *c,const u8 *m,u64 d,const u8 *n,const u8 *y,const u8 *x); int crypto_box_open(u8 *m,const u8 *c,u64 d,const u8 *n,const u8 *y,const u8 *x); int crypto_box_beforenm(u8 *k,const u8 *y,const u8 *x); +int crypto_scalarmult_base(u8 *q,const u8 *n); int crypto_secretbox(u8 *c,const u8 *m,u64 d,const u8 *n,const u8 *k); int crypto_secretbox_open(u8 *m,const u8 *c,u64 d,const u8 *n,const u8 *k); #ifdef __cplusplus diff --git a/src/zmq_utils.cpp b/src/zmq_utils.cpp index 12fda15c..adcdd19b 100644 --- a/src/zmq_utils.cpp +++ b/src/zmq_utils.cpp @@ -197,7 +197,7 @@ int zmq_curve_keypair (char *z85_public_key, char *z85_secret_key) uint8_t secret_key [32]; int rc = crypto_box_keypair (public_key, secret_key); - // Is there a sensible errno to set here? + // Is there a sensible errno to set here (no, it cannot fail)? if (rc) return rc; @@ -212,6 +212,41 @@ int zmq_curve_keypair (char *z85_public_key, char *z85_secret_key) #endif } +// -------------------------------------------------------------------------- +// Derive the public key from a private key using tweetnacl or libsodium. +// Derived key will be 40 byte z85-encoded string. +// Returns 0 on success, -1 on failure, setting errno. +// Sets errno = ENOTSUP in the absence of a CURVE library. + +int zmq_curve_public (char *z85_public_key, const char *z85_secret_key) +{ +#if defined (ZMQ_HAVE_CURVE) +# if crypto_box_PUBLICKEYBYTES != 32 \ + || crypto_box_SECRETKEYBYTES != 32 +# error "CURVE encryption library not built correctly" +# endif + + uint8_t public_key[32]; + uint8_t secret_key[32]; + + if (zmq_z85_decode (secret_key, z85_secret_key) == NULL) + return -1; + + int rc = crypto_scalarmult_base (public_key, secret_key); + // Is there a sensible errno to set here (no, it cannot fail)? + if (rc) + return rc; + + zmq_z85_encode (z85_public_key, public_key, 32); + + return 0; +#else + (void) z85_public_key, (void) z85_secret_key; + errno = ENOTSUP; + return -1; +#endif +} + // -------------------------------------------------------------------------- // Initialize a new atomic counter, which is set to zero