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