LCOV - code coverage report
Current view: top level - test - test_pem.c (source / functions) Hit Total Coverage
Test: lcov.info Lines: 62 62 100.0 %
Date: 2021-11-24 03:28:48 Functions: 3 3 100.0 %

          Line data    Source code
       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             : #include "lib/encoding/pem.h"
       9             : #include "lib/cc/compat_compiler.h"
      10             : #include "lib/malloc/malloc.h"
      11             : 
      12             : #include "test/test.h"
      13             : 
      14             : #include <string.h>
      15             : #include <stdio.h>
      16             : #include <stdlib.h>
      17             : 
      18             : static const char example_pre[] =
      19             :     "Lest you get the wrong impression, we wombats "
      20             :     "are not in the habit of tunneling madly about, without any supplies "
      21             :     "or even a map."; /* -- Ursula Vernon, _Digger_ */
      22             : static const char expected[] =
      23             :     "-----BEGIN WOMBAT QUOTE-----\n"
      24             :     "TGVzdCB5b3UgZ2V0IHRoZSB3cm9uZyBpbXByZXNzaW9uLCB3ZSB3b21iYXRzIGFy\n"
      25             :     "ZSBub3QgaW4gdGhlIGhhYml0IG9mIHR1bm5lbGluZyBtYWRseSBhYm91dCwgd2l0\n"
      26             :     "aG91dCBhbnkgc3VwcGxpZXMgb3IgZXZlbiBhIG1hcC4=\n"
      27             :     "-----END WOMBAT QUOTE-----\n";
      28             : 
      29             : static void
      30           1 : test_crypto_pem_encode(void *arg)
      31             : {
      32           1 :   (void)arg;
      33             : 
      34           1 :   char buf[4096];
      35             : 
      36           1 :   int n = (int) pem_encoded_size(strlen(example_pre), "WOMBAT QUOTE");
      37             : 
      38           1 :   int n2 = pem_encode(buf, sizeof(buf),
      39             :                       (const unsigned char *)example_pre, strlen(example_pre),
      40             :                       "WOMBAT QUOTE");
      41           1 :   tt_int_op(strlen(buf)+1, OP_EQ, n);
      42           1 :   tt_int_op(n2, OP_EQ, 0);
      43           1 :   tt_str_op(buf, OP_EQ, expected);
      44             : 
      45             :   /* Now make sure it succeeds if the buffer is exactly the length we want. */
      46           1 :   memset(buf, 0, sizeof(buf));
      47           1 :   n2 = pem_encode(buf, n, (const unsigned char *)example_pre,
      48             :                       strlen(example_pre), "WOMBAT QUOTE");
      49           1 :   tt_int_op(n2, OP_EQ, 0);
      50           1 :   tt_str_op(buf, OP_EQ, expected);
      51             : 
      52             :   /* Make sure it fails if the buffer is too short. */
      53           1 :   memset(buf, 0, sizeof(buf));
      54           1 :   n2 = pem_encode(buf, n - 1, (const unsigned char *)example_pre,
      55             :                   strlen(example_pre), "WOMBAT QUOTE");
      56           1 :   tt_int_op(n2, OP_EQ, -1);
      57             : 
      58           1 :  done:
      59           1 :   ;
      60           1 : }
      61             : 
      62             : static void
      63           1 : test_crypto_pem_decode(void *arg)
      64             : {
      65           1 :   (void)arg;
      66             : 
      67           1 :   unsigned char buf[4096];
      68             : 
      69             :   /* Try a straightforward decoding. */
      70           1 :   int n = pem_decode(buf, sizeof(buf),
      71             :                      expected, strlen(expected),
      72             :                      "WOMBAT QUOTE");
      73           1 :   tt_int_op(n, OP_EQ, strlen(example_pre));
      74           1 :   tt_mem_op(buf, OP_EQ, example_pre, n);
      75             : 
      76             :   /* Succeed if the buffer is exactly the right size. */
      77           1 :   memset(buf, 0xff, sizeof(buf));
      78           1 :   n = pem_decode(buf, strlen(example_pre),
      79             :                  expected, strlen(expected),
      80             :                  "WOMBAT QUOTE");
      81           1 :   tt_int_op(n, OP_EQ, strlen(example_pre));
      82           1 :   tt_mem_op(buf, OP_EQ, example_pre, n);
      83           1 :   tt_int_op(buf[n], OP_EQ, 0xff);
      84             : 
      85             :   /* Verify that it fails if the buffer is too small. */
      86           1 :   memset(buf, 0xff, sizeof(buf));
      87           1 :   n = pem_decode(buf, strlen(example_pre) - 1,
      88             :                  expected, strlen(expected),
      89             :                  "WOMBAT QUOTE");
      90           1 :   tt_int_op(n, OP_EQ, -1);
      91             : 
      92             :   /* Verify that it fails with an incorrect tag. */
      93           1 :   memset(buf, 0xff, sizeof(buf));
      94           1 :   n = pem_decode(buf, sizeof(buf),
      95             :                  expected, strlen(expected),
      96             :                  "QUOKKA VOTE");
      97           1 :   tt_int_op(n, OP_EQ, -1);
      98             : 
      99             :   /* Try truncated buffers of different sizes. */
     100             :   size_t i;
     101         233 :   for (i = 0; i <= strlen(expected); ++i) {
     102         232 :     char *truncated = tor_memdup(expected, i);
     103         232 :     n = pem_decode(buf, sizeof(buf),
     104             :                    truncated, i,
     105             :                    "WOMBAT QUOTE");
     106         232 :     tor_free(truncated);
     107         232 :     if (i < strlen(expected) - 1) {
     108         230 :       tt_int_op(n, OP_EQ, -1);
     109             :     } else {
     110         232 :       tt_int_op(n, OP_EQ, strlen(example_pre));
     111             :     }
     112             :   }
     113             : 
     114           1 :  done:
     115           1 :   ;
     116           1 : }
     117             : 
     118             : static void
     119           1 : test_crypto_pem_decode_crlf(void *arg)
     120             : {
     121           1 :   (void)arg;
     122           1 :   char crlf_version[4096];
     123           1 :   uint8_t buf[4096];
     124             : 
     125             :   /* Convert 'expected' to a version with CRLF instead of LF. */
     126           1 :   const char *inp = expected;
     127           1 :   char *outp = crlf_version;
     128         232 :   while (*inp) {
     129         231 :     if (*inp == '\n') {
     130           5 :       *outp++ = '\r';
     131             :     }
     132         231 :     *outp++ = *inp++;
     133             :   }
     134           1 :   *outp = 0;
     135             : 
     136             :   /* Decoding should succeed (or else we have bug 33032 again) */
     137           1 :   int n = pem_decode(buf, sizeof(buf),
     138             :                      crlf_version, strlen(crlf_version),
     139             :                      "WOMBAT QUOTE");
     140           1 :   tt_int_op(n, OP_EQ, strlen(example_pre));
     141           1 :   tt_mem_op(buf, OP_EQ, example_pre, n);
     142             : 
     143           1 :  done:
     144           1 :   ;
     145           1 : }
     146             : 
     147             : struct testcase_t pem_tests[] = {
     148             :   { "encode", test_crypto_pem_encode, 0, NULL, NULL },
     149             :   { "decode", test_crypto_pem_decode, 0, NULL, NULL },
     150             :   { "decode_crlf", test_crypto_pem_decode_crlf, 0, NULL, NULL },
     151             :   END_OF_TESTCASES
     152             : };

Generated by: LCOV version 1.14