LCOV - code coverage report
Current view: top level - src - trustlist.c (source / functions) Hit Total Coverage
Test: coverage.info Lines: 40 112 35.7 %
Date: 2018-11-15 08:49:49 Functions: 5 6 83.3 %

          Line data    Source code
       1             : /* trustlist.c - Trust item listing.
       2             :    Copyright (C) 2000 Werner Koch (dd9jn)
       3             :    Copyright (C) 2001, 2002, 2003, 2004 g10 Code GmbH
       4             : 
       5             :    This file is part of GPGME.
       6             : 
       7             :    GPGME is free software; you can redistribute it and/or modify it
       8             :    under the terms of the GNU Lesser General Public License as
       9             :    published by the Free Software Foundation; either version 2.1 of
      10             :    the License, or (at your option) any later version.
      11             : 
      12             :    GPGME is distributed in the hope that it will be useful, but
      13             :    WITHOUT ANY WARRANTY; without even the implied warranty of
      14             :    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
      15             :    Lesser General Public License for more details.
      16             : 
      17             :    You should have received a copy of the GNU Lesser General Public
      18             :    License along with this program; if not, write to the Free Software
      19             :    Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
      20             :    02111-1307, USA.  */
      21             : 
      22             : #if HAVE_CONFIG_H
      23             : #include <config.h>
      24             : #endif
      25             : #include <stdlib.h>
      26             : #include <string.h>
      27             : #include <assert.h>
      28             : #include <errno.h>
      29             : 
      30             : #include "gpgme.h"
      31             : #include "debug.h"
      32             : #include "util.h"
      33             : #include "context.h"
      34             : #include "ops.h"
      35             : 
      36             : 
      37             : struct trust_queue_item_s
      38             : {
      39             :   struct trust_queue_item_s *next;
      40             :   gpgme_trust_item_t item;
      41             : };
      42             : 
      43             : typedef struct
      44             : {
      45             :   /* Something new is available.  */
      46             :   int trust_cond;
      47             :   struct trust_queue_item_s *trust_queue;
      48             : } *op_data_t;
      49             : 
      50             : 
      51             : 
      52             : static gpgme_error_t
      53          10 : trustlist_status_handler (void *priv, gpgme_status_code_t code, char *args)
      54             : {
      55             :   (void)priv;
      56             :   (void)code;
      57             :   (void)args;
      58          10 :   return 0;
      59             : }
      60             : 
      61             : 
      62             : /* This handler is used to parse the output of --list-trust-path:
      63             :    Format:
      64             :    level:keyid:type:recno:ot:val:mc:cc:name:
      65             :    With TYPE = U for a user ID
      66             :                K for a key
      67             :    The RECNO is either the one of the dir record or the one of the uid
      68             :    record.  OT is the the usual trust letter and only available on K
      69             :    lines.  VAL is the calculated validity MC is the marginal trust
      70             :    counter and only available on U lines CC is the same for the
      71             :    complete count NAME ist the username and only printed on U
      72             :    lines.  */
      73             : static gpgme_error_t
      74           5 : trustlist_colon_handler (void *priv, char *line)
      75             : {
      76           5 :   gpgme_ctx_t ctx = (gpgme_ctx_t) priv;
      77             :   gpgme_error_t err;
      78             :   char *p, *pend;
      79           5 :   int field = 0;
      80           5 :   gpgme_trust_item_t item = NULL;
      81             : 
      82           5 :   if (!line)
      83           5 :     return 0; /* EOF */
      84             : 
      85           0 :   for (p = line; p; p = pend)
      86             :     {
      87           0 :       field++;
      88           0 :       pend = strchr (p, ':');
      89           0 :       if (pend)
      90           0 :         *pend++ = 0;
      91             : 
      92           0 :       switch (field)
      93             :         {
      94             :         case 1: /* level */
      95           0 :           err = _gpgme_trust_item_new (&item);
      96           0 :           if (err)
      97           0 :             return err;
      98           0 :           item->level = atoi (p);
      99           0 :           break;
     100             :         case 2: /* long keyid */
     101           0 :           if (strlen (p) == DIM(item->keyid) - 1)
     102           0 :             strcpy (item->keyid, p);
     103           0 :           break;
     104             :         case 3: /* type */
     105           0 :           item->type = *p == 'K'? 1 : *p == 'U'? 2 : 0;
     106           0 :           break;
     107             :         case 5: /* owner trust */
     108           0 :           item->_owner_trust[0] = *p;
     109           0 :           break;
     110             :         case 6: /* validity */
     111           0 :           item->_validity[0] = *p;
     112           0 :           break;
     113             :         case 9: /* user ID */
     114           0 :           item->name = strdup (p);
     115           0 :           if (!item->name)
     116             :             {
     117           0 :               int saved_err = gpg_error_from_syserror ();
     118           0 :               gpgme_trust_item_unref (item);
     119           0 :               return saved_err;
     120             :             }
     121           0 :           break;
     122             :         }
     123             :     }
     124             : 
     125           0 :   if (item)
     126           0 :     _gpgme_engine_io_event (ctx->engine, GPGME_EVENT_NEXT_TRUSTITEM, item);
     127           0 :   return 0;
     128             : }
     129             : 
     130             : 
     131             : void
     132           0 : _gpgme_op_trustlist_event_cb (void *data, gpgme_event_io_t type,
     133             :                               void *type_data)
     134             : {
     135           0 :   gpgme_ctx_t ctx = (gpgme_ctx_t) data;
     136             :   gpgme_error_t err;
     137             :   void *hook;
     138             :   op_data_t opd;
     139           0 :   gpgme_trust_item_t item = (gpgme_trust_item_t) type_data;
     140             :   struct trust_queue_item_s *q, *q2;
     141             : 
     142           0 :   assert (type == GPGME_EVENT_NEXT_TRUSTITEM);
     143             : 
     144           0 :   err = _gpgme_op_data_lookup (ctx, OPDATA_TRUSTLIST, &hook, -1, NULL);
     145           0 :   opd = hook;
     146           0 :   if (err)
     147           0 :     return;
     148             : 
     149           0 :   q = malloc (sizeof *q);
     150           0 :   if (!q)
     151             :     {
     152           0 :       gpgme_trust_item_unref (item);
     153             :       /* FIXME: GPGME_Out_Of_Core; */
     154           0 :       return;
     155             :     }
     156           0 :   q->item = item;
     157           0 :   q->next = NULL;
     158             :   /* FIXME: Use a tail pointer */
     159           0 :   q2 = opd->trust_queue;
     160           0 :   if (!q2)
     161           0 :     opd->trust_queue = q;
     162             :   else
     163             :     {
     164           0 :       while (q2->next)
     165           0 :         q2 = q2->next;
     166           0 :       q2->next = q;
     167             :     }
     168             :   /* FIXME: unlock queue */
     169           0 :   opd->trust_cond = 1;
     170             : }
     171             : 
     172             : 
     173             : gpgme_error_t
     174           5 : gpgme_op_trustlist_start (gpgme_ctx_t ctx, const char *pattern, int max_level)
     175             : {
     176           5 :   gpgme_error_t err = 0;
     177             :   void *hook;
     178             :   op_data_t opd;
     179             : 
     180           5 :   TRACE_BEG2 (DEBUG_CTX, "gpgme_op_trustlist_start", ctx,
     181             :               "pattern=%s, max_level=%i", pattern, max_level);
     182             : 
     183           5 :   if (!ctx || !pattern || !*pattern)
     184           0 :     return TRACE_ERR (gpg_error (GPG_ERR_INV_VALUE));
     185             : 
     186           5 :   err = _gpgme_op_reset (ctx, 2);
     187           5 :   if (err)
     188           0 :     return TRACE_ERR (err);
     189             : 
     190           5 :   err = _gpgme_op_data_lookup (ctx, OPDATA_TRUSTLIST, &hook,
     191             :                                sizeof (*opd), NULL);
     192           5 :   opd = hook;
     193           5 :   if (err)
     194           0 :     return TRACE_ERR (err);
     195             : 
     196           5 :   _gpgme_engine_set_status_handler (ctx->engine,
     197             :                                     trustlist_status_handler, ctx);
     198           5 :   err = _gpgme_engine_set_colon_line_handler (ctx->engine,
     199             :                                               trustlist_colon_handler, ctx);
     200           5 :   if (err)
     201           0 :     return TRACE_ERR (err);
     202             : 
     203           5 :   err = _gpgme_engine_op_trustlist (ctx->engine, pattern);
     204           5 :   return TRACE_ERR (err);
     205             : }
     206             : 
     207             : 
     208             : gpgme_error_t
     209           5 : gpgme_op_trustlist_next (gpgme_ctx_t ctx, gpgme_trust_item_t *r_item)
     210             : {
     211             :   gpgme_error_t err;
     212             :   void *hook;
     213             :   op_data_t opd;
     214             :   struct trust_queue_item_s *q;
     215             : 
     216           5 :   TRACE_BEG (DEBUG_CTX, "gpgme_op_trustlist_next", ctx);
     217             : 
     218           5 :   if (!ctx || !r_item)
     219           0 :     return TRACE_ERR (gpg_error (GPG_ERR_INV_VALUE));
     220           5 :   *r_item = NULL;
     221           5 :   if (!ctx)
     222           0 :     return TRACE_ERR (gpg_error (GPG_ERR_INV_VALUE));
     223             : 
     224           5 :   err = _gpgme_op_data_lookup (ctx, OPDATA_TRUSTLIST, &hook, -1, NULL);
     225           5 :   opd = hook;
     226           5 :   if (err)
     227           0 :     return TRACE_ERR (err);
     228           5 :   if (opd == NULL)
     229           0 :     return TRACE_ERR (gpg_error (GPG_ERR_INV_VALUE));
     230             : 
     231           5 :   if (!opd->trust_queue)
     232             :     {
     233           5 :       err = _gpgme_wait_on_condition (ctx, &opd->trust_cond, NULL);
     234           5 :       if (err)
     235           0 :         return TRACE_ERR (err);
     236           5 :       if (!opd->trust_cond)
     237           5 :         return TRACE_ERR (gpg_error (GPG_ERR_EOF));
     238           0 :       opd->trust_cond = 0;
     239           0 :       assert (opd->trust_queue);
     240             :     }
     241           0 :   q = opd->trust_queue;
     242           0 :   opd->trust_queue = q->next;
     243             : 
     244           0 :   *r_item = q->item;
     245           0 :   free (q);
     246           0 :   if ((*r_item)->type == 1)
     247             :     {
     248           0 :       TRACE_SUC5 ("trust_item=%p: %s: owner trust %s with level %i "
     249             :                   "and validity 0x%x", *r_item, (*r_item)->keyid,
     250             :                   (*r_item)->owner_trust, (*r_item)->level,
     251             :                   (*r_item)->validity);
     252             :     }
     253           0 :   else if ((*r_item)->type == 2)
     254             :     {
     255           0 :       TRACE_SUC5 ("trust_item=%p: %s: UID %s with level %i "
     256             :                   "and validity 0x%x", *r_item, (*r_item)->keyid,
     257             :                   (*r_item)->name, (*r_item)->level, (*r_item)->validity);
     258             :     }
     259             :   else
     260             :     {
     261           0 :       TRACE_SUC5 ("trust_item=%p: %s: unknown type %i with level %i "
     262             :                   "and validity 0x%x", *r_item, (*r_item)->keyid,
     263             :                   (*r_item)->type, (*r_item)->level, (*r_item)->validity);
     264             :     }
     265           0 :   return 0;
     266             : }
     267             : 
     268             : 
     269             : /* Terminate a pending trustlist operation within CTX.  */
     270             : gpgme_error_t
     271           4 : gpgme_op_trustlist_end (gpgme_ctx_t ctx)
     272             : {
     273           4 :   TRACE (DEBUG_CTX, "gpgme_op_trustlist_end", ctx);
     274             : 
     275           4 :   if (!ctx)
     276           0 :     return gpg_error (GPG_ERR_INV_VALUE);
     277             : 
     278           4 :   return 0;
     279             : }

Generated by: LCOV version 1.13