Print NO_SECKEY status line in gpgsm.
[gnupg.git] / g10 / armor.c
blob2dde9fe05a0c6bc28cda4a1f331bc65c6b89bc2b
1 /* armor.c - Armor flter
2 * Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006,
3 * 2007 Free Software Foundation, Inc.
5 * This file is part of GnuPG.
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.
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.
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/>.
21 #include <config.h>
22 #include <stdio.h>
23 #include <stdlib.h>
24 #include <string.h>
25 #include <errno.h>
26 #include <assert.h>
27 #include <ctype.h>
29 #include "gpg.h"
30 #include "status.h"
31 #include "iobuf.h"
32 #include "util.h"
33 #include "filter.h"
34 #include "packet.h"
35 #include "options.h"
36 #include "main.h"
37 #include "status.h"
38 #include "i18n.h"
40 #define MAX_LINELEN 20000
42 #define CRCINIT 0xB704CE
43 #define CRCPOLY 0X864CFB
44 #define CRCUPDATE(a,c) do { \
45 a = ((a) << 8) ^ crc_table[((a)&0xff >> 16) ^ (c)]; \
46 a &= 0x00ffffff; \
47 } while(0)
48 static u32 crc_table[256];
49 static byte bintoasc[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
50 "abcdefghijklmnopqrstuvwxyz"
51 "0123456789+/";
52 static byte asctobin[256]; /* runtime initialized */
53 static int is_initialized;
56 typedef enum {
57 fhdrHASArmor = 0,
58 fhdrNOArmor,
59 fhdrINIT,
60 fhdrINITCont,
61 fhdrINITSkip,
62 fhdrCHECKBegin,
63 fhdrWAITHeader,
64 fhdrWAITClearsig,
65 fhdrSKIPHeader,
66 fhdrCLEARSIG,
67 fhdrREADClearsig,
68 fhdrNullClearsig,
69 fhdrEMPTYClearsig,
70 fhdrCHECKClearsig,
71 fhdrCHECKClearsig2,
72 fhdrCHECKDashEscaped,
73 fhdrCHECKDashEscaped2,
74 fhdrCHECKDashEscaped3,
75 fhdrREADClearsigNext,
76 fhdrENDClearsig,
77 fhdrENDClearsigHelp,
78 fhdrTESTSpaces,
79 fhdrCLEARSIGSimple,
80 fhdrCLEARSIGSimpleNext,
81 fhdrTEXT,
82 fhdrTEXTSimple,
83 fhdrERROR,
84 fhdrERRORShow,
85 fhdrEOF
86 } fhdr_state_t;
89 /* if we encounter this armor string with this index, go
90 * into a mode which fakes packets and wait for the next armor */
91 #define BEGIN_SIGNATURE 2
92 #define BEGIN_SIGNED_MSG_IDX 3
93 static char *head_strings[] = {
94 "BEGIN PGP MESSAGE",
95 "BEGIN PGP PUBLIC KEY BLOCK",
96 "BEGIN PGP SIGNATURE",
97 "BEGIN PGP SIGNED MESSAGE",
98 "BEGIN PGP ARMORED FILE", /* gnupg extension */
99 "BEGIN PGP PRIVATE KEY BLOCK",
100 "BEGIN PGP SECRET KEY BLOCK", /* only used by pgp2 */
101 NULL
103 static char *tail_strings[] = {
104 "END PGP MESSAGE",
105 "END PGP PUBLIC KEY BLOCK",
106 "END PGP SIGNATURE",
107 "END dummy",
108 "END PGP ARMORED FILE",
109 "END PGP PRIVATE KEY BLOCK",
110 "END PGP SECRET KEY BLOCK",
111 NULL
115 static int armor_filter ( void *opaque, int control,
116 iobuf_t chain, byte *buf, size_t *ret_len);
121 /* Create a new context for armor filters. */
122 armor_filter_context_t *
123 new_armor_context (void)
125 armor_filter_context_t *afx;
127 afx = xcalloc (1, sizeof *afx);
128 afx->refcount = 1;
130 return afx;
133 /* Release an armor filter context. Passing NULL is explicitly
134 allowed and a no-op. */
135 void
136 release_armor_context (armor_filter_context_t *afx)
138 if (!afx)
139 return;
140 assert (afx->refcount);
141 if ( --afx->refcount )
142 return;
143 xfree (afx);
146 /* Push the armor filter onto the iobuf stream IOBUF. */
148 push_armor_filter (armor_filter_context_t *afx, iobuf_t iobuf)
150 int rc;
152 afx->refcount++;
153 rc = iobuf_push_filter (iobuf, armor_filter, afx);
154 if (rc)
155 afx->refcount--;
156 return rc;
163 static void
164 initialize(void)
166 int i, j;
167 u32 t;
168 byte *s;
170 /* init the crc lookup table */
171 crc_table[0] = 0;
172 for(i=j=0; j < 128; j++ ) {
173 t = crc_table[j];
174 if( t & 0x00800000 ) {
175 t <<= 1;
176 crc_table[i++] = t ^ CRCPOLY;
177 crc_table[i++] = t;
179 else {
180 t <<= 1;
181 crc_table[i++] = t;
182 crc_table[i++] = t ^ CRCPOLY;
185 /* build the helptable for radix64 to bin conversion */
186 for(i=0; i < 256; i++ )
187 asctobin[i] = 255; /* used to detect invalid characters */
188 for(s=bintoasc,i=0; *s; s++,i++ )
189 asctobin[*s] = i;
191 is_initialized=1;
194 /****************
195 * Check whether this is an armored file or not See also
196 * parse-packet.c for details on this code For unknown historic
197 * reasons we use a string here but only the first byte will be used.
198 * Returns: True if it seems to be armored
200 static int
201 is_armored( const byte *buf )
203 int ctb, pkttype;
205 ctb = *buf;
206 if( !(ctb & 0x80) )
207 return 1; /* invalid packet: assume it is armored */
208 pkttype = ctb & 0x40 ? (ctb & 0x3f) : ((ctb>>2)&0xf);
209 switch( pkttype ) {
210 case PKT_MARKER:
211 case PKT_SYMKEY_ENC:
212 case PKT_ONEPASS_SIG:
213 case PKT_PUBLIC_KEY:
214 case PKT_SECRET_KEY:
215 case PKT_PUBKEY_ENC:
216 case PKT_SIGNATURE:
217 case PKT_COMMENT:
218 case PKT_OLD_COMMENT:
219 case PKT_PLAINTEXT:
220 case PKT_COMPRESSED:
221 case PKT_ENCRYPTED:
222 return 0; /* seems to be a regular packet: not armored */
225 return 1;
229 /****************
230 * Try to check whether the iobuf is armored
231 * Returns true if this may be the case; the caller should use the
232 * filter to do further processing.
235 use_armor_filter( IOBUF a )
237 byte buf[1];
238 int n;
240 /* fixme: there might be a problem with iobuf_peek */
241 n = iobuf_peek(a, buf, 1 );
242 if( n == -1 )
243 return 0; /* EOF, doesn't matter whether armored or not */
244 if( !n )
245 return 1; /* can't check it: try armored */
246 return is_armored(buf);
252 static void
253 invalid_armor(void)
255 write_status(STATUS_BADARMOR);
256 g10_exit(1); /* stop here */
260 /****************
261 * check whether the armor header is valid on a signed message.
262 * this is for security reasons: the header lines are not included in the
263 * hash and by using some creative formatting rules, Mallory could fake
264 * any text at the beginning of a document; assuming it is read with
265 * a simple viewer. We only allow the Hash Header.
267 static int
268 parse_hash_header( const char *line )
270 const char *s, *s2;
271 unsigned found = 0;
273 if( strlen(line) < 6 || strlen(line) > 60 )
274 return 0; /* too short or too long */
275 if( memcmp( line, "Hash:", 5 ) )
276 return 0; /* invalid header */
277 s = line+5;
278 for(s=line+5;;s=s2) {
279 for(; *s && (*s==' ' || *s == '\t'); s++ )
281 if( !*s )
282 break;
283 for(s2=s+1; *s2 && *s2!=' ' && *s2 != '\t' && *s2 != ','; s2++ )
285 if( !strncmp( s, "RIPEMD160", s2-s ) )
286 found |= 1;
287 else if( !strncmp( s, "SHA1", s2-s ) )
288 found |= 2;
289 else if( !strncmp( s, "MD5", s2-s ) )
290 found |= 4;
291 else if( !strncmp( s, "SHA224", s2-s ) )
292 found |= 8;
293 else if( !strncmp( s, "SHA256", s2-s ) )
294 found |= 16;
295 else if( !strncmp( s, "SHA384", s2-s ) )
296 found |= 32;
297 else if( !strncmp( s, "SHA512", s2-s ) )
298 found |= 64;
299 else
300 return 0;
301 for(; *s2 && (*s2==' ' || *s2 == '\t'); s2++ )
303 if( *s2 && *s2 != ',' )
304 return 0;
305 if( *s2 )
306 s2++;
308 return found;
311 /* Returns true if this is a valid armor tag as per RFC-2440bis-21. */
312 static int
313 is_armor_tag(const char *line)
315 if(strncmp(line,"Version",7)==0
316 || strncmp(line,"Comment",7)==0
317 || strncmp(line,"MessageID",9)==0
318 || strncmp(line,"Hash",4)==0
319 || strncmp(line,"Charset",7)==0)
320 return 1;
322 return 0;
325 /****************
326 * Check whether this is a armor line.
327 * returns: -1 if it is not a armor header or the index number of the
328 * armor header.
330 static int
331 is_armor_header( byte *line, unsigned len )
333 const char *s;
334 byte *save_p, *p;
335 int save_c;
336 int i;
338 if( len < 15 )
339 return -1; /* too short */
340 if( memcmp( line, "-----", 5 ) )
341 return -1; /* no */
342 p = strstr( line+5, "-----");
343 if( !p )
344 return -1;
345 save_p = p;
346 p += 5;
348 /* Some Windows environments seem to add whitespace to the end of
349 the line, so we strip it here. This becomes strict if
350 --rfc2440 is set since 2440 reads "The header lines, therefore,
351 MUST start at the beginning of a line, and MUST NOT have text
352 following them on the same line." It is unclear whether "text"
353 refers to all text or just non-whitespace text. 4880 clarified
354 this was only non-whitespace text. */
356 if(RFC2440)
358 if( *p == '\r' )
359 p++;
360 if( *p == '\n' )
361 p++;
363 else
364 while(*p==' ' || *p=='\r' || *p=='\n' || *p=='\t')
365 p++;
367 if( *p )
368 return -1; /* garbage after dashes */
369 save_c = *save_p; *save_p = 0;
370 p = line+5;
371 for(i=0; (s=head_strings[i]); i++ )
372 if( !strcmp(s, p) )
373 break;
374 *save_p = save_c;
375 if( !s )
376 return -1; /* unknown armor line */
378 if( opt.verbose > 1 )
379 log_info(_("armor: %s\n"), head_strings[i]);
380 return i;
385 /****************
386 * Parse a header lines
387 * Return 0: Empty line (end of header lines)
388 * -1: invalid header line
389 * >0: Good header line
391 static int
392 parse_header_line( armor_filter_context_t *afx, byte *line, unsigned int len )
394 byte *p;
395 int hashes=0;
396 unsigned int len2;
398 len2 = length_sans_trailing_ws ( line, len );
399 if( !len2 ) {
400 afx->buffer_pos = len2; /* (it is not the fine way to do it here) */
401 return 0; /* WS only: same as empty line */
405 This is fussy. The spec says that a header line is delimited
406 with a colon-space pair. This means that a line such as
407 "Comment: " (with nothing else) is actually legal as an empty
408 string comment. However, email and cut-and-paste being what it
409 is, that trailing space may go away. Therefore, we accept empty
410 headers delimited with only a colon. --rfc2440, as always,
411 makes this strict and enforces the colon-space pair. -dms
414 p = strchr( line, ':');
415 if( !p || (RFC2440 && p[1]!=' ')
416 || (!RFC2440 && p[1]!=' ' && p[1]!='\n' && p[1]!='\r'))
418 log_error(_("invalid armor header: "));
419 print_string( stderr, line, len, 0 );
420 putc('\n', stderr);
421 return -1;
424 /* Chop off the whitespace we detected before */
425 len=len2;
426 line[len2]='\0';
428 if( opt.verbose ) {
429 log_info(_("armor header: "));
430 print_string( stderr, line, len, 0 );
431 putc('\n', stderr);
434 if( afx->in_cleartext )
436 if( (hashes=parse_hash_header( line )) )
437 afx->hashes |= hashes;
438 else if( strlen(line) > 15 && !memcmp( line, "NotDashEscaped:", 15 ) )
439 afx->not_dash_escaped = 1;
440 else
442 log_error(_("invalid clearsig header\n"));
443 return -1;
446 else if(!is_armor_tag(line))
448 /* Section 6.2: "Unknown keys should be reported to the user,
449 but OpenPGP should continue to process the message." Note
450 that in a clearsigned message this applies to the signature
451 part (i.e. "BEGIN PGP SIGNATURE") and not the signed data
452 ("BEGIN PGP SIGNED MESSAGE"). The only key allowed in the
453 signed data section is "Hash". */
455 log_info(_("unknown armor header: "));
456 print_string( stderr, line, len, 0 );
457 putc('\n', stderr);
460 return 1;
465 /* figure out whether the data is armored or not */
466 static int
467 check_input( armor_filter_context_t *afx, IOBUF a )
469 int rc = 0;
470 int i;
471 byte *line;
472 unsigned len;
473 unsigned maxlen;
474 int hdr_line = -1;
476 /* read the first line to see whether this is armored data */
477 maxlen = MAX_LINELEN;
478 len = afx->buffer_len = iobuf_read_line( a, &afx->buffer,
479 &afx->buffer_size, &maxlen );
480 line = afx->buffer;
481 if( !maxlen ) {
482 /* line has been truncated: assume not armored */
483 afx->inp_checked = 1;
484 afx->inp_bypass = 1;
485 return 0;
488 if( !len ) {
489 return -1; /* eof */
492 /* (the line is always a C string but maybe longer) */
493 if( *line == '\n' || ( len && (*line == '\r' && line[1]=='\n') ) )
495 else if( !is_armored( line ) ) {
496 afx->inp_checked = 1;
497 afx->inp_bypass = 1;
498 return 0;
501 /* find the armor header */
502 while(len) {
503 i = is_armor_header( line, len );
504 if( i >= 0 && !(afx->only_keyblocks && i != 1 && i != 5 && i != 6 )) {
505 hdr_line = i;
506 if( hdr_line == BEGIN_SIGNED_MSG_IDX ) {
507 if( afx->in_cleartext ) {
508 log_error(_("nested clear text signatures\n"));
509 rc = gpg_error (GPG_ERR_INV_ARMOR);
511 afx->in_cleartext = 1;
513 break;
515 /* read the next line (skip all truncated lines) */
516 do {
517 maxlen = MAX_LINELEN;
518 afx->buffer_len = iobuf_read_line( a, &afx->buffer,
519 &afx->buffer_size, &maxlen );
520 line = afx->buffer;
521 len = afx->buffer_len;
522 } while( !maxlen );
525 /* Parse the header lines. */
526 while(len) {
527 /* Read the next line (skip all truncated lines). */
528 do {
529 maxlen = MAX_LINELEN;
530 afx->buffer_len = iobuf_read_line( a, &afx->buffer,
531 &afx->buffer_size, &maxlen );
532 line = afx->buffer;
533 len = afx->buffer_len;
534 } while( !maxlen );
536 i = parse_header_line( afx, line, len );
537 if( i <= 0 ) {
538 if (i && RFC2440)
539 rc = G10ERR_INVALID_ARMOR;
540 break;
545 if( rc )
546 invalid_armor();
547 else if( afx->in_cleartext )
548 afx->faked = 1;
549 else {
550 afx->inp_checked = 1;
551 afx->crc = CRCINIT;
552 afx->idx = 0;
553 afx->radbuf[0] = 0;
556 return rc;
559 #define PARTIAL_CHUNK 512
560 #define PARTIAL_POW 9
562 /****************
563 * Fake a literal data packet and wait for the next armor line
564 * fixme: empty line handling and null length clear text signature are
565 * not implemented/checked.
567 static int
568 fake_packet( armor_filter_context_t *afx, IOBUF a,
569 size_t *retn, byte *buf, size_t size )
571 int rc = 0;
572 size_t len = 0;
573 int lastline = 0;
574 unsigned maxlen, n;
575 byte *p;
576 byte tempbuf[PARTIAL_CHUNK];
577 size_t tempbuf_len=0;
579 while( !rc && size-len>=(PARTIAL_CHUNK+1)) {
580 /* copy what we have in the line buffer */
581 if( afx->faked == 1 )
582 afx->faked++; /* skip the first (empty) line */
583 else
585 /* It's full, so write this partial chunk */
586 if(tempbuf_len==PARTIAL_CHUNK)
588 buf[len++]=0xE0+PARTIAL_POW;
589 memcpy(&buf[len],tempbuf,PARTIAL_CHUNK);
590 len+=PARTIAL_CHUNK;
591 tempbuf_len=0;
592 continue;
595 while( tempbuf_len < PARTIAL_CHUNK
596 && afx->buffer_pos < afx->buffer_len )
597 tempbuf[tempbuf_len++] = afx->buffer[afx->buffer_pos++];
598 if( tempbuf_len==PARTIAL_CHUNK )
599 continue;
602 /* read the next line */
603 maxlen = MAX_LINELEN;
604 afx->buffer_pos = 0;
605 afx->buffer_len = iobuf_read_line( a, &afx->buffer,
606 &afx->buffer_size, &maxlen );
607 if( !afx->buffer_len ) {
608 rc = -1; /* eof (should not happen) */
609 continue;
611 if( !maxlen )
612 afx->truncated++;
614 p = afx->buffer;
615 n = afx->buffer_len;
617 /* Armor header or dash-escaped line? */
618 if(p[0]=='-')
620 /* 2440bis-10: When reversing dash-escaping, an
621 implementation MUST strip the string "- " if it occurs
622 at the beginning of a line, and SHOULD warn on "-" and
623 any character other than a space at the beginning of a
624 line. */
626 if(p[1]==' ' && !afx->not_dash_escaped)
628 /* It's a dash-escaped line, so skip over the
629 escape. */
630 afx->buffer_pos = 2;
632 else if(p[1]=='-' && p[2]=='-' && p[3]=='-' && p[4]=='-')
634 /* Five dashes in a row mean it's probably armor
635 header. */
636 int type = is_armor_header( p, n );
637 if( afx->not_dash_escaped && type != BEGIN_SIGNATURE )
638 ; /* this is okay */
639 else
641 if( type != BEGIN_SIGNATURE )
643 log_info(_("unexpected armor: "));
644 print_string( stderr, p, n, 0 );
645 putc('\n', stderr);
648 lastline = 1;
649 rc = -1;
652 else if(!afx->not_dash_escaped)
654 /* Bad dash-escaping. */
655 log_info(_("invalid dash escaped line: "));
656 print_string( stderr, p, n, 0 );
657 putc('\n', stderr);
661 /* Now handle the end-of-line canonicalization */
662 if( !afx->not_dash_escaped )
664 int crlf = n > 1 && p[n-2] == '\r' && p[n-1]=='\n';
666 /* PGP2 does not treat a tab as white space character */
667 afx->buffer_len=
668 trim_trailing_chars( &p[afx->buffer_pos], n-afx->buffer_pos,
669 afx->pgp2mode ? " \r\n" : " \t\r\n");
670 afx->buffer_len+=afx->buffer_pos;
671 /* the buffer is always allocated with enough space to append
672 * the removed [CR], LF and a Nul
673 * The reason for this complicated procedure is to keep at least
674 * the original type of lineending - handling of the removed
675 * trailing spaces seems to be impossible in our method
676 * of faking a packet; either we have to use a temporary file
677 * or calculate the hash here in this module and somehow find
678 * a way to send the hash down the processing line (well, a special
679 * faked packet could do the job).
681 if( crlf )
682 afx->buffer[afx->buffer_len++] = '\r';
683 afx->buffer[afx->buffer_len++] = '\n';
684 afx->buffer[afx->buffer_len] = '\0';
688 if( lastline ) { /* write last (ending) length header */
689 if(tempbuf_len<192)
690 buf[len++]=tempbuf_len;
691 else
693 buf[len++]=((tempbuf_len-192)/256) + 192;
694 buf[len++]=(tempbuf_len-192) % 256;
696 memcpy(&buf[len],tempbuf,tempbuf_len);
697 len+=tempbuf_len;
699 rc = 0;
700 afx->faked = 0;
701 afx->in_cleartext = 0;
702 /* and now read the header lines */
703 afx->buffer_pos = 0;
704 for(;;) {
705 int i;
707 /* read the next line (skip all truncated lines) */
708 do {
709 maxlen = MAX_LINELEN;
710 afx->buffer_len = iobuf_read_line( a, &afx->buffer,
711 &afx->buffer_size, &maxlen );
712 } while( !maxlen );
713 p = afx->buffer;
714 n = afx->buffer_len;
715 if( !n ) {
716 rc = -1;
717 break; /* eof */
719 i = parse_header_line( afx, p , n );
720 if( i <= 0 ) {
721 if( i )
722 invalid_armor();
723 break;
726 afx->inp_checked = 1;
727 afx->crc = CRCINIT;
728 afx->idx = 0;
729 afx->radbuf[0] = 0;
732 *retn = len;
733 return rc;
737 static int
738 invalid_crc(void)
740 if ( opt.ignore_crc_error )
741 return 0;
742 log_inc_errorcount();
743 return gpg_error (GPG_ERR_INV_ARMOR);
747 static int
748 radix64_read( armor_filter_context_t *afx, IOBUF a, size_t *retn,
749 byte *buf, size_t size )
751 byte val;
752 int c=0, c2; /*init c because gcc is not clever enough for the continue*/
753 int checkcrc=0;
754 int rc = 0;
755 size_t n = 0;
756 int idx, i, onlypad=0;
757 u32 crc;
759 crc = afx->crc;
760 idx = afx->idx;
761 val = afx->radbuf[0];
762 for( n=0; n < size; ) {
764 if( afx->buffer_pos < afx->buffer_len )
765 c = afx->buffer[afx->buffer_pos++];
766 else { /* read the next line */
767 unsigned maxlen = MAX_LINELEN;
768 afx->buffer_pos = 0;
769 afx->buffer_len = iobuf_read_line( a, &afx->buffer,
770 &afx->buffer_size, &maxlen );
771 if( !maxlen )
772 afx->truncated++;
773 if( !afx->buffer_len )
774 break; /* eof */
775 continue;
778 again:
779 if( c == '\n' || c == ' ' || c == '\r' || c == '\t' )
780 continue;
781 else if( c == '=' ) { /* pad character: stop */
782 /* some mailers leave quoted-printable encoded characters
783 * so we try to workaround this */
784 if( afx->buffer_pos+2 < afx->buffer_len ) {
785 int cc1, cc2, cc3;
786 cc1 = afx->buffer[afx->buffer_pos];
787 cc2 = afx->buffer[afx->buffer_pos+1];
788 cc3 = afx->buffer[afx->buffer_pos+2];
789 if( isxdigit(cc1) && isxdigit(cc2)
790 && strchr( "=\n\r\t ", cc3 )) {
791 /* well it seems to be the case - adjust */
792 c = isdigit(cc1)? (cc1 - '0'): (ascii_toupper(cc1)-'A'+10);
793 c <<= 4;
794 c |= isdigit(cc2)? (cc2 - '0'): (ascii_toupper(cc2)-'A'+10);
795 afx->buffer_pos += 2;
796 afx->qp_detected = 1;
797 goto again;
800 else if(n==0)
801 onlypad=1;
803 if( idx == 1 )
804 buf[n++] = val;
805 checkcrc++;
806 break;
808 else if( (c = asctobin[(c2=c)]) == 255 ) {
809 log_error(_("invalid radix64 character %02X skipped\n"), c2);
810 continue;
812 switch(idx) {
813 case 0: val = c << 2; break;
814 case 1: val |= (c>>4)&3; buf[n++]=val;val=(c<<4)&0xf0;break;
815 case 2: val |= (c>>2)&15; buf[n++]=val;val=(c<<6)&0xc0;break;
816 case 3: val |= c&0x3f; buf[n++] = val; break;
818 idx = (idx+1) % 4;
821 for(i=0; i < n; i++ )
822 crc = (crc << 8) ^ crc_table[((crc >> 16)&0xff) ^ buf[i]];
823 crc &= 0x00ffffff;
824 afx->crc = crc;
825 afx->idx = idx;
826 afx->radbuf[0] = val;
828 if( checkcrc ) {
829 afx->any_data = 1;
830 afx->inp_checked=0;
831 afx->faked = 0;
832 for(;;) { /* skip lf and pad characters */
833 if( afx->buffer_pos < afx->buffer_len )
834 c = afx->buffer[afx->buffer_pos++];
835 else { /* read the next line */
836 unsigned maxlen = MAX_LINELEN;
837 afx->buffer_pos = 0;
838 afx->buffer_len = iobuf_read_line( a, &afx->buffer,
839 &afx->buffer_size, &maxlen );
840 if( !maxlen )
841 afx->truncated++;
842 if( !afx->buffer_len )
843 break; /* eof */
844 continue;
846 if( c == '\n' || c == ' ' || c == '\r'
847 || c == '\t' || c == '=' )
848 continue;
849 break;
851 if( c == -1 )
852 log_error(_("premature eof (no CRC)\n"));
853 else {
854 u32 mycrc = 0;
855 idx = 0;
856 do {
857 if( (c = asctobin[c]) == 255 )
858 break;
859 switch(idx) {
860 case 0: val = c << 2; break;
861 case 1: val |= (c>>4)&3; mycrc |= val << 16;val=(c<<4)&0xf0;break;
862 case 2: val |= (c>>2)&15; mycrc |= val << 8;val=(c<<6)&0xc0;break;
863 case 3: val |= c&0x3f; mycrc |= val; break;
865 for(;;) {
866 if( afx->buffer_pos < afx->buffer_len )
867 c = afx->buffer[afx->buffer_pos++];
868 else { /* read the next line */
869 unsigned maxlen = MAX_LINELEN;
870 afx->buffer_pos = 0;
871 afx->buffer_len = iobuf_read_line( a, &afx->buffer,
872 &afx->buffer_size,
873 &maxlen );
874 if( !maxlen )
875 afx->truncated++;
876 if( !afx->buffer_len )
877 break; /* eof */
878 continue;
880 break;
882 if( !afx->buffer_len )
883 break; /* eof */
884 } while( ++idx < 4 );
885 if( c == -1 ) {
886 log_info(_("premature eof (in CRC)\n"));
887 rc = invalid_crc();
889 else if( idx == 0 ) {
890 /* No CRC at all is legal ("MAY") */
891 rc=0;
893 else if( idx != 4 ) {
894 log_info(_("malformed CRC\n"));
895 rc = invalid_crc();
897 else if( mycrc != afx->crc ) {
898 log_info (_("CRC error; %06lX - %06lX\n"),
899 (ulong)afx->crc, (ulong)mycrc);
900 rc = invalid_crc();
902 else {
903 rc = 0;
904 /* FIXME: Here we should emit another control packet,
905 * so that we know in mainproc that we are processing
906 * a clearsign message */
907 #if 0
908 for(rc=0;!rc;) {
909 rc = 0 /*check_trailer( &fhdr, c )*/;
910 if( !rc ) {
911 if( (c=iobuf_get(a)) == -1 )
912 rc = 2;
915 if( rc == -1 )
916 rc = 0;
917 else if( rc == 2 ) {
918 log_error(_("premature eof (in trailer)\n"));
919 rc = G10ERR_INVALID_ARMOR;
921 else {
922 log_error(_("error in trailer line\n"));
923 rc = G10ERR_INVALID_ARMOR;
925 #endif
930 if( !n && !onlypad )
931 rc = -1;
933 *retn = n;
934 return rc;
937 /****************
938 * This filter is used to handle the armor stuff
940 static int
941 armor_filter( void *opaque, int control,
942 IOBUF a, byte *buf, size_t *ret_len)
944 size_t size = *ret_len;
945 armor_filter_context_t *afx = opaque;
946 int rc=0, i, c;
947 byte radbuf[3];
948 int idx, idx2;
949 size_t n=0;
950 u32 crc;
951 #if 0
952 static FILE *fp ;
954 if( !fp ) {
955 fp = fopen("armor.out", "w");
956 assert(fp);
958 #endif
960 if( DBG_FILTER )
961 log_debug("armor-filter: control: %d\n", control );
962 if( control == IOBUFCTRL_UNDERFLOW && afx->inp_bypass ) {
963 n = 0;
964 if( afx->buffer_len ) {
965 for(; n < size && afx->buffer_pos < afx->buffer_len; n++ )
966 buf[n++] = afx->buffer[afx->buffer_pos++];
967 if( afx->buffer_pos >= afx->buffer_len )
968 afx->buffer_len = 0;
970 for(; n < size; n++ ) {
971 if( (c=iobuf_get(a)) == -1 )
972 break;
973 buf[n] = c & 0xff;
975 if( !n )
976 rc = -1;
977 *ret_len = n;
979 else if( control == IOBUFCTRL_UNDERFLOW ) {
980 /* We need some space for the faked packet. The minmum
981 * required size is the PARTIAL_CHUNK size plus a byte for the
982 * length itself */
983 if( size < PARTIAL_CHUNK+1 )
984 BUG(); /* supplied buffer too short */
986 if( afx->faked )
987 rc = fake_packet( afx, a, &n, buf, size );
988 else if( !afx->inp_checked ) {
989 rc = check_input( afx, a );
990 if( afx->inp_bypass ) {
991 for(n=0; n < size && afx->buffer_pos < afx->buffer_len; )
992 buf[n++] = afx->buffer[afx->buffer_pos++];
993 if( afx->buffer_pos >= afx->buffer_len )
994 afx->buffer_len = 0;
995 if( !n )
996 rc = -1;
998 else if( afx->faked ) {
999 unsigned int hashes = afx->hashes;
1000 const byte *sesmark;
1001 size_t sesmarklen;
1003 sesmark = get_session_marker( &sesmarklen );
1004 if ( sesmarklen > 20 )
1005 BUG();
1007 /* the buffer is at least 15+n*15 bytes long, so it
1008 * is easy to construct the packets */
1010 hashes &= 1|2|4|8|16|32|64;
1011 if( !hashes ) {
1012 hashes |= 4; /* default to MD 5 */
1013 /* This is non-ideal since PGP 5-8 have the same
1014 end-of-line bugs as PGP 2. However, we only
1015 enable pgp2mode if there is no Hash: header. */
1016 if( opt.pgp2_workarounds )
1017 afx->pgp2mode = 1;
1019 n=0;
1020 /* First a gpg control packet... */
1021 buf[n++] = 0xff; /* new format, type 63, 1 length byte */
1022 n++; /* see below */
1023 memcpy(buf+n, sesmark, sesmarklen ); n+= sesmarklen;
1024 buf[n++] = CTRLPKT_CLEARSIGN_START;
1025 buf[n++] = afx->not_dash_escaped? 0:1; /* sigclass */
1026 if( hashes & 1 )
1027 buf[n++] = DIGEST_ALGO_RMD160;
1028 if( hashes & 2 )
1029 buf[n++] = DIGEST_ALGO_SHA1;
1030 if( hashes & 4 )
1031 buf[n++] = DIGEST_ALGO_MD5;
1032 if( hashes & 8 )
1033 buf[n++] = DIGEST_ALGO_SHA224;
1034 if( hashes & 16 )
1035 buf[n++] = DIGEST_ALGO_SHA256;
1036 if( hashes & 32 )
1037 buf[n++] = DIGEST_ALGO_SHA384;
1038 if( hashes & 64 )
1039 buf[n++] = DIGEST_ALGO_SHA512;
1040 buf[1] = n - 2;
1042 /* ...followed by an invented plaintext packet.
1043 Amusingly enough, this packet is not compliant with
1044 2440 as the initial partial length is less than 512
1045 bytes. Of course, we'll accept it anyway ;) */
1047 buf[n++] = 0xCB; /* new packet format, type 11 */
1048 buf[n++] = 0xE1; /* 2^1 == 2 bytes */
1049 buf[n++] = 't'; /* canonical text mode */
1050 buf[n++] = 0; /* namelength */
1051 buf[n++] = 0xE2; /* 2^2 == 4 more bytes */
1052 memset(buf+n, 0, 4); /* timestamp */
1053 n += 4;
1055 else if( !rc )
1056 rc = radix64_read( afx, a, &n, buf, size );
1058 else
1059 rc = radix64_read( afx, a, &n, buf, size );
1060 #if 0
1061 if( n )
1062 if( fwrite(buf, n, 1, fp ) != 1 )
1063 BUG();
1064 #endif
1065 *ret_len = n;
1067 else if( control == IOBUFCTRL_FLUSH && !afx->cancel ) {
1068 if( !afx->status ) { /* write the header line */
1069 const char *s;
1070 strlist_t comment=opt.comments;
1072 if( afx->what >= DIM(head_strings) )
1073 log_bug("afx->what=%d", afx->what);
1074 iobuf_writestr(a, "-----");
1075 iobuf_writestr(a, head_strings[afx->what] );
1076 iobuf_writestr(a, "-----" );
1077 iobuf_writestr(a,afx->eol);
1078 if( !opt.no_version )
1080 iobuf_writestr(a, "Version: GnuPG v" VERSION " ("
1081 PRINTABLE_OS_NAME ")" );
1082 iobuf_writestr(a,afx->eol);
1085 /* write the comment strings */
1086 for(s=comment->d;comment;comment=comment->next,s=comment->d)
1088 iobuf_writestr(a, "Comment: " );
1089 for( ; *s; s++ )
1091 if( *s == '\n' )
1092 iobuf_writestr(a, "\\n" );
1093 else if( *s == '\r' )
1094 iobuf_writestr(a, "\\r" );
1095 else if( *s == '\v' )
1096 iobuf_writestr(a, "\\v" );
1097 else
1098 iobuf_put(a, *s );
1101 iobuf_writestr(a,afx->eol);
1104 if ( afx->hdrlines ) {
1105 for ( s = afx->hdrlines; *s; s++ ) {
1106 #ifdef HAVE_DOSISH_SYSTEM
1107 if ( *s == '\n' )
1108 iobuf_put( a, '\r');
1109 #endif
1110 iobuf_put(a, *s );
1114 iobuf_writestr(a,afx->eol);
1115 afx->status++;
1116 afx->idx = 0;
1117 afx->idx2 = 0;
1118 afx->crc = CRCINIT;
1121 crc = afx->crc;
1122 idx = afx->idx;
1123 idx2 = afx->idx2;
1124 for(i=0; i < idx; i++ )
1125 radbuf[i] = afx->radbuf[i];
1127 for(i=0; i < size; i++ )
1128 crc = (crc << 8) ^ crc_table[((crc >> 16)&0xff) ^ buf[i]];
1129 crc &= 0x00ffffff;
1131 for( ; size; buf++, size-- ) {
1132 radbuf[idx++] = *buf;
1133 if( idx > 2 ) {
1134 idx = 0;
1135 c = bintoasc[(*radbuf >> 2) & 077];
1136 iobuf_put(a, c);
1137 c = bintoasc[(((*radbuf<<4)&060)|((radbuf[1] >> 4)&017))&077];
1138 iobuf_put(a, c);
1139 c = bintoasc[(((radbuf[1]<<2)&074)|((radbuf[2]>>6)&03))&077];
1140 iobuf_put(a, c);
1141 c = bintoasc[radbuf[2]&077];
1142 iobuf_put(a, c);
1143 if( ++idx2 >= (64/4) )
1144 { /* pgp doesn't like 72 here */
1145 iobuf_writestr(a,afx->eol);
1146 idx2=0;
1150 for(i=0; i < idx; i++ )
1151 afx->radbuf[i] = radbuf[i];
1152 afx->idx = idx;
1153 afx->idx2 = idx2;
1154 afx->crc = crc;
1156 else if( control == IOBUFCTRL_INIT )
1158 if( !is_initialized )
1159 initialize();
1161 /* Figure out what we're using for line endings if the caller
1162 didn't specify. */
1163 if(afx->eol[0]==0)
1165 #ifdef HAVE_DOSISH_SYSTEM
1166 afx->eol[0]='\r';
1167 afx->eol[1]='\n';
1168 #else
1169 afx->eol[0]='\n';
1170 #endif
1173 else if( control == IOBUFCTRL_CANCEL ) {
1174 afx->cancel = 1;
1176 else if( control == IOBUFCTRL_FREE ) {
1177 if( afx->cancel )
1179 else if( afx->status ) { /* pad, write cecksum, and bottom line */
1180 crc = afx->crc;
1181 idx = afx->idx;
1182 idx2 = afx->idx2;
1183 for(i=0; i < idx; i++ )
1184 radbuf[i] = afx->radbuf[i];
1185 if( idx ) {
1186 c = bintoasc[(*radbuf>>2)&077];
1187 iobuf_put(a, c);
1188 if( idx == 1 ) {
1189 c = bintoasc[((*radbuf << 4) & 060) & 077];
1190 iobuf_put(a, c);
1191 iobuf_put(a, '=');
1192 iobuf_put(a, '=');
1194 else { /* 2 */
1195 c = bintoasc[(((*radbuf<<4)&060)|((radbuf[1]>>4)&017))&077];
1196 iobuf_put(a, c);
1197 c = bintoasc[((radbuf[1] << 2) & 074) & 077];
1198 iobuf_put(a, c);
1199 iobuf_put(a, '=');
1201 if( ++idx2 >= (64/4) )
1202 { /* pgp doesn't like 72 here */
1203 iobuf_writestr(a,afx->eol);
1204 idx2=0;
1207 /* may need a linefeed */
1208 if( idx2 )
1209 iobuf_writestr(a,afx->eol);
1210 /* write the CRC */
1211 iobuf_put(a, '=');
1212 radbuf[0] = crc >>16;
1213 radbuf[1] = crc >> 8;
1214 radbuf[2] = crc;
1215 c = bintoasc[(*radbuf >> 2) & 077];
1216 iobuf_put(a, c);
1217 c = bintoasc[(((*radbuf<<4)&060)|((radbuf[1] >> 4)&017))&077];
1218 iobuf_put(a, c);
1219 c = bintoasc[(((radbuf[1]<<2)&074)|((radbuf[2]>>6)&03))&077];
1220 iobuf_put(a, c);
1221 c = bintoasc[radbuf[2]&077];
1222 iobuf_put(a, c);
1223 iobuf_writestr(a,afx->eol);
1224 /* and the the trailer */
1225 if( afx->what >= DIM(tail_strings) )
1226 log_bug("afx->what=%d", afx->what);
1227 iobuf_writestr(a, "-----");
1228 iobuf_writestr(a, tail_strings[afx->what] );
1229 iobuf_writestr(a, "-----" );
1230 iobuf_writestr(a,afx->eol);
1232 else if( !afx->any_data && !afx->inp_bypass ) {
1233 log_error(_("no valid OpenPGP data found.\n"));
1234 afx->no_openpgp_data = 1;
1235 write_status_text( STATUS_NODATA, "1" );
1237 if( afx->truncated )
1238 log_info(_("invalid armor: line longer than %d characters\n"),
1239 MAX_LINELEN );
1240 /* issue an error to enforce dissemination of correct software */
1241 if( afx->qp_detected )
1242 log_error(_("quoted printable character in armor - "
1243 "probably a buggy MTA has been used\n") );
1244 xfree( afx->buffer );
1245 afx->buffer = NULL;
1246 release_armor_context (afx);
1248 else if( control == IOBUFCTRL_DESC )
1249 *(char**)buf = "armor_filter";
1250 return rc;
1254 /****************
1255 * create a radix64 encoded string.
1257 char *
1258 make_radix64_string( const byte *data, size_t len )
1260 char *buffer, *p;
1262 buffer = p = xmalloc( (len+2)/3*4 + 1 );
1263 for( ; len >= 3 ; len -= 3, data += 3 ) {
1264 *p++ = bintoasc[(data[0] >> 2) & 077];
1265 *p++ = bintoasc[(((data[0] <<4)&060)|((data[1] >> 4)&017))&077];
1266 *p++ = bintoasc[(((data[1]<<2)&074)|((data[2]>>6)&03))&077];
1267 *p++ = bintoasc[data[2]&077];
1269 if( len == 2 ) {
1270 *p++ = bintoasc[(data[0] >> 2) & 077];
1271 *p++ = bintoasc[(((data[0] <<4)&060)|((data[1] >> 4)&017))&077];
1272 *p++ = bintoasc[((data[1]<<2)&074)];
1274 else if( len == 1 ) {
1275 *p++ = bintoasc[(data[0] >> 2) & 077];
1276 *p++ = bintoasc[(data[0] <<4)&060];
1278 *p = 0;
1279 return buffer;
1283 /***********************************************
1284 * For the pipemode command we can't use the armor filter for various
1285 * reasons, so we use this new unarmor_pump stuff to remove the armor
1288 enum unarmor_state_e {
1289 STA_init = 0,
1290 STA_bypass,
1291 STA_wait_newline,
1292 STA_wait_dash,
1293 STA_first_dash,
1294 STA_compare_header,
1295 STA_found_header_wait_newline,
1296 STA_skip_header_lines,
1297 STA_skip_header_lines_non_ws,
1298 STA_read_data,
1299 STA_wait_crc,
1300 STA_read_crc,
1301 STA_ready
1304 struct unarmor_pump_s {
1305 enum unarmor_state_e state;
1306 byte val;
1307 int checkcrc;
1308 int pos; /* counts from 0..3 */
1309 u32 crc;
1310 u32 mycrc; /* the one store in the data */
1315 UnarmorPump
1316 unarmor_pump_new (void)
1318 UnarmorPump x;
1320 if( !is_initialized )
1321 initialize();
1322 x = xmalloc_clear (sizeof *x);
1323 return x;
1326 void
1327 unarmor_pump_release (UnarmorPump x)
1329 xfree (x);
1333 * Get the next character from the ascii armor taken from the IOBUF
1334 * created earlier by unarmor_pump_new().
1335 * Return: c = Character
1336 * 256 = ignore this value
1337 * -1 = End of current armor
1338 * -2 = Premature EOF (not used)
1339 * -3 = Invalid armor
1342 unarmor_pump (UnarmorPump x, int c)
1344 int rval = 256; /* default is to ignore the return value */
1346 switch (x->state) {
1347 case STA_init:
1349 byte tmp[1];
1350 tmp[0] = c;
1351 if ( is_armored (tmp) )
1352 x->state = c == '-'? STA_first_dash : STA_wait_newline;
1353 else {
1354 x->state = STA_bypass;
1355 return c;
1358 break;
1359 case STA_bypass:
1360 return c; /* return here to avoid crc calculation */
1361 case STA_wait_newline:
1362 if (c == '\n')
1363 x->state = STA_wait_dash;
1364 break;
1365 case STA_wait_dash:
1366 x->state = c == '-'? STA_first_dash : STA_wait_newline;
1367 break;
1368 case STA_first_dash: /* just need for initalization */
1369 x->pos = 0;
1370 x->state = STA_compare_header;
1371 case STA_compare_header:
1372 if ( "-----BEGIN PGP SIGNATURE-----"[++x->pos] == c ) {
1373 if ( x->pos == 28 )
1374 x->state = STA_found_header_wait_newline;
1376 else
1377 x->state = c == '\n'? STA_wait_dash : STA_wait_newline;
1378 break;
1379 case STA_found_header_wait_newline:
1380 /* to make CR,LF issues easier we simply allow for white space
1381 behind the 5 dashes */
1382 if ( c == '\n' )
1383 x->state = STA_skip_header_lines;
1384 else if ( c != '\r' && c != ' ' && c != '\t' )
1385 x->state = STA_wait_dash; /* garbage after the header line */
1386 break;
1387 case STA_skip_header_lines:
1388 /* i.e. wait for one empty line */
1389 if ( c == '\n' ) {
1390 x->state = STA_read_data;
1391 x->crc = CRCINIT;
1392 x->val = 0;
1393 x->pos = 0;
1395 else if ( c != '\r' && c != ' ' && c != '\t' )
1396 x->state = STA_skip_header_lines_non_ws;
1397 break;
1398 case STA_skip_header_lines_non_ws:
1399 /* like above but we already encountered non white space */
1400 if ( c == '\n' )
1401 x->state = STA_skip_header_lines;
1402 break;
1403 case STA_read_data:
1404 /* fixme: we don't check for the trailing dash lines but rely
1405 * on the armor stop characters */
1406 if( c == '\n' || c == ' ' || c == '\r' || c == '\t' )
1407 break; /* skip all kind of white space */
1409 if( c == '=' ) { /* pad character: stop */
1410 if( x->pos == 1 ) /* in this case val has some value */
1411 rval = x->val;
1412 x->state = STA_wait_crc;
1413 break;
1417 int c2;
1418 if( (c = asctobin[(c2=c)]) == 255 ) {
1419 log_error(_("invalid radix64 character %02X skipped\n"), c2);
1420 break;
1424 switch(x->pos) {
1425 case 0:
1426 x->val = c << 2;
1427 break;
1428 case 1:
1429 x->val |= (c>>4)&3;
1430 rval = x->val;
1431 x->val = (c<<4)&0xf0;
1432 break;
1433 case 2:
1434 x->val |= (c>>2)&15;
1435 rval = x->val;
1436 x->val = (c<<6)&0xc0;
1437 break;
1438 case 3:
1439 x->val |= c&0x3f;
1440 rval = x->val;
1441 break;
1443 x->pos = (x->pos+1) % 4;
1444 break;
1445 case STA_wait_crc:
1446 if( c == '\n' || c == ' ' || c == '\r' || c == '\t' || c == '=' )
1447 break; /* skip ws and pad characters */
1448 /* assume that we are at the next line */
1449 x->state = STA_read_crc;
1450 x->pos = 0;
1451 x->mycrc = 0;
1452 case STA_read_crc:
1453 if( (c = asctobin[c]) == 255 ) {
1454 rval = -1; /* ready */
1455 if( x->crc != x->mycrc ) {
1456 log_info (_("CRC error; %06lX - %06lX\n"),
1457 (ulong)x->crc, (ulong)x->mycrc);
1458 if ( invalid_crc() )
1459 rval = -3;
1461 x->state = STA_ready; /* not sure whether this is correct */
1462 break;
1465 switch(x->pos) {
1466 case 0:
1467 x->val = c << 2;
1468 break;
1469 case 1:
1470 x->val |= (c>>4)&3;
1471 x->mycrc |= x->val << 16;
1472 x->val = (c<<4)&0xf0;
1473 break;
1474 case 2:
1475 x->val |= (c>>2)&15;
1476 x->mycrc |= x->val << 8;
1477 x->val = (c<<6)&0xc0;
1478 break;
1479 case 3:
1480 x->val |= c&0x3f;
1481 x->mycrc |= x->val;
1482 break;
1484 x->pos = (x->pos+1) % 4;
1485 break;
1486 case STA_ready:
1487 rval = -1;
1488 break;
1491 if ( !(rval & ~255) ) { /* compute the CRC */
1492 x->crc = (x->crc << 8) ^ crc_table[((x->crc >> 16)&0xff) ^ rval];
1493 x->crc &= 0x00ffffff;
1496 return rval;