chiark / gitweb /
Replace use of variable-length-arrays.
[gnupg2.git] / g10 / decrypt-data.c
1 /* decrypt-data.c - Decrypt an encrypted data packet
2  * Copyright (C) 1998, 1999, 2000, 2001, 2005,
3  *               2006, 2009 Free Software Foundation, Inc.
4  *
5  * This file is part of GnuPG.
6  *
7  * GnuPG is free software; you can redistribute it and/or modify
8  * it under the terms of the GNU General Public License as published by
9  * the Free Software Foundation; either version 3 of the License, or
10  * (at your option) any later version.
11  *
12  * GnuPG is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program; if not, see <https://www.gnu.org/licenses/>.
19  */
20
21 #include <config.h>
22 #include <stdio.h>
23 #include <stdlib.h>
24 #include <string.h>
25
26 #include "gpg.h"
27 #include "util.h"
28 #include "packet.h"
29 #include "options.h"
30 #include "i18n.h"
31 #include "status.h"
32
33
34 static int mdc_decode_filter ( void *opaque, int control, IOBUF a,
35                                byte *buf, size_t *ret_len);
36 static int decode_filter ( void *opaque, int control, IOBUF a,
37                                         byte *buf, size_t *ret_len);
38
39 typedef struct decode_filter_context_s
40 {
41   gcry_cipher_hd_t cipher_hd;
42   gcry_md_hd_t mdc_hash;
43   char defer[22];
44   int  defer_filled;
45   int  eof_seen;
46   int  refcount;
47   int  partial;   /* Working on a partial length packet.  */
48   size_t length;  /* If !partial: Remaining bytes in the packet.  */
49 } *decode_filter_ctx_t;
50
51
52 /* Helper to release the decode context.  */
53 static void
54 release_dfx_context (decode_filter_ctx_t dfx)
55 {
56   if (!dfx)
57     return;
58
59   log_assert (dfx->refcount);
60   if ( !--dfx->refcount )
61     {
62       gcry_cipher_close (dfx->cipher_hd);
63       dfx->cipher_hd = NULL;
64       gcry_md_close (dfx->mdc_hash);
65       dfx->mdc_hash = NULL;
66       xfree (dfx);
67     }
68 }
69
70
71
72 /****************
73  * Decrypt the data, specified by ED with the key DEK.
74  */
75 int
76 decrypt_data (ctrl_t ctrl, void *procctx, PKT_encrypted *ed, DEK *dek)
77 {
78   decode_filter_ctx_t dfx;
79   byte *p;
80   int rc=0, c, i;
81   byte temp[32];
82   unsigned blocksize;
83   unsigned nprefix;
84
85   dfx = xtrycalloc (1, sizeof *dfx);
86   if (!dfx)
87     return gpg_error_from_syserror ();
88   dfx->refcount = 1;
89
90   if ( opt.verbose && !dek->algo_info_printed )
91     {
92       if (!openpgp_cipher_test_algo (dek->algo))
93         log_info (_("%s encrypted data\n"),
94                   openpgp_cipher_algo_name (dek->algo));
95       else
96         log_info (_("encrypted with unknown algorithm %d\n"), dek->algo );
97       dek->algo_info_printed = 1;
98     }
99
100   {
101     char buf[20];
102
103     snprintf (buf, sizeof buf, "%d %d", ed->mdc_method, dek->algo);
104     write_status_text (STATUS_DECRYPTION_INFO, buf);
105   }
106
107   if (opt.show_session_key)
108     {
109       char numbuf[25];
110       char *hexbuf;
111
112       snprintf (numbuf, sizeof numbuf, "%d:", dek->algo);
113       hexbuf = bin2hex (dek->key, dek->keylen, NULL);
114       if (!hexbuf)
115         {
116           rc = gpg_error_from_syserror ();
117           goto leave;
118         }
119       log_info ("session key: '%s%s'\n", numbuf, hexbuf);
120       write_status_strings (STATUS_SESSION_KEY, numbuf, hexbuf, NULL);
121       xfree (hexbuf);
122     }
123
124   rc = openpgp_cipher_test_algo (dek->algo);
125   if (rc)
126     goto leave;
127   blocksize = openpgp_cipher_get_algo_blklen (dek->algo);
128   if ( !blocksize || blocksize > 16 )
129     log_fatal ("unsupported blocksize %u\n", blocksize );
130   nprefix = blocksize;
131   if ( ed->len && ed->len < (nprefix+2) )
132     {
133        /* An invalid message.  We can't check that during parsing
134           because we may not know the used cipher then.  */
135       rc = gpg_error (GPG_ERR_INV_PACKET);
136       goto leave;
137     }
138
139   if ( ed->mdc_method )
140     {
141       if (gcry_md_open (&dfx->mdc_hash, ed->mdc_method, 0 ))
142         BUG ();
143       if ( DBG_HASHING )
144         gcry_md_debug (dfx->mdc_hash, "checkmdc");
145     }
146
147   rc = openpgp_cipher_open (&dfx->cipher_hd, dek->algo,
148                             GCRY_CIPHER_MODE_CFB,
149                             (GCRY_CIPHER_SECURE
150                              | ((ed->mdc_method || dek->algo >= 100)?
151                                 0 : GCRY_CIPHER_ENABLE_SYNC)));
152   if (rc)
153     {
154       /* We should never get an error here cause we already checked
155        * that the algorithm is available.  */
156       BUG();
157     }
158
159
160   /* log_hexdump( "thekey", dek->key, dek->keylen );*/
161   rc = gcry_cipher_setkey (dfx->cipher_hd, dek->key, dek->keylen);
162   if ( gpg_err_code (rc) == GPG_ERR_WEAK_KEY )
163     {
164       log_info(_("WARNING: message was encrypted with"
165                  " a weak key in the symmetric cipher.\n"));
166       rc=0;
167     }
168   else if( rc )
169     {
170       log_error("key setup failed: %s\n", gpg_strerror (rc) );
171       goto leave;
172     }
173
174   if (!ed->buf)
175     {
176       log_error(_("problem handling encrypted packet\n"));
177       goto leave;
178     }
179
180   gcry_cipher_setiv (dfx->cipher_hd, NULL, 0);
181
182   if ( ed->len )
183     {
184       for (i=0; i < (nprefix+2) && ed->len; i++, ed->len-- )
185         {
186           if ( (c=iobuf_get(ed->buf)) == -1 )
187             break;
188           else
189             temp[i] = c;
190         }
191     }
192   else
193     {
194       for (i=0; i < (nprefix+2); i++ )
195         if ( (c=iobuf_get(ed->buf)) == -1 )
196           break;
197         else
198           temp[i] = c;
199     }
200
201   gcry_cipher_decrypt (dfx->cipher_hd, temp, nprefix+2, NULL, 0);
202   gcry_cipher_sync (dfx->cipher_hd);
203   p = temp;
204   /* log_hexdump( "prefix", temp, nprefix+2 ); */
205   if (dek->symmetric
206       && (p[nprefix-2] != p[nprefix] || p[nprefix-1] != p[nprefix+1]) )
207     {
208       rc = gpg_error (GPG_ERR_BAD_KEY);
209       goto leave;
210     }
211
212   if ( dfx->mdc_hash )
213     gcry_md_write (dfx->mdc_hash, temp, nprefix+2);
214
215   dfx->refcount++;
216   dfx->partial = ed->is_partial;
217   dfx->length = ed->len;
218   if ( ed->mdc_method )
219     iobuf_push_filter ( ed->buf, mdc_decode_filter, dfx );
220   else
221     iobuf_push_filter ( ed->buf, decode_filter, dfx );
222
223   if (opt.unwrap_encryption)
224     {
225       char *filename;
226       estream_t fp;
227       rc = get_output_file ("", 0, ed->buf, &filename, &fp);
228       if (! rc)
229         {
230           iobuf_t output = iobuf_esopen (fp, "w", 0);
231           armor_filter_context_t *afx = NULL;
232
233           if (opt.armor)
234             {
235               afx = new_armor_context ();
236               push_armor_filter (afx, output);
237             }
238
239           iobuf_copy (output, ed->buf);
240           if ((rc = iobuf_error (ed->buf)))
241             log_error (_("error reading '%s': %s\n"),
242                        filename, gpg_strerror (rc));
243           else if ((rc = iobuf_error (output)))
244             log_error (_("error writing '%s': %s\n"),
245                        filename, gpg_strerror (rc));
246
247           iobuf_close (output);
248           if (afx)
249             release_armor_context (afx);
250         }
251     }
252   else
253     proc_packets (ctrl, procctx, ed->buf );
254
255   ed->buf = NULL;
256   if (dfx->eof_seen > 1 )
257     rc = gpg_error (GPG_ERR_INV_PACKET);
258   else if ( ed->mdc_method )
259     {
260       /* We used to let parse-packet.c handle the MDC packet but this
261          turned out to be a problem with compressed packets: With old
262          style packets there is no length information available and
263          the decompressor uses an implicit end.  However we can't know
264          this implicit end beforehand (:-) and thus may feed the
265          decompressor with more bytes than actually needed.  It would
266          be possible to unread the extra bytes but due to our weird
267          iobuf system any unread is non reliable due to filters
268          already popped off.  The easy and sane solution is to care
269          about the MDC packet only here and never pass it to the
270          packet parser.  Fortunatley the OpenPGP spec requires a
271          strict format for the MDC packet so that we know that 22
272          bytes are appended.  */
273       int datalen = gcry_md_get_algo_dlen (ed->mdc_method);
274
275       log_assert (dfx->cipher_hd);
276       log_assert (dfx->mdc_hash);
277       gcry_cipher_decrypt (dfx->cipher_hd, dfx->defer, 22, NULL, 0);
278       gcry_md_write (dfx->mdc_hash, dfx->defer, 2);
279       gcry_md_final (dfx->mdc_hash);
280
281       if (   dfx->defer[0] != '\xd3'
282           || dfx->defer[1] != '\x14'
283           || datalen != 20
284           || memcmp (gcry_md_read (dfx->mdc_hash, 0), dfx->defer+2, datalen))
285         rc = gpg_error (GPG_ERR_BAD_SIGNATURE);
286       /* log_printhex("MDC message:", dfx->defer, 22); */
287       /* log_printhex("MDC calc:", gcry_md_read (dfx->mdc_hash,0), datalen); */
288     }
289
290
291  leave:
292   release_dfx_context (dfx);
293   return rc;
294 }
295
296
297
298 static int
299 mdc_decode_filter (void *opaque, int control, IOBUF a,
300                    byte *buf, size_t *ret_len)
301 {
302   decode_filter_ctx_t dfx = opaque;
303   size_t n, size = *ret_len;
304   int rc = 0;
305   int c;
306
307   /* Note: We need to distinguish between a partial and a fixed length
308      packet.  The first is the usual case as created by GPG.  However
309      for short messages the format degrades to a fixed length packet
310      and other implementations might use fixed length as well.  Only
311      looking for the EOF on fixed data works only if the encrypted
312      packet is not followed by other data.  This used to be a long
313      standing bug which was fixed on 2009-10-02.  */
314
315   if ( control == IOBUFCTRL_UNDERFLOW && dfx->eof_seen )
316     {
317       *ret_len = 0;
318       rc = -1;
319     }
320   else if( control == IOBUFCTRL_UNDERFLOW )
321     {
322       log_assert (a);
323       log_assert (size > 44); /* Our code requires at least this size.  */
324
325       /* Get at least 22 bytes and put it ahead in the buffer.  */
326       if (dfx->partial)
327         {
328           for (n=22; n < 44; n++)
329             {
330               if ( (c = iobuf_get(a)) == -1 )
331                 break;
332               buf[n] = c;
333             }
334         }
335       else
336         {
337           for (n=22; n < 44 && dfx->length; n++, dfx->length--)
338             {
339               c = iobuf_get (a);
340               if (c == -1)
341                 break; /* Premature EOF.  */
342               buf[n] = c;
343             }
344         }
345       if (n == 44)
346         {
347           /* We have enough stuff - flush the deferred stuff.  */
348           if ( !dfx->defer_filled )  /* First time. */
349             {
350               memcpy (buf, buf+22, 22);
351               n = 22;
352             }
353           else
354             {
355               memcpy (buf, dfx->defer, 22);
356             }
357           /* Fill up the buffer. */
358           if (dfx->partial)
359             {
360               for (; n < size; n++ )
361                 {
362                   if ( (c = iobuf_get(a)) == -1 )
363                     {
364                       dfx->eof_seen = 1; /* Normal EOF. */
365                       break;
366                     }
367                   buf[n] = c;
368                 }
369             }
370           else
371             {
372               for (; n < size && dfx->length; n++, dfx->length--)
373                 {
374                   c = iobuf_get(a);
375                   if (c == -1)
376                     {
377                       dfx->eof_seen = 3; /* Premature EOF. */
378                       break;
379                     }
380                   buf[n] = c;
381                 }
382               if (!dfx->length)
383                 dfx->eof_seen = 1; /* Normal EOF.  */
384             }
385
386           /* Move the trailing 22 bytes back to the defer buffer.  We
387              have at least 44 bytes thus a memmove is not needed.  */
388           n -= 22;
389           memcpy (dfx->defer, buf+n, 22 );
390           dfx->defer_filled = 1;
391         }
392       else if ( !dfx->defer_filled )  /* EOF seen but empty defer buffer. */
393         {
394           /* This is bad because it means an incomplete hash. */
395           n -= 22;
396           memcpy (buf, buf+22, n );
397           dfx->eof_seen = 2; /* EOF with incomplete hash.  */
398         }
399       else  /* EOF seen (i.e. read less than 22 bytes). */
400         {
401           memcpy (buf, dfx->defer, 22 );
402           n -= 22;
403           memcpy (dfx->defer, buf+n, 22 );
404           dfx->eof_seen = 1; /* Normal EOF. */
405         }
406
407       if ( n )
408         {
409           if ( dfx->cipher_hd )
410             gcry_cipher_decrypt (dfx->cipher_hd, buf, n, NULL, 0);
411           if ( dfx->mdc_hash )
412             gcry_md_write (dfx->mdc_hash, buf, n);
413         }
414       else
415         {
416           log_assert ( dfx->eof_seen );
417           rc = -1; /* Return EOF.  */
418         }
419       *ret_len = n;
420     }
421   else if ( control == IOBUFCTRL_FREE )
422     {
423       release_dfx_context (dfx);
424     }
425   else if ( control == IOBUFCTRL_DESC )
426     {
427       mem2str (buf, "mdc_decode_filter", *ret_len);
428     }
429   return rc;
430 }
431
432
433 static int
434 decode_filter( void *opaque, int control, IOBUF a, byte *buf, size_t *ret_len)
435 {
436   decode_filter_ctx_t fc = opaque;
437   size_t size = *ret_len;
438   size_t n;
439   int c, rc = 0;
440
441
442   if ( control == IOBUFCTRL_UNDERFLOW && fc->eof_seen )
443     {
444       *ret_len = 0;
445       rc = -1;
446     }
447   else if ( control == IOBUFCTRL_UNDERFLOW )
448     {
449       log_assert (a);
450
451       if (fc->partial)
452         {
453           for (n=0; n < size; n++ )
454             {
455               c = iobuf_get(a);
456               if (c == -1)
457                 {
458                   fc->eof_seen = 1; /* Normal EOF. */
459                   break;
460                 }
461               buf[n] = c;
462             }
463         }
464       else
465         {
466           for (n=0; n < size && fc->length; n++, fc->length--)
467             {
468               c = iobuf_get(a);
469               if (c == -1)
470                 {
471                   fc->eof_seen = 3; /* Premature EOF. */
472                   break;
473                 }
474               buf[n] = c;
475             }
476           if (!fc->length)
477             fc->eof_seen = 1; /* Normal EOF.  */
478         }
479       if (n)
480         {
481           if (fc->cipher_hd)
482             gcry_cipher_decrypt (fc->cipher_hd, buf, n, NULL, 0);
483         }
484       else
485         {
486           if (!fc->eof_seen)
487             fc->eof_seen = 1;
488           rc = -1; /* Return EOF. */
489         }
490       *ret_len = n;
491     }
492   else if ( control == IOBUFCTRL_FREE )
493     {
494       release_dfx_context (fc);
495     }
496   else if ( control == IOBUFCTRL_DESC )
497     {
498       mem2str (buf, "decode_filter", *ret_len);
499     }
500   return rc;
501 }