LCOV - code coverage report
Current view: top level - kbx - keybox-openpgp.c (source / functions) Hit Total Coverage
Test: coverage.info Lines: 143 238 60.1 %
Date: 2016-09-12 12:29:17 Functions: 4 4 100.0 %

          Line data    Source code
       1             : /* keybox-openpgp.c - OpenPGP key parsing
       2             :  * Copyright (C) 2001, 2003, 2011 Free Software Foundation, Inc.
       3             :  *
       4             :  * This file is part of GnuPG.
       5             :  *
       6             :  * GnuPG is free software; you can redistribute it and/or modify
       7             :  * it under the terms of the GNU General Public License as published by
       8             :  * the Free Software Foundation; either version 3 of the License, or
       9             :  * (at your option) any later version.
      10             :  *
      11             :  * GnuPG is distributed in the hope that it will be useful,
      12             :  * but WITHOUT ANY WARRANTY; without even the implied warranty of
      13             :  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      14             :  * GNU General Public License for more details.
      15             :  *
      16             :  * You should have received a copy of the GNU General Public License
      17             :  * along with this program; if not, see <http://www.gnu.org/licenses/>.
      18             :  */
      19             : 
      20             : /* This is a simple OpenPGP parser suitable for all OpenPGP key
      21             :    material.  It just provides the functionality required to build and
      22             :    parse an KBX OpenPGP key blob.  Thus it is not a complete parser.
      23             :    However it is self-contained and optimized for fast in-memory
      24             :    parsing.  Note that we don't support old ElGamal v3 keys
      25             :    anymore. */
      26             : 
      27             : #include <config.h>
      28             : #include <stdlib.h>
      29             : #include <stdio.h>
      30             : #include <string.h>
      31             : #include <errno.h>
      32             : #include <assert.h>
      33             : 
      34             : #include "keybox-defs.h"
      35             : 
      36             : #include <gcrypt.h>
      37             : 
      38             : #include "../common/openpgpdefs.h"
      39             : #include "host2net.h"
      40             : 
      41             : /* Assume a valid OpenPGP packet at the address pointed to by BUFBTR
      42             :    which has a maximum length as stored at BUFLEN.  Return the header
      43             :    information of that packet and advance the pointer stored at BUFPTR
      44             :    to the next packet; also adjust the length stored at BUFLEN to
      45             :    match the remaining bytes. If there are no more packets, store NULL
      46             :    at BUFPTR.  Return an non-zero error code on failure or the
      47             :    following data on success:
      48             : 
      49             :    R_DATAPKT = Pointer to the begin of the packet data.
      50             :    R_DATALEN = Length of this data.  This has already been checked to fit
      51             :                into the buffer.
      52             :    R_PKTTYPE = The packet type.
      53             :    R_NTOTAL  = The total number of bytes of this packet
      54             : 
      55             :    Note that these values are only updated on success.
      56             : */
      57             : static gpg_error_t
      58         486 : next_packet (unsigned char const **bufptr, size_t *buflen,
      59             :              unsigned char const **r_data, size_t *r_datalen, int *r_pkttype,
      60             :              size_t *r_ntotal)
      61             : {
      62         486 :   const unsigned char *buf = *bufptr;
      63         486 :   size_t len = *buflen;
      64             :   int c, ctb, pkttype;
      65             :   unsigned long pktlen;
      66             : 
      67         486 :   if (!len)
      68           0 :     return gpg_error (GPG_ERR_NO_DATA);
      69             : 
      70         486 :   ctb = *buf++; len--;
      71         486 :   if ( !(ctb & 0x80) )
      72           0 :     return gpg_error (GPG_ERR_INV_PACKET); /* Invalid CTB. */
      73             : 
      74         486 :   if ((ctb & 0x40))  /* New style (OpenPGP) CTB.  */
      75             :     {
      76           0 :       pkttype = (ctb & 0x3f);
      77           0 :       if (!len)
      78           0 :         return gpg_error (GPG_ERR_INV_PACKET); /* No 1st length byte. */
      79           0 :       c = *buf++; len--;
      80           0 :       if (pkttype == PKT_COMPRESSED)
      81           0 :         return gpg_error (GPG_ERR_UNEXPECTED); /* ... packet in a keyblock. */
      82           0 :       if ( c < 192 )
      83           0 :         pktlen = c;
      84           0 :       else if ( c < 224 )
      85             :         {
      86           0 :           pktlen = (c - 192) * 256;
      87           0 :           if (!len)
      88           0 :             return gpg_error (GPG_ERR_INV_PACKET); /* No 2nd length byte. */
      89           0 :           c = *buf++; len--;
      90           0 :           pktlen += c + 192;
      91             :         }
      92           0 :       else if (c == 255)
      93             :         {
      94           0 :           if (len <4 )
      95           0 :             return gpg_error (GPG_ERR_INV_PACKET); /* No length bytes. */
      96           0 :           pktlen = buf32_to_ulong (buf);
      97           0 :           buf += 4;
      98           0 :           len -= 4;
      99             :       }
     100             :       else /* Partial length encoding is not allowed for key packets. */
     101           0 :         return gpg_error (GPG_ERR_UNEXPECTED);
     102             :     }
     103             :   else /* Old style CTB.  */
     104             :     {
     105             :       int lenbytes;
     106             : 
     107         486 :       pktlen = 0;
     108         486 :       pkttype = (ctb>>2)&0xf;
     109         486 :       lenbytes = ((ctb&3)==3)? 0 : (1<<(ctb & 3));
     110         486 :       if (!lenbytes) /* Not allowed in key packets.  */
     111           0 :         return gpg_error (GPG_ERR_UNEXPECTED);
     112         486 :       if (len < lenbytes)
     113           0 :         return gpg_error (GPG_ERR_INV_PACKET); /* Not enough length bytes.  */
     114        1121 :       for (; lenbytes; lenbytes--)
     115             :         {
     116         635 :           pktlen <<= 8;
     117         635 :           pktlen |= *buf++; len--;
     118             :         }
     119             :     }
     120             : 
     121             :   /* Do some basic sanity check.  */
     122         486 :   switch (pkttype)
     123             :     {
     124             :     case PKT_SIGNATURE:
     125             :     case PKT_SECRET_KEY:
     126             :     case PKT_PUBLIC_KEY:
     127             :     case PKT_SECRET_SUBKEY:
     128             :     case PKT_MARKER:
     129             :     case PKT_RING_TRUST:
     130             :     case PKT_USER_ID:
     131             :     case PKT_PUBLIC_SUBKEY:
     132             :     case PKT_OLD_COMMENT:
     133             :     case PKT_ATTRIBUTE:
     134             :     case PKT_COMMENT:
     135             :     case PKT_GPG_CONTROL:
     136         486 :       break; /* Okay these are allowed packets. */
     137             :     default:
     138           0 :       return gpg_error (GPG_ERR_UNEXPECTED);
     139             :     }
     140             : 
     141         486 :   if (pkttype == 63 && pktlen == 0xFFFFFFFF)
     142             :     /* Sometimes the decompressing layer enters an error state in
     143             :        which it simply outputs 0xff for every byte read.  If we have a
     144             :        stream of 0xff bytes, then it will be detected as a new format
     145             :        packet with type 63 and a 4-byte encoded length that is 4G-1.
     146             :        Since packets with type 63 are private and we use them as a
     147             :        control packet, which won't be 4 GB, we reject such packets as
     148             :        invalid.  */
     149           0 :     return gpg_error (GPG_ERR_INV_PACKET);
     150             : 
     151         486 :   if (pktlen > len)
     152           0 :     return gpg_error (GPG_ERR_INV_PACKET); /* Packet length header too long. */
     153             : 
     154         486 :   *r_data = buf;
     155         486 :   *r_datalen = pktlen;
     156         486 :   *r_pkttype = pkttype;
     157         486 :   *r_ntotal = (buf - *bufptr) + pktlen;
     158             : 
     159         486 :   *bufptr = buf + pktlen;
     160         486 :   *buflen = len - pktlen;
     161         486 :   if (!*buflen)
     162          66 :     *bufptr = NULL;
     163             : 
     164         486 :   return 0;
     165             : }
     166             : 
     167             : 
     168             : /* Parse a key packet and store the information in KI. */
     169             : static gpg_error_t
     170         124 : parse_key (const unsigned char *data, size_t datalen,
     171             :            struct _keybox_openpgp_key_info *ki)
     172             : {
     173             :   gpg_error_t err;
     174         124 :   const unsigned char *data_start = data;
     175             :   int i, version, algorithm;
     176             :   size_t n;
     177             :   int npkey;
     178             :   unsigned char hashbuffer[768];
     179         124 :   const unsigned char *mpi_n = NULL;
     180         124 :   size_t mpi_n_len = 0, mpi_e_len = 0;
     181             :   gcry_md_hd_t md;
     182         124 :   int is_ecc = 0;
     183             : 
     184         124 :   if (datalen < 5)
     185           0 :     return gpg_error (GPG_ERR_INV_PACKET);
     186         124 :   version = *data++; datalen--;
     187         124 :   if (version < 2 || version > 4 )
     188           0 :     return gpg_error (GPG_ERR_INV_PACKET); /* Invalid version. */
     189             : 
     190             :   /*timestamp = ((data[0]<<24)|(data[1]<<16)|(data[2]<<8)|(data[3]));*/
     191         124 :   data +=4; datalen -=4;
     192             : 
     193         124 :   if (version < 4)
     194             :     {
     195           0 :       if (datalen < 2)
     196           0 :         return gpg_error (GPG_ERR_INV_PACKET);
     197           0 :       data +=2; datalen -= 2;
     198             :     }
     199             : 
     200         124 :   if (!datalen)
     201           0 :     return gpg_error (GPG_ERR_INV_PACKET);
     202         124 :   algorithm = *data++; datalen--;
     203             : 
     204         124 :   switch (algorithm)
     205             :     {
     206             :     case PUBKEY_ALGO_RSA:
     207             :     case PUBKEY_ALGO_RSA_E:
     208             :     case PUBKEY_ALGO_RSA_S:
     209          32 :       npkey = 2;
     210          32 :       break;
     211             :     case PUBKEY_ALGO_ELGAMAL_E:
     212             :     case PUBKEY_ALGO_ELGAMAL:
     213          40 :       npkey = 3;
     214          40 :       break;
     215             :     case PUBKEY_ALGO_DSA:
     216          40 :       npkey = 4;
     217          40 :       break;
     218             :     case PUBKEY_ALGO_ECDH:
     219           5 :       npkey = 3;
     220           5 :       is_ecc = 1;
     221           5 :       break;
     222             :     case PUBKEY_ALGO_ECDSA:
     223             :     case PUBKEY_ALGO_EDDSA:
     224           7 :       npkey = 2;
     225           7 :       is_ecc = 1;
     226           7 :       break;
     227             :     default: /* Unknown algorithm. */
     228           0 :       return gpg_error (GPG_ERR_UNKNOWN_ALGORITHM);
     229             :     }
     230             : 
     231         124 :   ki->algo = algorithm;
     232             : 
     233         497 :   for (i=0; i < npkey; i++ )
     234             :     {
     235             :       unsigned int nbits, nbytes;
     236             : 
     237         373 :       if (datalen < 2)
     238           0 :         return gpg_error (GPG_ERR_INV_PACKET);
     239             : 
     240         373 :       if (is_ecc && (i == 0 || i == 2))
     241             :         {
     242          17 :           nbytes = data[0];
     243          17 :           if (nbytes < 2 || nbytes > 254)
     244           0 :             return gpg_error (GPG_ERR_INV_PACKET);
     245          17 :           nbytes++; /* The size byte itself.  */
     246          34 :           if (datalen < nbytes)
     247           0 :             return gpg_error (GPG_ERR_INV_PACKET);
     248             :         }
     249             :       else
     250             :         {
     251         356 :           nbits = ((data[0]<<8)|(data[1]));
     252         356 :           data += 2;
     253         356 :           datalen -= 2;
     254         356 :           nbytes = (nbits+7) / 8;
     255         356 :           if (datalen < nbytes)
     256           0 :             return gpg_error (GPG_ERR_INV_PACKET);
     257             :           /* For use by v3 fingerprint calculation we need to know the RSA
     258             :              modulus and exponent. */
     259         356 :           if (i==0)
     260             :             {
     261         112 :               mpi_n = data;
     262         112 :               mpi_n_len = nbytes;
     263             :             }
     264         244 :           else if (i==1)
     265         124 :             mpi_e_len = nbytes;
     266             :         }
     267             : 
     268         373 :       data += nbytes; datalen -= nbytes;
     269             :     }
     270         124 :   n = data - data_start;
     271             : 
     272         124 :   if (version < 4)
     273             :     {
     274             :       /* We do not support any other algorithm than RSA in v3
     275             :          packets. */
     276           0 :       if (algorithm < 1 || algorithm > 3)
     277           0 :         return gpg_error (GPG_ERR_UNSUPPORTED_ALGORITHM);
     278             : 
     279           0 :       err = gcry_md_open (&md, GCRY_MD_MD5, 0);
     280           0 :       if (err)
     281           0 :         return err; /* Oops */
     282           0 :       gcry_md_write (md, mpi_n, mpi_n_len);
     283           0 :       gcry_md_write (md, mpi_n+mpi_n_len+2, mpi_e_len);
     284           0 :       memcpy (ki->fpr, gcry_md_read (md, 0), 16);
     285           0 :       gcry_md_close (md);
     286           0 :       ki->fprlen = 16;
     287             : 
     288           0 :       if (mpi_n_len < 8)
     289             :         {
     290             :           /* Moduli less than 64 bit are out of the specs scope.  Zero
     291             :              them out because this is what gpg does too. */
     292           0 :           memset (ki->keyid, 0, 8);
     293             :         }
     294             :       else
     295           0 :         memcpy (ki->keyid, mpi_n + mpi_n_len - 8, 8);
     296             :     }
     297             :   else
     298             :     {
     299             :       /* Its a pitty that we need to prefix the buffer with the tag
     300             :          and a length header: We can't simply pass it to the fast
     301             :          hashing function for that reason.  It might be a good idea to
     302             :          have a scatter-gather enabled hash function. What we do here
     303             :          is to use a static buffer if this one is large enough and
     304             :          only use the regular hash functions if this buffer is not
     305             :          large enough. */
     306         124 :       if ( 3 + n < sizeof hashbuffer )
     307             :         {
     308         124 :           hashbuffer[0] = 0x99;     /* CTB */
     309         124 :           hashbuffer[1] = (n >> 8); /* 2 byte length header. */
     310         124 :           hashbuffer[2] = n;
     311         124 :           memcpy (hashbuffer + 3, data_start, n);
     312         124 :           gcry_md_hash_buffer (GCRY_MD_SHA1, ki->fpr, hashbuffer, 3 + n);
     313             :         }
     314             :       else
     315             :         {
     316           0 :           err = gcry_md_open (&md, GCRY_MD_SHA1, 0);
     317           0 :           if (err)
     318           0 :             return err; /* Oops */
     319           0 :           gcry_md_putc (md, 0x99 );     /* CTB */
     320           0 :           gcry_md_putc (md, (n >> 8) ); /* 2 byte length header. */
     321           0 :           gcry_md_putc (md, n );
     322           0 :           gcry_md_write (md, data_start, n);
     323           0 :           memcpy (ki->fpr, gcry_md_read (md, 0), 20);
     324           0 :           gcry_md_close (md);
     325             :         }
     326         124 :       ki->fprlen = 20;
     327         124 :       memcpy (ki->keyid, ki->fpr+12, 8);
     328             :     }
     329             : 
     330         124 :   return 0;
     331             : }
     332             : 
     333             : 
     334             : 
     335             : /* The caller must pass the address of an INFO structure which will
     336             :    get filled on success with information pertaining to the OpenPGP
     337             :    keyblock IMAGE of length IMAGELEN.  Note that a caller does only
     338             :    need to release this INFO structure if the function returns
     339             :    success.  If NPARSED is not NULL the actual number of bytes parsed
     340             :    will be stored at this address.  */
     341             : gpg_error_t
     342          66 : _keybox_parse_openpgp (const unsigned char *image, size_t imagelen,
     343             :                        size_t *nparsed, keybox_openpgp_info_t info)
     344             : {
     345          66 :   gpg_error_t err = 0;
     346             :   const unsigned char *image_start, *data;
     347             :   size_t n, datalen;
     348             :   int pkttype;
     349          66 :   int first = 1;
     350          66 :   int read_error = 0;
     351          66 :   struct _keybox_openpgp_key_info *k, **ktail = NULL;
     352          66 :   struct _keybox_openpgp_uid_info *u, **utail = NULL;
     353             : 
     354          66 :   memset (info, 0, sizeof *info);
     355          66 :   if (nparsed)
     356          66 :     *nparsed = 0;
     357             : 
     358          66 :   image_start = image;
     359         618 :   while (image)
     360             :     {
     361         486 :       err = next_packet (&image, &imagelen, &data, &datalen, &pkttype, &n);
     362         486 :       if (err)
     363             :         {
     364           0 :           read_error = 1;
     365           0 :           break;
     366             :         }
     367             : 
     368         486 :       if (first)
     369             :         {
     370          66 :           if (pkttype == PKT_PUBLIC_KEY)
     371             :             ;
     372           0 :           else if (pkttype == PKT_SECRET_KEY)
     373           0 :             info->is_secret = 1;
     374             :           else
     375             :             {
     376           0 :               err = gpg_error (GPG_ERR_UNEXPECTED);
     377           0 :               if (nparsed)
     378           0 :                 *nparsed += n;
     379           0 :               break;
     380             :             }
     381          66 :           first = 0;
     382             :         }
     383         420 :       else if (pkttype == PKT_PUBLIC_KEY || pkttype == PKT_SECRET_KEY)
     384             :         break; /* Next keyblock encountered - ready. */
     385             : 
     386         486 :       if (nparsed)
     387         486 :         *nparsed += n;
     388             : 
     389         486 :       if (pkttype == PKT_SIGNATURE)
     390             :         {
     391             :           /* For now we only count the total number of signatures. */
     392         282 :           info->nsigs++;
     393             :         }
     394         204 :       else if (pkttype == PKT_USER_ID)
     395             :         {
     396          80 :           info->nuids++;
     397          80 :           if (info->nuids == 1)
     398             :             {
     399          66 :               info->uids.off = data - image_start;
     400          66 :               info->uids.len = datalen;
     401          66 :               utail = &info->uids.next;
     402             :             }
     403             :           else
     404             :             {
     405          14 :               u = xtrycalloc (1, sizeof *u);
     406          14 :               if (!u)
     407             :                 {
     408           0 :                   err = gpg_error_from_syserror ();
     409           0 :                   break;
     410             :                 }
     411          14 :               u->off = data - image_start;
     412          14 :               u->len = datalen;
     413          14 :               *utail = u;
     414          14 :               utail = &u->next;
     415             :             }
     416             :         }
     417         124 :       else if (pkttype == PKT_PUBLIC_KEY || pkttype == PKT_SECRET_KEY)
     418             :         {
     419          66 :           err = parse_key (data, datalen, &info->primary);
     420         132 :           if (err)
     421           0 :             break;
     422             :         }
     423          58 :       else if( pkttype == PKT_PUBLIC_SUBKEY && datalen && *data == '#' )
     424             :         {
     425             :           /* Early versions of GnuPG used old PGP comment packets;
     426             :            * luckily all those comments are prefixed by a hash
     427             :            * sign - ignore these packets. */
     428             :         }
     429          58 :       else if (pkttype == PKT_PUBLIC_SUBKEY || pkttype == PKT_SECRET_SUBKEY)
     430             :         {
     431          58 :           info->nsubkeys++;
     432          58 :           if (info->nsubkeys == 1)
     433             :             {
     434          52 :               err = parse_key (data, datalen, &info->subkeys);
     435          52 :               if (err)
     436             :                 {
     437           0 :                   info->nsubkeys--;
     438             :                   /* We ignore subkeys with unknown algorithms. */
     439           0 :                   if (gpg_err_code (err) == GPG_ERR_UNKNOWN_ALGORITHM
     440           0 :                       || gpg_err_code (err) == GPG_ERR_UNSUPPORTED_ALGORITHM)
     441           0 :                     err = 0;
     442           0 :                   if (err)
     443           0 :                     break;
     444             :                 }
     445             :               else
     446          52 :                 ktail = &info->subkeys.next;
     447             :             }
     448             :           else
     449             :             {
     450           6 :               k = xtrycalloc (1, sizeof *k);
     451           6 :               if (!k)
     452             :                 {
     453           0 :                   err = gpg_error_from_syserror ();
     454           0 :                   break;
     455             :                 }
     456           6 :               err = parse_key (data, datalen, k);
     457           6 :               if (err)
     458             :                 {
     459           0 :                   xfree (k);
     460           0 :                   info->nsubkeys--;
     461             :                   /* We ignore subkeys with unknown algorithms. */
     462           0 :                   if (gpg_err_code (err) == GPG_ERR_UNKNOWN_ALGORITHM
     463           0 :                       || gpg_err_code (err) == GPG_ERR_UNSUPPORTED_ALGORITHM)
     464           0 :                     err = 0;
     465           0 :                   if (err)
     466           0 :                     break;
     467             :                 }
     468             :               else
     469             :                 {
     470           6 :                   *ktail = k;
     471           6 :                   ktail = &k->next;
     472             :                 }
     473             :             }
     474             :         }
     475             :     }
     476             : 
     477          66 :   if (err)
     478             :     {
     479           0 :       _keybox_destroy_openpgp_info (info);
     480           0 :       if (!read_error)
     481             :         {
     482             :           /* Packet parsing worked, thus we should be able to skip the
     483             :              rest of the keyblock.  */
     484           0 :           while (image)
     485             :             {
     486           0 :               if (next_packet (&image, &imagelen,
     487             :                                &data, &datalen, &pkttype, &n) )
     488           0 :                 break; /* Another error - stop here. */
     489             : 
     490           0 :               if (pkttype == PKT_PUBLIC_KEY || pkttype == PKT_SECRET_KEY)
     491             :                 break; /* Next keyblock encountered - ready. */
     492             : 
     493           0 :               if (nparsed)
     494           0 :                 *nparsed += n;
     495             :             }
     496             :         }
     497             :     }
     498             : 
     499          66 :   return err;
     500             : }
     501             : 
     502             : 
     503             : /* Release any malloced data in INFO but not INFO itself! */
     504             : void
     505          66 : _keybox_destroy_openpgp_info (keybox_openpgp_info_t info)
     506             : {
     507             :   struct _keybox_openpgp_key_info *k, *k2;
     508             :   struct _keybox_openpgp_uid_info *u, *u2;
     509             : 
     510          66 :   assert (!info->primary.next);
     511          72 :   for (k=info->subkeys.next; k; k = k2)
     512             :     {
     513           6 :       k2 = k->next;
     514           6 :       xfree (k);
     515             :     }
     516             : 
     517          80 :   for (u=info->uids.next; u; u = u2)
     518             :     {
     519          14 :       u2 = u->next;
     520          14 :       xfree (u);
     521             :     }
     522          66 : }

Generated by: LCOV version 1.11