Release 0.1.4 gpgme-0-1-4
authorWerner Koch <wk@gnupg.org>
Thu, 11 Jan 2001 11:56:34 +0000 (11:56 +0000)
committerWerner Koch <wk@gnupg.org>
Thu, 11 Jan 2001 11:56:34 +0000 (11:56 +0000)
17 files changed:
README
configure.in
gpgme/context.h
gpgme/decrypt.c
gpgme/encrypt.c
gpgme/gpgme.c
gpgme/gpgme.h
gpgme/key.c
gpgme/keylist.c
gpgme/ops.h
gpgme/recipient.c
gpgme/rungpg.h
gpgme/status-table.h
gpgme/trustlist.c
tests/t-encrypt.c
tests/t-keylist.c
tests/t-trustlist.c

diff --git a/README b/README
index 75b10f2..11966b1 100644 (file)
--- a/README
+++ b/README
@@ -5,12 +5,10 @@
 
 If you want to hack on it, start with one of the tests/t-foo programs.
 You need the latest CVS version of GnuPG 1.0, see
-http://www.gnupg.org/cvs-access.html .  If you use passphrases for
-your keys, you should get the gpg-agent which comes with the GnuPG
-unstable version (either CVS HEAD or
-ftp.gnupg.org/pub/gcrypt/alpha/gnupg/gnupg-1.1.2.tar.gz) and install
-the agent from the agent subdirectory or use the new 
-gpgme_set_passphrase_cb() 
+http://www.gnupg.org/cvs-access.html .  
+
+You need at least GnuPG 1.0.4d  (but don't use a 1.1.x version).
+
 
 To build the W32 version, use 
 ./autogen.sh --build-w32
index 369d0f1..839ca82 100644 (file)
@@ -13,9 +13,9 @@ AM_MAINTAINER_MODE
 #    AGE, set REVISION to 0.
 # 3. Interfaces removed (BAD, breaks upward compatibility): Increment
 #    CURRENT, set AGE and REVISION to 0.
-AM_INIT_AUTOMAKE(gpgme,0.1.3a)
-LIBGPGME_LT_CURRENT=1
-LIBGPGME_LT_AGE=1
+AM_INIT_AUTOMAKE(gpgme,0.1.4)
+LIBGPGME_LT_CURRENT=2
+LIBGPGME_LT_AGE=2
 LIBGPGME_LT_REVISION=0
 ##############################################
 
index 32ed8d5..982eb1d 100644 (file)
@@ -105,8 +105,7 @@ struct gpgme_data_s {
 
 struct user_id_s {
     struct user_id_s *next;
-    int validity; /* 0 = undefined, 1 = not, 2 = marginal,
-                     3 = full, 4 = ultimate */
+    GpgmeValidity validity; 
     const char *name_part;    /* all 3 point into strings behind name */
     const char *email_part;   /* or to read-only strings */
     const char *comment_part;
index 465101b..083e5e8 100644 (file)
@@ -34,12 +34,19 @@ struct decrypt_result_s {
     int okay;
     int failed;
     void *last_pw_handle;
+    char *userid_hint;
+    char *passphrase_info;
+    int bad_passphrase;
 };
 
 
 void
 _gpgme_release_decrypt_result ( DecryptResult res )
 {
+    if (!res )
+        return;
+    xfree (res->passphrase_info);
+    xfree (res->userid_hint);
     xfree (res);
 }
 
@@ -73,9 +80,25 @@ decrypt_status_handler ( GpgmeCtx ctx, GpgStatusCode code, char *args )
       case STATUS_EOF:
         break;
 
+      case STATUS_USERID_HINT:
+        xfree (ctx->result.decrypt->userid_hint);
+        if (!(ctx->result.decrypt->userid_hint = xtrystrdup (args)) )
+            ctx->out_of_core = 1;
+        break;
+
+      case STATUS_BAD_PASSPHRASE:
+        ctx->result.decrypt->bad_passphrase++;
+        break;
+
+      case STATUS_GOOD_PASSPHRASE:
+        ctx->result.decrypt->bad_passphrase = 0;
+        break;
+
       case STATUS_NEED_PASSPHRASE:
       case STATUS_NEED_PASSPHRASE_SYM:
-        fprintf (stderr, "need a passphrase ...\n" );
+        xfree (ctx->result.decrypt->passphrase_info);
+        if (!(ctx->result.decrypt->passphrase_info = xtrystrdup (args)) )
+            ctx->out_of_core = 1;
         break;
 
       case STATUS_MISSING_PASSPHRASE:
@@ -94,11 +117,11 @@ decrypt_status_handler ( GpgmeCtx ctx, GpgStatusCode code, char *args )
 
       default:
         /* ignore all other codes */
-        fprintf (stderr, "decrypt_status: code=%d not handled\n", code );
         break;
     }
 }
 
+
 static const char *
 command_handler ( void *opaque, GpgStatusCode code, const char *key )
 {
@@ -115,7 +138,7 @@ command_handler ( void *opaque, GpgStatusCode code, const char *key )
         /* We have been called for cleanup */
         if ( c->passphrase_cb ) { 
             /* Fixme: take the key in account */
-            c->passphrase_cb (c->passphrase_cb_value, 0
+            c->passphrase_cb (c->passphrase_cb_value, NULL
                               &c->result.decrypt->last_pw_handle );
         }
         
@@ -126,9 +149,31 @@ command_handler ( void *opaque, GpgStatusCode code, const char *key )
         return NULL;
     
     if ( code == STATUS_GET_HIDDEN && !strcmp (key, "passphrase.enter") ) {
-        return c->passphrase_cb (c->passphrase_cb_value,
-                                 "Hey, Mr. Hoover wants your passphrase!",
-                                 &c->result.decrypt->last_pw_handle );
+        const char *userid_hint = c->result.decrypt->userid_hint;
+        const char *passphrase_info = c->result.decrypt->passphrase_info;
+        int bad_passphrase = c->result.decrypt->bad_passphrase;
+        char *buf;
+        const char *s;
+
+        c->result.decrypt->bad_passphrase = 0;
+        if (!userid_hint)
+            userid_hint = "[User ID hint missing]";
+        if (!passphrase_info)
+            passphrase_info = "[passphrase info missing]";
+        buf = xtrymalloc ( 20 + strlen (userid_hint)
+                           + strlen (passphrase_info) + 3);
+        if (!buf) {
+            c->out_of_core = 1;
+            return NULL;
+        }
+        sprintf (buf, "%s\n%s\n%s",
+                 bad_passphrase? "TRY_AGAIN":"ENTER",
+                 userid_hint, passphrase_info );
+
+        s = c->passphrase_cb (c->passphrase_cb_value,
+                              buf, &c->result.decrypt->last_pw_handle );
+        xfree (buf);
+        return s;
    }
     
     return NULL;
index 30704d2..91520a8 100644 (file)
@@ -70,6 +70,10 @@ gpgme_op_encrypt_start ( GpgmeCtx c, GpgmeRecipients recp,
         _gpgme_gpg_add_arg ( c->gpg, "--armor" );
     for ( i=0; i < c->verbosity; i++ )
         _gpgme_gpg_add_arg ( c->gpg, "--verbose" );
+    /* If we know that all recipients are valid (full or ultimate trust)
+     * we can pass suppress further checks */
+    if ( _gpgme_recipients_all_valid (recp) )
+        _gpgme_gpg_add_arg ( c->gpg, "--always-trust" );
     
     _gpgme_append_gpg_args_from_recipients ( recp, c->gpg );
 
index 7a2fcbe..10bdd8a 100644 (file)
@@ -69,7 +69,7 @@ gpgme_release ( GpgmeCtx c )
         return;
     _gpgme_gpg_release ( c->gpg ); 
     _gpgme_release_result ( c );
-    _gpgme_key_release ( c->tmp_key );
+    gpgme_key_release ( c->tmp_key );
     gpgme_data_release ( c->help_data_1 );
     gpgme_data_release ( c->notation );
     /* fixme: release the key_queue */
@@ -202,7 +202,7 @@ gpgme_set_keylist_mode ( GpgmeCtx c, int mode )
  * and called whenever gpgme needs a passphrase. DESC will have a nice
  * text, to be used to prompt for the passphrase and R_HD is just a parameter
  * to be used by the callback it self.  Becuase the callback returns a const
- * string, the callback might want to know when it can releae resources
+ * string, the callback might want to know when it can release resources
  * assocated with that returned string; gpgme helps here by calling this
  * passphrase callback with an DESC of %NULL as soon as it does not need
  * the returned string anymore.  The callback function might then choose
index 6cb7567..57e0130 100644 (file)
@@ -42,7 +42,7 @@ extern "C" {
  * let autoconf (using the AM_PATH_GPGME macro) check that this
  * header matches the installed library.
  * Warning: Do not edit the next line.  configure will do that for you! */
-#define GPGME_VERSION "0.1.3a"
+#define GPGME_VERSION "0.1.4"
 
 
 
@@ -127,6 +127,15 @@ typedef enum {
     GPGME_ATTR_TYPE    = 14
 } GpgmeAttr;
 
+typedef enum {
+    GPGME_VALIDITY_UNKNOWN = 0,
+    GPGME_VALIDITY_UNDEFINED = 1,
+    GPGME_VALIDITY_NEVER = 2,
+    GPGME_VALIDITY_MARGINAL = 3,
+    GPGME_VALIDITY_FULL = 4,
+    GPGME_VALIDITY_ULTIMATE = 5
+} GpgmeValidity;
+
 
 typedef const char *(*GpgmePassphraseCb)(void*,
                                          const char *desc, void *r_hd);
@@ -156,6 +165,9 @@ GpgmeError   gpgme_recipients_new (GpgmeRecipients *r_rset);
 void         gpgme_recipients_release ( GpgmeRecipients rset);
 GpgmeError   gpgme_recipients_add_name (GpgmeRecipients rset,
                                         const char *name);
+GpgmeError   gpgme_recipients_add_name_with_validity (GpgmeRecipients rset,
+                                                      const char *name,
+                                                      GpgmeValidity val );
 unsigned int gpgme_recipients_count ( const GpgmeRecipients rset );
 GpgmeError gpgme_recipients_enum_open (const GpgmeRecipients rset,void **ctx);
 const char *gpgme_recipients_enum_read (const GpgmeRecipients rset,void **ctx);
@@ -188,6 +200,7 @@ GpgmeError    gpgme_data_write ( GpgmeData dh,
 
 
 /* Key and trust functions */
+void gpgme_key_release ( GpgmeKey key );
 char *gpgme_key_get_as_xml ( GpgmeKey key );
 const char  *gpgme_key_get_string_attr ( GpgmeKey key, GpgmeAttr what,
                                          const void *reserved, int idx );
index f00f8df..89e545b 100644 (file)
@@ -84,7 +84,7 @@ _gpgme_key_add_subkey (GpgmeKey key)
 
 
 void
-_gpgme_key_release ( GpgmeKey key )
+gpgme_key_release ( GpgmeKey key )
 {
     struct user_id_s *u, *u2;
     struct subkey_s *k, *k2;
@@ -422,7 +422,18 @@ gpgme_key_get_string_attr ( GpgmeKey key, GpgmeAttr what,
         val = u? u->comment_part : NULL;
         break;
       case GPGME_ATTR_VALIDITY:
-        val = "[foxme]";
+        for (u=key->uids; u && idx; u=u->next, idx-- )
+            ;
+        if (u) {
+            switch (u->validity) {
+              case GPGME_VALIDITY_UNKNOWN:   val = "?"; break;
+              case GPGME_VALIDITY_UNDEFINED: val = "q"; break;
+              case GPGME_VALIDITY_NEVER:     val = "n"; break;
+              case GPGME_VALIDITY_MARGINAL:  val = "m"; break;
+              case GPGME_VALIDITY_FULL:      val = "f"; break;
+              case GPGME_VALIDITY_ULTIMATE:  val = "u"; break;
+            }
+        }
         break;
       case GPGME_ATTR_LEVEL:  /* not used here */
       case GPGME_ATTR_TYPE:
@@ -437,6 +448,7 @@ gpgme_key_get_ulong_attr ( GpgmeKey key, GpgmeAttr what,
                            const void *reserved, int idx )
 {
     unsigned long val = 0;
+    struct user_id_s *u;
 
     if (!key)
         return 0;
@@ -455,6 +467,12 @@ gpgme_key_get_ulong_attr ( GpgmeKey key, GpgmeAttr what,
       case GPGME_ATTR_CREATED: 
         val = key->keys.timestamp < 0? 0L:(unsigned long)key->keys.timestamp;
         break;
+      case GPGME_ATTR_VALIDITY:
+        for (u=key->uids; u && idx; u=u->next, idx-- )
+            ;
+        if (u)
+            val = u->validity;
+        break;
       default:
         break;
     }
index b4d4303..a1c356f 100644 (file)
@@ -311,7 +311,7 @@ finish_key ( GpgmeCtx ctx )
     
     q = xtrymalloc ( sizeof *q );
     if ( !q ) {
-        _gpgme_key_release (key);
+        gpgme_key_release (key);
         ctx->out_of_core = 1;
         return;
     }
@@ -348,7 +348,7 @@ gpgme_op_keylist_start ( GpgmeCtx c,  const char *pattern, int secret_only )
         _gpgme_gpg_release ( c->gpg ); 
         c->gpg = NULL;
     }
-    _gpgme_key_release (c->tmp_key);
+    gpgme_key_release (c->tmp_key);
     c->tmp_key = NULL;
     /* Fixme: release key_queue */
     
index 0019b82..43001f2 100644 (file)
@@ -37,6 +37,7 @@ void _gpgme_thaw_fd ( int fd );
 void _gpgme_append_gpg_args_from_recipients (
     const GpgmeRecipients rset,
     GpgObject gpg );
+int _gpgme_recipients_all_valid ( const GpgmeRecipients rset );
 
 
 /*-- data.c --*/
@@ -61,7 +62,6 @@ GpgmeError    _gpgme_data_unread (GpgmeData dh,
 
 /*-- key.c --*/
 GpgmeError _gpgme_key_new( GpgmeKey *r_key );
-void       _gpgme_key_release ( GpgmeKey key );
 
 
 /*-- verify.c --*/
index 02438e4..5a14c0a 100644 (file)
@@ -50,6 +50,16 @@ gpgme_recipients_release ( GpgmeRecipients rset )
 GpgmeError
 gpgme_recipients_add_name (GpgmeRecipients rset, const char *name )
 {
+    return gpgme_recipients_add_name_with_validity (
+        rset, name, GPGME_VALIDITY_UNKNOWN
+        );
+}
+
+GpgmeError
+gpgme_recipients_add_name_with_validity (GpgmeRecipients rset,
+                                         const char *name,
+                                         GpgmeValidity val )
+{
     struct user_id_s *r;
 
     if (!name || !rset )
@@ -57,6 +67,7 @@ gpgme_recipients_add_name (GpgmeRecipients rset, const char *name )
     r = xtrymalloc ( sizeof *r + strlen (name) );
     if (!r)
         return mk_error (Out_Of_Core);
+    r->validity = val;
     r->name_part = "";
     r->email_part = "";
     r->comment_part = "";
@@ -66,6 +77,8 @@ gpgme_recipients_add_name (GpgmeRecipients rset, const char *name )
     return 0;
 }
 
+
+
 unsigned int 
 gpgme_recipients_count ( const GpgmeRecipients rset )
 {
@@ -134,7 +147,19 @@ _gpgme_append_gpg_args_from_recipients (
     }    
 }
 
+int
+_gpgme_recipients_all_valid ( const GpgmeRecipients rset )
+{
+    struct user_id_s *r;
 
+    assert (rset);
+    for (r=rset->list ; r; r = r->next ) {
+        if (r->validity != GPGME_VALIDITY_FULL
+            && r->validity != GPGME_VALIDITY_ULTIMATE )
+            return 0; /*no*/
+    }
+    return 1; /*yes*/
+}
 
 
 
index 0d7be62..27ccf3e 100644 (file)
@@ -47,6 +47,7 @@ typedef enum  {
     STATUS_SHM_GET_BOOL       ,
     STATUS_SHM_GET_HIDDEN     ,
     STATUS_NEED_PASSPHRASE    ,
+    STATUS_USERID_HINT        ,
     STATUS_VALIDSIG           ,
     STATUS_SIG_ID            ,
     STATUS_ENC_TO            ,
index 4922d4e..c55e34c 100644 (file)
@@ -64,6 +64,7 @@ static struct status_table_s status_table[] =
   { "TRUST_NEVER", STATUS_TRUST_NEVER },
   { "TRUST_ULTIMATE", STATUS_TRUST_ULTIMATE },
   { "TRUST_UNDEFINED", STATUS_TRUST_UNDEFINED },
+  { "USERID_HINT", STATUS_USERID_HINT },
   { "VALIDSIG", STATUS_VALIDSIG },
   {NULL, 0}
 };
index a877f4e..156bbb8 100644 (file)
@@ -141,7 +141,7 @@ trustlist_colon_handler ( GpgmeCtx ctx, char *line )
             item->val[0] = *p;
             item->val[1] = 0;
             break;
-          case 10: /* user ID */
+          case 9: /* user ID */
             item->name = xtrystrdup (p);
             if (!item->name)
                 ctx->out_of_core = 1;
index 01c5379..ba7097e 100644 (file)
@@ -69,9 +69,11 @@ main (int argc, char **argv )
 
     err = gpgme_recipients_new (&rset);
     fail_if_err (err);
-    err = gpgme_recipients_add_name (rset, "Bob");
+    err = gpgme_recipients_add_name_with_validity (rset, "Bob",
+                                                   GPGME_VALIDITY_FULL);
     fail_if_err (err);
-    err = gpgme_recipients_add_name (rset, "Alpha");
+    err = gpgme_recipients_add_name_with_validity (rset, "Alpha",
+                                                   GPGME_VALIDITY_FULL);
     fail_if_err (err);
 
 
index d17c8da..978174f 100644 (file)
@@ -69,6 +69,7 @@ doit ( GpgmeCtx ctx, const char *pattern )
             printf ("<!-- comment.%d=%s -->\n", i, s );
         }
         printf ("<!-- End key object (%p) -->\n", key );
+        gpgme_key_release (key);
     }
     if ( err != GPGME_EOF )
         fail_if_err (err);
index ad01486..ce83d62 100644 (file)
@@ -72,7 +72,7 @@ main (int argc, char **argv )
         loop = 1;
         argc--; argv++;
     }
-    pattern = argc? *argv : NULL;
+    pattern = argc? *argv : "alice";
 
     err = gpgme_new (&ctx);
     fail_if_err (err);