From 4b289c3021a9cf5b7b62205c5b90e15eb7d20022 Mon Sep 17 00:00:00 2001 From: Levi Neely <141506390+lneely@users.noreply.github.com> Date: Tue, 4 Mar 2025 10:31:10 +0100 Subject: [PATCH] remove ssl compatibility junk, rely on mbedtls for hw accel --- control_tools.cpp | 10 +- pclsync/pcommands.h | 8 + pclsync/pcryptofolder.c | 22 +- pclsync/pcryptofolder.h | 10 +- pclsync/pssl.c | 605 ++++++++++++---------------------------- pclsync/pssl.h | 244 +++------------- pclsync/pstatus.h | 8 + pclsync_lib.cpp | 62 ++-- 8 files changed, 299 insertions(+), 670 deletions(-) create mode 100644 pclsync/pcommands.h diff --git a/control_tools.cpp b/control_tools.cpp index 4113afd..1a2290a 100644 --- a/control_tools.cpp +++ b/control_tools.cpp @@ -43,6 +43,7 @@ #include "pclsync/pshm.h" #include "pclsync/pfoldersync.h" #include "pclsync/rpcclient.h" +#include "pclsync/pcommands.h" #include "CLI11.hpp" @@ -52,15 +53,6 @@ namespace control_tools { static const int STOP = 0; -enum command_ids_ { - STARTCRYPTO = 20, - STOPCRYPTO, - FINALIZE, - LISTSYNC, - ADDSYNC, - STOPSYNC -}; - int list_sync_folders() { int ret; char *errm; diff --git a/pclsync/pcommands.h b/pclsync/pcommands.h new file mode 100644 index 0000000..9fca4c1 --- /dev/null +++ b/pclsync/pcommands.h @@ -0,0 +1,8 @@ +enum command_ids_ { + STARTCRYPTO = 20, + STOPCRYPTO, + FINALIZE, + LISTSYNC, + ADDSYNC, + STOPSYNC +}; diff --git a/pclsync/pcryptofolder.c b/pclsync/pcryptofolder.c index efaaeda..ec8b3db 100644 --- a/pclsync/pcryptofolder.c +++ b/pclsync/pcryptofolder.c @@ -548,7 +548,6 @@ int pcryptofolder_unlock(const char *password) { * to have some thread to hold sql_lock and wait for read lock. This will * normally deadlock with us holding writelock and waiting for sql_lock. * Therefore we use sql_trylock here. - * */ retry: pthread_rwlock_wrlock(&crypto_lock); @@ -604,6 +603,8 @@ retry: debug(D_NOTICE, "got keys from the database"); assert(rowcnt == 4); } + + debug(D_NOTICE, "trying to load public key"); crypto_pubkey = psync_ssl_rsa_load_public(rsapub, rsapublen); if (crypto_pubkey == PSYNC_INVALID_RSA) { pthread_rwlock_unlock(&crypto_lock); @@ -613,6 +614,10 @@ retry: psync_free(salt); return PRINT_RETURN_CONST(PSYNC_CRYPTO_START_UNKNOWN_KEY_FORMAT); } + debug(D_NOTICE, "successfully loaded public key"); + + + debug(D_NOTICE, "generating symmetric key"); aeskey = psync_ssl_gen_symmetric_key_from_pass( password, PSYNC_AES256_KEY_SIZE + PSYNC_AES256_BLOCK_SIZE, salt, saltlen, iterations); @@ -622,19 +627,26 @@ retry: memcpy(rsaprivdec, rsapriv, rsaprivlen); pcrypto_ctr_encdec_decode(enc, rsaprivdec, rsaprivlen, 0); pcrypto_ctr_encdec_free(enc); + debug(D_NOTICE, "successfully generated symmetric key"); + + + debug(D_NOTICE, "trying to load private key"); crypto_privkey = psync_ssl_rsa_load_private(rsaprivdec, rsaprivlen); psync_ssl_memclean(rsaprivdec, rsaprivlen); pmemlock_free(rsaprivdec); if (crypto_privkey == PSYNC_INVALID_RSA) { + debug(D_NOTICE, "failed to load private key"); psync_ssl_rsa_free_public(crypto_pubkey); crypto_pubkey = PSYNC_INVALID_RSA; pthread_rwlock_unlock(&crypto_lock); - debug(D_NOTICE, "bad password"); psync_free(rsapriv); psync_free(rsapub); psync_free(salt); return PRINT_RETURN_CONST(PSYNC_CRYPTO_START_BAD_PASSWORD); } + debug(D_NOTICE, "successfully loaded private key"); + + debug(D_NOTICE, "verify matching public and private key"); if (!crypto_keys_match()) { psync_ssl_rsa_free_public(crypto_pubkey); crypto_pubkey = PSYNC_INVALID_RSA; @@ -647,13 +659,17 @@ retry: psync_free(salt); return PRINT_RETURN_CONST(PSYNC_CRYPTO_START_KEYS_DONT_MATCH); } + debug(D_NOTICE, "public and private keys match, setting crypto started"); + crypto_started_l = 1; crypto_started_un = 1; pthread_rwlock_unlock(&crypto_lock); - if (rowcnt < 4) + if (rowcnt < 4) { + debug(D_NOTICE, "saving crypto setup to database"); psync_cloud_crypto_setup_save_to_db(rsapriv, rsaprivlen, rsapub, rsapublen, salt, saltlen, iterations, 0, publicsha1, privatesha1, flags); + } psync_free(rsapriv); psync_free(rsapub); psync_free(salt); diff --git a/pclsync/pcryptofolder.h b/pclsync/pcryptofolder.h index 80e1c9c..488985d 100644 --- a/pclsync/pcryptofolder.h +++ b/pclsync/pcryptofolder.h @@ -32,10 +32,14 @@ #ifndef __PCRYPTOFOLDER_H #define __PCRYPTOFOLDER_H +#ifdef __cplusplus +extern "C" { +#endif + #include "papi.h" #include "pcrypto.h" +#include "pfoldersync.h" #include "pfsfolder.h" -#include "psynclib.h" #define PSYNC_CRYPTO_SYM_FLAG_ISDIR 1 @@ -74,4 +78,8 @@ int pcryptofolder_reset(); int pcryptofolder_setup(const char *password, const char *hint); int pcryptofolder_unlock(const char *password); +#ifdef __cplusplus +} +#endif + #endif diff --git a/pclsync/pssl.c b/pclsync/pssl.c index ad8017d..5db24c7 100644 --- a/pclsync/pssl.c +++ b/pclsync/pssl.c @@ -44,8 +44,8 @@ #include #include #include +#include -#include "pfile.h" #include "pcompiler.h" #include "pcache.h" @@ -63,11 +63,46 @@ #include #include +typedef struct { + mbedtls_ctr_drbg_context rnd; + pthread_mutex_t mutex; +} ctr_drbg_context_locked; + +typedef struct { + mbedtls_net_context srv; + mbedtls_ssl_context ssl; + mbedtls_ssl_config cfg; + int sock; + int isbroken; + char cachekey[]; +} ssl_connection_t; + +static pthread_mutex_t rsa_decr_mutex = PTHREAD_MUTEX_INITIALIZER; +static ctr_drbg_context_locked psync_mbed_rng; +static mbedtls_entropy_context psync_mbed_entropy; +static mbedtls_x509_crt psync_mbed_trusted_certs_x509; +PSYNC_THREAD int psync_ssl_errno; +static psync_ssl_debug_callback_t debug_cb = NULL; +static void *debug_ctx = NULL; +static const int psync_mbed_ciphersuite[] = { + MBEDTLS_TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384, + MBEDTLS_TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384, + MBEDTLS_TLS_DHE_RSA_WITH_AES_256_GCM_SHA384, + MBEDTLS_TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384, + MBEDTLS_TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384, + MBEDTLS_TLS_DHE_RSA_WITH_AES_256_CBC_SHA256, + MBEDTLS_TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, + MBEDTLS_TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256, + MBEDTLS_TLS_DHE_RSA_WITH_AES_128_GCM_SHA256, + MBEDTLS_TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256, + MBEDTLS_TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256, + MBEDTLS_TLS_DHE_RSA_WITH_AES_128_CBC_SHA256, + 0}; + // HACK: This function is duplicated from mbedtls/library/pkparse.c, because // it is needed to properly parse the RSA keys returned by the pcloud server // for some reason... see the fallback code in psync_ssl_rsa_load_public. -static int pk_get_rsapubkey(unsigned char **p, const unsigned char *end, - mbedtls_rsa_context *rsa) { +static int pk_get_rsapubkey(unsigned char **p, const unsigned char *end, mbedtls_rsa_context *rsa) { int ret; size_t len; mbedtls_mpi N, E; @@ -134,192 +169,44 @@ cleanup: return ret; } - -static pthread_mutex_t rsa_decr_mutex = PTHREAD_MUTEX_INITIALIZER; - static void psync_ssl_free_psync_encrypted_data_t(psync_encrypted_data_t e) { psync_ssl_memclean(e->data, e->datalen); pmemlock_free(e); } -void psync_ssl_rsa_free_binary(psync_binary_rsa_key_t bin) { - psync_ssl_free_psync_encrypted_data_t(bin); +static inline void psync_aes256_encode_block(psync_aes256_encoder enc, const unsigned char *src, unsigned char *dst) { + mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_ENCRYPT, src, dst); } -void psync_ssl_free_symmetric_key(psync_symmetric_key_t key) { - psync_ssl_memclean(key->key, key->keylen); - pmemlock_free(key); +static inline void psync_aes256_decode_block(psync_aes256_decoder enc, const unsigned char *src, unsigned char *dst) { + mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, src, dst); } -psync_encrypted_symmetric_key_t -psync_ssl_alloc_encrypted_symmetric_key(size_t len) { - psync_encrypted_symmetric_key_t ret; - ret = psync_malloc(offsetof(psync_encrypted_data_struct_t, data) + len); - ret->datalen = len; - return ret; +static inline void psync_aes256_encode_2blocks_consec(psync_aes256_decoder enc, const unsigned char *src, unsigned char *dst) { + mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_ENCRYPT, src, dst); + mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_ENCRYPT, src + PSYNC_AES256_BLOCK_SIZE, + dst + PSYNC_AES256_BLOCK_SIZE); } -psync_encrypted_symmetric_key_t -psync_ssl_copy_encrypted_symmetric_key(psync_encrypted_symmetric_key_t src) { - psync_encrypted_symmetric_key_t ret; - ret = psync_malloc(offsetof(psync_encrypted_data_struct_t, data) + - src->datalen); - ret->datalen = src->datalen; - memcpy(ret->data, src->data, src->datalen); - return ret; +static inline void psync_aes256_decode_2blocks_consec(psync_aes256_decoder enc, const unsigned char *src, unsigned char *dst) { + mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, src, dst); + mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, src + PSYNC_AES256_BLOCK_SIZE, + dst + PSYNC_AES256_BLOCK_SIZE); } -psync_symmetric_key_t psync_ssl_rsa_decrypt_symm_key_lock( - psync_rsa_privatekey_t *rsa, - const psync_encrypted_symmetric_key_t *enckey) { - psync_symmetric_key_t sym_key; - - debug(D_NOTICE, "Get RSA decrypt key lock."); - pthread_mutex_lock(&rsa_decr_mutex); - - sym_key = psync_ssl_rsa_decrypt_symmetric_key(*rsa, *enckey); - - pthread_mutex_unlock(&rsa_decr_mutex); - debug(D_NOTICE, "RSA decrypt key Lock released."); - - return sym_key; -} - -#if defined(PSYNC_AES_HW_MSC) -#include -#include -#endif - -static const int psync_mbed_ciphersuite[] = { - MBEDTLS_TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384, - MBEDTLS_TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384, - MBEDTLS_TLS_DHE_RSA_WITH_AES_256_GCM_SHA384, - MBEDTLS_TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384, - MBEDTLS_TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384, - MBEDTLS_TLS_DHE_RSA_WITH_AES_256_CBC_SHA256, - MBEDTLS_TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, - MBEDTLS_TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256, - MBEDTLS_TLS_DHE_RSA_WITH_AES_128_GCM_SHA256, - MBEDTLS_TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256, - MBEDTLS_TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256, - MBEDTLS_TLS_DHE_RSA_WITH_AES_128_CBC_SHA256, - 0}; - -typedef struct { - mbedtls_ctr_drbg_context rnd; - pthread_mutex_t mutex; -} ctr_drbg_context_locked; - -typedef struct { - mbedtls_net_context srv; - mbedtls_ssl_context ssl; - mbedtls_ssl_config cfg; - int sock; - int isbroken; - char cachekey[]; -} ssl_connection_t; - -static ctr_drbg_context_locked psync_mbed_rng; -static mbedtls_entropy_context psync_mbed_entropy; -static mbedtls_x509_crt psync_mbed_trusted_certs_x509; - -PSYNC_THREAD int psync_ssl_errno; - -#if defined(PSYNC_AES_HW) -int psync_ssl_hw_aes; -#endif - -static psync_ssl_debug_callback_t debug_cb = NULL; -static void *debug_ctx = NULL; - -void psync_ssl_set_log_threshold(int threshold) { - mbedtls_debug_set_threshold(threshold); -} - -void psync_ssl_set_debug_callback(psync_ssl_debug_callback_t cb, void *ctx) { - debug_cb = cb; - debug_ctx = ctx; -} - -int ctr_drbg_random_locked(void *p_rng, unsigned char *output, - size_t output_len) { - ctr_drbg_context_locked *rng; - int ret; - rng = (ctr_drbg_context_locked *)p_rng; - pthread_mutex_lock(&rng->mutex); - ret = mbedtls_ctr_drbg_random(&rng->rnd, output, output_len); - pthread_mutex_unlock(&rng->mutex); - return ret; -} - -#if defined(PSYNC_AES_HW_GCC) -static int psync_ssl_detect_aes_hw() { - uint32_t eax, ecx; - eax = 1; - __asm__("cpuid" : "=c"(ecx) : "a"(eax) : "%ebx", "%edx"); - ecx = (ecx >> 25) & 1; - if (ecx) - debug(D_NOTICE, "hardware AES support detected"); - else - debug(D_NOTICE, "hardware AES support not detected"); - return ecx; -} -#elif defined(PSYNC_AES_HW_MSC) -static int psync_ssl_detect_aes_hw() { - int info[4]; - int ret; - __cpuid(info, 1); - ret = (info[2] >> 25) & 1; - if (ret) - debug(D_NOTICE, "hardware AES support detected"); - else - debug(D_NOTICE, "hardware AES support not detected"); - return ret; -} -#endif - -int psync_ssl_init() { - unsigned char seed[PSYNC_LHASH_DIGEST_LEN]; +static inline void psync_aes256_decode_4blocks_consec_xor(psync_aes256_decoder enc, const unsigned char *src, unsigned char *dst, unsigned char *bxor) { unsigned long i; - int result; - -#if defined(PSYNC_AES_HW) - psync_ssl_hw_aes = psync_ssl_detect_aes_hw(); -#else - debug(D_NOTICE, "hardware AES is not supported for this compiler"); -#endif - if (pthread_mutex_init(&psync_mbed_rng.mutex, NULL)) - return PRINT_RETURN(-1); - - mbedtls_entropy_init(&psync_mbed_entropy); - prand_seed(seed, seed, sizeof(seed), 0); - mbedtls_entropy_update_manual(&psync_mbed_entropy, seed, sizeof(seed)); - - mbedtls_ctr_drbg_init(&psync_mbed_rng.rnd); - if ((result = mbedtls_ctr_drbg_seed(&psync_mbed_rng.rnd, mbedtls_entropy_func, - &psync_mbed_entropy, NULL, 0))) { - debug(D_ERROR, "mbedtls_ctr_drbg_seed failed with return code %d", result); - return PRINT_RETURN(-1); - } - - mbedtls_x509_crt_init(&psync_mbed_trusted_certs_x509); - for (i = 0; i < ARRAY_SIZE(psync_ssl_trusted_certs); i++) { - result = mbedtls_x509_crt_parse(&psync_mbed_trusted_certs_x509, - (unsigned char *)psync_ssl_trusted_certs[i], - 1 + strlen(psync_ssl_trusted_certs[i])); - if (result) { - debug(D_ERROR, "failed to load certificate %lu, got result %d", - (unsigned long)i, result); - } - } - - return 0; -} - -void psync_ssl_memclean(void *ptr, size_t len) { - volatile unsigned char *p = ptr; - while (len--) - *p++ = 0; + mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, src, dst); + mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, src + PSYNC_AES256_BLOCK_SIZE, + dst + PSYNC_AES256_BLOCK_SIZE); + mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, + src + PSYNC_AES256_BLOCK_SIZE * 2, + dst + PSYNC_AES256_BLOCK_SIZE * 2); + mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, + src + PSYNC_AES256_BLOCK_SIZE * 3, + dst + PSYNC_AES256_BLOCK_SIZE * 3); + for (i = 0; i < PSYNC_AES256_BLOCK_SIZE * 4 / sizeof(unsigned long); i++) + ((unsigned long *)dst)[i] ^= ((unsigned long *)bxor)[i]; } static ssl_connection_t *psync_ssl_alloc_conn(const char *hostname) { @@ -407,7 +294,6 @@ static int psync_ssl_check_peer_public_key(ssl_connection_t *conn) { char sighex[66]; int i; - // TODO: returning null, why? cert = mbedtls_ssl_get_peer_cert(&conn->ssl); if (!cert) { debug(D_WARNING, "ssl_get_peer_cert returned NULL"); @@ -436,6 +322,104 @@ static int psync_ssl_check_peer_public_key(ssl_connection_t *conn) { return -1; } +void psync_ssl_set_log_threshold(int threshold) { + mbedtls_debug_set_threshold(threshold); +} + +void psync_ssl_set_debug_callback(psync_ssl_debug_callback_t cb, void *ctx) { + debug_cb = cb; + debug_ctx = ctx; +} + +int ctr_drbg_random_locked(void *p_rng, unsigned char *output, + size_t output_len) { + ctr_drbg_context_locked *rng; + int ret; + rng = (ctr_drbg_context_locked *)p_rng; + pthread_mutex_lock(&rng->mutex); + ret = mbedtls_ctr_drbg_random(&rng->rnd, output, output_len); + pthread_mutex_unlock(&rng->mutex); + return ret; +} + +void psync_ssl_rsa_free_binary(psync_binary_rsa_key_t bin) { + psync_ssl_free_psync_encrypted_data_t(bin); +} + +void psync_ssl_free_symmetric_key(psync_symmetric_key_t key) { + psync_ssl_memclean(key->key, key->keylen); + pmemlock_free(key); +} + +psync_encrypted_symmetric_key_t psync_ssl_alloc_encrypted_symmetric_key(size_t len) { + psync_encrypted_symmetric_key_t ret; + ret = psync_malloc(offsetof(psync_encrypted_data_struct_t, data) + len); + ret->datalen = len; + return ret; +} + +psync_encrypted_symmetric_key_t psync_ssl_copy_encrypted_symmetric_key(psync_encrypted_symmetric_key_t src) { + psync_encrypted_symmetric_key_t ret; + ret = psync_malloc(offsetof(psync_encrypted_data_struct_t, data) + + src->datalen); + ret->datalen = src->datalen; + memcpy(ret->data, src->data, src->datalen); + return ret; +} + +psync_symmetric_key_t psync_ssl_rsa_decrypt_symm_key_lock(psync_rsa_privatekey_t *rsa, const psync_encrypted_symmetric_key_t *enckey) { + psync_symmetric_key_t sym_key; + + debug(D_NOTICE, "Get RSA decrypt key lock."); + pthread_mutex_lock(&rsa_decr_mutex); + + sym_key = psync_ssl_rsa_decrypt_symmetric_key(*rsa, *enckey); + + pthread_mutex_unlock(&rsa_decr_mutex); + debug(D_NOTICE, "RSA decrypt key Lock released."); + + return sym_key; +} + +int psync_ssl_init() { + unsigned char seed[PSYNC_LHASH_DIGEST_LEN]; + unsigned long i; + int result; + + if (pthread_mutex_init(&psync_mbed_rng.mutex, NULL)) + return PRINT_RETURN(-1); + + mbedtls_entropy_init(&psync_mbed_entropy); + prand_seed(seed, seed, sizeof(seed), 0); + mbedtls_entropy_update_manual(&psync_mbed_entropy, seed, sizeof(seed)); + + mbedtls_ctr_drbg_init(&psync_mbed_rng.rnd); + if ((result = mbedtls_ctr_drbg_seed(&psync_mbed_rng.rnd, mbedtls_entropy_func, + &psync_mbed_entropy, NULL, 0))) { + debug(D_ERROR, "mbedtls_ctr_drbg_seed failed with return code %d", result); + return PRINT_RETURN(-1); + } + + mbedtls_x509_crt_init(&psync_mbed_trusted_certs_x509); + for (i = 0; i < ARRAY_SIZE(psync_ssl_trusted_certs); i++) { + result = mbedtls_x509_crt_parse(&psync_mbed_trusted_certs_x509, + (unsigned char *)psync_ssl_trusted_certs[i], + 1 + strlen(psync_ssl_trusted_certs[i])); + if (result) { + debug(D_ERROR, "failed to load certificate %lu, got result %d", + (unsigned long)i, result); + } + } + + return 0; +} + +void psync_ssl_memclean(void *ptr, size_t len) { + volatile unsigned char *p = ptr; + while (len--) + *p++ = 0; +} + int psync_ssl_connect(int sock, void **sslconn, const char *hostname) { ssl_connection_t *conn; mbedtls_ssl_session *sess; @@ -553,7 +537,6 @@ fail: return PRINT_RETURN_CONST(PSYNC_SSL_FAIL); } - int psync_ssl_shutdown(void *sslconn) { ssl_connection_t *conn; int ret; @@ -669,8 +652,7 @@ void psync_ssl_rsa_free_private(psync_rsa_privatekey_t key) { psync_ssl_free_rsa(key); } -psync_binary_rsa_key_t -psync_ssl_rsa_public_to_binary(psync_rsa_publickey_t rsa) { +psync_binary_rsa_key_t psync_ssl_rsa_public_to_binary(psync_rsa_publickey_t rsa) { unsigned char buff[4096], *p; mbedtls_pk_context ctx; psync_binary_rsa_key_t ret; @@ -691,8 +673,7 @@ psync_ssl_rsa_public_to_binary(psync_rsa_publickey_t rsa) { return ret; } -psync_binary_rsa_key_t -psync_ssl_rsa_private_to_binary(psync_rsa_privatekey_t rsa) { +psync_binary_rsa_key_t psync_ssl_rsa_private_to_binary(psync_rsa_privatekey_t rsa) { unsigned char buff[4096]; mbedtls_pk_context ctx; psync_binary_rsa_key_t ret; @@ -713,8 +694,7 @@ psync_ssl_rsa_private_to_binary(psync_rsa_privatekey_t rsa) { return ret; } -psync_rsa_publickey_t psync_ssl_rsa_load_public(const unsigned char *keydata, - size_t keylen) { +psync_rsa_publickey_t psync_ssl_rsa_load_public(const unsigned char *keydata, size_t keylen) { mbedtls_pk_context ctx; mbedtls_rsa_context *rsa; int ret; @@ -768,14 +748,13 @@ psync_rsa_publickey_t psync_ssl_rsa_load_public(const unsigned char *keydata, } } -psync_rsa_privatekey_t psync_ssl_rsa_load_private(const unsigned char *keydata, - size_t keylen) { +psync_rsa_privatekey_t psync_ssl_rsa_load_private(const unsigned char *keydata, size_t keylen) { mbedtls_pk_context ctx; mbedtls_rsa_context *rsa; int ret; mbedtls_pk_init(&ctx); if (unlikely(ret = mbedtls_pk_parse_key(&ctx, keydata, keylen, NULL, 0, mbedtls_ctr_drbg_random, &psync_mbed_rng.rnd))) { - debug(D_WARNING, "pk_parse_key failed with code %d", ret); + debug(D_WARNING, "mbedtls_pk_parse_key failed with code %d", ret); return PSYNC_INVALID_RSA; } rsa = psync_new(mbedtls_rsa_context); @@ -794,20 +773,15 @@ psync_rsa_privatekey_t psync_ssl_rsa_load_private(const unsigned char *keydata, } } -psync_rsa_publickey_t -psync_ssl_rsa_binary_to_public(psync_binary_rsa_key_t bin) { +psync_rsa_publickey_t psync_ssl_rsa_binary_to_public(psync_binary_rsa_key_t bin) { return psync_ssl_rsa_load_public(bin->data, bin->datalen); } -psync_rsa_privatekey_t -psync_ssl_rsa_binary_to_private(psync_binary_rsa_key_t bin) { +psync_rsa_privatekey_t psync_ssl_rsa_binary_to_private(psync_binary_rsa_key_t bin) { return psync_ssl_rsa_load_private(bin->data, bin->datalen); } -psync_symmetric_key_t -psync_ssl_gen_symmetric_key_from_pass(const char *password, size_t keylen, - const unsigned char *salt, size_t saltlen, - size_t iterations) { +psync_symmetric_key_t psync_ssl_gen_symmetric_key_from_pass(const char *password, size_t keylen, const unsigned char *salt, size_t saltlen, size_t iterations) { psync_symmetric_key_t key = (psync_symmetric_key_t)pmemlock_malloc( keylen + offsetof(psync_symmetric_key_struct_t, key)); mbedtls_md_context_t ctx; @@ -823,8 +797,7 @@ psync_ssl_gen_symmetric_key_from_pass(const char *password, size_t keylen, return key; } -char *psync_ssl_derive_password_from_passphrase(const char *username, - const char *passphrase) { +char *psync_ssl_derive_password_from_passphrase(const char *username, const char *passphrase) { unsigned char *usercopy; unsigned char usersha512[PSYNC_SHA512_DIGEST_LEN], passwordbin[32]; mbedtls_md_context_t ctx; @@ -850,9 +823,7 @@ char *psync_ssl_derive_password_from_passphrase(const char *username, return (char *)usercopy; } -psync_encrypted_symmetric_key_t -psync_ssl_rsa_encrypt_data(psync_rsa_publickey_t rsa, const unsigned char *data, - size_t datalen) { +psync_encrypted_symmetric_key_t psync_ssl_rsa_encrypt_data(psync_rsa_publickey_t rsa, const unsigned char *data, size_t datalen) { psync_encrypted_symmetric_key_t ret; int code; size_t rsalen; @@ -875,9 +846,7 @@ psync_ssl_rsa_encrypt_data(psync_rsa_publickey_t rsa, const unsigned char *data, return ret; } -psync_symmetric_key_t psync_ssl_rsa_decrypt_data(psync_rsa_privatekey_t rsa, - const unsigned char *data, - size_t datalen) { +psync_symmetric_key_t psync_ssl_rsa_decrypt_data(psync_rsa_privatekey_t rsa, const unsigned char *data, size_t datalen) { unsigned char buff[2048]; psync_symmetric_key_t ret; size_t len; @@ -893,19 +862,15 @@ psync_symmetric_key_t psync_ssl_rsa_decrypt_data(psync_rsa_privatekey_t rsa, return ret; } -psync_encrypted_symmetric_key_t -psync_ssl_rsa_encrypt_symmetric_key(psync_rsa_publickey_t rsa, - const psync_symmetric_key_t key) { +psync_encrypted_symmetric_key_t psync_ssl_rsa_encrypt_symmetric_key(psync_rsa_publickey_t rsa, const psync_symmetric_key_t key) { return psync_ssl_rsa_encrypt_data(rsa, key->key, key->keylen); } -psync_symmetric_key_t psync_ssl_rsa_decrypt_symmetric_key( - psync_rsa_privatekey_t rsa, const psync_encrypted_symmetric_key_t enckey) { +psync_symmetric_key_t psync_ssl_rsa_decrypt_symmetric_key(psync_rsa_privatekey_t rsa, const psync_encrypted_symmetric_key_t enckey) { return psync_ssl_rsa_decrypt_data(rsa, enckey->data, enckey->datalen); } -psync_aes256_encoder -psync_ssl_aes256_create_encoder(psync_symmetric_key_t key) { +psync_aes256_encoder psync_ssl_aes256_create_encoder(psync_symmetric_key_t key) { mbedtls_aes_context *aes; assert(key->keylen >= PSYNC_AES256_KEY_SIZE); aes = psync_new(mbedtls_aes_context); @@ -918,8 +883,7 @@ void psync_ssl_aes256_free_encoder(psync_aes256_encoder aes) { psync_free(aes); } -psync_aes256_encoder -psync_ssl_aes256_create_decoder(psync_symmetric_key_t key) { +psync_aes256_encoder psync_ssl_aes256_create_decoder(psync_symmetric_key_t key) { mbedtls_aes_context *aes; assert(key->keylen >= PSYNC_AES256_KEY_SIZE); aes = psync_new(mbedtls_aes_context); @@ -932,9 +896,7 @@ void psync_ssl_aes256_free_decoder(psync_aes256_encoder aes) { psync_free(aes); } -psync_rsa_signature_t -psync_ssl_rsa_sign_sha256_hash(psync_rsa_privatekey_t rsa, - const unsigned char *data) { +psync_rsa_signature_t psync_ssl_rsa_sign_sha256_hash(psync_rsa_privatekey_t rsa, const unsigned char *data) { psync_rsa_signature_t ret; int padding, hash_id; size_t rsalen; @@ -959,218 +921,7 @@ psync_ssl_rsa_sign_sha256_hash(psync_rsa_privatekey_t rsa, return ret; } -#if defined(PSYNC_AES_HW_GCC) - -#define SSE2FUNC __attribute__((__target__("sse2"))) - -#define AESDEC ".byte 0x66,0x0F,0x38,0xDE," -#define AESDECLAST ".byte 0x66,0x0F,0x38,0xDF," -#define AESENC ".byte 0x66,0x0F,0x38,0xDC," -#define AESENCLAST ".byte 0x66,0x0F,0x38,0xDD," - -#define xmm0_xmm1 "0xC8" -#define xmm0_xmm2 "0xD0" -#define xmm0_xmm3 "0xD8" -#define xmm0_xmm4 "0xE0" -#define xmm0_xmm5 "0xE8" -// #define xmm1_xmm0 "0xC1" // unused, may be important later -#define xmm1_xmm2 "0xD1" -#define xmm1_xmm3 "0xD9" -#define xmm1_xmm4 "0xE1" -#define xmm1_xmm5 "0xE9" - -SSE2FUNC void psync_aes256_encode_block_hw(psync_aes256_encoder enc, - const unsigned char *src, - unsigned char *dst) { - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_ENCRYPT, src, dst); -} - -SSE2FUNC void psync_aes256_decode_block_hw(psync_aes256_decoder enc, - const unsigned char *src, - unsigned char *dst) { - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, src, dst); -} - -SSE2FUNC void psync_aes256_encode_2blocks_consec_hw(psync_aes256_encoder enc, - const unsigned char *src, - unsigned char *dst) { - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_ENCRYPT, src, dst); - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_ENCRYPT, src + 16, dst + 16); -} - -SSE2FUNC void psync_aes256_decode_2blocks_consec_hw(psync_aes256_decoder enc, - const unsigned char *src, - unsigned char *dst) { - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, src, dst); - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, src + 16, dst + 16); -} - -SSE2FUNC void psync_aes256_decode_4blocks_consec_xor_hw( - psync_aes256_decoder enc, const unsigned char *src, unsigned char *dst, - unsigned char *bxor) { - unsigned char temp[16]; - for (int i = 0; i < 4; i++) { - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, src + i * 16, temp); - for (int j = 0; j < 16; j++) { - dst[i * 16 + j] = temp[j] ^ bxor[i * 16 + j]; - } - } -} - -#elif defined(PSYNC_AES_HW_MSC) - -void psync_aes256_encode_block_hw(psync_aes256_encoder enc, - const unsigned char *src, - unsigned char *dst) { - __m128i r0, r1; - unsigned char *key; - unsigned cnt; - key = (unsigned char *)enc->rk; - r0 = _mm_loadu_si128((__m128i *)key); - r1 = _mm_load_si128((__m128i *)src); - cnt = enc->nr - 1; - key += 16; - r1 = _mm_xor_si128(r0, r1); - r0 = _mm_loadu_si128((__m128i *)key); - do { - key += 16; - r1 = _mm_aesenc_si128(r1, r0); - r0 = _mm_loadu_si128((__m128i *)key); - } while (--cnt); - r1 = _mm_aesenclast_si128(r1, r0); - _mm_store_si128((__m128i *)dst, r1); -} - -void psync_aes256_decode_block_hw(psync_aes256_encoder enc, - const unsigned char *src, - unsigned char *dst) { - __m128i r0, r1; - unsigned char *key; - unsigned cnt; - key = (unsigned char *)enc->rk; - r0 = _mm_loadu_si128((__m128i *)key); - r1 = _mm_load_si128((__m128i *)src); - cnt = enc->nr - 1; - key += 16; - r1 = _mm_xor_si128(r0, r1); - r0 = _mm_loadu_si128((__m128i *)key); - do { - key += 16; - r1 = _mm_aesdec_si128(r1, r0); - r0 = _mm_loadu_si128((__m128i *)key); - } while (--cnt); - r1 = _mm_aesdeclast_si128(r1, r0); - _mm_store_si128((__m128i *)dst, r1); -} - -void psync_aes256_encode_2blocks_consec_hw(psync_aes256_encoder enc, - const unsigned char *src, - unsigned char *dst) { - __m128i r0, r1, r2; - unsigned char *key; - unsigned cnt; - key = (unsigned char *)enc->rk; - r0 = _mm_loadu_si128((__m128i *)key); - r1 = _mm_load_si128((__m128i *)src); - r2 = _mm_load_si128((__m128i *)(src + 16)); - cnt = enc->nr - 1; - key += 16; - r1 = _mm_xor_si128(r0, r1); - r2 = _mm_xor_si128(r0, r2); - r0 = _mm_loadu_si128((__m128i *)key); - do { - key += 16; - r1 = _mm_aesenc_si128(r1, r0); - r2 = _mm_aesenc_si128(r2, r0); - r0 = _mm_loadu_si128((__m128i *)key); - } while (--cnt); - r1 = _mm_aesenclast_si128(r1, r0); - r2 = _mm_aesenclast_si128(r2, r0); - _mm_store_si128((__m128i *)dst, r1); - _mm_store_si128((__m128i *)(dst + 16), r2); -} - -void psync_aes256_decode_2blocks_consec_hw(psync_aes256_decoder enc, - const unsigned char *src, - unsigned char *dst) { - __m128i r0, r1, r2; - unsigned char *key; - unsigned cnt; - key = (unsigned char *)enc->rk; - r0 = _mm_loadu_si128((__m128i *)key); - r1 = _mm_load_si128((__m128i *)src); - r2 = _mm_load_si128((__m128i *)(src + 16)); - cnt = enc->nr - 1; - key += 16; - r1 = _mm_xor_si128(r0, r1); - r2 = _mm_xor_si128(r0, r2); - r0 = _mm_loadu_si128((__m128i *)key); - do { - key += 16; - r1 = _mm_aesdec_si128(r1, r0); - r2 = _mm_aesdec_si128(r2, r0); - r0 = _mm_loadu_si128((__m128i *)key); - } while (--cnt); - r1 = _mm_aesdeclast_si128(r1, r0); - r2 = _mm_aesdeclast_si128(r2, r0); - _mm_store_si128((__m128i *)dst, r1); - _mm_store_si128((__m128i *)(dst + 16), r2); -} - -void psync_aes256_decode_4blocks_consec_xor_hw(psync_aes256_decoder enc, - const unsigned char *src, - unsigned char *dst, - unsigned char *bxor) { - __m128i r0, r1, r2, r3, r4; - unsigned char *key; - unsigned cnt; - key = (unsigned char *)enc->rk; - r0 = _mm_loadu_si128((__m128i *)key); - r1 = _mm_load_si128((__m128i *)src); - r2 = _mm_load_si128((__m128i *)(src + 16)); - r3 = _mm_load_si128((__m128i *)(src + 32)); - r4 = _mm_load_si128((__m128i *)(src + 48)); - cnt = enc->nr - 1; - key += 16; - r1 = _mm_xor_si128(r0, r1); - r2 = _mm_xor_si128(r0, r2); - r3 = _mm_xor_si128(r0, r3); - r4 = _mm_xor_si128(r0, r4); - r0 = _mm_loadu_si128((__m128i *)key); - do { - key += 16; - r1 = _mm_aesdec_si128(r1, r0); - r2 = _mm_aesdec_si128(r2, r0); - r3 = _mm_aesdec_si128(r3, r0); - r4 = _mm_aesdec_si128(r4, r0); - r0 = _mm_loadu_si128((__m128i *)key); - } while (--cnt); - r1 = _mm_aesdeclast_si128(r1, r0); - r2 = _mm_aesdeclast_si128(r2, r0); - r3 = _mm_aesdeclast_si128(r3, r0); - r4 = _mm_aesdeclast_si128(r4, r0); - r0 = _mm_load_si128((__m128i *)bxor); - r1 = _mm_xor_si128(r0, r1); - r0 = _mm_load_si128((__m128i *)(bxor + 16)); - _mm_store_si128((__m128i *)dst, r1); - r2 = _mm_xor_si128(r0, r2); - r0 = _mm_load_si128((__m128i *)(bxor + 32)); - _mm_store_si128((__m128i *)(dst + 16), r2); - r3 = _mm_xor_si128(r0, r3); - r0 = _mm_load_si128((__m128i *)(bxor + 48)); - _mm_store_si128((__m128i *)(dst + 32), r3); - r4 = _mm_xor_si128(r0, r4); - _mm_store_si128((__m128i *)(dst + 48), r4); -} - -#endif - -#if defined(PSYNC_AES_HW) - -void psync_aes256_decode_4blocks_consec_xor_sw(psync_aes256_decoder enc, - const unsigned char *src, - unsigned char *dst, - unsigned char *bxor) { +void psync_aes256_decode_4blocks_consec_xor_sw(psync_aes256_decoder enc, const unsigned char *src, unsigned char *dst, unsigned char *bxor) { unsigned long i; mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, src, dst); mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, src + PSYNC_AES256_BLOCK_SIZE, @@ -1184,5 +935,3 @@ void psync_aes256_decode_4blocks_consec_xor_sw(psync_aes256_decoder enc, for (i = 0; i < PSYNC_AES256_BLOCK_SIZE * 4 / sizeof(unsigned long); i++) ((unsigned long *)dst)[i] ^= ((unsigned long *)bxor)[i]; } - -#endif diff --git a/pclsync/pssl.h b/pclsync/pssl.h index 32babbe..b9f263f 100644 --- a/pclsync/pssl.h +++ b/pclsync/pssl.h @@ -40,12 +40,11 @@ #include "pcompiler.h" +// AES256 #define PSYNC_AES256_BLOCK_SIZE 16 #define PSYNC_AES256_KEY_SIZE 32 -#define PSYNC_INVALID_RSA NULL -#define PSYNC_INVALID_SYM_KEY NULL - +// SHA1 #define PSYNC_SHA1_BLOCK_LEN 64 #define PSYNC_SHA1_DIGEST_LEN 20 #define PSYNC_SHA1_DIGEST_HEXLEN 40 @@ -57,6 +56,7 @@ mbedtls_sha1_update(pctx, (const unsigned char *)data, datalen) #define psync_sha1_final(checksum, pctx) mbedtls_sha1_finish(pctx, checksum) +// SHA256 #define PSYNC_SHA256_BLOCK_LEN 64 #define PSYNC_SHA256_DIGEST_LEN 32 #define PSYNC_SHA256_DIGEST_HEXLEN 64 @@ -68,6 +68,7 @@ mbedtls_sha256_update(pctx, (const unsigned char *)data, datalen) #define psync_sha256_final(checksum, pctx) mbedtls_sha256_finish(pctx, checksum) +// SHA512 #define PSYNC_SHA512_BLOCK_LEN 128 #define PSYNC_SHA512_DIGEST_LEN 64 #define PSYNC_SHA512_DIGEST_HEXLEN 128 @@ -79,246 +80,85 @@ mbedtls_sha512_update(pctx, (const unsigned char *)data, datalen) #define psync_sha512_final(checksum, pctx) mbedtls_sha512_finish(pctx, checksum) -typedef mbedtls_rsa_context *psync_rsa_t; -typedef mbedtls_rsa_context *psync_rsa_publickey_t; -typedef mbedtls_rsa_context *psync_rsa_privatekey_t; - -typedef struct { - size_t keylen; - unsigned char key[]; -} psync_symmetric_key_struct_t, *psync_symmetric_key_t; - -typedef mbedtls_aes_context *psync_aes256_encoder; -typedef mbedtls_aes_context *psync_aes256_decoder; - -// ctx, level, message, ???, ??? -typedef void (*psync_ssl_debug_callback_t)(void *, int, const char *, int, - const char *); -void psync_ssl_set_log_threshold(int threshold); -void psync_ssl_set_debug_callback(psync_ssl_debug_callback_t cb, void *ctx); - -#if defined(__GNUC__) && \ - (defined(__amd64__) || defined(__x86_64__) || defined(__i386__)) -#define PSYNC_AES_HW -#define PSYNC_AES_HW_GCC -#elif defined(_MSC_VER) -#define PSYNC_AES_HW -#define PSYNC_AES_HW_MSC -#endif - -#if defined(PSYNC_AES_HW) -extern int psync_ssl_hw_aes; - -void psync_aes256_encode_block_hw(psync_aes256_encoder enc, - const unsigned char *src, unsigned char *dst); -void psync_aes256_decode_block_hw(psync_aes256_decoder enc, - const unsigned char *src, unsigned char *dst); -void psync_aes256_encode_2blocks_consec_hw(psync_aes256_encoder enc, - const unsigned char *src, - unsigned char *dst); -void psync_aes256_decode_2blocks_consec_hw(psync_aes256_decoder enc, - const unsigned char *src, - unsigned char *dst); -void psync_aes256_decode_4blocks_consec_xor_hw(psync_aes256_decoder enc, - const unsigned char *src, - unsigned char *dst, - unsigned char *bxor); -void psync_aes256_decode_4blocks_consec_xor_sw(psync_aes256_decoder enc, - const unsigned char *src, - unsigned char *dst, - unsigned char *bxor); - -static inline void psync_aes256_encode_block(psync_aes256_encoder enc, - const unsigned char *src, - unsigned char *dst) { - if (likely(psync_ssl_hw_aes)) - psync_aes256_encode_block_hw(enc, src, dst); - else - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_ENCRYPT, src, dst); -} - -static inline void psync_aes256_decode_block(psync_aes256_decoder enc, - const unsigned char *src, - unsigned char *dst) { - if (likely(psync_ssl_hw_aes)) - psync_aes256_decode_block_hw(enc, src, dst); - else - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, src, dst); -} - -static inline void psync_aes256_encode_2blocks_consec(psync_aes256_decoder enc, - const unsigned char *src, - unsigned char *dst) { - if (likely(psync_ssl_hw_aes)) - psync_aes256_encode_2blocks_consec_hw(enc, src, dst); - else { - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_ENCRYPT, src, dst); - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_ENCRYPT, - src + PSYNC_AES256_BLOCK_SIZE, - dst + PSYNC_AES256_BLOCK_SIZE); - } -} - -static inline void psync_aes256_decode_2blocks_consec(psync_aes256_decoder enc, - const unsigned char *src, - unsigned char *dst) { - if (likely(psync_ssl_hw_aes)) - psync_aes256_decode_2blocks_consec_hw(enc, src, dst); - else { - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, src, dst); - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, - src + PSYNC_AES256_BLOCK_SIZE, - dst + PSYNC_AES256_BLOCK_SIZE); - } -} - -static inline void psync_aes256_decode_4blocks_consec_xor( - psync_aes256_decoder enc, const unsigned char *src, unsigned char *dst, - unsigned char *bxor) { - if (psync_ssl_hw_aes) - psync_aes256_decode_4blocks_consec_xor_hw(enc, src, dst, bxor); - else - psync_aes256_decode_4blocks_consec_xor_sw(enc, src, dst, bxor); -} - -#else - -static inline void psync_aes256_encode_block(psync_aes256_encoder enc, - const unsigned char *src, - unsigned char *dst) { - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_ENCRYPT, src, dst); -} - -static inline void psync_aes256_decode_block(psync_aes256_decoder enc, - const unsigned char *src, - unsigned char *dst) { - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, src, dst); -} - -static inline void psync_aes256_encode_2blocks_consec(psync_aes256_decoder enc, - const unsigned char *src, - unsigned char *dst) { - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_ENCRYPT, src, dst); - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_ENCRYPT, src + PSYNC_AES256_BLOCK_SIZE, - dst + PSYNC_AES256_BLOCK_SIZE); -} - -static inline void psync_aes256_decode_2blocks_consec(psync_aes256_decoder enc, - const unsigned char *src, - unsigned char *dst) { - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, src, dst); - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, src + PSYNC_AES256_BLOCK_SIZE, - dst + PSYNC_AES256_BLOCK_SIZE); -} - -static inline void psync_aes256_decode_4blocks_consec_xor( - psync_aes256_decoder enc, const unsigned char *src, unsigned char *dst, - unsigned char *bxor) { - unsigned long i; - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, src, dst); - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, src + PSYNC_AES256_BLOCK_SIZE, - dst + PSYNC_AES256_BLOCK_SIZE); - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, - src + PSYNC_AES256_BLOCK_SIZE * 2, - dst + PSYNC_AES256_BLOCK_SIZE * 2); - mbedtls_aes_crypt_ecb(enc, MBEDTLS_AES_DECRYPT, - src + PSYNC_AES256_BLOCK_SIZE * 3, - dst + PSYNC_AES256_BLOCK_SIZE * 3); - for (i = 0; i < PSYNC_AES256_BLOCK_SIZE * 4 / sizeof(unsigned long); i++) - ((unsigned long *)dst)[i] ^= ((unsigned long *)bxor)[i]; -} - -#endif - +// externs extern PSYNC_THREAD int psync_ssl_errno; +#define PSYNC_INVALID_RSA NULL +#define PSYNC_INVALID_SYM_KEY NULL +#define PSYNC_INVALID_ENC_SYM_KEY NULL +#define PSYNC_INVALID_ENCODER NULL +#define PSYNC_INVALID_BIN_RSA NULL #define PSYNC_SSL_ERR_WANT_READ 1 #define PSYNC_SSL_ERR_WANT_WRITE 2 #define PSYNC_SSL_ERR_UNKNOWN 3 - #define PSYNC_SSL_NEED_FINISH -2 #define PSYNC_SSL_FAIL -1 #define PSYNC_SSL_SUCCESS 0 +#define psync_ssl_alloc_binary_rsa psync_ssl_alloc_encrypted_symmetric_key + typedef struct { size_t datalen; unsigned char data[]; } psync_encrypted_data_struct_t, *psync_encrypted_data_t; +typedef struct { + size_t keylen; + unsigned char key[]; +} psync_symmetric_key_struct_t, *psync_symmetric_key_t; + +typedef mbedtls_rsa_context *psync_rsa_t; +typedef mbedtls_rsa_context *psync_rsa_publickey_t; +typedef mbedtls_rsa_context *psync_rsa_privatekey_t; +typedef mbedtls_aes_context *psync_aes256_encoder; +typedef mbedtls_aes_context *psync_aes256_decoder; typedef psync_encrypted_data_t psync_encrypted_symmetric_key_t; typedef psync_encrypted_data_t psync_binary_rsa_key_t; typedef psync_encrypted_data_t psync_rsa_signature_t; -#define PSYNC_INVALID_ENC_SYM_KEY NULL -#define PSYNC_INVALID_ENCODER NULL -#define PSYNC_INVALID_BIN_RSA NULL - -#define psync_ssl_alloc_binary_rsa psync_ssl_alloc_encrypted_symmetric_key +typedef void (*psync_ssl_debug_callback_t)(void *ctx, int level, const char *msg, int, const char *); // Lock used to serialize access to RSA decrypt key function - +void psync_ssl_set_log_threshold(int threshold); +void psync_ssl_set_debug_callback(psync_ssl_debug_callback_t cb, void *ctx); int psync_ssl_init(); void psync_ssl_memclean(void *ptr, size_t len); -int psync_ssl_connect(int sock, void **sslconn, - const char *hostname); +int psync_ssl_connect(int sock, void **sslconn, const char *hostname); int psync_ssl_connect_finish(void *sslconn, const char *hostname); void psync_ssl_free(void *sslconn); int psync_ssl_shutdown(void *sslconn); int psync_ssl_pendingdata(void *sslconn); int psync_ssl_read(void *sslconn, void *buf, int num); int psync_ssl_write(void *sslconn, const void *buf, int num); - void psync_ssl_rand_strong(unsigned char *buf, int num); void psync_ssl_rand_weak(unsigned char *buf, int num); - psync_rsa_t psync_ssl_gen_rsa(int bits); void psync_ssl_free_rsa(psync_rsa_t rsa); psync_rsa_publickey_t psync_ssl_rsa_get_public(psync_rsa_t rsa); void psync_ssl_rsa_free_public(psync_rsa_publickey_t key); psync_rsa_privatekey_t psync_ssl_rsa_get_private(psync_rsa_t rsa); void psync_ssl_rsa_free_private(psync_rsa_privatekey_t key); -psync_binary_rsa_key_t -psync_ssl_rsa_public_to_binary(psync_rsa_publickey_t rsa); -psync_binary_rsa_key_t -psync_ssl_rsa_private_to_binary(psync_rsa_privatekey_t rsa); -psync_rsa_publickey_t psync_ssl_rsa_load_public(const unsigned char *keydata, - size_t keylen); -psync_rsa_privatekey_t psync_ssl_rsa_load_private(const unsigned char *keydata, - size_t keylen); -psync_rsa_publickey_t -psync_ssl_rsa_binary_to_public(psync_binary_rsa_key_t bin); -psync_rsa_privatekey_t -psync_ssl_rsa_binary_to_private(psync_binary_rsa_key_t bin); +psync_binary_rsa_key_t psync_ssl_rsa_public_to_binary(psync_rsa_publickey_t rsa); +psync_binary_rsa_key_t psync_ssl_rsa_private_to_binary(psync_rsa_privatekey_t rsa); +psync_rsa_publickey_t psync_ssl_rsa_load_public(const unsigned char *keydata, size_t keylen); +psync_rsa_privatekey_t psync_ssl_rsa_load_private(const unsigned char *keydata, size_t keylen); +psync_rsa_publickey_t psync_ssl_rsa_binary_to_public(psync_binary_rsa_key_t bin); +psync_rsa_privatekey_t psync_ssl_rsa_binary_to_private(psync_binary_rsa_key_t bin); void psync_ssl_rsa_free_binary(psync_binary_rsa_key_t bin); -psync_symmetric_key_t -psync_ssl_gen_symmetric_key_from_pass(const char *password, size_t keylen, - const unsigned char *salt, size_t saltlen, - size_t iterations); -char *psync_ssl_derive_password_from_passphrase(const char *username, - const char *passphrase); -psync_encrypted_symmetric_key_t -psync_ssl_alloc_encrypted_symmetric_key(size_t len); -psync_encrypted_symmetric_key_t -psync_ssl_copy_encrypted_symmetric_key(psync_encrypted_symmetric_key_t src); +psync_symmetric_key_t psync_ssl_gen_symmetric_key_from_pass(const char *password, size_t keylen, const unsigned char *salt, size_t saltlen, size_t iterations); +char *psync_ssl_derive_password_from_passphrase(const char *username, const char *passphrase); +psync_encrypted_symmetric_key_t psync_ssl_alloc_encrypted_symmetric_key(size_t len); +psync_encrypted_symmetric_key_t psync_ssl_copy_encrypted_symmetric_key(psync_encrypted_symmetric_key_t src); void psync_ssl_free_symmetric_key(psync_symmetric_key_t key); -psync_encrypted_symmetric_key_t -psync_ssl_rsa_encrypt_data(psync_rsa_publickey_t rsa, const unsigned char *data, - size_t datalen); -psync_symmetric_key_t psync_ssl_rsa_decrypt_data(psync_rsa_privatekey_t rsa, - const unsigned char *data, - size_t datalen); -psync_encrypted_symmetric_key_t -psync_ssl_rsa_encrypt_symmetric_key(psync_rsa_publickey_t rsa, - const psync_symmetric_key_t key); -psync_symmetric_key_t psync_ssl_rsa_decrypt_symmetric_key( - psync_rsa_privatekey_t rsa, const psync_encrypted_symmetric_key_t enckey); +psync_encrypted_symmetric_key_t psync_ssl_rsa_encrypt_data(psync_rsa_publickey_t rsa, const unsigned char *data, size_t datalen); +psync_symmetric_key_t psync_ssl_rsa_decrypt_data(psync_rsa_privatekey_t rsa, const unsigned char *data, size_t datalen); +psync_encrypted_symmetric_key_t psync_ssl_rsa_encrypt_symmetric_key(psync_rsa_publickey_t rsa, const psync_symmetric_key_t key); +psync_symmetric_key_t psync_ssl_rsa_decrypt_symmetric_key(psync_rsa_privatekey_t rsa, const psync_encrypted_symmetric_key_t enckey); psync_aes256_encoder psync_ssl_aes256_create_encoder(psync_symmetric_key_t key); void psync_ssl_aes256_free_encoder(psync_aes256_encoder aes); psync_aes256_encoder psync_ssl_aes256_create_decoder(psync_symmetric_key_t key); void psync_ssl_aes256_free_decoder(psync_aes256_encoder aes); -psync_rsa_signature_t psync_ssl_rsa_sign_sha256_hash(psync_rsa_privatekey_t rsa, - const unsigned char *data); -psync_symmetric_key_t psync_ssl_rsa_decrypt_symm_key_lock( - psync_rsa_privatekey_t *rsa, const psync_encrypted_symmetric_key_t *enckey); +psync_rsa_signature_t psync_ssl_rsa_sign_sha256_hash(psync_rsa_privatekey_t rsa, const unsigned char *data); +psync_symmetric_key_t psync_ssl_rsa_decrypt_symm_key_lock(psync_rsa_privatekey_t *rsa, const psync_encrypted_symmetric_key_t *enckey); #endif diff --git a/pclsync/pstatus.h b/pclsync/pstatus.h index ddee192..7246dc9 100644 --- a/pclsync/pstatus.h +++ b/pclsync/pstatus.h @@ -31,6 +31,10 @@ #ifndef _PSYNC_STATUS_H #define _PSYNC_STATUS_H +#ifdef __cplusplus +extern "C" { +#endif + #include #include "plist.h" @@ -155,4 +159,8 @@ void pstatus_get_cb(pstatus_t *status); void pstatus_set_cb(pstatus_change_callback_t callback); void pstatus_send_status_update(); +#ifdef __cplusplus +} +#endif + #endif diff --git a/pclsync_lib.cpp b/pclsync_lib.cpp index 5feaac7..6285602 100644 --- a/pclsync_lib.cpp +++ b/pclsync_lib.cpp @@ -37,10 +37,12 @@ #include #include +#include "pcryptofolder.h" #include "prpc.h" #include "psynclib.h" #include "pshm.h" #include "pdevice.h" +#include "pcommands.h" #include "pclsync_lib.h" @@ -199,28 +201,35 @@ void event_handler(psync_eventtype_t event, psync_eventdata_t eventdata) { } static int lib_setup_cripto() { - int ret = 0; - ret = psync_crypto_issetup(); - if (ret) { - ret = psync_crypto_start( - clib::pclsync_lib::get_lib().get_crypto_pass().c_str()); - std::cout << "crypto is setup, login result=" << ret << std::endl; - } else { - std::cout << "crypto is not setup" << std::endl; - ret = psync_crypto_setup( - clib::pclsync_lib::get_lib().get_crypto_pass().c_str(), "no hint"); - if (ret) { - std::cout << "crypto setup failed" << std::endl; - } else { - ret = psync_crypto_start( - clib::pclsync_lib::get_lib().get_crypto_pass().c_str()); - std::cout << "crypto setup successful, start=" << ret << std::endl; - ret = psync_crypto_mkdir(0, "Crypto", NULL, NULL); - std::cout << "creating folder=" << ret << std::endl; - } + const char *pwd = clib::pclsync_lib::get_lib().get_crypto_pass().c_str(); + + if(pstatus_get(PSTATUS_TYPE_ONLINE) == PSTATUS_ONLINE_OFFLINE) { + std::cout << "Cannot unlock crypto folder, pcloudcc is offline" << std::endl; + return PSYNC_CRYPTO_CANT_CONNECT; } + + if(!psync_crypto_issetup()) { + std::cout << "crypto is not setup, setting it up now..." << std::endl; + if(int ret = pcryptofolder_setup(pwd, "no hint") != PSYNC_CRYPTO_SETUP_SUCCESS) { + std::cout << "crypto setup failed, error code was " << ret << std::endl; + return ret; + } + if(int ret = pcryptofolder_mkdir(0, "Crypto", NULL, NULL) != PSYNC_CRYPTO_SUCCESS) { + std::cout << "failed to create crypto directory, error code was" << ret << std::endl; + return ret; + } + std::cout << "crypto folder was setup using the provided password, " + << "you may want to change your password hint on the " + << "pcloud website." << std::endl; + } + + if(int ret = pcryptofolder_unlock(pwd) != PSYNC_CRYPTO_START_SUCCESS) { + std::cout << "Failed to unlock crypto folder: error code was " << ret << std::endl; + return ret; + } + clib::pclsync_lib::get_lib().crypto_on_ = true; - return ret; + return 0; } static const char *status2string(uint32_t status) { @@ -334,7 +343,6 @@ static void status_change(pstatus_t *status) { } int clib::pclsync_lib::start_crypto(const char *pass) { - std::cout << "calling startcrypto pass: " << pass << std::endl; get_lib().crypto_pass_ = pass; return lib_setup_cripto(); } @@ -451,12 +459,12 @@ int clib::pclsync_lib::init() { psync_free(username_old); } - psync_overlay_register_callback(20, &clib::pclsync_lib::start_crypto); - psync_overlay_register_callback(21, &clib::pclsync_lib::stop_crypto); - psync_overlay_register_callback(22, &clib::pclsync_lib::finalize); - psync_overlay_register_callback(23, &clib::pclsync_lib::list_sync_folders); - psync_overlay_register_callback(24, &clib::pclsync_lib::add_sync_folder); - psync_overlay_register_callback(25, &clib::pclsync_lib::remove_sync_folder); + psync_overlay_register_callback(STARTCRYPTO, &clib::pclsync_lib::start_crypto); + psync_overlay_register_callback(STOPCRYPTO, &clib::pclsync_lib::stop_crypto); + psync_overlay_register_callback(FINALIZE, &clib::pclsync_lib::finalize); + psync_overlay_register_callback(LISTSYNC, &clib::pclsync_lib::list_sync_folders); + psync_overlay_register_callback(ADDSYNC, &clib::pclsync_lib::add_sync_folder); + psync_overlay_register_callback(STOPSYNC, &clib::pclsync_lib::remove_sync_folder); return 0; }