LCOV - code coverage report
Current view: top level - src/plugins/fcrypt - testmod_fcrypt.c (source / functions) Hit Total Coverage
Test: coverage-filtered.info Lines: 0 151 0.0 %
Date: 2019-09-12 12:28:41 Functions: 0 11 0.0 %

          Line data    Source code
       1             : /**
       2             :  * @file
       3             :  *
       4             :  * @brief test suite for the fcrypt plugin
       5             :  *
       6             :  * @copyright BSD License (see LICENSE.md or https://www.libelektra.org)
       7             :  *
       8             :  */
       9             : 
      10             : #include <kdb.h>
      11             : #include <kdbinternal.h>
      12             : #include <stdio.h>
      13             : #include <stdlib.h>
      14             : #include <string.h>
      15             : #include <tests_internal.h>
      16             : #include <tests_plugin.h>
      17             : 
      18             : #include <gpg.h>
      19             : #include <test_key.h>
      20             : 
      21             : #include "../crypto/common_gpg_tests.c"
      22             : #include "../crypto/gpgagent_teardown.h"
      23             : #include "fcrypt.h"
      24             : 
      25             : #define PLUGIN_NAME "fcrypt"
      26             : #define TEST_KEY_ID "DDEBEF9EE2DC931701338212DAF635B17F230E8D"
      27             : #define TEST_FILE "fcrypt_testfile"
      28             : #define BUFFER_SIZE 2048
      29             : 
      30             : #define FAULTY_SIGNATURE_FILE                                                                                                              \
      31             :         "-----BEGIN PGP SIGNED MESSAGE-----\n\
      32             : Hash: SHA512\n\
      33             : \n\
      34             : test (modified)\n\
      35             : -----BEGIN PGP SIGNATURE-----\n\
      36             : \n\
      37             : iJwEAQEKAAYFAlmqZsMACgkQ2vY1sX8jDo2etAP/UA4s7e+SR38wa+AqQbWXKrPp\n\
      38             : i3hoYLPP9lIz5ypedFBlNjcJRjv47wvGc0Z2C1Q6pMtTNcI+is2X9zJNucv9aMeA\n\
      39             : nghsNiEgaIARzOFIe13QTevCg/HEFnq48gFSYNyeVgcsPmVP6tu3xWoEUkVEu6Vf\n\
      40             : XRrYPw+gFVq5zeOAI4A=\n\
      41             : =MjjB\n\
      42             : -----END PGP SIGNATURE-----\n"
      43             : 
      44             : static const kdb_octet_t testContent[] = { 0x01, 0x02, 0xCA, 0xFE, 0xBA, 0xBE, 0x03, 0x04 };
      45             : 
      46           0 : static KeySet * newPluginConfiguration (void)
      47             : {
      48             :         // clang-format off
      49           0 :         return ksNew (3,
      50             :                 keyNew (ELEKTRA_RECIPIENT_KEY, KEY_VALUE, TEST_KEY_ID, KEY_END),
      51             :                 keyNew (ELEKTRA_CRYPTO_PARAM_GPG_UNIT_TEST, KEY_VALUE, "1", KEY_END),
      52             :                 keyNew (ELEKTRA_SIGNATURE_KEY, KEY_VALUE, TEST_KEY_ID, KEY_END),
      53             :                 keyNew (ELEKTRA_FCRYPT_CONFIG_TEXTMODE, KEY_VALUE, "0", KEY_END),
      54             :                 KS_END);
      55             :         // clang-format on
      56             : }
      57             : 
      58           0 : static KeySet * newPluginConfigurationWithTextmodeEnabled (void)
      59             : {
      60             :         // clang-format off
      61           0 :         return ksNew (3,
      62             :                 keyNew (ELEKTRA_RECIPIENT_KEY, KEY_VALUE, TEST_KEY_ID, KEY_END),
      63             :                 keyNew (ELEKTRA_CRYPTO_PARAM_GPG_UNIT_TEST, KEY_VALUE, "1", KEY_END),
      64             :                 keyNew (ELEKTRA_SIGNATURE_KEY, KEY_VALUE, TEST_KEY_ID, KEY_END),
      65             :                 keyNew (ELEKTRA_FCRYPT_CONFIG_TEXTMODE, KEY_VALUE, "1", KEY_END),
      66             :                 KS_END);
      67             :         // clang-format on
      68             : }
      69             : 
      70           0 : static void writeTestFile (const char * file)
      71             : {
      72           0 :         FILE * f = fopen (file, "wb");
      73           0 :         succeed_if (f, "can not write to temporary file");
      74           0 :         if (!f) return;
      75           0 :         succeed_if (fwrite (testContent, 1, sizeof (testContent), f) == sizeof (testContent), "test file preparation failed");
      76           0 :         fclose (f);
      77             : }
      78             : 
      79           0 : static void writeFaultySignatureFile (const char * file)
      80             : {
      81           0 :         FILE * f = fopen (file, "w");
      82           0 :         succeed_if (f, "can not write to temporary file");
      83           0 :         if (!f) return;
      84           0 :         succeed_if (fwrite (FAULTY_SIGNATURE_FILE, 1, strlen (FAULTY_SIGNATURE_FILE), f) == strlen (FAULTY_SIGNATURE_FILE),
      85             :                     "test file preparation failed");
      86           0 :         fclose (f);
      87             : }
      88             : 
      89             : /**
      90             :  * @brief read in the content stored in file and compare it to the test vector.
      91             :  * @retval 1 if the file content is equal to the test vector.
      92             :  * @retval -1 if the file content is not equal to the test vector or an error occurred.
      93             :  */
      94           0 : static int isTestFileCorrect (const char * file)
      95             : {
      96           0 :         int returnValue = -1;
      97           0 :         kdb_octet_t readBuffer[2 * sizeof (testContent)] = { 0 };
      98           0 :         size_t readCount = 0;
      99             : 
     100           0 :         FILE * f = fopen (file, "rb");
     101           0 :         succeed_if (f, "can not read from temporary file");
     102           0 :         if (!f) return -1;
     103             : 
     104           0 :         readCount = fread (readBuffer, 1, sizeof (readBuffer), f);
     105           0 :         succeed_if (readCount > 0, "temporary file is empty.");
     106             : 
     107           0 :         if (readCount == sizeof (testContent))
     108             :         {
     109           0 :                 if (memcmp (readBuffer, testContent, sizeof (testContent)) == 0)
     110             :                 {
     111           0 :                         returnValue = 1;
     112             :                 }
     113             :         }
     114             : 
     115           0 :         fclose (f);
     116           0 :         return returnValue;
     117             : }
     118             : 
     119           0 : static void test_init (void)
     120             : {
     121           0 :         Plugin * plugin = NULL;
     122           0 :         Key * parentKey = keyNew ("system", KEY_END);
     123           0 :         KeySet * modules = ksNew (0, KS_END);
     124           0 :         KeySet * configKs = newPluginConfiguration ();
     125           0 :         elektraModulesInit (modules, 0);
     126             : 
     127           0 :         plugin = elektraPluginOpen (PLUGIN_NAME, modules, configKs, 0);
     128           0 :         succeed_if (plugin != 0, "failed to open the plugin");
     129           0 :         if (plugin)
     130             :         {
     131           0 :                 succeed_if (!strcmp (plugin->name, PLUGIN_NAME), "got wrong name");
     132             : 
     133           0 :                 KeySet * config = elektraPluginGetConfig (plugin);
     134           0 :                 succeed_if (config != 0, "there should be a config");
     135             : 
     136           0 :                 succeed_if (plugin->kdbOpen != 0, "no open pointer");
     137           0 :                 succeed_if (plugin->kdbClose != 0, "no close pointer");
     138           0 :                 succeed_if (plugin->kdbGet != 0, "no get pointer");
     139           0 :                 succeed_if (plugin->kdbSet != 0, "no set pointer");
     140             : 
     141           0 :                 elektraPluginClose (plugin, 0);
     142             :         }
     143             : 
     144           0 :         elektraModulesClose (modules, 0);
     145           0 :         ksDel (modules);
     146           0 :         keyDel (parentKey);
     147           0 : }
     148             : 
     149           0 : static void test_gpg (void)
     150             : {
     151             :         // Plugin configuration
     152           0 :         KeySet * conf = newPluginConfiguration ();
     153           0 :         Key * errorKey = keyNew (0);
     154             : 
     155             :         // install the gpg key
     156           0 :         char * argv[] = { "", "-a", "--import", NULL };
     157           0 :         const size_t argc = 4;
     158           0 :         Key * msg = keyNew (0);
     159           0 :         keySetBinary (msg, test_key_asc, test_key_asc_len);
     160             : 
     161           0 :         succeed_if (ELEKTRA_PLUGIN_FUNCTION (gpgCall) (conf, errorKey, msg, argv, argc) == 1, "failed to install the GPG test key");
     162             : 
     163           0 :         keyDel (msg);
     164           0 :         keyDel (errorKey);
     165           0 :         ksDel (conf);
     166           0 : }
     167             : 
     168           0 : static void test_file_crypto_operations (void)
     169             : {
     170           0 :         Plugin * plugin = NULL;
     171           0 :         Key * parentKey = keyNew ("system", KEY_END);
     172           0 :         KeySet * modules = ksNew (0, KS_END);
     173           0 :         KeySet * config = newPluginConfiguration ();
     174             : 
     175           0 :         elektraModulesInit (modules, 0);
     176           0 :         plugin = elektraPluginOpen (PLUGIN_NAME, modules, config, 0);
     177           0 :         succeed_if (plugin, "failed to open plugin handle");
     178           0 :         if (plugin)
     179             :         {
     180           0 :                 KeySet * data = ksNew (0, KS_END);
     181           0 :                 const char * tmpFile = elektraFilename ();
     182           0 :                 if (tmpFile)
     183             :                 {
     184             :                         // prepare test file to be encrypted
     185           0 :                         writeTestFile (tmpFile);
     186           0 :                         keySetString (parentKey, tmpFile);
     187             : 
     188             :                         // try to encrypt the file
     189           0 :                         succeed_if (plugin->kdbSet (plugin, data, parentKey) == 1, "kdb set failed");
     190           0 :                         succeed_if (isTestFileCorrect (tmpFile) == -1, "file content did not change during encryption");
     191             : 
     192             :                         // try to decrypt the file again (simulating the pregetstorage call)
     193           0 :                         succeed_if (plugin->kdbGet (plugin, data, parentKey) == 1, "kdb get (pregetstorage) failed");
     194           0 :                         succeed_if (isTestFileCorrect (keyString (parentKey)) == 1, "file content could not be restored during decryption");
     195             : 
     196             :                         // a second call to kdb get (the postgetstorage call) should re-encrypt the file again
     197           0 :                         succeed_if (plugin->kdbGet (plugin, data, parentKey) == 1, "kdb get (postgetstorage) failed");
     198           0 :                         succeed_if (isTestFileCorrect (tmpFile) == -1, "postgetstorage did not encrypt the file again");
     199             : 
     200           0 :                         remove (tmpFile);
     201             :                 }
     202             : 
     203           0 :                 ksDel (data);
     204           0 :                 elektraPluginClose (plugin, 0);
     205             :         }
     206             : 
     207           0 :         elektraModulesClose (modules, 0);
     208           0 :         ksDel (modules);
     209           0 :         keyDel (parentKey);
     210           0 : }
     211             : 
     212           0 : static void test_file_signature_operations (void)
     213             : {
     214           0 :         Plugin * plugin = NULL;
     215           0 :         Key * parentKey = keyNew ("system", KEY_END);
     216           0 :         KeySet * modules = ksNew (0, KS_END);
     217           0 :         KeySet * config = newPluginConfiguration ();
     218             : 
     219           0 :         elektraModulesInit (modules, 0);
     220           0 :         plugin = elektraPluginOpen (PLUGIN_NAME, modules, config, 0);
     221           0 :         succeed_if (plugin, "failed to open plugin handle");
     222           0 :         if (plugin)
     223             :         {
     224           0 :                 KeySet * data = ksNew (0, KS_END);
     225           0 :                 const char * tmpFile = elektraFilename ();
     226           0 :                 if (tmpFile)
     227             :                 {
     228             :                         // prepare test file to be encrypted
     229           0 :                         writeTestFile (tmpFile);
     230           0 :                         keySetString (parentKey, tmpFile);
     231             : 
     232             :                         // try to encrypt the file
     233           0 :                         succeed_if (plugin->kdbSet (plugin, data, parentKey) == 1, "kdb set failed");
     234           0 :                         succeed_if (isTestFileCorrect (tmpFile) == -1, "file content did not change during encryption");
     235             : 
     236             :                         // try to decrypt/verify the file
     237           0 :                         succeed_if (plugin->kdbGet (plugin, data, parentKey) == 1, "kdb get failed");
     238             : 
     239           0 :                         remove (tmpFile);
     240             :                 }
     241             : 
     242           0 :                 ksDel (data);
     243           0 :                 elektraPluginClose (plugin, 0);
     244             :         }
     245             : 
     246           0 :         elektraModulesClose (modules, 0);
     247           0 :         ksDel (modules);
     248           0 :         keyDel (parentKey);
     249           0 : }
     250             : 
     251           0 : static void test_file_faulty_signature (void)
     252             : {
     253           0 :         Plugin * plugin = NULL;
     254           0 :         Key * parentKey = keyNew ("system", KEY_END);
     255           0 :         KeySet * modules = ksNew (0, KS_END);
     256           0 :         KeySet * config = newPluginConfigurationWithTextmodeEnabled ();
     257             : 
     258           0 :         elektraModulesInit (modules, 0);
     259           0 :         plugin = elektraPluginOpen (PLUGIN_NAME, modules, config, 0);
     260           0 :         succeed_if (plugin, "failed to open plugin handle");
     261           0 :         if (plugin)
     262             :         {
     263           0 :                 KeySet * data = ksNew (0, KS_END);
     264           0 :                 const char * tmpFile = elektraFilename ();
     265           0 :                 if (tmpFile)
     266             :                 {
     267             :                         // prepare test file to be encrypted
     268           0 :                         writeFaultySignatureFile (tmpFile);
     269           0 :                         keySetString (parentKey, tmpFile);
     270             : 
     271             :                         // try to decrypt/verify the file -- should fail
     272           0 :                         succeed_if (plugin->kdbGet (plugin, data, parentKey) == -1, "kdb get succeeded on a faulty signature");
     273             : 
     274           0 :                         remove (tmpFile);
     275             :                 }
     276             : 
     277           0 :                 ksDel (data);
     278           0 :                 elektraPluginClose (plugin, 0);
     279             :         }
     280             : 
     281           0 :         elektraModulesClose (modules, 0);
     282           0 :         ksDel (modules);
     283           0 :         keyDel (parentKey);
     284           0 : }
     285             : 
     286           0 : int main (int argc, char ** argv)
     287             : {
     288           0 :         printf ("FCRYPT       TESTS\n");
     289           0 :         printf ("==================\n\n");
     290             : 
     291           0 :         init (argc, argv);
     292             : 
     293           0 :         if (!gpg_available (newPluginConfiguration ()))
     294             :         {
     295           0 :                 printf ("The test was disabled because gpg could not be found on the system.\n");
     296           0 :                 return nbError;
     297             :         }
     298             : 
     299           0 :         test_gpg ();
     300           0 :         test_init ();
     301           0 :         test_file_crypto_operations ();
     302           0 :         test_file_signature_operations ();
     303           0 :         test_file_faulty_signature ();
     304           0 :         test_teardown ();
     305             : 
     306           0 :         print_result (ELEKTRA_PLUGIN_NAME);
     307           0 :         return nbError;
     308             : }

Generated by: LCOV version 1.13