tor

The Tor anonymity network
git clone https://git.dasho.dev/tor.git
Log | Files | Refs | README | LICENSE

test_crypto_openssl.c (2921B)


      1 /* Copyright (c) 2001-2004, Roger Dingledine.
      2 * Copyright (c) 2004-2006, Roger Dingledine, Nick Mathewson.
      3 * Copyright (c) 2007-2021, The Tor Project, Inc. */
      4 /* See LICENSE for licensing information */
      5 
      6 #include "orconfig.h"
      7 
      8 #define CRYPTO_RAND_PRIVATE
      9 
     10 #include "lib/crypt_ops/compat_openssl.h"
     11 #include "lib/crypt_ops/crypto_rand.h"
     12 #include "lib/encoding/binascii.h"
     13 #include "lib/malloc/malloc.h"
     14 #include "test/test.h"
     15 
     16 #include <openssl/evp.h>
     17 #include <openssl/rand.h>
     18 #include <string.h>
     19 
     20 /* Test for rectifying openssl RAND engine. */
     21 static void
     22 test_crypto_rng_engine(void *arg)
     23 {
     24  (void)arg;
     25  RAND_METHOD dummy_method;
     26  memset(&dummy_method, 0, sizeof(dummy_method));
     27 
     28  /* We should be a no-op if we're already on RAND_OpenSSL */
     29  tt_int_op(0, OP_EQ, crypto_force_rand_ssleay());
     30  tt_assert(RAND_get_rand_method() == RAND_OpenSSL());
     31 
     32  /* We should correct the method if it's a dummy. */
     33  RAND_set_rand_method(&dummy_method);
     34 #ifdef LIBRESSL_VERSION_NUMBER
     35  /* On libressl, you can't override the RNG. */
     36  tt_assert(RAND_get_rand_method() == RAND_OpenSSL());
     37  tt_int_op(0, OP_EQ, crypto_force_rand_ssleay());
     38 #else
     39  tt_assert(RAND_get_rand_method() == &dummy_method);
     40  tt_int_op(1, OP_EQ, crypto_force_rand_ssleay());
     41 #endif /* defined(LIBRESSL_VERSION_NUMBER) */
     42  tt_assert(RAND_get_rand_method() == RAND_OpenSSL());
     43 
     44  /* Make sure we aren't calling dummy_method */
     45  crypto_rand((void *) &dummy_method, sizeof(dummy_method));
     46  crypto_rand((void *) &dummy_method, sizeof(dummy_method));
     47 
     48 done:
     49  ;
     50 }
     51 
     52 /** Encode src into dest with OpenSSL's EVP Encode interface, returning the
     53 * length of the encoded data in bytes.
     54 */
     55 static int
     56 base64_encode_evp(char *dest, char *src, size_t srclen)
     57 {
     58  const unsigned char *s = (unsigned char*)src;
     59  EVP_ENCODE_CTX *ctx = EVP_ENCODE_CTX_new();
     60  int len, ret;
     61 
     62  EVP_EncodeInit(ctx);
     63  EVP_EncodeUpdate(ctx, (unsigned char *)dest, &len, s, (int)srclen);
     64  EVP_EncodeFinal(ctx, (unsigned char *)(dest + len), &ret);
     65  EVP_ENCODE_CTX_free(ctx);
     66  return ret+ len;
     67 }
     68 
     69 static void
     70 test_crypto_base64_encode_matches(void *arg)
     71 {
     72  (void)arg;
     73  int i, j;
     74  char data1[1024];
     75  char data2[1024];
     76  char data3[1024];
     77 
     78  for (i = 0; i < 256; i++) {
     79    /* Test the multiline format Base64 encoder with 0 .. 256 bytes of
     80     * output against OpenSSL.
     81     */
     82    const size_t enclen = base64_encode_size(i, BASE64_ENCODE_MULTILINE);
     83    data1[i] = i;
     84    j = base64_encode(data2, 1024, data1, i, BASE64_ENCODE_MULTILINE);
     85    tt_int_op(j, OP_EQ, enclen);
     86    j = base64_encode_evp(data3, data1, i);
     87    tt_int_op(j, OP_EQ, enclen);
     88    tt_mem_op(data2, OP_EQ, data3, enclen);
     89    tt_int_op(j, OP_EQ, strlen(data2));
     90  }
     91 
     92 done:
     93  ;
     94 }
     95 
     96 struct testcase_t crypto_openssl_tests[] = {
     97  { "rng_engine", test_crypto_rng_engine, TT_FORK, NULL, NULL },
     98  { "base64_encode_match", test_crypto_base64_encode_matches,
     99    TT_FORK, NULL, NULL },
    100  END_OF_TESTCASES
    101 };