diff --git a/.gitmodules b/.gitmodules index 062b2a8b..f9def22f 100644 --- a/.gitmodules +++ b/.gitmodules @@ -1,6 +1,6 @@ [submodule "deps/mbedtls"] path = deps/mbedtls - url = https://github.com/Mbed-TLS/mbedtls + url = https://github.com/Mbed-TLS/mbedtls.git [submodule "deps/esp-idf"] path = deps/esp-idf url = https://github.com/espressif/esp-idf.git diff --git a/.vscode/c_cpp_properties.json b/.vscode/c_cpp_properties.json index 33ee7ef8..5e9180d8 100644 --- a/.vscode/c_cpp_properties.json +++ b/.vscode/c_cpp_properties.json @@ -2,7 +2,7 @@ "configurations": [ { "name": "default", - "configurationProvider": "ms-vscode.cmake-tools", + // "configurationProvider": "ms-vscode.cmake-tools", "includePath": [ "${default}", "${workspaceFolder}/include/**", diff --git a/CMakeLists.txt b/CMakeLists.txt index 0e78d1b8..a37a4722 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -82,11 +82,35 @@ if(NOT BUILD_ESP_IDF) # build for other platforms NAME AES_CTR COMMAND $) - add_executable(test_main test/test_main.c) - target_link_libraries(test_main PRIVATE at_client) + add_executable(test_rsapublicpopulate test/test_rsapublicpopulate.c) + target_link_libraries(test_rsapublicpopulate PRIVATE at_client) add_test( - NAME MAIN - COMMAND $) + NAME RSA_PUBLICPOPULATE + COMMAND $) + + add_executable(test_rsaprivatepopulate test/test_rsaprivatepopulate.c) + target_link_libraries(test_rsaprivatepopulate PRIVATE at_client) + add_test( + NAME RSA_PRIVATEPOPULATE + COMMAND $) + + add_executable(test_rsasign test/test_rsasign.c) + target_link_libraries(test_rsasign PRIVATE at_client) + add_test( + NAME RSA_SIGN + COMMAND $) + + add_executable(test_rsaencrypt test/test_rsaencrypt.c) + target_link_libraries(test_rsaencrypt PRIVATE at_client) + add_test( + NAME RSA_ENCRYPT + COMMAND $) + + add_executable(test_rsadecrypt test/test_rsadecrypt.c) + target_link_libraries(test_rsadecrypt PRIVATE at_client) + add_test( + NAME RSA_DECRYPT + COMMAND $) # compiler flags target_compile_options(at_client # https://vladiant.github.io/blog/2021/08/14/cpp-compiler-flags diff --git a/include/at_chops.h b/include/at_chops.h index 6a65bac7..147de652 100644 --- a/include/at_chops.h +++ b/include/at_chops.h @@ -5,8 +5,9 @@ extern "C" { #endif -#include "base64.h" -#include "aes_ctr.h" +#include "at_chops/base64.h" +#include "at_chops/aes_ctr.h" +#include "at_chops/rsa.h" #ifdef __cplusplus } diff --git a/include/at_chops/aes_ctr.h b/include/at_chops/aes_ctr.h index e8d6553b..a6d7a7b6 100644 --- a/include/at_chops/aes_ctr.h +++ b/include/at_chops/aes_ctr.h @@ -1,10 +1,10 @@ #pragma once -// #ifdef BUILD_MBEDTLS -// #ifdef __cplusplus -// extern "C" -// { -// #endif +#ifdef BUILD_MBEDTLS +#ifdef __cplusplus +extern "C" +{ +#endif #include @@ -23,7 +23,7 @@ typedef struct { } AESResult; /** - * @brief AES 256 CTR encrypt plaintext + * @brief AES CTR encrypt plaintext * * @param key_base64 the base64 encoded AES 256 key (e.g. "1DPU9OP3CYvamnVBMwGgL7fm8yB1klAap0Uc5Z9R79g=") * @param plaintext the plain text to encryt, must be null terminated `\0` @@ -32,7 +32,7 @@ typedef struct { AESResult *atchops_aes_ctr_encrypt(const char *key_base64, const AESKeySize key_size, const unsigned char *plaintext); /** - * @brief AES 256 CTR decrypt cipher text + * @brief AES CTR decrypt cipher text * * @param key_base64 the base64 encoded AES 256 key (e.g. "1DPU9OP3CYvamnVBMwGgL7fm8yB1klAap0Uc5Z9R79g=") * @param ciphertext the base64 encoded cipher text, must be null terminated `\0` @@ -40,7 +40,7 @@ AESResult *atchops_aes_ctr_encrypt(const char *key_base64, const AESKeySize key_ */ AESResult *atchops_aes_ctr_decrypt(const char *key_base64, const AESKeySize key_size, const unsigned char *ciphertext); -// #ifdef __cplusplus -// } -// #endif -// #endif \ No newline at end of file +#ifdef __cplusplus +} +#endif +#endif \ No newline at end of file diff --git a/include/at_chops/base64.h b/include/at_chops/base64.h index ae7e3241..2da0509a 100644 --- a/include/at_chops/base64.h +++ b/include/at_chops/base64.h @@ -7,6 +7,8 @@ extern "C" #include +#define MAX_TEXT_LENGTH_FORBASE64_ENCODING_OPERATION 10000 // the max length of base64 encoded text (should be more than enough) + /** * @brief Encodes a string to base64 * diff --git a/include/at_chops/byteutil.h b/include/at_chops/byteutil.h new file mode 100644 index 00000000..706a1369 --- /dev/null +++ b/include/at_chops/byteutil.h @@ -0,0 +1,13 @@ +#pragma once + +#ifdef __cplusplus +extern "C" { +#endif + +void printx(unsigned char *data, size_t len); + +void copy(unsigned char *dst, unsigned char *src, size_t len); + +#ifdef __cplusplus +} +#endif diff --git a/include/at_chops/rsa.h b/include/at_chops/rsa.h new file mode 100644 index 00000000..02fb9e42 --- /dev/null +++ b/include/at_chops/rsa.h @@ -0,0 +1,84 @@ +#pragma once + +#ifdef BUILD_MBEDTLS +#ifdef __cplusplus +extern "C" +{ +#endif + +#include + +typedef struct rsa_param { + size_t len; + unsigned char *value; // hex byte array of the number +} rsa_param; + +typedef struct { + rsa_param n_param; // modulus + rsa_param e_param; // public exponent +} atchops_rsa2048_publickey; + +typedef struct { + rsa_param n_param; // modulus + rsa_param e_param; // public exponent + rsa_param d_param; // private exponent + rsa_param p_param; // prime 1 + rsa_param q_param; // prime 2 +} atchops_rsa2048_privatekey; + +typedef enum { + ATCHOPS_MD_NONE=0, /**< None. */ + ATCHOPS_MD_MD5, /**< The MD5 message digest. */ + ATCHOPS_MD_SHA1, /**< The SHA-1 message digest. */ + ATCHOPS_MD_SHA224, /**< The SHA-224 message digest. */ + ATCHOPS_MD_SHA256, /**< The SHA-256 message digest. */ + ATCHOPS_MD_SHA384, /**< The SHA-384 message digest. */ + ATCHOPS_MD_SHA512, /**< The SHA-512 message digest. */ + ATCHOPS_MD_RIPEMD160, +} atchops_md_type; + +/** + * @brief Populate a public key struct from a base64 string + * + * @param publickeybase64 a base64 string representing an RSA 2048 Public Key + * @param publickeybase64len the length of the base64 string + * @param publickeystruct the public key struct to populate + * @return int 0 on success + */ +int atchops_rsa_populate_publickey(const char *publickeybase64, const size_t publickeybase64len, atchops_rsa2048_publickey *publickeystruct); + +/** + * @brief Populate a private key struct from a base64 string + * + * @param privatekeybase64 the base64 string representing an RSA 2048 Private Key + * @param privatekeybase64len the length of the base64 string + * @param privatekeystruct the private key struct to populate + * @return int 0 on success + */ +int atchops_rsa_populate_privatekey(const char *privatekeybase64, const size_t privatekeybase64len, atchops_rsa2048_privatekey *privatekeystruct); + +/** + * @brief Sign a message with an RSA 2048 Private Key + * + * @param privatekeystruct the private key struct to use for signing + * @param mdtype the message digest type to use + * @param signature the signature to populate. Pass in a pointer to a pointer to an unsigned char array. The pointer will be reassigned to the newly allocated array. + * @param signaturelen the output length of the signature + * @param message the message to sign + * @param messagelen the length of the message + * @return int 0 on success + */ +int atchops_rsa_sign(atchops_rsa2048_privatekey privatekeystruct, atchops_md_type mdtype, unsigned char **signature, size_t *signaturelen, const unsigned char *message, const size_t messagelen); + +// todo +// int atchops_rsa2048_verify(atchops_rsa2048_publickey *publickeystruct, const unsigned char *signature, const size_t signaturelen, ); + +// todo comments +int atchops_rsa_encrypt(atchops_rsa2048_publickey publickeystruct, const char *plaintext, const size_t plaintextlen, char **ciphertext, size_t *ciphertextolen); + +// todo comments +int atchops_rsa_decrypt(atchops_rsa2048_privatekey privatekeystruct, const char *ciphertextbase64encoded, const size_t ciphertextbase64encodedlen, char **plaintext, size_t *plaintextolen); +#ifdef __cplusplus +} +#endif +#endif \ No newline at end of file diff --git a/run.sh b/run.sh new file mode 100755 index 00000000..b342c4e1 --- /dev/null +++ b/run.sh @@ -0,0 +1,4 @@ +#!/bin/bash +# python3 tool.py -p desktop -f mbedtls clean +python3 tool.py -p desktop -f mbedtls build +python3 tool.py -p desktop -f mbedtls test \ No newline at end of file diff --git a/src/at_chops/aes_ctr.c b/src/at_chops/aes_ctr.c index 43d82b63..be759899 100644 --- a/src/at_chops/aes_ctr.c +++ b/src/at_chops/aes_ctr.c @@ -16,7 +16,6 @@ extern "C" #define IV_AMOUNT_BYTES 16 #define MAX_BYTES_ALLOCATED_FOR_ENCRYPTION_OPERATION 5000 -#define MAX_TEXT_LENGTH_FORBASE64_ENCODING_OPERATION 10000 // the max length of base64 encoded text (should be more than enough) AESResult *atchops_aes_ctr_encrypt(const char *key_base64, const AESKeySize key_size, const unsigned char *plaintext ) { @@ -65,6 +64,8 @@ AESResult *atchops_aes_ctr_encrypt(const char *key_base64, const AESKeySize key_ unsigned char *stream_block = malloc(sizeof(unsigned char) * IV_AMOUNT_BYTES); unsigned char *aes_encrypted = malloc(sizeof(unsigned char) * MAX_BYTES_ALLOCATED_FOR_ENCRYPTION_OPERATION); + // maybe base 64 encode it before feeding to cipher + // run encrypt result->status = mbedtls_aes_crypt_ctr(ctx, plaintext_paddedlen, iv_ctr, iv, stream_block, plaintext_padded, aes_encrypted); @@ -141,13 +142,22 @@ AESResult *atchops_aes_ctr_decrypt(const char *key_base64, const AESKeySize key_ // find the value of the pad unsigned char pad_val = *(aes_decrypted + aes_decryptedlen - 2); + // printf("pad_val: %02x\n", pad_val); if(pad_val >= 0x00 && pad_val <= 0x0F || pad_val == 0x10) // https://www.ibm.com/docs/en/zos/2.4.0?topic=rules-pkcs-padding-method { // eliminate that amount of padding aes_decryptedlen -= (pad_val+1); *(aes_decrypted+aes_decryptedlen) = '\0'; - } - + } + + // printf("aa"); + // printf("aa\n"); + // for(int i = 0; i < aes_decryptedlen + 10; i++) + // { + // printf("%02x ", *(aes_decrypted+i)); + // } + // printf("aa\n"); + unsigned char *aes_decrypted_unpadded = malloc(sizeof(unsigned char) * aes_decryptedlen); for (int i = 0; i < aes_decryptedlen; i++) { diff --git a/src/at_chops/byteutil.c b/src/at_chops/byteutil.c new file mode 100644 index 00000000..30abfff7 --- /dev/null +++ b/src/at_chops/byteutil.c @@ -0,0 +1,31 @@ + +#ifdef __cplusplus +extern "C" +{ +#endif + +#include +#include "byteutil.h" + +void printx(unsigned char *data, size_t len) +{ + // TODO check len here, error handle return an int + for (size_t i = 0; i < len; i++) + { + printf("%02x ", data[i]); + } + printf("\n"); +} + +void copy(unsigned char *dst, unsigned char *src, size_t len) +{ + // TODO: check len here, error handle return an int + for (size_t i = 0; i < len; i++) + { + dst[i] = src[i]; + } +} + +#ifdef __cplusplus +} +#endif \ No newline at end of file diff --git a/src/at_chops/rsa.c b/src/at_chops/rsa.c new file mode 100644 index 00000000..3b9c53de --- /dev/null +++ b/src/at_chops/rsa.c @@ -0,0 +1,533 @@ +#ifdef BUILD_MBEDTLS +#ifdef __cplusplus +extern "C" +{ +#endif + +#include +#include +#include +#include +#include +#include +#include +#include +#include "at_chops/rsa.h" +#include "at_chops/base64.h" +#include "at_chops/byteutil.h" + +int atchops_rsa_populate_publickey(const char *publickeybase64, const size_t publickeybase64len, atchops_rsa2048_publickey *publickeystruct) +{ + int ret = 0; + + // 1. base64 decode the key + size_t dstlen = MAX_TEXT_LENGTH_FORBASE64_ENCODING_OPERATION; + unsigned char *dst = malloc(sizeof(unsigned char) * dstlen); + size_t *writtenlen = malloc(sizeof(size_t)); + ret = atchops_base64_decode(dst, dstlen, writtenlen, publickeybase64, publickeybase64len); + if (ret != 0) + goto ret; + + // printf("\n"); + // printf("writtenlen: %lu\n", *writtenlen); + // printx(dst, *writtenlen); + + const unsigned char *end = dst + (*writtenlen); + + size_t *lengthread = malloc(sizeof(size_t)); + ret = mbedtls_asn1_get_tag(&dst, end, lengthread, MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE); + // printf("ret: %d\n", ret); + if (ret != 0) + goto ret; + // printf("lengthread: %lu\n", *lengthread); + // printf("*(dst+0) now points to : %02x\n", *(dst+0)); + // printf("*(dst+1) now points to : %02x\n", *(dst+1)); + // printf("*(dst+2) now points to : %02x\n", *(dst+2)); + + size_t *lengthread2 = malloc(sizeof(size_t)); + ret = mbedtls_asn1_get_tag(&dst, end, lengthread2, MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE); + // printf("ret: %d\n", ret); + if (ret != 0) + goto ret; + // printf("lengthread2: %lu\n", *lengthread2); + // printf("*(dst+0) now points to : %02x\n", *(dst+0)); + // printf("*(dst+1) now points to : %02x\n", *(dst+1)); + // printf("*(dst+2) now points to : %02x\n", *(dst+2)); + dst = dst + (*lengthread2); + // printf("\n*(dst+0) now points to : %02x\n", *(dst+0)); + // printf("*(dst+1) now points to : %02x\n", *(dst+1)); + // printf("*(dst+2) now points to : %02x\n", *(dst+2)); + + size_t *lengthread3 = malloc(sizeof(size_t)); + ret = mbedtls_asn1_get_tag(&dst, end, lengthread3, MBEDTLS_ASN1_BIT_STRING); + // printf("ret: %d\n", ret); + if (ret != 0) + goto ret; + // printf("lengthread3: %lu\n", *lengthread3); + // printf("*(dst+0) now points to : %02x\n", *(dst+0)); + // printf("*(dst+1) now points to : %02x\n", *(dst+1)); + // printf("*(dst+2) now points to : %02x\n", *(dst+2)); + if (*dst == 0x00) + { + dst = dst + 1; + } + + mbedtls_asn1_sequence *seq = malloc(sizeof(mbedtls_asn1_sequence)); + ret = mbedtls_asn1_get_sequence_of(&dst, end, seq, MBEDTLS_ASN1_INTEGER); + // printf("ret: %d\n", ret); + if (ret != 0) + goto ret; + + mbedtls_asn1_sequence *current = seq; + // while (current != NULL) + // { + // printf("current->buf.tag: %02x\n", current->buf.tag); + // printf("current->buf.len: %lu\n", current->buf.len); + // printf("current->buf.p:\n"); + // for(int i = 0; i < current->buf.len; i++) + // { + // printf("%02x ", *(current->buf.p + i)); + // } + // printf("\n"); + // current = current->next; + // } + publickeystruct->n_param.len = current->buf.len; + publickeystruct->n_param.value = malloc(sizeof(unsigned char) * publickeystruct->n_param.len); + copy(publickeystruct->n_param.value, current->buf.p, publickeystruct->n_param.len); + + current = current->next; + publickeystruct->e_param.len = current->buf.len; + publickeystruct->e_param.value = malloc(sizeof(unsigned char) * publickeystruct->e_param.len); + copy(publickeystruct->e_param.value, current->buf.p, publickeystruct->e_param.len); + + goto ret; + + ret: + { + return ret; + } +} + +int atchops_rsa_populate_privatekey(const char *privatekeybase64, const size_t privatekeybase64len, atchops_rsa2048_privatekey *privatekeystruct) +{ + int ret = 1; + + size_t dstlen = MAX_TEXT_LENGTH_FORBASE64_ENCODING_OPERATION; + unsigned char *dst = malloc(sizeof(unsigned char) * dstlen); + size_t *writtenlen = malloc(sizeof(size_t)); + ret = atchops_base64_decode(dst, dstlen, writtenlen, privatekeybase64, privatekeybase64len); + if (ret != 0) + goto ret; + + // printf("\n"); + // printx(dst, *writtenlen); + // printf("writtenlen: %lu\n", *writtenlen); + // printf("\n"); + + char *end = dst + (*writtenlen); + + // printf("1st get tag\n"); + size_t *lengthread = malloc(sizeof(size_t)); + ret = mbedtls_asn1_get_tag(&dst, end, lengthread, MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE); + if (ret != 0) + goto ret; + // printf("ret: %d\n", ret); + // printf("lengthread: %lu\n", *lengthread); + // printf("*(dst+0) now points to : %02x\n", *(dst+0)); + // printf("*(dst+1) now points to : %02x\n", *(dst+1)); + // printf("*(dst+2) now points to : %02x\n", *(dst+2)); + // printf("*(dst+3) now points to : %02x\n", *(dst+3)); + // printf("*(dst+4) now points to : %02x\n", *(dst+4)); + + // printf("2nd get tag\n"); + size_t *lengthread2 = malloc(sizeof(size_t)); + ret = mbedtls_asn1_get_tag(&dst, end, lengthread2, MBEDTLS_ASN1_INTEGER); + if (ret != 0) + goto ret; + // printf("ret: %d\n", ret); + // printf("lengthread2: %lu\n", *lengthread2); + dst = dst + (*lengthread2); + // printf("*(dst+0) now points to : %02x\n", *(dst+0)); + // printf("*(dst+1) now points to : %02x\n", *(dst+1)); + // printf("*(dst+2) now points to : %02x\n", *(dst+2)); + // printf("*(dst+3) now points to : %02x\n", *(dst+3)); + // printf("*(dst+4) now points to : %02x\n", *(dst+4)); + + // printf("3rd get tag\n"); + size_t *lengthread3 = malloc(sizeof(size_t)); + ret = mbedtls_asn1_get_tag(&dst, end, lengthread3, MBEDTLS_ASN1_CONSTRUCTED | MBEDTLS_ASN1_SEQUENCE); + if (ret != 0) + goto ret; + // printf("ret: %d\n", ret); + // printf("lengthread3: %lu\n", *lengthread3); + dst = dst + (*lengthread3); + // printf("*(dst+0) now points to : %02x\n", *(dst+0)); + // printf("*(dst+1) now points to : %02x\n", *(dst+1)); + // printf("*(dst+2) now points to : %02x\n", *(dst+2)); + // printf("*(dst+3) now points to : %02x\n", *(dst+3)); + // printf("*(dst+4) now points to : %02x\n", *(dst+4)); + + // printf("4th get tag\n"); + size_t *lengthread4 = malloc(sizeof(size_t)); + ret = mbedtls_asn1_get_tag(&dst, end, lengthread4, 0x04); + if (ret != 0) + goto ret; + // printf("ret: %d\n", ret); + // printf("lengthread4: %lu\n", *lengthread4); + // printf("*(dst+0) now points to : %02x\n", *(dst+0)); + // printf("*(dst+1) now points to : %02x\n", *(dst+1)); + // printf("*(dst+2) now points to : %02x\n", *(dst+2)); + // printf("*(dst+3) now points to : %02x\n", *(dst+3)); + + // printf("5th get tag\n"); + mbedtls_asn1_sequence *seq = malloc(sizeof(mbedtls_asn1_sequence)); + ret = mbedtls_asn1_get_sequence_of(&dst, end, seq, MBEDTLS_ASN1_INTEGER); + if (ret != 0) + goto ret; + // printf("ret: %d\n", ret); + + // traverse seq + mbedtls_asn1_sequence *current = seq; + // current = seq; + // while (current != NULL) + // { + // printf("current->buf.tag: %02x\n", current->buf.tag); + // printf("current->buf.len: %lu\n", current->buf.len); + // printf("current->buf.p:\n"); + // for(int i = 0; i < current->buf.len; i++) + // { + // printf("%02x ", *(current->buf.p + i)); + // } + // printf("\n"); + + // current = current->next; + // } + + // printf("\n--------"); + + current = current->next; + + // printf("n\n"); + privatekeystruct->n_param.len = current->buf.len; + privatekeystruct->n_param.value = malloc(sizeof(unsigned char) * privatekeystruct->n_param.len); + copy(privatekeystruct->n_param.value, current->buf.p, privatekeystruct->n_param.len); + + // printf("e\n"); + current = current->next; + privatekeystruct->e_param.len = current->buf.len; + privatekeystruct->e_param.value = malloc(sizeof(unsigned char) * privatekeystruct->e_param.len); + copy(privatekeystruct->e_param.value, current->buf.p, privatekeystruct->e_param.len); + + // printf("d\n"); + current = current->next; + privatekeystruct->d_param.len = current->buf.len; + privatekeystruct->d_param.value = malloc(sizeof(unsigned char) * privatekeystruct->d_param.len); + copy(privatekeystruct->d_param.value, current->buf.p, privatekeystruct->d_param.len); + + // printf("p\n"); + current = current->next; + privatekeystruct->p_param.len = current->buf.len; + privatekeystruct->p_param.value = malloc(sizeof(unsigned char) * privatekeystruct->p_param.len); + copy(privatekeystruct->p_param.value, current->buf.p, privatekeystruct->p_param.len); + + // printf("q\n"); + current = current->next; + privatekeystruct->q_param.len = current->buf.len; + privatekeystruct->q_param.value = malloc(sizeof(unsigned char) * privatekeystruct->q_param.len); + copy(privatekeystruct->q_param.value, current->buf.p, privatekeystruct->q_param.len); + + goto ret; + + ret: + { + return ret; + } +} + +int atchops_rsa_sign(atchops_rsa2048_privatekey privatekeystruct, atchops_md_type mdtype, unsigned char **signature, size_t *signaturelen, const unsigned char *message, const size_t messagelen) +{ + int ret = 1; // error, until successful. + + mbedtls_md_context_t md_ctx; + mbedtls_md_init(&md_ctx); + + mbedtls_md_type_t md_type = mdtype; // TODO dynamic + + ret = mbedtls_md_setup(&md_ctx, mbedtls_md_info_from_type(md_type), 0); + if (ret != 0) + goto ret; + + ret = mbedtls_md_starts(&md_ctx); + if (ret != 0) + goto ret; + + ret = mbedtls_md_update(&md_ctx, message, messagelen); + if (ret != 0) + goto ret; + + const size_t hashlen = mbedtls_md_get_size(mbedtls_md_info_from_type(md_type)); + // printf("hashlen: %lu\n", hashlen); + unsigned char *hash = malloc(sizeof(unsigned char) * hashlen); + + ret = mbedtls_md_finish(&md_ctx, hash); + if (ret != 0) + goto ret; + + mbedtls_md_free(&md_ctx); + + // printf("signaturelen: %lu\n", *signaturelen); + // for(int i = 0; i < *signaturelen; i++) + // { + // printf("%02x ", *(*signature + i)); + // } + // printf("\n"); + + // *signature = malloc(sizeof(unsigned char) * (*signaturelen)); + + mbedtls_rsa_context rsa; + mbedtls_rsa_init(&rsa); + + // printf("\nn: %lu\n", privatekeystruct->n->len); + // printx(privatekeystruct->n->n, privatekeystruct->n->len); + // printf("\ne: %lu\n", privatekeystruct->e->len); + // printx(privatekeystruct->e->e, privatekeystruct->e->len); + // printf("\nd: %lu\n", privatekeystruct->d->len); + // printx(privatekeystruct->d->d, privatekeystruct->d->len); + // printf("\np: %lu\n", privatekeystruct->p->len); + // printx(privatekeystruct->p->p, privatekeystruct->p->len); + // printf("\nq: %lu\n", privatekeystruct->q->len); + // printx(privatekeystruct->q->q, privatekeystruct->q->len); + + ret = mbedtls_rsa_import_raw(&rsa, + privatekeystruct.n_param.value, privatekeystruct.n_param.len, + privatekeystruct.p_param.value, privatekeystruct.p_param.len, + privatekeystruct.q_param.value, privatekeystruct.q_param.len, + privatekeystruct.d_param.value, privatekeystruct.d_param.len, + privatekeystruct.e_param.value, privatekeystruct.e_param.len); + + // printf("rsa import: %d\n", ret); + if (ret != 0) + goto ret; + + ret = mbedtls_rsa_complete(&rsa); + // printf("rsa complete: %d\n", ret); + if (ret != 0) + goto ret; + + ret = mbedtls_rsa_check_privkey(&rsa); + // printf("rsa check privkey: %d\n", ret); + if (ret != 0) + goto ret; + + mbedtls_entropy_context entropy_ctx; + mbedtls_entropy_init(&entropy_ctx); + + mbedtls_ctr_drbg_context ctr_drbg_ctx; + mbedtls_ctr_drbg_init(&ctr_drbg_ctx); + ret = mbedtls_ctr_drbg_seed(&ctr_drbg_ctx, mbedtls_entropy_func, &entropy_ctx, NULL, 0); + // printf("mbedtls_ctr_drbg_seed: %d\n", ret); + if (ret != 0) + goto ret; + + // printf("mbedtls_rsa_self_test: %d\n", mbedtls_rsa_self_test(0)); + + // printf("hashlen: %lu\n", hashlen); + // printf("hash: "); + // printx(hash, hashlen); + int buflen = 256; + unsigned char *buf = malloc(sizeof(unsigned char) * buflen + 1); // +1 for null terminator + ret = mbedtls_rsa_pkcs1_sign(&rsa, mbedtls_ctr_drbg_random, &ctr_drbg_ctx, MBEDTLS_MD_SHA256, hashlen, hash, buf); + // printf("mbedtls_rsa_pkcs1_sign: %d\n", ret); + if (ret != 0) + goto ret; + + // printf("buflen: %lu\n", buflen); + // for (int i = 0; i < buflen; i++) + // { + // printf("%02x ", *(buf + i)); + // } + // printf("\n"); + + // base64 encode + size_t *writtenlen = malloc(sizeof(size_t)); + unsigned char *dst = malloc(sizeof(unsigned char) * MAX_TEXT_LENGTH_FORBASE64_ENCODING_OPERATION); + ret = atchops_base64_encode(dst, MAX_TEXT_LENGTH_FORBASE64_ENCODING_OPERATION, writtenlen, buf, buflen); + if (ret != 0) + goto ret; + + // append null terminator + *(dst + *writtenlen) = '\0'; + // printf("Challenge: %s\n", dst); + + *signature = dst; + *signaturelen = *writtenlen; + + goto ret; + + ret: + { + return ret; + } +} + +int atchops_rsa_encrypt(atchops_rsa2048_publickey publickeystruct, const char *plaintext, const size_t plaintextlen, char **ciphertext, size_t *ciphertextolen) +{ + int ret = 1; + + mbedtls_rsa_context rsa; + mbedtls_rsa_init(&rsa); + + // printf("importing raw...\n"); + ret = mbedtls_rsa_import_raw(&rsa, publickeystruct.n_param.value, publickeystruct.n_param.len, NULL, NULL, NULL, NULL, NULL, NULL, publickeystruct.e_param.value, publickeystruct.e_param.len); + if(ret != 0) + goto ret; + + // printf("n: %d\n", publickeystruct.n_param.len); + // printx(publickeystruct.n_param.value, publickeystruct.n_param.len); + + // printf("e: %d\n", publickeystruct.e_param.len); + // printx(publickeystruct.e_param.value, publickeystruct.e_param.len); + + + // printf("checking public key...\n"); + ret = mbedtls_rsa_check_pubkey(&rsa); + // printf("public key check: %d\n", ret); + if(ret != 0) + goto ret; + + // printf("completing rsa...\n"); + ret = mbedtls_rsa_complete(&rsa); + if(ret != 0) + goto ret; + + // printf("base64 encoding...\n"); + // base64 encode the plain text + size_t dstlen = MAX_TEXT_LENGTH_FORBASE64_ENCODING_OPERATION; + unsigned char *dst = malloc(sizeof(unsigned char) * dstlen); + size_t *olen = malloc(sizeof(size_t)); + ret = atchops_base64_encode(dst, dstlen, olen, plaintext, plaintextlen); + if(ret != 0) + goto ret; + + mbedtls_entropy_context entropy_ctx; + mbedtls_entropy_init(&entropy_ctx); + + // printf("seeding...\n"); + mbedtls_ctr_drbg_context ctr_drbg_ctx; + mbedtls_ctr_drbg_init(&ctr_drbg_ctx); + ret = mbedtls_ctr_drbg_seed(&ctr_drbg_ctx, mbedtls_entropy_func, &entropy_ctx, NULL, 0); + // printf("mbedtls_ctr_drbg_seed: %d\n", ret); + if (ret != 0) + goto ret; + + // printf("encrypting...\n"); + // encrypt the base64 encoded text + size_t outputlen = 256; // 256 bytes is the result of an RSA + unsigned char *output = malloc(sizeof(unsigned char) * outputlen); + ret = mbedtls_rsa_pkcs1_encrypt(&rsa, mbedtls_ctr_drbg_random, &ctr_drbg_ctx, plaintextlen, plaintext, output); + if(ret != 0) + goto ret; + + dstlen = MAX_TEXT_LENGTH_FORBASE64_ENCODING_OPERATION; + unsigned char *dst2 = malloc(sizeof(unsigned char) * dstlen); + free(olen); + *olen = malloc(sizeof(size_t)); + + ret = atchops_base64_encode(dst2, dstlen, olen, output, outputlen); + if(ret != 0) + goto ret; + + // printx(dst2, *olen); + // printf("%s\n", dst2); + + *ciphertext = dst2; + *ciphertextolen = *olen; + + goto ret; + + ret: + { + return ret; + } + +} + +int atchops_rsa_decrypt(atchops_rsa2048_privatekey privatekeystruct, const char *ciphertextbase64encoded, const size_t ciphertextbase64encodedlen, char **plaintext, size_t *plaintextolen) +{ + int ret = 1; + + mbedtls_rsa_context rsa; + mbedtls_rsa_init(&rsa); + + ret = mbedtls_rsa_import_raw(&rsa, privatekeystruct.n_param.value, privatekeystruct.n_param.len, privatekeystruct.p_param.value, privatekeystruct.p_param.len, privatekeystruct.q_param.value, privatekeystruct.q_param.len, privatekeystruct.d_param.value, privatekeystruct.d_param.len, privatekeystruct.e_param.value, privatekeystruct.e_param.len); + if(ret != 0) + goto ret; + + // printf("n: %lu\n", privatekeystruct.n_param.len); + // printx(privatekeystruct.n_param.value, privatekeystruct.n_param.len); + // printf("e: %lu\n", privatekeystruct.e_param.len); + // printx(privatekeystruct.e_param.value, privatekeystruct.e_param.len); + // printf("d: %lu\n", privatekeystruct.d_param.len); + // printx(privatekeystruct.d_param.value, privatekeystruct.d_param.len); + // printf("p: %lu\n", privatekeystruct.p_param.len); + // printx(privatekeystruct.p_param.value, privatekeystruct.p_param.len); + // printf("q: %lu\n", privatekeystruct.q_param.len); + // printx(privatekeystruct.q_param.value, privatekeystruct.q_param.len); + + ret = mbedtls_rsa_complete(&rsa); + if(ret != 0) + goto ret; + + ret = mbedtls_rsa_check_privkey(&rsa); + if(ret != 0) + goto ret; + + + // base64 decode the ciphertext + const size_t dstlen = MAX_TEXT_LENGTH_FORBASE64_ENCODING_OPERATION; + unsigned char *dst = malloc(sizeof(unsigned char) * dstlen); + size_t *writtenlen = malloc(sizeof(size_t)); + ret = atchops_base64_decode(dst, dstlen, writtenlen, ciphertextbase64encoded, ciphertextbase64encodedlen); + if(ret != 0) + goto ret; + + mbedtls_entropy_context entropy_ctx; + mbedtls_entropy_init(&entropy_ctx); + + mbedtls_ctr_drbg_context ctr_drbg_ctx; + mbedtls_ctr_drbg_init(&ctr_drbg_ctx); + ret = mbedtls_ctr_drbg_seed(&ctr_drbg_ctx, mbedtls_entropy_func, &entropy_ctx, NULL, 0); + if (ret != 0) + goto ret; + + // rsa decrypt dst + const size_t outputmaxlen = 5000; + unsigned char *output = malloc(sizeof(unsigned char) * outputmaxlen); + size_t *writtenlen2 = malloc(sizeof(size_t)); + ret = mbedtls_rsa_pkcs1_decrypt(&rsa, mbedtls_ctr_drbg_random, &ctr_drbg_ctx, writtenlen2, dst, output, outputmaxlen); + if(ret != 0) + goto ret; + + // base64 decode the output + // const size_t dstlen2 = MAX_TEXT_LENGTH_FORBASE64_ENCODING_OPERATION; + // unsigned char *dst2 = malloc(sizeof(unsigned char) * dstlen2); + // size_t *writtenlen3 = malloc(sizeof(size_t)); + // printf("7\n"); + // ret = atchops_base64_encode(dst2, dstlen2, writtenlen3, output, *writtenlen); + // if(ret != 0) + // goto ret; + + *plaintext = output; + *plaintextolen = *writtenlen2; + + goto ret; + + ret: { + return ret; + } +} + +#ifdef __cplusplus +} +#endif +#endif \ No newline at end of file diff --git a/test/test_aes_ctr.c b/test/test_aes_ctr.c index d9125440..834efad2 100644 --- a/test/test_aes_ctr.c +++ b/test/test_aes_ctr.c @@ -15,8 +15,8 @@ void printx(const unsigned char *str, size_t len) int main() { int retval = 0; - const char *aes_key = "1DPU9OP3CYvamnVBMwGgL7fm8yB1klAap0Uc5Z9R79g="; // 32 byte key - const char *plaintext = "i like to eat pizza 123 ++ -- //"; + const char *aes_key = "1DPU9OP3CYvamnVBMwGgL7fm8yB1klAap0Uc5Z9R79g="; // 32 byte key == 256 bits + const char *plaintext = "i like to eat pizza !! ++"; // printf("plaintext: "); // printf("%s\n", plaintext); // printx((const unsigned char *)plaintext, strlen(plaintext)); diff --git a/test/test_main.c b/test/test_main.c deleted file mode 100644 index 61d2c572..00000000 --- a/test/test_main.c +++ /dev/null @@ -1,9 +0,0 @@ - - -#include - -int main() -{ - // printf("Hello World!\n"); - return 0; -} \ No newline at end of file diff --git a/test/test_rsa.c b/test/test_rsa.c new file mode 100644 index 00000000..b5cc91a0 --- /dev/null +++ b/test/test_rsa.c @@ -0,0 +1,114 @@ +#include +#include +#include +#include +#include "at_chops/rsa.h" +#include "at_chops/base64.h" + +int main() +{ + int ret = 0; + // const unsigned char *privatekeybase64 = "MIIEvAIBADANBgkqhkiG9w0BAQEFAASCBKYwggSiAgEAAoIBAQCy64Pzy9ZDdm6e96z3DmjektD7sKUo40Ax+1VD12Ksm3pUPTGDkM3Nf4Sp2ATcy6ZbCRHSEWtx7dPfC/H1p7yS9KOVLtAmx8aT0SNiT+WGsclshI/n/XP+jCjxrpYwf4ntgX2i6p6hlo/ZiW8i3+Ayyhw8uYuVMUyMHv70EaoTN0+N5QF9l74LkLYL7cXyfZayDPTZJxbLF2WEoQz4ZWJhgFk40EeBw03jiLg/T0hw1gbS0z97HhZs/QPtTaDR9EJYq27eZagRFZ6em7esrjjTpmGaTJmtZjEomV6o/EOtdvImRe1tViI22DWGAKi87BBGXR5Zr3xoRXPSypHLqLsNAgMBAAECggEAatzd//QEMmD/KzVU+m6B1kYsSde0nZo1kmTCBXYUenGWe8/cze7j7NQ4AVWDefiskHz3Rteeq/pXbEXvK0EXEVLKjWTbb/4sLcdg8ew0c+GmI4l9hhtMd4FxRwB2tdrHH7MSvgaR3oNVwaEjXtoGR2+Ns/tCUkaSqLIupsoSIc0Mj07Teq7SZvAe++oMyNgkyArR509oSG0GQFQp706VgLaUVrvtlMEXvtGB0pcn/y1Axz/l9VvYpojYp7MqSwVU6R4GWxjrn4JXCVQrh48VmuJS83i2oqFgbAXD2KyNjjkoW3Z26uhfJ0qgN2PeQgMYH06gNhfEYOAGTI8HgtfChQKBgQDc7xIYG0IchAX/0lds4yUXRRF9wEjZmsvaf6LZPEs97/z11cAbTp41zlppCqpGL0md/lTwFVwsmGuZNob999sGKi7A6mM2sBj+QiBoHACvl2e167O72eFYqyXtJwDH5XOA5JMHbc6GJpSeVE29UnIgq1czgp3DtapQRX3BOPMRYwKBgQDPUVjZJERK5N9ccs59gjyKiu6e60m42AVjpvaCWbqPSZXTEhGM8X9OJNsdZufRoMi6tYctXGthiB4HOoV1E5ACvJxgWpOTmbqqbBDA5pQPrJ4eRdigHjGnrAWdsJ+3smMbhk/6Ai00gmqwz8rv7eyGSY+dwOem/vPoJOrlRFFkzwKBgH+IhbJiscQSNgBZpFvXtwZ6uUEU6Tir0bccbJ3n3ysuyKAENnPM6yj2KFxwaqA/FcjdEpzQR7f6eEomHsCl/cnOOdTkuEbOWm8TLu/KEl9KD/UEzWjHufxcN3VxSVMa0ZT63SCxs0DfLnVDBukdmYHgRmMWqAlcaacSpigOvskvAoGADVikSp5OEzA2vOHbLzNCKH0XLX3iKhcmCatG9U9Hdk/7aDIilRs64dH3lSX5yIH8SiDDigUIGKhFnpuC2e2feL2hp4ZNN9ROswfv8Csn3vZy22oNrwkikzO8zNEBBzdhr/Tukx6uwFGhAq7t1pJPhrmXmEVB5HtHQmuV/5ptTvsCgYA5d5L3hO3+1Na4C6xj8luQXFhkSLNe0rwoe16OLjcyzcnhlb2KKA8rORGP28s1JcCL4Htasf0YzCkOJ/jR28GzX/0qvWu0hBSilV2mCAqwQ1fvZx0L4quJznkAhJPMZ+oag8o1LlQiJGgnhsIMbDLZApKh3NuYlTmdqo20FfkZkg=="; + // size_t privatekeybase64len = strlen(privatekeybase64); + + // atchops_rsa2048_privatekey *privatekeystruct; + // atchops_rsa2048_privatekey_init(&privatekeystruct); + + // ret = atchops_rsa_populate_privatekey(privatekeybase64, privatekeybase64len, privatekeystruct); + // if (ret != 0) goto ret; + // printf("ret: %d\n", ret); + + // // print n e d p q lengths + // printf("n len: %lu\n", privatekeystruct->n->len); + // printf("e len: %lu\n", privatekeystruct->e->len); + // printf("d len: %lu\n", privatekeystruct->d->len); + // printf("p len: %lu\n", privatekeystruct->p->len); + // printf("q len: %lu\n", privatekeystruct->q->len); + + // print n e d p q + // printf("n: "); + // printx(privatekeystruct->n->n, privatekeystruct->n->len); + // printf("e: "); + // printx(privatekeystruct->e->e, privatekeystruct->e->len); + // printf("d: "); + // printx(privatekeystruct->d->d, privatekeystruct->d->len); + // printf("p: "); + // printx(privatekeystruct->p->p, privatekeystruct->p->len); + // printf("q: "); + // printx(privatekeystruct->q->q, privatekeystruct->q->len); + + // atchops_rsa2048_privatekey_free(privatekeystruct); + + // ===== + // public key test + // ==== + + // const unsigned char *publickeybase64 = "MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAsuuD88vWQ3Zunves9w5o3pLQ+7ClKONAMftVQ9dirJt6VD0xg5DNzX+EqdgE3MumWwkR0hFrce3T3wvx9ae8kvSjlS7QJsfGk9EjYk/lhrHJbISP5/1z/owo8a6WMH+J7YF9ouqeoZaP2YlvIt/gMsocPLmLlTFMjB7+9BGqEzdPjeUBfZe+C5C2C+3F8n2Wsgz02ScWyxdlhKEM+GViYYBZONBHgcNN44i4P09IcNYG0tM/ex4WbP0D7U2g0fRCWKtu3mWoERWenpu3rK4406ZhmkyZrWYxKJleqPxDrXbyJkXtbVYiNtg1hgCovOwQRl0eWa98aEVz0sqRy6i7DQIDAQAB"; + + // size_t publickeybase64len = strlen(publickeybase64); + + // atchops_rsa2048_publickey *publickeystruct; + // atchops_rsa2048_publickey_init(&publickeystruct); + + // ret = atchops_rsa_populate_publickey(publickeybase64, publickeybase64len, publickeystruct); + // if (ret != 0) goto ret; + + // print n e lengths + // printf("n len: %lu\n", publickeystruct->n->len); + // printf("e len: %lu\n", publickeystruct->e->len); + + // print n e + // printf("n: "); + // printx(publickeystruct->n->n, publickeystruct->n->len); + // printf("e: "); + // printx(publickeystruct->e->e, publickeystruct->e->len); + + // atchops_rsa2048_publickey_free(publickeystruct); + + + // ===== + // encrypt test + // ==== + + // const unsigned char* plaintext = "lemonade"; + // size_t plaintextlen = strlen(plaintext); + + // const size_t ciphertextlen = 1000; + // unsigned char *ciphertext = malloc(sizeof(unsigned char) * ciphertextlen); + // size_t *ciphertextolen = malloc(sizeof(size_t)); + + // ret = atchops_rsa2048_encrypt(publickeystruct, plaintext, plaintextlen, ciphertext, ciphertextlen, ciphertextolen); + // if (ret != 0) goto ret; + + // ===== + // signing + // ===== + + // unsigned char *signature = malloc(sizeof(unsigned char) * 5000); + // size_t *signaturelen = malloc(sizeof(size_t)); + // const unsigned char *message = "_4a160d33-0c63-4800-bee0-ee254752f8c8@jeremy_0:6c987cc1-0dde-4ba1-af56-a9677086182"; + // const size_t messagelen = strlen(message); + + // ret = atchops_rsa_sign(privatekeystruct, ATCHOPS_MD_SHA256, &signature, signaturelen, message, messagelen); + // if(ret != 0) goto ret; + + // printf("signature len: %lu\n", *signaturelen); + // printf("signature: %s\n", signature); + + // ret = strncmp(signature, "AwsKWNqRHiCtdNJ0U5GXZ1H5obptEWVR1+A1kPhot4cdLfmulvBVXRaBIrP+jd2TSP2J/KNAgv2BDLH7DXUibdTnzJaKm/QKAjpwpuShnV6Y9KSWTnomBw9x9OWDkVrBzSo5rOFpHHOTZJhp4ygStKEzZDa108g8uP5PpkfzntO2eIVEOdMHoL9/yAkuYJcz+VmCH+1AJtCdeKfhjfmlk0bP72fwsait6pA3TW0iEll9ptZmlLjNtCTi982h1yNprh+XtrjMz7ClbJChQf3LLHiJMZ+7r4yKTrehdBVfxQoNNw9r2D7TBRaY8bXYwMombMHRuu0oVbqNU1jEs60NGQ==", *signaturelen); + // if(ret != 0) goto ret; + + // TODO signature to use mpi_ constant A buffer length of #MBEDTLS_MPI_MAX_SIZE is always safe. + + // unsigned char *signature_str = malloc(sizeof(unsigned char) * ((*signaturelen) + 1)); + // memcpy(signature_str, signature, *signaturelen); + // signature_str[*signaturelen] = '\0'; + // printf("Signature: %s\n", signature_str); + + goto ret; + + ret: { + return ret; + } +} + diff --git a/test/test_rsadecrypt.c b/test/test_rsadecrypt.c new file mode 100644 index 00000000..96a4d3db --- /dev/null +++ b/test/test_rsadecrypt.c @@ -0,0 +1,40 @@ +#include +#include +#include +#include "at_chops/rsa.h" + +#define PRIVATEKEYBASE64 "MIIEvAIBADANBgkqhkiG9w0BAQEFAASCBKYwggSiAgEAAoIBAQCDc/uZ5+pmDYY1A+IQdiKeZNhRxttbYCv1aLksIP+5Fk1GJAnKlsBBum+Tp8CjXCHk22nWSM8YesiKRQFVEQi1OS6Whs449U1oLkVSDzqRAnZaT5nI9oIh+u2jsa/7KfYOIqqN1h17GOZopsw73RZJnvISYLaarxtFABIPQ+gbdFfWySEaRXUW89sfg4QO7MzEd8ZwK8KLf4E9xuCMshP90p7bMAdLn98T04rVvP78W60lMXwzospBjwT6HZxCNMSfdFEmVwynivCr/QY2abeY1jkSFRxqYqJJYgsb1rydjN4hRp9eYRIJmT4nXJW71ByZc/wOiS/7gou/vr9jVGypAgMBAAECggEAFTkjlQypfoKOeX6///Ji0nnrpwBZKB6V2lBnHSXSw7pDDaEB57CBJ9uG6ir6YiWc30tBgjRNI2GngRN1DJvscP3jdLAdGXsZXUmjLYWB6imgnCIf7R9HkV7nATfN9tomfM/CA5ZfOiGiCaFsdfnTAF3mLWtp7/13hKNnRwmqrsvUzJrqzNFqZty7YRtkm2pxxetsycq2WGKkOjwEyJdDZSI5XbQyAzuu878WEi+Th4EI2MV21jAuP7WEAZC/tBSLLFSZgiHnMaMnQ9ogWnxCbdIJfWPBiK54kcDRN2o/I7iXAVD5W3oadEYgEn6SBuG4ZQtqTM8cFSofxrGuVfyQgQKBgQDZnwC501pza1Jm4/H/lvB67kup9EFwQFbCTjJKuHd1NuV1O0LcHER5wfgLOac2My7kXva8gsheLHdi9ciPNtqhHrJVpl4QyXYd6h7m3FImGCfd1xwqrfWPPA0aMM8e8QZGANrX7Z20xzEzSgMu/0trg7WS4P7ChO2VHXviEn4mMQKBgQCaorqBjvajf9wkwh5V06HmpaI8Ji7JvRD44l1G0eGJgCrSYbvFUQr4KzfaQltfwaMJnqoNVrqey9yhPaFacjI2QbBM3zECjmasy9m20VS70QsV7XKq7tKco8M+YfUwzOFOKrpxUm/AG7SoTmTIwsg+VkZNTPWQB74kwKmRkkj3+QKBgGxnXi8y702rWmLSjYvqHmS+K4a/m5FVG2KzHS5HcYo8DFU3bfjDRAD69Jpy366KFIPCIlqJM1JmCBqNoJhmlMXJysALnbPzBxmjtDz/5xP+2G0TaH6CJV5yZXx0b9hT6/IXHuyM+xBAYWvRJIDWvzURaPN/jKhNGyQ6ial12M0hAoGAdFadbr+6O0QEwfrxi6zPD5HpvssTRF/kFvtnJdLdle9BSEqTVF4mnJMXUDPAPwiVurUORz7K5JGHih+t9zgXIs7E7vC0FLJB+RrczzgqQauCZZrhPEy1U3e5eoOETpS1pXNsFbnprWSqxD1GgexZbtzFw350+Ul5+nigmo6uKzECgYBuZVdUFt0XpIWZ8hugSMhCxHhNZMrOAIbQp0eXMs3U25zd8RpUx4qXK39Sp+X6Ifs8jCfSjThhI5Ip0L0/vz5IyBrTUwbaCJVmLZU69UHNm2g8I6FoMQx3w7/ILo2mlfhd9QwTEzyT9dsdXq23HJeMkWzoVLieTHySu20n+PxXbQ==" + +#define CIPHERTEXTBASE64 "QVZmFo7iE0qr8QbF9pwBM9/AwPezOe+zzzSl2J/CKkyjwc8RsU4MCi5Mr/L09S+t8j3a092pax6OglKeS49xGlfmBWoFoCStb98T+ifwlYFnnKiSehDqUh3tvtMDgmmiUVxbCKR5CTsQYndGVeQaKhCLzl2Pv5OOutP9Uon2C42NQK3nOlEV7vMIlzY/HyiSWU+0sUkWLG01lChjI4m8cdfLjM/c+vxJe8qOFJKewtAuTdg63Q0tR0qZ/O7EHJ1JMKdc/fPFpKz8whZAevhx3UIIzilI7xBluMYKEi4jDH/p4UARTc1LALGE/7eQ5mVdPsdPU/h4Jd5jWbkXWOA1nA==" + +int main() +{ + int ret = 1; + atchops_rsa2048_privatekey privatekeystruct; + + const size_t privatekeylen = strlen(PRIVATEKEYBASE64); + const char *privatekey = PRIVATEKEYBASE64; + + const size_t ciphertextlen = strlen(CIPHERTEXTBASE64); + const char *ciphertext = CIPHERTEXTBASE64; + + ret = atchops_rsa_populate_privatekey(privatekey, privatekeylen, &privatekeystruct); + if(ret != 0) + goto ret; + + char *plaintext = malloc(sizeof(unsigned char) * 5000); + size_t *plaintextlen = malloc(sizeof(size_t)); + plaintext[*plaintextlen] = '\0'; // add null terminator, not necessary but it's okay + + ret = atchops_rsa_decrypt(privatekeystruct, ciphertext, ciphertextlen, &plaintext, plaintextlen); + if(ret != 0) + goto ret; + + // printf("plaintext: %s\n", plaintext); + + goto ret; + + ret: { + return ret; + } +} \ No newline at end of file diff --git a/test/test_rsaencrypt.c b/test/test_rsaencrypt.c new file mode 100644 index 00000000..1d71b837 --- /dev/null +++ b/test/test_rsaencrypt.c @@ -0,0 +1,48 @@ + +#include +#include +#include +#include "at_chops/rsa.h" +#include "at_chops/byteutil.h" + +#define PUBLICKEYBASE64 "MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAg3P7mefqZg2GNQPiEHYinmTYUcbbW2Ar9Wi5LCD/uRZNRiQJypbAQbpvk6fAo1wh5Ntp1kjPGHrIikUBVREItTkulobOOPVNaC5FUg86kQJ2Wk+ZyPaCIfrto7Gv+yn2DiKqjdYdexjmaKbMO90WSZ7yEmC2mq8bRQASD0PoG3RX1skhGkV1FvPbH4OEDuzMxHfGcCvCi3+BPcbgjLIT/dKe2zAHS5/fE9OK1bz+/FutJTF8M6LKQY8E+h2cQjTEn3RRJlcMp4rwq/0GNmm3mNY5EhUcamKiSWILG9a8nYzeIUafXmESCZk+J1yVu9QcmXP8Dokv+4KLv76/Y1RsqQIDAQAB" + +#define PLAINTEXT "banana" + +int main() +{ + int ret = 1; + + size_t publickeylen = strlen(PUBLICKEYBASE64); + const char *publickey = PUBLICKEYBASE64; + + const char *plaintext = PLAINTEXT; + const size_t plaintextlen = strlen(plaintext); + + atchops_rsa2048_publickey publickeystruct; + + // printf("populating public key struct..\n"); + ret = atchops_rsa_populate_publickey(publickey, publickeylen, &publickeystruct); + if(ret != 0) + goto ret; + + const size_t ciphertextlen = 256; + char *ciphertext = malloc((sizeof(unsigned char) * ciphertextlen) + 1); + size_t *ciphertextolen = malloc(sizeof(size_t)); + ciphertext[*ciphertextolen] = '\0'; // add null terminator, not necessary but it's okay + + // printf("encrypting...\n"); + ret = atchops_rsa_encrypt(publickeystruct, plaintext, plaintextlen, &ciphertext, ciphertextolen); + if(ret != 0) + goto ret; + + printf("ciphertext (base64 encoded): %s\n", ciphertext); + // printx(ciphertext, *ciphertextolen); + + goto ret; + + ret: + { + return ret; + } +} \ No newline at end of file diff --git a/test/test_rsaprivatepopulate.c b/test/test_rsaprivatepopulate.c new file mode 100644 index 00000000..043a833a --- /dev/null +++ b/test/test_rsaprivatepopulate.c @@ -0,0 +1,72 @@ +#include "at_chops/rsa.h" +#include "at_chops/byteutil.h" +#include +#include + +#define PRIVATE_KEY_BASE64 "MIIEvAIBADANBgkqhkiG9w0BAQEFAASCBKYwggSiAgEAAoIBAQCy64Pzy9ZDdm6e96z3DmjektD7sKUo40Ax+1VD12Ksm3pUPTGDkM3Nf4Sp2ATcy6ZbCRHSEWtx7dPfC/H1p7yS9KOVLtAmx8aT0SNiT+WGsclshI/n/XP+jCjxrpYwf4ntgX2i6p6hlo/ZiW8i3+Ayyhw8uYuVMUyMHv70EaoTN0+N5QF9l74LkLYL7cXyfZayDPTZJxbLF2WEoQz4ZWJhgFk40EeBw03jiLg/T0hw1gbS0z97HhZs/QPtTaDR9EJYq27eZagRFZ6em7esrjjTpmGaTJmtZjEomV6o/EOtdvImRe1tViI22DWGAKi87BBGXR5Zr3xoRXPSypHLqLsNAgMBAAECggEAatzd//QEMmD/KzVU+m6B1kYsSde0nZo1kmTCBXYUenGWe8/cze7j7NQ4AVWDefiskHz3Rteeq/pXbEXvK0EXEVLKjWTbb/4sLcdg8ew0c+GmI4l9hhtMd4FxRwB2tdrHH7MSvgaR3oNVwaEjXtoGR2+Ns/tCUkaSqLIupsoSIc0Mj07Teq7SZvAe++oMyNgkyArR509oSG0GQFQp706VgLaUVrvtlMEXvtGB0pcn/y1Axz/l9VvYpojYp7MqSwVU6R4GWxjrn4JXCVQrh48VmuJS83i2oqFgbAXD2KyNjjkoW3Z26uhfJ0qgN2PeQgMYH06gNhfEYOAGTI8HgtfChQKBgQDc7xIYG0IchAX/0lds4yUXRRF9wEjZmsvaf6LZPEs97/z11cAbTp41zlppCqpGL0md/lTwFVwsmGuZNob999sGKi7A6mM2sBj+QiBoHACvl2e167O72eFYqyXtJwDH5XOA5JMHbc6GJpSeVE29UnIgq1czgp3DtapQRX3BOPMRYwKBgQDPUVjZJERK5N9ccs59gjyKiu6e60m42AVjpvaCWbqPSZXTEhGM8X9OJNsdZufRoMi6tYctXGthiB4HOoV1E5ACvJxgWpOTmbqqbBDA5pQPrJ4eRdigHjGnrAWdsJ+3smMbhk/6Ai00gmqwz8rv7eyGSY+dwOem/vPoJOrlRFFkzwKBgH+IhbJiscQSNgBZpFvXtwZ6uUEU6Tir0bccbJ3n3ysuyKAENnPM6yj2KFxwaqA/FcjdEpzQR7f6eEomHsCl/cnOOdTkuEbOWm8TLu/KEl9KD/UEzWjHufxcN3VxSVMa0ZT63SCxs0DfLnVDBukdmYHgRmMWqAlcaacSpigOvskvAoGADVikSp5OEzA2vOHbLzNCKH0XLX3iKhcmCatG9U9Hdk/7aDIilRs64dH3lSX5yIH8SiDDigUIGKhFnpuC2e2feL2hp4ZNN9ROswfv8Csn3vZy22oNrwkikzO8zNEBBzdhr/Tukx6uwFGhAq7t1pJPhrmXmEVB5HtHQmuV/5ptTvsCgYA5d5L3hO3+1Na4C6xj8luQXFhkSLNe0rwoe16OLjcyzcnhlb2KKA8rORGP28s1JcCL4Htasf0YzCkOJ/jR28GzX/0qvWu0hBSilV2mCAqwQ1fvZx0L4quJznkAhJPMZ+oag8o1LlQiJGgnhsIMbDLZApKh3NuYlTmdqo20FfkZkg==" + +int main() +{ + int ret = 1; + + const size_t privatekeybase64len = strlen(PRIVATE_KEY_BASE64); + const unsigned char *privatekeybase64 = PRIVATE_KEY_BASE64; + + atchops_rsa2048_privatekey privatekeystruct; + ret = atchops_rsa_populate_privatekey(privatekeybase64, privatekeybase64len, &privatekeystruct); + if (ret != 0) + { + goto ret; + } + + if (privatekeystruct.n_param.len <= 0) + { + ret = 1; + goto ret; + } + + if (privatekeystruct.e_param.len <= 0) + { + ret = 1; + goto ret; + } + + if (privatekeystruct.d_param.len <= 0) + { + ret = 1; + goto ret; + } + + if (privatekeystruct.p_param.len <= 0) + { + ret = 1; + goto ret; + } + + if (privatekeystruct.q_param.len <= 0) + { + ret = 1; + goto ret; + } + + // printf("n: %lu\n", privatekeystruct.n_param.len); + // printx(privatekeystruct.n_param.n, privatekeystruct.n_param.len); + + // printf("e: %lu\n", privatekeystruct.e_param.len); + // printx(privatekeystruct.e_param.e, privatekeystruct.e_param.len); + + // printf("d: %lu\n", privatekeystruct.d_param.len); + // printx(privatekeystruct.d_param.d, privatekeystruct.d_param.len); + + // printf("p: %lu\n", privatekeystruct.p_param.len); + // printx(privatekeystruct.p_param.p, privatekeystruct.p_param.len); + + // printf("q: %lu\n", privatekeystruct.q_param.len); + // printx(privatekeystruct.q_param.q, privatekeystruct.q_param.len); + + goto ret; +ret: +{ + return ret; +} +} \ No newline at end of file diff --git a/test/test_rsapublicpopulate.c b/test/test_rsapublicpopulate.c new file mode 100644 index 00000000..b29cd610 --- /dev/null +++ b/test/test_rsapublicpopulate.c @@ -0,0 +1,45 @@ + +#include +#include +#include "at_chops/rsa.h" +#include "at_chops/byteutil.h" + +#define PUBLIC_KEY_BASE64 "MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAsuuD88vWQ3Zunves9w5o3pLQ+7ClKONAMftVQ9dirJt6VD0xg5DNzX+EqdgE3MumWwkR0hFrce3T3wvx9ae8kvSjlS7QJsfGk9EjYk/lhrHJbISP5/1z/owo8a6WMH+J7YF9ouqeoZaP2YlvIt/gMsocPLmLlTFMjB7+9BGqEzdPjeUBfZe+C5C2C+3F8n2Wsgz02ScWyxdlhKEM+GViYYBZONBHgcNN44i4P09IcNYG0tM/ex4WbP0D7U2g0fRCWKtu3mWoERWenpu3rK4406ZhmkyZrWYxKJleqPxDrXbyJkXtbVYiNtg1hgCovOwQRl0eWa98aEVz0sqRy6i7DQIDAQAB" + +int main() +{ + int ret = 1; + + size_t publickeybase64len = strlen(PUBLIC_KEY_BASE64); + const unsigned char *publickeybase64 = PUBLIC_KEY_BASE64; + + atchops_rsa2048_publickey publickeystruct; + ret = atchops_rsa_populate_publickey(publickeybase64, publickeybase64len, &publickeystruct); + if (ret != 0) + { + goto ret; + } + + if (publickeystruct.n_param.len <= 0) + { + ret = 1; + goto ret; + } + + if (publickeystruct.e_param.len <= 0) + { + ret = 1; + goto ret; + } + + // printf("n: "); + // printx(publickeystruct.n_param.n, publickeystruct.n_param.len); + // printf("e: "); + // printx(publickeystruct.e_param.e, publickeystruct.e_param.len); + + goto ret; + ret: + { + return ret; + } +} \ No newline at end of file diff --git a/test/test_rsasign.c b/test/test_rsasign.c new file mode 100644 index 00000000..cf57ca05 --- /dev/null +++ b/test/test_rsasign.c @@ -0,0 +1,46 @@ + +#include +#include +#include +#include "at_chops/rsa.h" + +#define PRIVATE_KEY_BASE64 "MIIEvAIBADANBgkqhkiG9w0BAQEFAASCBKYwggSiAgEAAoIBAQCy64Pzy9ZDdm6e96z3DmjektD7sKUo40Ax+1VD12Ksm3pUPTGDkM3Nf4Sp2ATcy6ZbCRHSEWtx7dPfC/H1p7yS9KOVLtAmx8aT0SNiT+WGsclshI/n/XP+jCjxrpYwf4ntgX2i6p6hlo/ZiW8i3+Ayyhw8uYuVMUyMHv70EaoTN0+N5QF9l74LkLYL7cXyfZayDPTZJxbLF2WEoQz4ZWJhgFk40EeBw03jiLg/T0hw1gbS0z97HhZs/QPtTaDR9EJYq27eZagRFZ6em7esrjjTpmGaTJmtZjEomV6o/EOtdvImRe1tViI22DWGAKi87BBGXR5Zr3xoRXPSypHLqLsNAgMBAAECggEAatzd//QEMmD/KzVU+m6B1kYsSde0nZo1kmTCBXYUenGWe8/cze7j7NQ4AVWDefiskHz3Rteeq/pXbEXvK0EXEVLKjWTbb/4sLcdg8ew0c+GmI4l9hhtMd4FxRwB2tdrHH7MSvgaR3oNVwaEjXtoGR2+Ns/tCUkaSqLIupsoSIc0Mj07Teq7SZvAe++oMyNgkyArR509oSG0GQFQp706VgLaUVrvtlMEXvtGB0pcn/y1Axz/l9VvYpojYp7MqSwVU6R4GWxjrn4JXCVQrh48VmuJS83i2oqFgbAXD2KyNjjkoW3Z26uhfJ0qgN2PeQgMYH06gNhfEYOAGTI8HgtfChQKBgQDc7xIYG0IchAX/0lds4yUXRRF9wEjZmsvaf6LZPEs97/z11cAbTp41zlppCqpGL0md/lTwFVwsmGuZNob999sGKi7A6mM2sBj+QiBoHACvl2e167O72eFYqyXtJwDH5XOA5JMHbc6GJpSeVE29UnIgq1czgp3DtapQRX3BOPMRYwKBgQDPUVjZJERK5N9ccs59gjyKiu6e60m42AVjpvaCWbqPSZXTEhGM8X9OJNsdZufRoMi6tYctXGthiB4HOoV1E5ACvJxgWpOTmbqqbBDA5pQPrJ4eRdigHjGnrAWdsJ+3smMbhk/6Ai00gmqwz8rv7eyGSY+dwOem/vPoJOrlRFFkzwKBgH+IhbJiscQSNgBZpFvXtwZ6uUEU6Tir0bccbJ3n3ysuyKAENnPM6yj2KFxwaqA/FcjdEpzQR7f6eEomHsCl/cnOOdTkuEbOWm8TLu/KEl9KD/UEzWjHufxcN3VxSVMa0ZT63SCxs0DfLnVDBukdmYHgRmMWqAlcaacSpigOvskvAoGADVikSp5OEzA2vOHbLzNCKH0XLX3iKhcmCatG9U9Hdk/7aDIilRs64dH3lSX5yIH8SiDDigUIGKhFnpuC2e2feL2hp4ZNN9ROswfv8Csn3vZy22oNrwkikzO8zNEBBzdhr/Tukx6uwFGhAq7t1pJPhrmXmEVB5HtHQmuV/5ptTvsCgYA5d5L3hO3+1Na4C6xj8luQXFhkSLNe0rwoe16OLjcyzcnhlb2KKA8rORGP28s1JcCL4Htasf0YzCkOJ/jR28GzX/0qvWu0hBSilV2mCAqwQ1fvZx0L4quJznkAhJPMZ+oag8o1LlQiJGgnhsIMbDLZApKh3NuYlTmdqo20FfkZkg==" + +#define SIGNATURE_BUFFER_LEN 5000 + +#define MESSAGE "_4a160d33-0c63-4800-bee0-ee254752f8c8@jeremy_0:6c987cc1-0dde-4ba1-af56-a9677086182" + +int main() +{ + + int ret = 0; + + size_t privatekeybase64len = strlen(PRIVATE_KEY_BASE64); + const unsigned char *privatekeybase64 = PRIVATE_KEY_BASE64; + + atchops_rsa2048_privatekey privatekeystruct; + ret = atchops_rsa_populate_privatekey(privatekeybase64, privatekeybase64len, &privatekeystruct); + if (ret != 0) + goto ret; + + size_t *signaturelen = malloc(sizeof(size_t)); + unsigned char *signature = malloc(sizeof(unsigned char) * SIGNATURE_BUFFER_LEN); + + const unsigned char *message = MESSAGE; + const size_t messagelen = strlen(message); + + ret = atchops_rsa_sign(privatekeystruct, ATCHOPS_MD_SHA256, &signature, signaturelen, message, messagelen); + if(ret != 0) + goto ret; + + ret = strncmp(signature, "AwsKWNqRHiCtdNJ0U5GXZ1H5obptEWVR1+A1kPhot4cdLfmulvBVXRaBIrP+jd2TSP2J/KNAgv2BDLH7DXUibdTnzJaKm/QKAjpwpuShnV6Y9KSWTnomBw9x9OWDkVrBzSo5rOFpHHOTZJhp4ygStKEzZDa108g8uP5PpkfzntO2eIVEOdMHoL9/yAkuYJcz+VmCH+1AJtCdeKfhjfmlk0bP72fwsait6pA3TW0iEll9ptZmlLjNtCTi982h1yNprh+XtrjMz7ClbJChQf3LLHiJMZ+7r4yKTrehdBVfxQoNNw9r2D7TBRaY8bXYwMombMHRuu0oVbqNU1jEs60NGQ==", *signaturelen); + if(ret != 0) goto ret; + + // printf("signature len: %lu\n", *signaturelen); + // printf("signature: %s\n", signature); + +ret: +{ + return ret; +} +} \ No newline at end of file