[gmime] Fixed gpg unit tests to pass again
- From: Jeffrey Stedfast <fejj src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gmime] Fixed gpg unit tests to pass again
- Date: Sat, 10 Dec 2016 06:12:53 +0000 (UTC)
commit 978274d953470700d9e2d55f294f13f65e6c5509
Author: Jeffrey Stedfast <fejj gnome org>
Date: Sat Dec 10 01:11:23 2016 -0500
Fixed gpg unit tests to pass again
ChangeLog | 9 ++++
gmime/gmime-gpg-context.c | 91 +++++++++++++++++++++++++++++++++++++++-----
gmime/gmime-gpg-context.h | 2 +
tests/test-pgp.c | 6 ++-
tests/test-pgpmime.c | 10 +++--
tests/test-smime.c | 4 +-
tests/testsuite.c | 85 ++++++++---------------------------------
tests/testsuite.h | 4 +-
8 files changed, 123 insertions(+), 88 deletions(-)
---
diff --git a/ChangeLog b/ChangeLog
index 586cf82..5342127 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,12 @@
+2016-12-10 Jeffrey Stedfast <fejj gnome org>
+
+ * gmime/gmime-gpg-context.c (gpg_ctx_get_argv): Add back --batch
+ and --yes to fix the unit tests for GnuPG 1.4.x.
+ (gpg_ctx_get_argv): Now also takes a path argument to gpg to use
+ as the first argument instead of hard-coding "gpg".
+ (g_mime_gpg_context_new): Updated to query the GnuPG version in
+ case we need that information (turns out we don't at the moment).
+
2016-12-09 Jeffrey Stedfast <fejj gnome org>
* gmime/gmime-crypto-context.c (g_mime_crypto_context_set_retrieve_session_key):
diff --git a/gmime/gmime-gpg-context.c b/gmime/gmime-gpg-context.c
index 9d54458..6df00e6 100644
--- a/gmime/gmime-gpg-context.c
+++ b/gmime/gmime-gpg-context.c
@@ -615,8 +615,16 @@ gpg_digest_str (GMimeDigestAlgo digest)
}
}
+static const char *
+filename (const char *path)
+{
+ const char *slash = strrchr (path, '/');
+
+ return slash != NULL ? slash + 1 : path;
+}
+
static char **
-gpg_ctx_get_argv (struct _GpgCtx *gpg, int status_fd, int secret_fd, char ***strv)
+gpg_ctx_get_argv (struct _GpgCtx *gpg, const char *path, int status_fd, int secret_fd, char ***strv)
{
const char *digest_str;
char **argv, *buf;
@@ -627,13 +635,21 @@ gpg_ctx_get_argv (struct _GpgCtx *gpg, int status_fd, int secret_fd, char ***str
*strv = g_new (char *, 3);
args = g_ptr_array_new ();
- g_ptr_array_add (args, "gpg");
+ g_ptr_array_add (args, (char *) filename (path));
g_ptr_array_add (args, "--verbose");
g_ptr_array_add (args, "--no-secmem-warning");
g_ptr_array_add (args, "--no-greeting");
g_ptr_array_add (args, "--no-tty");
- g_ptr_array_add (args, "--batch");
+
+ if (!gpg->need_passwd) {
+ /* only use batch mode if we don't intend on using the
+ interactive --command-fd option to send it the
+ user's password */
+ g_ptr_array_add (args, "--batch");
+ g_ptr_array_add (args, "--yes");
+ }
+
g_ptr_array_add (args, "--charset=UTF-8");
(*strv)[v++] = buf = g_strdup_printf ("--status-fd=%d", status_fd);
@@ -757,7 +773,7 @@ gpg_ctx_get_argv (struct _GpgCtx *gpg, int status_fd, int secret_fd, char ***str
}
static int
-gpg_ctx_op_start (struct _GpgCtx *gpg)
+gpg_ctx_op_start (struct _GpgCtx *gpg, const char *path)
{
int i, maxfd, errnosave, fds[10];
char **argv, **strv = NULL;
@@ -776,7 +792,7 @@ gpg_ctx_op_start (struct _GpgCtx *gpg)
goto exception;
}
- argv = gpg_ctx_get_argv (gpg, fds[7], fds[8], &strv);
+ argv = gpg_ctx_get_argv (gpg, path, fds[7], fds[8], &strv);
if (!(gpg->pid = fork ())) {
/* child process */
@@ -1904,7 +1920,7 @@ gpg_sign (GMimeCryptoContext *context, const char *userid, GMimeDigestAlgo diges
gpg_ctx_set_istream (gpg, istream);
gpg_ctx_set_ostream (gpg, ostream);
- if (gpg_ctx_op_start (gpg) == -1) {
+ if (gpg_ctx_op_start (gpg, ctx->path) == -1) {
g_set_error (err, GMIME_ERROR, errno,
_("Failed to execute gpg: %s"),
errno ? g_strerror (errno) : _("Unknown"));
@@ -1966,7 +1982,7 @@ gpg_verify (GMimeCryptoContext *context, GMimeDigestAlgo digest,
gpg_ctx_set_istream (gpg, istream);
gpg_ctx_set_digest (gpg, digest);
- if (gpg_ctx_op_start (gpg) == -1) {
+ if (gpg_ctx_op_start (gpg, ctx->path) == -1) {
g_set_error (err, GMIME_ERROR, errno,
_("Failed to execute gpg: %s"),
errno ? g_strerror (errno) : _("Unknown"));
@@ -2039,7 +2055,7 @@ gpg_encrypt (GMimeCryptoContext *context, gboolean sign, const char *userid,
for (i = 0; i < recipients->len; i++)
gpg_ctx_add_recipient (gpg, recipients->pdata[i]);
- if (gpg_ctx_op_start (gpg) == -1) {
+ if (gpg_ctx_op_start (gpg, ctx->path) == -1) {
g_set_error (err, GMIME_ERROR, errno,
_("Failed to execute gpg: %s"),
errno ? g_strerror (errno) : _("Unknown"));
@@ -2110,7 +2126,7 @@ gpg_decrypt_session (GMimeCryptoContext *context, const char *session_key,
if (session_key)
gpg->override_session_key = TRUE;
- if (gpg_ctx_op_start (gpg) == -1) {
+ if (gpg_ctx_op_start (gpg, ctx->path) == -1) {
g_set_error (err, GMIME_ERROR, errno,
_("Failed to execute gpg: %s"),
errno ? g_strerror (errno) : _("Unknown"));
@@ -2179,7 +2195,7 @@ gpg_import_keys (GMimeCryptoContext *context, GMimeStream *istream, GError **err
gpg_ctx_set_mode (gpg, GPG_CTX_MODE_IMPORT);
gpg_ctx_set_istream (gpg, istream);
- if (gpg_ctx_op_start (gpg) == -1) {
+ if (gpg_ctx_op_start (gpg, ctx->path) == -1) {
g_set_error (err, GMIME_ERROR, errno,
_("Failed to execute gpg: %s"),
errno ? g_strerror (errno) : _("Unknown"));
@@ -2238,7 +2254,7 @@ gpg_export_keys (GMimeCryptoContext *context, GPtrArray *keys, GMimeStream *ostr
gpg_ctx_add_recipient (gpg, keys->pdata[i]);
}
- if (gpg_ctx_op_start (gpg) == -1) {
+ if (gpg_ctx_op_start (gpg, ctx->path) == -1) {
g_set_error (err, GMIME_ERROR, errno,
_("Failed to execute gpg: %s"),
errno ? g_strerror (errno) : _("Unknown"));
@@ -2280,6 +2296,57 @@ gpg_export_keys (GMimeCryptoContext *context, GPtrArray *keys, GMimeStream *ostr
#endif /* ENABLE_CRYPTOGRAPHY */
}
+int
+_g_mime_get_gpg_version (const char *path)
+{
+ const char vheader[] = "gpg (GnuPG) ";
+ int v, n = 0, version = 0;
+ const char *inptr;
+ char buffer[128];
+ char *command;
+ FILE *gpg;
+
+ g_return_val_if_fail (path != NULL, -1);
+
+ command = g_strdup_printf ("%s --version", path);
+ gpg = popen (command, "r");
+ g_free (command);
+
+ if (gpg == NULL)
+ return -1;
+
+ inptr = fgets (buffer, 128, gpg);
+ pclose (gpg);
+
+ if (strncmp (inptr, vheader, sizeof (vheader) - 1) != 0)
+ return -1;
+
+ inptr += sizeof (vheader) - 1;
+ while (*inptr >= '0' && *inptr <= '9' && n < 4) {
+ v = 0;
+
+ while (*inptr >= '0' && *inptr <= '9' && (v < 25 || (v == 25 && *inptr < '6'))) {
+ v = (v * 10) + (*inptr - '0');
+ inptr++;
+ }
+
+ version = (version << 8) + v;
+ n++;
+
+ if (*inptr != '.')
+ break;
+
+ inptr++;
+ }
+
+ if (n == 0)
+ return -1;
+
+ if (n < 4)
+ version = version << ((4 - n) * 8);
+
+ return version;
+}
/**
* g_mime_gpg_context_new:
@@ -2300,6 +2367,8 @@ g_mime_gpg_context_new (GMimePasswordRequestFunc request_passwd, const char *pat
ctx = g_object_newv (GMIME_TYPE_GPG_CONTEXT, 0, NULL);
ctx->path = g_strdup (path ? path : "gpg");
+ ctx->version = _g_mime_get_gpg_version (ctx->path);
+
crypto = (GMimeCryptoContext *) ctx;
crypto->request_passwd = request_passwd;
diff --git a/gmime/gmime-gpg-context.h b/gmime/gmime-gpg-context.h
index 8625d33..1218ffa 100644
--- a/gmime/gmime-gpg-context.h
+++ b/gmime/gmime-gpg-context.h
@@ -45,6 +45,7 @@ typedef struct _GMimeGpgContextClass GMimeGpgContextClass;
* @use_agent: %TRUE if gpg should use the gpg-agent for requesting passphrases
* @path: path to gpg
* @retrieve_session_key: %TRUE if session keys should be retrieved when decrypting
+ * @version: The GnuPG version.
*
* A GnuPG crypto context.
**/
@@ -55,6 +56,7 @@ struct _GMimeGpgContext {
gboolean use_agent;
char *path;
gboolean retrieve_session_key;
+ int version;
};
struct _GMimeGpgContextClass {
diff --git a/tests/test-pgp.c b/tests/test-pgp.c
index 81a4b9d..9740b92 100644
--- a/tests/test-pgp.c
+++ b/tests/test-pgp.c
@@ -34,6 +34,8 @@
#include "testsuite.h"
+#define GPG_PATH "/usr/bin/gpg2"
+
extern int verbose;
#define v(x) if (verbose > 3) x
@@ -288,7 +290,7 @@ int main (int argc, char **argv)
testsuite_init (argc, argv);
- if (testsuite_setup_gpghome () != 0)
+ if (testsuite_setup_gpghome (GPG_PATH) != 0)
return EXIT_FAILURE;
for (i = 1; i < argc; i++) {
@@ -303,7 +305,7 @@ int main (int argc, char **argv)
testsuite_start ("GnuPG crypto context");
- ctx = g_mime_gpg_context_new (request_passwd, NULL);
+ ctx = g_mime_gpg_context_new (request_passwd, GPG_PATH);
g_mime_gpg_context_set_always_trust ((GMimeGpgContext *) ctx, TRUE);
testsuite_check ("GMimeGpgContext::import");
diff --git a/tests/test-pgpmime.c b/tests/test-pgpmime.c
index cfd2d81..695293f 100644
--- a/tests/test-pgpmime.c
+++ b/tests/test-pgpmime.c
@@ -35,6 +35,8 @@
#include "testsuite.h"
+#define GPG_PATH "/usr/bin/gpg"
+
extern int verbose;
#define v(x) if (verbose > 3) x
@@ -450,7 +452,7 @@ int main (int argc, char *argv[])
testsuite_init (argc, argv);
- if (testsuite_setup_gpghome () != 0)
+ if (testsuite_setup_gpghome (GPG_PATH) != 0)
return EXIT_FAILURE;
for (i = 1; i < argc; i++) {
@@ -465,7 +467,7 @@ int main (int argc, char *argv[])
testsuite_start ("PGP/MIME implementation");
- ctx = g_mime_gpg_context_new (request_passwd, NULL);
+ ctx = g_mime_gpg_context_new (request_passwd, GPG_PATH);
g_mime_gpg_context_set_always_trust ((GMimeGpgContext *) ctx, TRUE);
if (g_mime_crypto_context_set_retrieve_session_key (ctx, TRUE, &err) != 0) {
fprintf (stderr, "Failed to set retrieve_session_key on GMimeGpgContext: %s\n",
@@ -507,7 +509,7 @@ int main (int argc, char *argv[])
try {
create_encrypted_message (ctx, FALSE, &cleartext, &stream);
session_key = test_multipart_encrypted (ctx, FALSE, cleartext, stream, NULL);
- if (testsuite_can_safely_override_session_key ())
+ if (testsuite_can_safely_override_session_key (GPG_PATH))
g_free (test_multipart_encrypted (ctx, FALSE, cleartext, stream, session_key));
testsuite_check_passed ();
} catch (ex) {
@@ -528,7 +530,7 @@ int main (int argc, char *argv[])
try {
create_encrypted_message (ctx, TRUE, &cleartext, &stream);
session_key = test_multipart_encrypted (ctx, TRUE, cleartext, stream, NULL);
- if (testsuite_can_safely_override_session_key ())
+ if (testsuite_can_safely_override_session_key (GPG_PATH))
g_free (test_multipart_encrypted (ctx, TRUE, cleartext, stream, session_key));
testsuite_check_passed ();
} catch (ex) {
diff --git a/tests/test-smime.c b/tests/test-smime.c
index fa838e8..6f37d62 100644
--- a/tests/test-smime.c
+++ b/tests/test-smime.c
@@ -36,6 +36,8 @@
#include "testsuite.h"
+#define GPG_PATH "/usr/bin/gpg"
+
extern int verbose;
#define v(x) if (verbose > 3) x
@@ -420,7 +422,7 @@ int main (int argc, char *argv[])
testsuite_init (argc, argv);
- if (testsuite_setup_gpghome () != 0)
+ if (testsuite_setup_gpghome (GPG_PATH) != 0)
return EXIT_FAILURE;
for (i = 1; i < argc; i++) {
diff --git a/tests/testsuite.c b/tests/testsuite.c
index 4e6cdc2..8e1d5b1 100644
--- a/tests/testsuite.c
+++ b/tests/testsuite.c
@@ -350,58 +350,6 @@ g_throw (Exception *ex)
longjmp (env->env, 1);
}
-static const char *
-get_gpg_version (void)
-{
- static gboolean found = FALSE;
- static char version[1024];
- const char vheader[] = "gpg (GnuPG) ";
- char *vstring = NULL;
- size_t vlen = 0;
- FILE *vpipe;
- int ret;
-
- if (found)
- return version;
-
- if ((vpipe = popen ("gpg --version", "r")) == NULL)
- return NULL;
-
- if (getline (&vstring, &vlen, vpipe) == -1) {
- free (vstring);
- pclose (vpipe);
- return NULL;
- }
-
- pclose (vpipe);
-
- if (strncmp (vstring, vheader, sizeof (vheader) - 1)) {
- free (vstring);
- return NULL;
- }
-
- strncpy (version, vstring + sizeof (vheader) - 1, sizeof (version) - 1);
- version[sizeof (version) - 1] = '\0';
- free (vstring);
- found = TRUE;
-
- return version;
-}
-
-static int
-is_gpg_modern (void)
-{
- const char *ver = get_gpg_version ();
-
- if (!ver)
- return 0;
-
- return (ver[0] > '2') ||
- (ver[0] == '2' &&
- ver[1] == '.' &&
- ver[2] >= '1');
-}
-
/* in versions of gpg before 2.1.16, the only mechanism to override
the session key was --override-session-key, which leaks its
argument to the process table.
@@ -410,25 +358,21 @@ is_gpg_modern (void)
gmime uses to be safe.
*/
+#define v2_1_16 ((2 << 24) | (1 << 16) | (16 << 8))
+
+int _g_mime_get_gpg_version (const char *gpg);
+
int
-testsuite_can_safely_override_session_key (void)
+testsuite_can_safely_override_session_key (const char *gpg)
{
- const char *ver = get_gpg_version ();
-
- if (!ver)
- return 0;
-
- return (ver[0] > '2') ||
- ((ver[0] == '2' && ver[1] == '.' ) &&
- ((ver[2] > '1') ||
- ((ver[2] == '1' && ver[3] == '.') &&
- (atoi(ver+4) >= 16))));
+ return _g_mime_get_gpg_version (gpg) >= v2_1_16;
}
int
-testsuite_setup_gpghome (void)
+testsuite_setup_gpghome (const char *gpg)
{
const char directive[] = "pinentry-mode loopback\n";
+ char *command;
/* reset .gnupg config directory */
if (system ("/bin/rm -rf ./tmp") != 0)
@@ -443,10 +387,15 @@ testsuite_setup_gpghome (void)
g_unsetenv ("DISPLAY");
g_unsetenv ("GPG_TTY");
- if (system ("gpg --list-keys > /dev/null 2>&1") != 0)
+ command = g_strdup_printf ("%s --list-keys > /dev/null 2>&1", gpg);
+ if (system (command) != 0) {
+ g_free (command);
return EXIT_FAILURE;
+ }
+
+ g_free (command);
- if (is_gpg_modern ()) {
+ if (_g_mime_get_gpg_version (gpg) >= ((2 << 24) | (1 << 16))) {
FILE *fp;
if ((fp = fopen ("./tmp/.gnupg/gpg.conf", "w")) == NULL)
@@ -467,8 +416,8 @@ testsuite_setup_gpghome (void)
int
testsuite_destroy_gpghome (void)
{
- if (system ("/bin/rm -rf ./tmp") != 0)
- return EXIT_FAILURE;
+ //if (system ("/bin/rm -rf ./tmp") != 0)
+ // return EXIT_FAILURE;
return EXIT_SUCCESS;
}
diff --git a/tests/testsuite.h b/tests/testsuite.h
index 87d3126..c2b0146 100644
--- a/tests/testsuite.h
+++ b/tests/testsuite.h
@@ -46,9 +46,9 @@ void testsuite_check_passed (void);
int testsuite_total_errors (void);
/* GnuPG test suite utility functions */
-int testsuite_setup_gpghome (void);
+int testsuite_setup_gpghome (const char *gpg);
int testsuite_destroy_gpghome (void);
-int testsuite_can_safely_override_session_key (void);
+int testsuite_can_safely_override_session_key (const char *gpg);
/*#if __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 96)
#define G_GNUC_NORETURN __attribute__((noreturn))
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]