diff options
Diffstat (limited to 'src/lib/tests')
| -rw-r--r-- | src/lib/tests/CMakeLists.txt | 16 | ||||
| -rw-r--r-- | src/lib/tests/auth_test.c | 643 | ||||
| -rw-r--r-- | src/lib/tests/bitmap_test.c | 27 | ||||
| -rw-r--r-- | src/lib/tests/btree_test.c | 2 | ||||
| -rw-r--r-- | src/lib/tests/crc32_test.c | 2 | ||||
| -rw-r--r-- | src/lib/tests/crypt_test.c | 258 | ||||
| -rw-r--r-- | src/lib/tests/hash_test.c | 202 | ||||
| -rw-r--r-- | src/lib/tests/md5_test.c | 2 | ||||
| -rw-r--r-- | src/lib/tests/sha3_test.c | 2 | ||||
| -rw-r--r-- | src/lib/tests/shm_rbuff_test.c | 2 | ||||
| -rw-r--r-- | src/lib/tests/sockets_test.c | 98 | ||||
| -rw-r--r-- | src/lib/tests/time_test.c | 529 | ||||
| -rw-r--r-- | src/lib/tests/time_utils_test.c | 164 | ||||
| -rw-r--r-- | src/lib/tests/tpm_test.c | 104 | 
14 files changed, 1867 insertions, 184 deletions
diff --git a/src/lib/tests/CMakeLists.txt b/src/lib/tests/CMakeLists.txt index 9e23b0ee..2791dd0d 100644 --- a/src/lib/tests/CMakeLists.txt +++ b/src/lib/tests/CMakeLists.txt @@ -3,13 +3,18 @@ get_filename_component(PARENT_DIR ${PARENT_PATH} NAME)  create_test_sourcelist(${PARENT_DIR}_tests test_suite.c    # Add new tests here +  auth_test.c    bitmap_test.c    btree_test.c    crc32_test.c +  crypt_test.c +  hash_test.c    md5_test.c    sha3_test.c    shm_rbuff_test.c -  time_utils_test.c +  sockets_test.c +  time_test.c +  tpm_test.c    )  add_executable(${PARENT_DIR}_test EXCLUDE_FROM_ALL ${${PARENT_DIR}_tests}) @@ -19,9 +24,16 @@ target_link_libraries(${PARENT_DIR}_test ouroboros-common)  add_dependencies(check ${PARENT_DIR}_test)  set(tests_to_run ${${PARENT_DIR}_tests}) -remove(tests_to_run test_suite.c) +if(CMAKE_VERSION VERSION_LESS "3.29.0") +  remove(tests_to_run test_suite.c) +else () +  list(POP_FRONT tests_to_run) +endif()  foreach (test ${tests_to_run})    get_filename_component(test_name ${test} NAME_WE)    add_test(${test_name} ${C_TEST_PATH}/${PARENT_DIR}_test ${test_name})  endforeach (test) + +set_property(TEST auth_test PROPERTY SKIP_RETURN_CODE 1) +set_property(TEST crypt_test PROPERTY SKIP_RETURN_CODE 1) diff --git a/src/lib/tests/auth_test.c b/src/lib/tests/auth_test.c new file mode 100644 index 00000000..ede294b8 --- /dev/null +++ b/src/lib/tests/auth_test.c @@ -0,0 +1,643 @@ +/* + * Ouroboros - Copyright (C) 2016 - 2024 + * + * Test of the authentication functions + * + *    Dimitri Staessens <dimitri@ouroboros.rocks> + *    Sander Vrijders   <sander@ouroboros.rocks> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., http://www.fsf.org/about/contact/. + */ + +#include "config.h" + +#include <ouroboros/test.h> +#include <ouroboros/crypt.h> +#include <ouroboros/random.h> +#include <ouroboros/utils.h> + +#define TEST_MSG_SIZE 1500 + +/* +* Certificates created following the guide +*   Building an openssl certificate authority +* on +*   https://community.f5.com/kb/technicalarticles/ +*/ + +/* Root certificate for CA ca.unittest.o7s */ +static const char * root_ca_crt = \ +"-----BEGIN CERTIFICATE-----\n" +"MIICXTCCAgOgAwIBAgIURlENlCOy1OsA/AXFscPUQ2li8OYwCgYIKoZIzj0EAwIw\n" +"fDELMAkGA1UEBhMCQkUxDDAKBgNVBAgMA09WTDEOMAwGA1UEBwwFR2hlbnQxDDAK\n" +"BgNVBAoMA283czEVMBMGA1UECwwMdW5pdHRlc3QubzdzMRgwFgYDVQQDDA9jYS51\n" +"bml0dGVzdC5vN3MxEDAOBgkqhkiG9w0BCQEWASAwHhcNMjUwODAzMTg1MzE1WhcN\n" +"NDUwNzI5MTg1MzE1WjB8MQswCQYDVQQGEwJCRTEMMAoGA1UECAwDT1ZMMQ4wDAYD\n" +"VQQHDAVHaGVudDEMMAoGA1UECgwDbzdzMRUwEwYDVQQLDAx1bml0dGVzdC5vN3Mx\n" +"GDAWBgNVBAMMD2NhLnVuaXR0ZXN0Lm83czEQMA4GCSqGSIb3DQEJARYBIDBZMBMG\n" +"ByqGSM49AgEGCCqGSM49AwEHA0IABEPMseCScbd/d5TlHmyYVszn/YGVeNdUCnFR\n" +"naOr95WlTNo3MyKKBuoiEFwHhjPASgXr/VDVjJLSyM3JUPebAcGjYzBhMB0GA1Ud\n" +"DgQWBBQkxjMILHH6lZ+rnCMnD/63GO3y1zAfBgNVHSMEGDAWgBQkxjMILHH6lZ+r\n" +"nCMnD/63GO3y1zAPBgNVHRMBAf8EBTADAQH/MA4GA1UdDwEB/wQEAwIBhjAKBggq\n" +"hkjOPQQDAgNIADBFAiEA1jVJWW4idkCgAYv0m2LT9C33Dq42aLyRkJ+9YdzDqLwC\n" +"IHT6MS4I0k52YP/hxoqWVBbpOW79PKYMRLyXTk1r7+Fa\n" +"-----END CERTIFICATE-----\n"; + + +/* Certificate for intermediary im.unittest.o7s used for signing */ +static const char * intermediate_ca_crt = \ +"-----BEGIN CERTIFICATE-----\n" +"MIICbTCCAhOgAwIBAgICEAMwCgYIKoZIzj0EAwIwfDELMAkGA1UEBhMCQkUxDDAK\n" +"BgNVBAgMA09WTDEOMAwGA1UEBwwFR2hlbnQxDDAKBgNVBAoMA283czEVMBMGA1UE\n" +"CwwMdW5pdHRlc3QubzdzMRgwFgYDVQQDDA9jYS51bml0dGVzdC5vN3MxEDAOBgkq\n" +"hkiG9w0BCQEWASAwHhcNMjUwODAzMTkwMjU3WhcNNDUwNzI5MTkwMjU3WjBaMQsw\n" +"CQYDVQQGEwJCRTEMMAoGA1UECAwDT1ZMMQwwCgYDVQQKDANvN3MxFTATBgNVBAsM\n" +"DHVuaXR0ZXN0Lm83czEYMBYGA1UEAwwPaW0udW5pdHRlc3QubzdzMFkwEwYHKoZI\n" +"zj0CAQYIKoZIzj0DAQcDQgAEdlra08XItIPtVl5veaq4UF6LIcBXj2mZFqKNEXFh\n" +"l9uAz6UAbIc+FUPNfom6dwKbg/AjQ82a100eh6K/jCY7eKOBpjCBozAdBgNVHQ4E\n" +"FgQUy8Go8BIO6i0lJ+mgBr9lvh2L0eswHwYDVR0jBBgwFoAUJMYzCCxx+pWfq5wj\n" +"Jw/+txjt8tcwEgYDVR0TAQH/BAgwBgEB/wIBADAOBgNVHQ8BAf8EBAMCAYYwEQYD\n" +"VR0fBAowCDAGoASgAoYAMCoGCCsGAQUFBwEBBB4wHDAMBggrBgEFBQcwAoYAMAwG\n" +"CCsGAQUFBzABhgAwCgYIKoZIzj0EAwIDSAAwRQIhAN3ZYhqu6mVLGidmONsbANk5\n" +"rzT6aHJcmvj19OxMusaXAiBKy0gBFCri/GLizi4wZo09wf31yZMqfr8IrApvPaLw\n" +"qA==\n" +"-----END CERTIFICATE-----\n"; + +/* Server test-1.unittest.o7s private-public key pair */ +static const char * server_ec_pkp = \ +"-----BEGIN EC PRIVATE KEY-----\n" +"MHcCAQEEIA4/bcmquVvGrY4+TtfnFSy1SpXs896r5xJjGuD6NmGRoAoGCCqGSM49\n" +"AwEHoUQDQgAE4BSOhv36q4bCMLSkJaCvzwZ3pPy2M0YzRKFKeV48tG5eD+MBaTrT\n" +"eoHUcRfpz0EO/inq3FVDzEoAQ2NWpnz0kA==\n" +"-----END EC PRIVATE KEY-----\n"; + +/* Public key for the Private key */ +static const char * server_ec_pk = \ +"-----BEGIN PUBLIC KEY-----\n" +"MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAE4BSOhv36q4bCMLSkJaCvzwZ3pPy2\n" +"M0YzRKFKeV48tG5eD+MBaTrTeoHUcRfpz0EO/inq3FVDzEoAQ2NWpnz0kA==\n" +"-----END PUBLIC KEY-----\n"; + +/* Valid signed server certificate for test-1.unittest.o7s */ +static const char * signed_server_crt = \ +"-----BEGIN CERTIFICATE-----\n" +"MIIDiTCCAy+gAwIBAgICEAUwCgYIKoZIzj0EAwIwWjELMAkGA1UEBhMCQkUxDDAK\n" +"BgNVBAgMA09WTDEMMAoGA1UECgwDbzdzMRUwEwYDVQQLDAx1bml0dGVzdC5vN3Mx\n" +"GDAWBgNVBAMMD2ltLnVuaXR0ZXN0Lm83czAeFw0yNTA4MDgxODQ4NTNaFw00NTA4\n" +"MDMxODQ4NTNaMG4xCzAJBgNVBAYTAkJFMQwwCgYDVQQIDANPVkwxDjAMBgNVBAcM\n" +"BUdoZW50MQwwCgYDVQQKDANvN3MxFTATBgNVBAsMDHVuaXR0ZXN0Lm83czEcMBoG\n" +"A1UEAwwTdGVzdC0xLnVuaXR0ZXN0Lm83czBZMBMGByqGSM49AgEGCCqGSM49AwEH\n" +"A0IABOAUjob9+quGwjC0pCWgr88Gd6T8tjNGM0ShSnlePLRuXg/jAWk603qB1HEX\n" +"6c9BDv4p6txVQ8xKAENjVqZ89JCjggHPMIIByzAJBgNVHRMEAjAAMBEGCWCGSAGG\n" +"+EIBAQQEAwIGQDA4BglghkgBhvhCAQ0EKxYpbzdzIHVuaXR0ZXN0IEdlbmVyYXRl\n" +"ZCBTZXJ2ZXIgQ2VydGlmaWNhdGUwHQYDVR0OBBYEFI+htsK0xxy6e1CqCyxn7mqi\n" +"wRrpMIGoBgNVHSMEgaAwgZ2AFMvBqPASDuotJSfpoAa/Zb4di9HroYGApH4wfDEL\n" +"MAkGA1UEBhMCQkUxDDAKBgNVBAgMA09WTDEOMAwGA1UEBwwFR2hlbnQxDDAKBgNV\n" +"BAoMA283czEVMBMGA1UECwwMdW5pdHRlc3QubzdzMRgwFgYDVQQDDA9jYS51bml0\n" +"dGVzdC5vN3MxEDAOBgkqhkiG9w0BCQEWASCCAhADMA4GA1UdDwEB/wQEAwIFoDAT\n" +"BgNVHSUEDDAKBggrBgEFBQcDATAoBgNVHR8EITAfMB2gG6AZhhdodHRwczovL291\n" +"cm9ib3Jvcy5yb2NrczBYBggrBgEFBQcBAQRMMEowIwYIKwYBBQUHMAKGF2h0dHBz\n" +"Oi8vb3Vyb2Jvcm9zLnJvY2tzMCMGCCsGAQUFBzABhhdodHRwczovL291cm9ib3Jv\n" +"cy5yb2NrczAKBggqhkjOPQQDAgNIADBFAiBZuw/Yb2pq925H7pEiOXr4fMo0wknz\n" +"ktkxoHAFbjQEPQIhAMInHI7lvRmS0IMw1wBF/WlUZWKvhyU/TeMIZfk/JGCS\n" +"-----END CERTIFICATE-----\n"; + +/* Self-signed by server test-1.unittest.o7s using its key */ +static const char * server_crt = \ +"-----BEGIN CERTIFICATE-----\n" +"MIIBfjCCASWgAwIBAgIUB5VYxp7i+sgYjvLiwfpf0W5NfqQwCgYIKoZIzj0EAwIw\n" +"HjEcMBoGA1UEAwwTdGVzdC0xLnVuaXR0ZXN0Lm83czAeFw0yNTA4MDMxOTI4MzVa\n" +"Fw00NTA3MjkxOTI4MzVaMB4xHDAaBgNVBAMME3Rlc3QtMS51bml0dGVzdC5vN3Mw\n" +"WTATBgcqhkjOPQIBBggqhkjOPQMBBwNCAATgFI6G/fqrhsIwtKQloK/PBnek/LYz\n" +"RjNEoUp5Xjy0bl4P4wFpOtN6gdRxF+nPQQ7+KercVUPMSgBDY1amfPSQo0EwPzAe\n" +"BgNVHREEFzAVghN0ZXN0LTEudW5pdHRlc3QubzdzMB0GA1UdDgQWBBSPobbCtMcc\n" +"untQqgssZ+5qosEa6TAKBggqhkjOPQQDAgNHADBEAiAoFC/rqgrRXmMUx4y5cPbv\n" +"jOKpoL3FpehRgGkPatmL/QIgMRHc2TSGo6q1SG22Xt1dHAIBsaN2AlSfhjKULMH5\n" +"gRo=\n" +"-----END CERTIFICATE-----\n"; + +static int test_auth_create_destroy_ctx(void) +{ +        struct auth_ctx * ctx; + +        TEST_START(); + +        ctx = auth_create_ctx(); +        if (ctx == NULL) { +                printf("Failed to create auth context.\n"); +                goto fail_create; +        } + +        auth_destroy_ctx(ctx); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail_create: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +static int test_load_free_crt(void) +{ +        void * crt; + +        TEST_START(); + +        if (crypt_load_crt_str(root_ca_crt, &crt) < 0) { +                printf("Failed to load certificate string.\n"); +                goto fail_load; +        } + +        crypt_free_crt(crt); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail_load: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +static int test_crypt_get_pubkey_crt(void) +{ +        void * pk; +        void * crt; + +        TEST_START(); + +        if (crypt_load_crt_str(signed_server_crt, &crt) < 0) { +                printf("Failed to load server certificate from string.\n"); +                goto fail_load; +        } + +        if (crypt_get_pubkey_crt(crt, &pk) < 0) { +                printf("Failed to get public key from certificate.\n"); +                goto fail_get_pubkey; +        } + +        crypt_free_key(pk); +        crypt_free_crt(crt); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + + fail_get_pubkey: +        crypt_free_crt(crt); + fail_load: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +static int test_check_crt_name(void) +{ +        void * crt; + +        TEST_START(); + +        if (crypt_load_crt_str(signed_server_crt, &crt) < 0) { +                printf("Failed to load certificate from string.\n"); +                goto fail_load; +        } + +        if (crypt_check_crt_name(crt, "test-1.unittest.o7s") < 0) { +                printf("Failed to verify correct name.\n"); +                goto fail_check; +        } + +        if (crypt_check_crt_name(crt, "bogus.name") == 0) { +                printf("Failed to detect incorrect name.\n"); +                goto fail_check; +        } + +        crypt_free_crt(crt); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail_check: +        crypt_free_crt(crt); + fail_load: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +static int test_load_free_privkey(void) +{ +        void * key; + +        TEST_START(); + +        if (crypt_load_privkey_str(server_ec_pkp, &key) < 0) { +                printf("Failed to load server key pair from string.\n"); +                goto fail_load; +        } + +        crypt_free_key(key); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail_load: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +static int test_load_free_pubkey(void) +{ +        void * key; + +        TEST_START(); + +        if (crypt_load_pubkey_str(server_ec_pk, &key) < 0) { +                printf("Failed to load server public key from string.\n"); +                goto fail_load; +        } + +        crypt_free_key(key); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail_load: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +static int test_crypt_check_pubkey_crt(void) +{ +        void * pk; +        void * crt_pk; +        void * crt; + +        TEST_START(); + +        if (crypt_load_crt_str(signed_server_crt, &crt) < 0) { +                printf("Failed to load public certificate from string.\n"); +                goto fail_crt; +        } + +        if (crypt_load_pubkey_str(server_ec_pk, &pk) < 0) { +                printf("Failed to load public key from string.\n"); +                goto fail_pubkey; +        } + +        if (crypt_get_pubkey_crt(crt, &crt_pk) < 0) { +                printf("Failed to get public key from certificate.\n"); +                goto fail_get_pubkey; +        } + +        if (crypt_cmp_key(pk, crt_pk) != 0) { +                printf("Public keys do not match .\n"); +                goto fail_check; +        } + + +        crypt_free_key(crt_pk); +        crypt_free_key(pk); +        crypt_free_crt(crt); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail_check: +        crypt_free_key(crt_pk); + fail_get_pubkey: +        crypt_free_key(pk); + fail_pubkey: +        crypt_free_crt(crt); + fail_crt: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +static int test_store_add(void) +{ +        struct auth_ctx * ctx; +        void *            _root_ca_crt; + +        TEST_START(); + +        ctx = auth_create_ctx(); +        if (ctx == NULL) { +                printf("Failed to create auth context.\n"); +                goto fail_create; +        } + +        if (crypt_load_crt_str(root_ca_crt, &_root_ca_crt) < 0) { +                printf("Failed to load root crt from string.\n"); +                goto fail_load; +        } + +        if (auth_add_crt_to_store(ctx, _root_ca_crt) < 0) { +                printf("Failed to add root crt to auth store.\n"); +                goto fail_add; +        } + +        crypt_free_crt(_root_ca_crt); +        auth_destroy_ctx(ctx); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + + fail_add: +        crypt_free_crt(_root_ca_crt); + fail_load: +        crypt_free_crt(_root_ca_crt); + fail_create: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +static int test_verify_crt(void) +{ +        struct auth_ctx * auth; +        void *            _server_crt; +        void *            _signed_server_crt; +        void *            _root_ca_crt; +        void *            _intermediate_ca_crt; + +        TEST_START(); + +        auth = auth_create_ctx(); +        if (auth == NULL) { +                printf("Failed to create auth context.\n"); +                goto fail_create_ctx; +        } + +        if (crypt_load_crt_str(server_crt, &_server_crt) < 0) { +                printf("Failed to load self-signed crt from string.\n"); +                goto fail_load_server_crt; +        } + +        if (crypt_load_crt_str(signed_server_crt, &_signed_server_crt) < 0) { +                printf("Failed to load signed crt from string.\n"); +                goto fail_load_signed_server_crt; +        } + +        if (crypt_load_crt_str(root_ca_crt, &_root_ca_crt) < 0) { +                printf("Failed to load root crt from string.\n"); +                goto fail_load_root_ca_crt; +        } + +        if (crypt_load_crt_str(intermediate_ca_crt, &_intermediate_ca_crt) < 0) { +                printf("Failed to load intermediate crt from string.\n"); +                goto fail_load_intermediate_ca_crt; +        } + +        if (auth_add_crt_to_store(auth, _root_ca_crt) < 0) { +                printf("Failed to add root ca crt to auth store.\n"); +                goto fail_verify; +        } + +        if (auth_add_crt_to_store(auth, _intermediate_ca_crt) < 0) { +                printf("Failed to add intermediate ca crt to auth store.\n"); +                goto fail_verify; +        } + +        if (auth_verify_crt(auth, _signed_server_crt) < 0) { +                printf("Failed to verify signed crt with ca crt.\n"); +                goto fail_verify; +        } + +        if (auth_verify_crt(auth, _server_crt) == 0) { +                printf("Failed to detect untrusted crt.\n"); +                goto fail_verify; +        } + +        crypt_free_crt(_intermediate_ca_crt); +        crypt_free_crt(_root_ca_crt); +        crypt_free_crt(_signed_server_crt); +        crypt_free_crt(_server_crt); + +        auth_destroy_ctx(auth); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail_verify: +        crypt_free_crt(_intermediate_ca_crt); + fail_load_intermediate_ca_crt: +        crypt_free_crt(_root_ca_crt); + fail_load_root_ca_crt: +        crypt_free_crt(_signed_server_crt); + fail_load_signed_server_crt: +        crypt_free_crt(_server_crt); + fail_load_server_crt: +        auth_destroy_ctx(auth); + fail_create_ctx: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +int test_auth_sign(void) +{ +        uint8_t  buf[TEST_MSG_SIZE]; +        void *   pkp; +        void *   pk; +        buffer_t msg; +        buffer_t sig; + +        TEST_START(); + +        msg.data = buf; +        msg.len  = sizeof(buf); + +        if (random_buffer(msg.data, msg.len) < 0) { +                printf("Failed to generate random message.\n"); +                goto fail_init; +        } + +        if (crypt_load_privkey_str(server_ec_pkp, &pkp) < 0) { +                printf("Failed to load server key pair from string.\n"); +                goto fail_init; +        } + +        if (crypt_load_pubkey_str(server_ec_pk, &pk) < 0) { +                printf("Failed to load public key.\n"); +                goto fail_pubkey; +        } + +        if (auth_sign(pkp, msg, &sig) < 0) { +                printf("Failed to sign message.\n"); +                goto fail_sign; +        } + +        if (auth_verify_sig(pk, msg, sig) < 0) { +                printf("Failed to verify signature.\n"); +                goto fail_verify; +        } + +        freebuf(sig); + +        crypt_free_key(pk); +        crypt_free_key(pkp); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail_verify: +        freebuf(sig); + fail_sign: +        crypt_free_key(pk); + fail_pubkey: +        crypt_free_key(pkp); + fail_init: +        return TEST_RC_FAIL; +} + +int test_auth_bad_signature(void) +{ +        uint8_t  buf[TEST_MSG_SIZE]; +        void *   pkp; +        void *   pk; +        buffer_t msg; +        buffer_t sig; +        buffer_t fake_sig; + +        TEST_START(); + +        msg.data = buf; +        msg.len  = sizeof(buf); + +        if (random_buffer(msg.data, msg.len) < 0) { +                printf("Failed to generate random message.\n"); +                goto fail_init; +        } + +        if (crypt_load_privkey_str(server_ec_pkp, &pkp) < 0) { +                printf("Failed to load server key pair from string.\n"); +                goto fail_init; +        } + +        if (crypt_load_pubkey_str(server_ec_pk, &pk) < 0) { +                printf("Failed to load public key.\n"); +                goto fail_pubkey; +        } + +        if (auth_sign(pkp, msg, &sig) < 0) { +                printf("Failed to sign message.\n"); +                goto fail_sign; +        } + +        fake_sig.data = malloc(sig.len); +        if (fake_sig.data == NULL) { +                printf("Failed to allocate memory for fake signature.\n"); +                goto fail_malloc; +        } + +        fake_sig.len = sig.len; +        if (random_buffer(fake_sig.data, fake_sig.len) < 0) { +                printf("Failed to generate random fake signature.\n"); +                goto fail_malloc; +        } + +        if (auth_verify_sig(pk, msg, fake_sig) == 0) { +                printf("Failed to detect bad signature.\n"); +                goto fail_verify; +        } + +        freebuf(fake_sig); +        freebuf(sig); + +        crypt_free_key(pk); +        crypt_free_key(pkp); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail_verify: +        freebuf(fake_sig); + fail_malloc: +        freebuf(sig); + fail_sign: +        crypt_free_key(pk); + fail_pubkey: +        crypt_free_key(pkp); + fail_init: +        return TEST_RC_FAIL; +} + +int test_crt_str(void) +{ +        char str[2295]; +        void * crt; + +        TEST_START(); + +        if (crypt_load_crt_str(signed_server_crt, &crt) < 0) { +                printf("Failed to load certificate from string.\n"); +                goto fail_load; +        } + +        if (crypt_crt_str(crt, str) < 0) { +                printf("Failed to convert certificate to string.\n"); +                goto fail_to_str; +        } + +        printf("Certificate string:\n%s\n", str); + +        crypt_free_crt(crt); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + + fail_to_str: +        crypt_free_crt(crt); + fail_load: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +int auth_test(int     argc, +              char ** argv) +{ +        int ret = 0; + +        (void) argc; +        (void) argv; + +        ret |= test_auth_create_destroy_ctx(); +#ifdef HAVE_OPENSSL +        ret |= test_load_free_crt(); +        ret |= test_check_crt_name(); +        ret |= test_crypt_get_pubkey_crt(); +        ret |= test_load_free_privkey(); +        ret |= test_load_free_pubkey(); +        ret |= test_crypt_check_pubkey_crt(); +        ret |= test_store_add(); +        ret |= test_verify_crt(); +        ret |= test_auth_sign(); +        ret |= test_auth_bad_signature(); +        ret |= test_crt_str(); +#else +        (void) test_load_free_crt; +        (void) test_check_crt_name; +        (void) test_crypt_get_pubkey_crt; +        (void) test_load_free_privkey; +        (void) test_load_free_pubkey; +        (void) test_crypt_check_pubkey_crt; +        (void) test_store_add; +        (void) test_verify_crt; +        (void) test_auth_sign; +        (void) test_auth_bad_signature; +        (void) test_crt_str; + +        ret = TEST_RC_SKIP; +#endif +        return ret; +} diff --git a/src/lib/tests/bitmap_test.c b/src/lib/tests/bitmap_test.c index 0815ecff..4dbd6653 100644 --- a/src/lib/tests/bitmap_test.c +++ b/src/lib/tests/bitmap_test.c @@ -1,5 +1,5 @@  /* - * Ouroboros - Copyright (C) 2016 - 2021 + * Ouroboros - Copyright (C) 2016 - 2024   *   * Test of the bitmap   * @@ -27,7 +27,8 @@  #define BITMAP_SIZE 200 -int bitmap_test(int argc, char ** argv) +int bitmap_test(int     argc, +                char ** argv)  {          struct bmp * bmp;          ssize_t bits = BITMAP_SIZE; @@ -60,27 +61,23 @@ int bitmap_test(int argc, char ** argv)                  if (!bmp_is_id_valid(bmp, id)) {                          if (i < BITMAP_SIZE + offset) {                                  printf("Failed valid ID %d (%zd).\n", i, id); -                                bmp_destroy(bmp); -                                return -1; +                                goto fail;                          }                          if (id >= offset && id < bits + offset) {                                  printf("Valid ID %zd returned invalid.\n", id); -                                bmp_destroy(bmp); -                                return -1; +                                goto fail;                          }                          continue;                  }                  if (!bmp_is_id_used(bmp, id)) {                          printf("ID not marked in use.\n"); -                        bmp_destroy(bmp); -                        return -1; +                        goto fail;                  }                  if (id != i) {                          printf("Wrong ID returned.\n"); -                        bmp_destroy(bmp); -                        return -1; +                        goto fail;                  }          } @@ -89,20 +86,24 @@ int bitmap_test(int argc, char ** argv)                  if (bmp_release(bmp, r)) {                          printf("Failed to release ID.\n"); -                        return -1; +                        goto fail;                  }                  id = bmp_allocate(bmp);                  if (!bmp_is_id_valid(bmp, id))                          continue; +                  if (id != r) {                          printf("Wrong prev ID returned.\n"); -                        bmp_destroy(bmp); -                        return -1; +                        goto fail;                  }          }          bmp_destroy(bmp);          return 0; + + fail: +        bmp_destroy(bmp); +        return -1;  } diff --git a/src/lib/tests/btree_test.c b/src/lib/tests/btree_test.c index 9dc59d32..8bd30370 100644 --- a/src/lib/tests/btree_test.c +++ b/src/lib/tests/btree_test.c @@ -1,5 +1,5 @@  /* - * Ouroboros - Copyright (C) 2016 - 2021 + * Ouroboros - Copyright (C) 2016 - 2024   *   * Test of the B-tree implementation   * diff --git a/src/lib/tests/crc32_test.c b/src/lib/tests/crc32_test.c index a0f70423..a26c8220 100644 --- a/src/lib/tests/crc32_test.c +++ b/src/lib/tests/crc32_test.c @@ -1,5 +1,5 @@  /* - * Ouroboros - Copyright (C) 2016 - 2021 + * Ouroboros - Copyright (C) 2016 - 2024   *   * Test of the CRC32 function   * diff --git a/src/lib/tests/crypt_test.c b/src/lib/tests/crypt_test.c new file mode 100644 index 00000000..e7a09e8f --- /dev/null +++ b/src/lib/tests/crypt_test.c @@ -0,0 +1,258 @@ +/* + * Ouroboros - Copyright (C) 2016 - 2024 + * + * Test of the cryptography functions + * + *    Dimitri Staessens <dimitri@ouroboros.rocks> + *    Sander Vrijders   <sander@ouroboros.rocks> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., http://www.fsf.org/about/contact/. + */ + +#include "config.h" + +#include <ouroboros/test.h> +#include <ouroboros/crypt.h> +#include <ouroboros/random.h> +#include <ouroboros/utils.h> + +#define TEST_PACKET_SIZE 1500 + +static int test_crypt_create_destroy(void) +{ +        struct crypt_ctx * ctx; + +        TEST_START(); + +        ctx = crypt_create_ctx(NULL); +        if (ctx == NULL) { +                printf("Failed to initialize cryptography.\n"); +                goto fail; +        } + +        crypt_destroy_ctx(ctx); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +static int test_crypt_create_destroy_with_key(void) +{ +        struct crypt_ctx * ctx; +        uint8_t            key[SYMMKEYSZ]; + +        TEST_START(); + +        memset(key, 0, sizeof(key)); + +        ctx = crypt_create_ctx(key); +        if (ctx == NULL) { +                printf("Failed to initialize cryptography.\n"); +                goto fail; +        } + +        crypt_destroy_ctx(ctx); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +static int test_crypt_dh_pkp_create_destroy(void) +{ +        void *  pkp; +        uint8_t buf[MSGBUFSZ]; + +        TEST_START(); + +        if (crypt_dh_pkp_create(&pkp, buf) < 0) { +                printf("Failed to create DH PKP."); +                goto fail; +        } + +        crypt_dh_pkp_destroy(pkp); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +static int test_crypt_dh_derive(void) +{ +        void *   pkp1; +        void *   pkp2; +        buffer_t pk1; +        buffer_t pk2; +        ssize_t  len; +        uint8_t  buf1[MSGBUFSZ]; +        uint8_t  buf2[MSGBUFSZ]; +        uint8_t  s1[SYMMKEYSZ]; +        uint8_t  s2[SYMMKEYSZ]; + +        TEST_START(); + +        len = crypt_dh_pkp_create(&pkp1, buf1); +        if (len < 0) { +                printf("Failed to create first key pair."); +                goto fail_pkp1; +        } + +        pk1.len  = (size_t) len; +        pk1.data = buf1; + +        len = crypt_dh_pkp_create(&pkp2, buf2); +        if (len < 0) { +                printf("Failed to create second key pair."); +                goto fail_pkp2; +        } + +        pk2.len  = (size_t) len; +        pk2.data = buf2; + +        if (crypt_dh_derive(pkp1, pk2, s1) < 0) { +                printf("Failed to derive first key."); +                goto fail; +        } + +        if (crypt_dh_derive(pkp2, pk1, s2) < 0) { +                printf("Failed to derive second key."); +                goto fail; +        } + +        if (memcmp(s1, s2, SYMMKEYSZ) != 0) { +                printf("Derived keys do not match."); +                goto fail; +        } + +        crypt_dh_pkp_destroy(pkp2); +        crypt_dh_pkp_destroy(pkp1); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail: +        crypt_dh_pkp_destroy(pkp2); + fail_pkp2: +        crypt_dh_pkp_destroy(pkp1); + fail_pkp1: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +int test_crypt_encrypt_decrypt(void) +{ +        uint8_t            pkt[TEST_PACKET_SIZE]; +        uint8_t            key[SYMMKEYSZ]; +        struct crypt_ctx * ctx; +        buffer_t           in; +        buffer_t           out; +        buffer_t           out2; + +        TEST_START(); + +        if (random_buffer(key, sizeof(key)) < 0) { +                printf("Failed to generate random key.\n"); +                goto fail_init; +        } + +        if (random_buffer(pkt, sizeof(pkt)) < 0) { +                printf("Failed to generate random data.\n"); +                goto fail_init; +        } + +        ctx = crypt_create_ctx(key); +        if (ctx == NULL) { +                printf("Failed to initialize cryptography.\n"); +                goto fail_init; +        } + +        in.len  = sizeof(pkt); +        in.data = pkt; + +        if (crypt_encrypt(ctx, in, &out) < 0) { +                printf("Encryption failed.\n"); +                goto fail_encrypt; +        } + +        if (out.len < in.len) { +                printf("Encryption returned too little data.\n"); +                goto fail_encrypt; +        } + +        if (crypt_decrypt(ctx, out, &out2) < 0) { +                printf("Decryption failed.\n"); +                goto fail_decrypt; +        } + +        if (out2.len != in.len) { +                printf("Decrypted data length does not match original.\n"); +                goto fail_chk; +        } + +        if (memcmp(in.data, out2.data, in.len) != 0) { +                printf("Decrypted data does not match original.\n"); +                goto fail_chk; +        } + +        crypt_destroy_ctx(ctx); +        freebuf(out2); +        freebuf(out); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail_chk: +        freebuf(out2); + fail_decrypt: +        freebuf(out); + fail_encrypt: +        crypt_destroy_ctx(ctx); + fail_init: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +int crypt_test(int     argc, +               char ** argv) +{ +        int ret = 0; + +        (void) argc; +        (void) argv; + +        ret |= test_crypt_create_destroy(); +        ret |= test_crypt_create_destroy_with_key(); +#ifdef HAVE_OPENSSL +        ret |= test_crypt_dh_pkp_create_destroy(); +        ret |= test_crypt_dh_derive(); +        ret |= test_crypt_encrypt_decrypt(); +#else +        (void) test_crypt_dh_pkp_create_destroy; +        (void) test_crypt_dh_derive; +        (void) test_crypt_encrypt_decrypt; + +        ret = TEST_RC_SKIP; +#endif +        return ret; +} diff --git a/src/lib/tests/hash_test.c b/src/lib/tests/hash_test.c new file mode 100644 index 00000000..970d9185 --- /dev/null +++ b/src/lib/tests/hash_test.c @@ -0,0 +1,202 @@ +/* + * Ouroboros - Copyright (C) 2016 - 2024 + * + * Test of the hashing functions + * + *    Dimitri Staessens <dimitri@ouroboros.rocks> + *    Sander Vrijders   <sander@ouroboros.rocks> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., http://www.fsf.org/about/contact/. + */ + +#include <ouroboros/hash.h> +#include <ouroboros/test.h> + +#include <stdlib.h> +#include <stdint.h> +#include <assert.h> +#include <string.h> +#include <stdio.h> + +/* + * Test vectors calculated at + * https://www.lammertbies.nl/comm/info/crc-calculation.html + */ + +struct vec_entry { +        char * in; +        char * out; +}; + +static int test_crc32(void) +{ +        int ret = 0; + +        struct vec_entry vec [] = { +                { "0",         "f4dbdf21" }, +                { "123456789", "cbf43926" }, +                { "987654321", "015f0201" }, +                { NULL,        NULL       } +        }; + +        struct vec_entry * cur = vec; + +        TEST_START(); + +        while (cur->in != NULL) { +                uint8_t crc[4]; +                char    res[9]; + +                str_hash(HASH_CRC32, crc, cur->in); + +                sprintf(res, HASH_FMT32, HASH_VAL32(crc)); +                if (strcmp(res, cur->out) != 0) { +                        printf("Hash failed %s != %s.\n", res, cur->out); +                        ret |= -1; +                } + +                ++cur; +        } + +        TEST_END(ret); + +        return ret; +} + +static int test_md5(void) +{ +        int ret = 0; + +        struct vec_entry vec [] = {{ +                "abc", +                "900150983cd24fb0d6963f7d28e17f72" +        }, { +                "The quick brown fox jumps over the lazy dog", +                "9e107d9d372bb6826bd81d3542a419d6" +        }, { +                "abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq", +                "8215ef0796a20bcaaae116d3876c664a" +        }, { +                NULL, +                NULL +        }}; + +        struct vec_entry * cur = vec; + +        TEST_START(); + + +        while (cur->in != NULL) { +                uint8_t md5[16]; +                char    res[33]; + +                str_hash(HASH_MD5, md5, cur->in); + +                sprintf(res, HASH_FMT128, HASH_VAL128(md5)); +                if (strcmp(res, cur->out) != 0) { +                        printf("Hash failed %s != %s.\n", res, cur->out); +                        ret |= -1; +                } + +                ++cur; +        } + +        TEST_END(ret); + +        return ret; +} + +static int test_sha3(void) +{ +        int ret = 0; + +        uint8_t sha3[64]; +        char    res[129]; + +        char * in = "abc"; + +        char * out = +                "e642824c3f8cf24ad09234ee7d3c766f" +                "c9a3a5168d0c94ad73b46fdf"; + +        TEST_START(); + +        str_hash(HASH_SHA3_224, sha3, in); + +        sprintf(res, HASH_FMT224, HASH_VAL224(sha3)); +        if (strcmp(res, out) != 0) { +                printf("SHA3-224 failed %s != %s", res, out); +                ret |= -1; +        } + +        out = +                "3a985da74fe225b2045c172d6bd390bd" +                "855f086e3e9d525b46bfe24511431532"; + +        str_hash(HASH_SHA3_256, sha3, in); + +        sprintf(res, HASH_FMT256, HASH_VAL256(sha3)); +        if (strcmp(res, out) != 0) { +                printf("SHA3-256 failed %s != %s.\n", res, out); +                ret |= -1; +        } + +        out = +                "ec01498288516fc926459f58e2c6ad8d" +                "f9b473cb0fc08c2596da7cf0e49be4b2" +                "98d88cea927ac7f539f1edf228376d25"; + +        str_hash(HASH_SHA3_384, sha3, in); + +        sprintf(res, HASH_FMT384, HASH_VAL384(sha3)); +        if (strcmp(res, out) != 0) { +                printf("SHA3-384failed %s != %s.'n", res, out); +                ret |= -1; +        } + +        out = +                "b751850b1a57168a5693cd924b6b096e" +                "08f621827444f70d884f5d0240d2712e" +                "10e116e9192af3c91a7ec57647e39340" +                "57340b4cf408d5a56592f8274eec53f0"; + +        str_hash(HASH_SHA3_512, sha3, in); + +        sprintf(res, HASH_FMT512, HASH_VAL512(sha3)); +        if (strcmp(res, out) != 0) { +                printf("SHA3-512 failed %s != %s.\n", res, out); +                ret |= -1; +        } + +        TEST_END(ret); + +        return ret; +} + +int hash_test(int     argc, +              char ** argv) +{ +        int ret = 0; + +        (void) argc; +        (void) argv; + +        ret |= test_crc32(); + +        ret |= test_md5(); + +        ret |= test_sha3(); + +        return ret; +} diff --git a/src/lib/tests/md5_test.c b/src/lib/tests/md5_test.c index b5ad127f..28e8f42f 100644 --- a/src/lib/tests/md5_test.c +++ b/src/lib/tests/md5_test.c @@ -1,5 +1,5 @@  /* - * Ouroboros - Copyright (C) 2016 - 2021 + * Ouroboros - Copyright (C) 2016 - 2024   *   * Test of the MD5 function   * diff --git a/src/lib/tests/sha3_test.c b/src/lib/tests/sha3_test.c index 4860cd9b..82b4ef0d 100644 --- a/src/lib/tests/sha3_test.c +++ b/src/lib/tests/sha3_test.c @@ -1,5 +1,5 @@  /* - * Ouroboros - Copyright (C) 2016 - 2021 + * Ouroboros - Copyright (C) 2016 - 2024   *   * Test of the SHA3 function   * diff --git a/src/lib/tests/shm_rbuff_test.c b/src/lib/tests/shm_rbuff_test.c index a3ed1449..e36c3229 100644 --- a/src/lib/tests/shm_rbuff_test.c +++ b/src/lib/tests/shm_rbuff_test.c @@ -1,5 +1,5 @@  /* - * Ouroboros - Copyright (C) 2016 - 2021 + * Ouroboros - Copyright (C) 2016 - 2024   *   * Test of the shm_rbuff   * diff --git a/src/lib/tests/sockets_test.c b/src/lib/tests/sockets_test.c new file mode 100644 index 00000000..bbf2323b --- /dev/null +++ b/src/lib/tests/sockets_test.c @@ -0,0 +1,98 @@ +/* + * Ouroboros - Copyright (C) 2016 - 2024 + * + * Tests for socket.c + * + *    Dimitri Staessens <dimitri@ouroboros.rocks> + *    Sander Vrijders   <sander@ouroboros.rocks> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., http://www.fsf.org/about/contact/. + */ + +#define _POSIX_C_SOURCE 200112L + +#include <ouroboros/sockets.h> +#include <ouroboros/test.h> + +#include <assert.h> +#include <stdio.h> +#include <stdlib.h> + +#define TEST_PID              1234 +#define TEST_PID_STR          "1234" +#define TEST_SERVER_PATH      "/tmp/test.sock" +#define TEST_SERVER_PREFIX    "/tmp/ouroboros/test." +#define TEST_SOCK_PATH_PREFIX "var/run/ouroboros/test." + +static int test_sock_path(void) +{ +        char * path; +        char * exp = TEST_SOCK_PATH_PREFIX TEST_PID_STR SOCK_PATH_SUFFIX; + +        TEST_START(); + +        path = sock_path(TEST_PID, TEST_SOCK_PATH_PREFIX); +        if (path == NULL) { +                printf("Path is NULL.\n"); +                goto fail_path; +        } + +        if (strcmp(path, exp) != 0) { +                printf("Expected path '%s', got '%s'.\n", exp, path); +                goto fail_cmp; +        } + +        free(path); + +        TEST_SUCCESS(); +        return TEST_RC_SUCCESS; + fail_cmp: +        free(path); + fail_path: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +static int test_server_socket_open(void) +{ +        int sockfd; + +        TEST_START(); + +        sockfd = server_socket_open(TEST_SERVER_PATH); +        if (sockfd < 0) { +                printf("Failed to open server socket.\n"); +                goto fail_sock; +        } + +        close(sockfd); + +        unlink(TEST_SERVER_PATH); + +        TEST_SUCCESS(); +        return TEST_RC_SUCCESS; + fail_sock: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +int sockets_test(void) +{ +        int ret = 0; + +        ret |= test_sock_path(); +        ret |= test_server_socket_open(); + +        return ret; +} diff --git a/src/lib/tests/time_test.c b/src/lib/tests/time_test.c new file mode 100644 index 00000000..2b75b873 --- /dev/null +++ b/src/lib/tests/time_test.c @@ -0,0 +1,529 @@ +/* + * Ouroboros - Copyright (C) 2016 - 2024 + * + * Test of the time utilities + * + *    Dimitri Staessens <dimitri@ouroboros.rocks> + *    Sander Vrijders   <sander@ouroboros.rocks> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., http://www.fsf.org/about/contact/. + */ + +#define _POSIX_C_SOURCE 200809L + +#include <ouroboros/test.h> +#include <ouroboros/time.h> + +#include <stdio.h> + +static int ts_check(struct timespec * s, +                    time_t            sec, +                    time_t            nsec) +{ +        return s->tv_sec == sec && s->tv_nsec == nsec; +} + +static int tv_check(struct timeval * v, +                    time_t           sec, +                    time_t           usec) +{ +        return v->tv_sec == sec && v->tv_usec == usec; +} + + +static int test_time_ts_init(void) +{ +        struct timespec s  = TIMESPEC_INIT_S (100); +        struct timespec ms = TIMESPEC_INIT_MS(100); +        struct timespec us = TIMESPEC_INIT_US(100); +        struct timespec ns = TIMESPEC_INIT_NS(100); + +        TEST_START(); + +        if (!ts_check(&s, 100, 0)) { +                printf("timespec_init_s failed.\n"); +                goto fail; +        } + +        if (!ts_check(&ms, 0, 100 * MILLION)) { +                printf("timespec_init_ms failed.\n"); +                goto fail; +        } + +        if (!ts_check(&us, 0, 100* 1000L)) { +                printf("timespec_init_us failed.\n"); +                goto fail; +        } + +        if (!ts_check(&ns, 0, 100)) { +                printf("timespec_init_ns failed.\n"); +                goto fail; +        } + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +static int test_time_tv_init(void) +{ +        struct timeval s  = TIMEVAL_INIT_S (100); +        struct timeval ms = TIMEVAL_INIT_MS(100); +        struct timeval us = TIMEVAL_INIT_US(100); + +        TEST_START(); + +        if (!tv_check(&s, 100, 0)) { +                printf("timeval_init_s failed.\n"); +                goto fail; +        } + +        if (!tv_check(&ms, 0, 100 * 1000L)) { +                printf("timeval_init_ms failed.\n"); +                goto fail; +        } + +        if (!tv_check(&us, 0, 100)) { +                printf("timeval_init_us failed.\n"); +                goto fail; +        } + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +static int test_ts_diff(void) +{ +        struct timespec s0  = TIMESPEC_INIT_S (100); +        struct timespec s1  = TIMESPEC_INIT_S (200); +        struct timespec ms0 = TIMESPEC_INIT_MS(100); +        struct timespec ms1 = TIMESPEC_INIT_MS(200); +        struct timespec us0 = TIMESPEC_INIT_US(100); +        struct timespec us1 = TIMESPEC_INIT_US(200); +        struct timespec ns0 = TIMESPEC_INIT_NS(100); +        struct timespec ns1 = TIMESPEC_INIT_NS(200); +        struct timespec res; + +        TEST_START(); + +        ts_diff(&s0, &s1, &res); +        if (!ts_check(&res, -100, 0)) { +                printf("timespec_diff failed at s0 - s1.\n"); +                goto fail; +        } + +        ts_diff(&s1, &s0, &res); +        if (!ts_check(&res, 100, 0)) { +                printf("timespec_diff failed at s1 - s0.\n"); +                goto fail; +        } + +        ts_diff(&ms0, &ms1, &res); +        if (!ts_check(&res, -1, 900 * MILLION)) { +                printf("timespec_diff failed at ms0 - ms1.\n"); +                goto fail; +        } + +        ts_diff(&ms1, &ms0, &res); +        if (!ts_check(&res, 0, 100 * MILLION)) { +                printf("timespec_diff failed at ms1 - ms0.\n"); +                goto fail; +        } + +        ts_diff(&us0, &us1, &res); +        if (!ts_check(&res, -1, 999900 * 1000L)) { +                printf("timespec_diff failed at us0 - us1.\n"); +                goto fail; +        } + +        ts_diff(&us1, &us0, &res); +        if (!ts_check(&res, 0, 100 * 1000L)) { +                printf("timespec_diff failed at us1 - us0.\n"); +                goto fail; +        } + +        ts_diff(&ns0, &ns1, &res); +        if (!ts_check(&res, -1, 999999900)) { +                printf("timespec_diff failed at ns0 - ns1.\n"); +                goto fail; +        } + +        ts_diff(&ns1, &ns0, &res); +        if (!ts_check(&res, 0, 100)) { +                printf("timespec_diff failed at ns1 - ns0.\n"); +                goto fail; +        } + +        ts_diff(&s0, &ms0, &res); +        if (!ts_check(&res, 99, 900 * MILLION)) { +                printf("timespec_diff failed at s0 - ms0.\n"); +                goto fail; +        } + +        ts_diff(&s0, &us0, &res); +        if (!ts_check(&res, 99, 999900 * 1000L)) { +                printf("timespec_diff failed at s0 - us0.\n"); +                goto fail; +        } + +        ts_diff(&s0, &ns0, &res); +        if (!ts_check(&res, 99, 999999900)) { +                printf("timespec_diff failed at s0 - ns0.\n"); +                goto fail; +        } + +        ts_diff(&ms0, &us0, &res); +        if (!ts_check(&res, 0, 99900 * 1000L)) { +                printf("timespec_diff failed at ms0 - us0.\n"); +                goto fail; +        } + +        ts_diff(&ms0, &ns0, &res); +        if (!ts_check(&res, 0, 99999900)) { +                printf("timespec_diff failed at ms0 - ns0.\n"); +                goto fail; +        } + +        ts_diff(&us0, &ns0, &res); +        if (!ts_check(&res, 0, 99900)) { +                printf("timespec_diff failed at us0 - ns0.\n"); +                goto fail; +        } + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +static int test_tv_diff(void) +{ +        struct timeval s0  = TIMEVAL_INIT_S (100); +        struct timeval s1  = TIMEVAL_INIT_S (200); +        struct timeval ms0 = TIMEVAL_INIT_MS(100); +        struct timeval ms1 = TIMEVAL_INIT_MS(200); +        struct timeval us0 = TIMEVAL_INIT_US(100); +        struct timeval us1 = TIMEVAL_INIT_US(200); +        struct timeval res; + +        TEST_START(); + +        tv_diff(&s0, &s1, &res); +        if (!tv_check(&res, -100, 0)) { +                printf("timeval_diff failed at s0 - s1.\n"); +                goto fail; +        } + +        tv_diff(&s1, &s0, &res); +        if (!tv_check(&res, 100, 0)) { +                printf("timeval_diff failed at s1 - s0.\n"); +                goto fail; +        } + +        tv_diff(&ms0, &ms1, &res); +        if (!tv_check(&res, -1, 900 * 1000L)) { +                printf("timeval_diff failed at ms0 - ms1.\n"); +                goto fail; +        } + +        tv_diff(&ms1, &ms0, &res); +        if (!tv_check(&res, 0, 100 * 1000L)) { +                printf("timeval_diff failed at ms1 - ms0.\n"); +                goto fail; +        } + +        tv_diff(&us0, &us1, &res); +        if (!tv_check(&res, -1, 999900)) { +                printf("timeval_diff failed at us0 - us1.\n"); +                goto fail; +        } + +        tv_diff(&us1, &us0, &res); +        if (!tv_check(&res, 0, 100)) { +                printf("timeval_diff failed at us1 - us0.\n"); +                goto fail; +        } + +        tv_diff(&s0, &ms0, &res); +        if (!tv_check(&res, 99, 900 * 1000L)) { +                printf("timeval_diff failed at s0 - ms0.\n"); +                goto fail; +        } + +        tv_diff(&s0, &us0, &res); +        if (!tv_check(&res, 99, 999900)) { +                printf("timeval_diff failed at s0 - us0.\n"); +                goto fail; +        } + +        tv_diff(&ms0, &us0, &res); +        if (!tv_check(&res, 0, 99900)) { +                printf("timeval_diff failed at ms0 - us0.\n"); +                goto fail; +        } + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +static int test_ts_diff_time(void) +{ +        struct timespec s0  = TIMESPEC_INIT_S (100); +        struct timespec s1  = TIMESPEC_INIT_S (200); +        struct timespec ms0 = TIMESPEC_INIT_MS(100); +        struct timespec ms1 = TIMESPEC_INIT_MS(200); +        struct timespec us0 = TIMESPEC_INIT_US(100); +        struct timespec us1 = TIMESPEC_INIT_US(200); +        struct timespec ns0 = TIMESPEC_INIT_NS(100); +        struct timespec ns1 = TIMESPEC_INIT_NS(200); + +        TEST_START(); + +        if (ts_diff_ms(&s0, &s1) != -100 * 1000L) { +                printf("timespec_diff_ms failed at s0 - s1.\n"); +                goto fail; +        } + +        if (ts_diff_ms(&s1, &s0) != 100 * 1000L) { +                printf("timespec_diff_ms failed at s1 - s0.\n"); +                goto fail; +        } + +        if (ts_diff_us(&s0, &s1) != -100 * MILLION) { +                printf("timespec_diff_us failed at s1 - s0.\n"); +                goto fail; +        } + +        if (ts_diff_us(&s1, &s0) != 100 * MILLION) { +                printf("timespec_diff_us failed at s0 - s1.\n"); +                goto fail; +        } + +        if (ts_diff_ns(&s0, &s1) != -100 * BILLION) { +                printf("timespec_diff_ns failed at s0 - s1.\n"); +                goto fail; +        } + +        if (ts_diff_ns(&s1, &s0) != 100 * BILLION) { +                printf("timespec_diff_ns failed at s1 - s0.\n"); +                goto fail; +        } + +        if (ts_diff_ms(&ms0, &ms1) != -100) { +                printf("timespec_diff_ms failed at ms0 - ms1.\n"); +                goto fail; +        } + +        if (ts_diff_ms(&ms1, &ms0) != 100) { +                printf("timespec_diff_ms failed at ms1 - ms0.\n"); +                goto fail; +        } + +        if (ts_diff_us(&ms0, &ms1) != -100 * 1000L) { +                printf("timespec_diff_us failed at ms0 - ms1.\n"); +                goto fail; +        } + +        if (ts_diff_us(&ms1, &ms0) != 100 * 1000L) { +                printf("timespec_diff_us failed at ms1 - ms0.\n"); +                goto fail; +        } + +        if (ts_diff_ns(&ms0, &ms1) != -100 * MILLION) { +                printf("timespec_diff_ns failed at ms0 - ms1.\n"); +                goto fail; +        } + +        if (ts_diff_ns(&ms1, &ms0) != 100 * MILLION) { +                printf("timespec_diff_ns failed at ms1 - ms0.\n"); +                goto fail; +        } + +        if (ts_diff_ms(&us0, &us1) != 0) { +                printf("timespec_diff_ms failed at us0 - us1.\n"); +                goto fail; +        } + +        if (ts_diff_ms(&us1, &us0) != 0) { +                printf("timespec_diff_ms failed at us1 - us0.\n"); +                goto fail; +        } + +        if (ts_diff_us(&us0, &us1) != -100) { +                printf("timespec_diff_us failed at us0 - us1.\n"); +                goto fail; +        } + +        if (ts_diff_us(&us1, &us0) != 100) { +                printf("timespec_diff_us failed at us1 - us0.\n"); +                goto fail; +        } + +        if (ts_diff_ns(&us0, &us1) != -100 * 1000L) { +                printf("timespec_diff_ns failed at us0 - us1.\n"); +                goto fail; +        } + +        if (ts_diff_ns(&us1, &us0) != 100 * 1000L) { +                printf("timespec_diff_ns failed at us1 - us0.\n"); +                goto fail; +        } + +        if (ts_diff_ms(&ns0, &ns1) != 0) { +                printf("timespec_diff_ms failed at ns0 - ns1.\n"); +                goto fail; +        } + +        if (ts_diff_ms(&ns1, &ns0) != 0) { +                printf("timespec_diff_ms failed at ns1 - ns0.\n"); +                goto fail; +        } + +        if (ts_diff_us(&ns0, &ns1) != 0) { +                printf("timespec_diff_us failed at ns0 - ns1.\n"); +                goto fail; +        } + +        if (ts_diff_us(&ns1, &ns0) != 0) { +                printf("timespec_diff_us failed at ns1 - ns0.\n"); +                goto fail; +        } + +        if (ts_diff_ns(&ns0, &ns1) != -100) { +                printf("timespec_diff_ns failed at ns0 - ns1.\n"); +                goto fail; +        } + +        if (ts_diff_ns(&ns1, &ns0) != 100) { +                printf("timespec_diff_ns failed at ns1 - ns0.\n"); +                goto fail; +        } + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +static int test_tv_diff_time(void) +{ +        struct timeval s0  = TIMEVAL_INIT_S (100); +        struct timeval s1  = TIMEVAL_INIT_S (200); +        struct timeval ms0 = TIMEVAL_INIT_MS(100); +        struct timeval ms1 = TIMEVAL_INIT_MS(200); +        struct timeval us0 = TIMEVAL_INIT_US(100); +        struct timeval us1 = TIMEVAL_INIT_US(200); + +        TEST_START(); + +        if (tv_diff_ms(&s0, &s1) != -100 * 1000L) { +                printf("timeval_diff_ms failed at s0 - s1.\n"); +                goto fail; +        } + +        if (tv_diff_ms(&s1, &s0) != 100 * 1000L) { +                printf("timeval_diff_ms failed at s1 - s0.\n"); +                goto fail; +        } + +        if (tv_diff_us(&s0, &s1) != -100 * MILLION) { +                printf("timeval_diff_us failed at s0 - s1.\n"); +                goto fail; +        } + +        if (tv_diff_us(&s1, &s0) != 100 * MILLION) { +                printf("timeval_diff_us failed at s1 - s0.\n"); +                goto fail; +        } + +        if (tv_diff_ms(&ms0, &ms1) != -100) { +                printf("timeval_diff_ms failed at ms0 - ms1.\n"); +                goto fail; +        } + +        if (tv_diff_ms(&ms1, &ms0) != 100) { +                printf("timeval_diff_ms failed at ms1 - ms0.\n"); +                goto fail; +        } + +        if (tv_diff_us(&ms0, &ms1) != -100 * 1000L) { +                printf("timeval_diff_us failed at ms0 - ms1.\n"); +                goto fail; +        } + +        if (tv_diff_us(&ms1, &ms0) != 100 * 1000L) { +                printf("timeval_diff_us failed at ms1 - ms0.\n"); +                goto fail; +        } + +        if (tv_diff_ms(&us0, &us1) != 0) { +                printf("timeval_diff_ms failed at us0 - us1.\n"); +                goto fail; +        } + +        if (tv_diff_ms(&us1, &us0) != 0) { +                printf("timeval_diff_ms failed at us1 - us0.\n"); +                goto fail; +        } + +        if (tv_diff_us(&us0, &us1) != -100) { +                printf("timeval_diff_us failed at us0 - us1.\n"); +                goto fail; +        } + +        if (tv_diff_us(&us1, &us0) != 100) { +                printf("timeval_diff_us failed at us1 - us0.\n"); +                goto fail; +        } + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +int time_test(int argc, +              char ** argv) +{ +        int ret = 0; + +        (void) argc; +        (void) argv; + +        ret |= test_time_ts_init(); +        ret |= test_time_tv_init(); +        ret |= test_ts_diff(); +        ret |= test_tv_diff(); +        ret |= test_ts_diff_time(); +        ret |= test_tv_diff_time(); + +        return ret; +} diff --git a/src/lib/tests/time_utils_test.c b/src/lib/tests/time_utils_test.c deleted file mode 100644 index fa65c4dc..00000000 --- a/src/lib/tests/time_utils_test.c +++ /dev/null @@ -1,164 +0,0 @@ -/* - * Ouroboros - Copyright (C) 2016 - 2021 - * - * Test of the time utilities - * - *    Dimitri Staessens <dimitri@ouroboros.rocks> - *    Sander Vrijders   <sander@ouroboros.rocks> - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License version 2 as - * published by the Free Software Foundation. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., http://www.fsf.org/about/contact/. - */ - -#define _POSIX_C_SOURCE 200809L - -#include <ouroboros/time_utils.h> - -#include <stdio.h> - -static void ts_print(struct timespec * s) -{ -        printf("timespec is %zd:%ld.\n", (ssize_t) s->tv_sec, s->tv_nsec); -} - -static void tv_print(struct timeval * v) -{ -        printf("timeval is %zd:%zu.\n", (ssize_t) v->tv_sec, (size_t) v->tv_usec); -} - -static void ts_init(struct timespec * s, -                    time_t            sec, -                    time_t            nsec) -{ -        s->tv_sec  = sec; -        s->tv_nsec = nsec; -} - -static void tv_init(struct timeval * v, -                    time_t           sec, -                    time_t           usec) -{ -        v->tv_sec  = sec; -        v->tv_usec = usec; -} - -static int ts_check(struct timespec * s, -                    time_t            sec, -                    time_t            nsec) -{ -        return s->tv_sec == sec && s->tv_nsec == nsec; -} - -static int tv_check(struct timeval * v, -                    time_t           sec, -                    time_t           usec) -{ -        return v->tv_sec == sec && v->tv_usec == usec; -} - -int time_utils_test(int     argc, -                    char ** argv) -{ -        struct timespec s0; -        struct timespec s1; -        struct timespec s2; - -        struct timeval v0; -        struct timeval v1; -        struct timeval v2; - -        (void) argc; -        (void) argv; - -        ts_init(&s0, 0, 0); -        ts_init(&s1, 5, 0); - -        ts_add(&s0, &s1, &s2); -        if (!ts_check(&s2, 5, 0)) { -                printf("ts_add failed.\n"); -                ts_print(&s2); -                return -1; -        } - -        tv_init(&v0, 0, 0); -        tv_init(&v1, 5, 0); - -        tv_add(&v0, &v1, &v2); -        if (!tv_check(&v2, 5, 0)) { -                printf("tv_add failed.\n"); -                tv_print(&v2); -                return -1; -        } - -        ts_init(&s0, 0, 500 * MILLION); -        ts_init(&s1, 0, 600 * MILLION); - -        ts_add(&s0, &s1, &s2); -        if (!ts_check(&s2, 1, 100 * MILLION)) { -                printf("ts_add with nano overflow failed.\n"); -                ts_print(&s2); -                return -1; -        } - -        tv_init(&v0, 0, 500 * 1000); -        tv_init(&v1, 0, 600 * 1000); - -        tv_add(&v0, &v1, &v2); -        if (!tv_check(&v2, 1, 100 * 1000)) { -                printf("tv_add with nano overflow failed.\n"); -                tv_print(&v2); -                return -1; -        } - -        ts_init(&s0, 0, 0); -        ts_init(&s1, 5, 0); - -        ts_diff(&s0, &s1, &s2); -        if (!ts_check(&s2, -5, 0)) { -                printf("ts_diff failed.\n"); -                ts_print(&s2); -                return -1; -        } - -        tv_init(&v0, 0, 0); -        tv_init(&v1, 5, 0); - -        tv_diff(&v0, &v1, &v2); -        if (!tv_check(&v2, -5, 0)) { -                printf("tv_diff failed.\n"); -                tv_print(&v2); -                return -1; -        } - -        ts_init(&s0, 0, 500 * MILLION); -        ts_init(&s1, 0, 600 * MILLION); - -        ts_diff(&s0, &s1, &s2); -        if (!ts_check(&s2, -1, 900 * MILLION)) { -                printf("ts_diff with nano underflow failed.\n"); -                ts_print(&s2); -                return -1; -        } - -        tv_init(&v0, 0, 500 * 1000); -        tv_init(&v1, 0, 600 * 1000); - -        tv_diff(&v0, &v1, &v2); -        if (!tv_check(&v2, -1, 900 * 1000)) { -                printf("tv_diff with nano underflow failed.\n"); -                tv_print(&v2); -                return -1; -        } - -        return 0; -} diff --git a/src/lib/tests/tpm_test.c b/src/lib/tests/tpm_test.c new file mode 100644 index 00000000..98d4fab3 --- /dev/null +++ b/src/lib/tests/tpm_test.c @@ -0,0 +1,104 @@ +/* + * Ouroboros - Copyright (C) 2016 - 2024 + * + * Tests for the threadpool manager + * + *    Dimitri Staessens <dimitri@ouroboros.rocks> + *    Sander Vrijders   <sander@ouroboros.rocks> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., http://www.fsf.org/about/contact/. + */ + + +#include "tpm.c" + +#include <ouroboros/test.h> + +static void * test_func(void * o) +{ +        (void) o; + +        while(1) +                sleep(1); + +        return NULL; +} + +static int test_tpm_create_destroy(void) +{ +        struct tpm *tpm; + +        TEST_START(); + +        tpm = tpm_create(2, 2, &test_func, NULL); +        if (tpm == NULL) { +                printf("Failed to initialize TPM.\n"); +                goto fail; +        } + +        tpm_destroy(tpm); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +static int test_tpm_start_stop(void * (* fn)(void *), +                               void * o) +{ +        struct tpm *tpm; + +        TEST_START(); + +        tpm = tpm_create(2, 2, fn, o); +        if (tpm == NULL) { +                printf("Failed to initialize TPM.\n"); +                goto fail_create; +        } + +        if (tpm_start(tpm) < 0) { +                printf("Failed to start TPM.\n"); +                goto fail_start; +        } + +        tpm_stop(tpm); + +        tpm_destroy(tpm); + +        TEST_SUCCESS(); + +        return TEST_RC_SUCCESS; + fail_start: +        tpm_destroy(tpm); + fail_create: +        TEST_FAIL(); +        return TEST_RC_FAIL; +} + +int tpm_test(int     argc, +             char ** argv) +{ +        int ret = 0; + +        (void) argc; +        (void) argv; + +        ret |= test_tpm_create_destroy(); +        ret |= test_tpm_start_stop(&test_func, NULL); + +        return ret; +}  | 
