/[winpt]/trunk/Gnupg/parse-packet.c
ViewVC logotype

Annotation of /trunk/Gnupg/parse-packet.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 2 - (hide annotations)
Mon Jan 31 11:02:21 2005 UTC (20 years, 1 month ago) by twoaday
File MIME type: text/plain
File size: 77357 byte(s)
WinPT initial checkin.


1 twoaday 2 /* parse-packet.c - read packets
2     * Copyright (C) 1998, 1999, 2000, 2001, 2002 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 2 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, write to the Free Software
18     * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
19     */
20    
21     #include <stdio.h>
22     #include <stdlib.h>
23     #include <string.h>
24     #include <time.h>
25     #include <assert.h>
26     #include <process.h>
27     #include <sys/types.h>
28    
29     #include "openpgp.h"
30     #include "packet.h"
31     #include "md.h"
32    
33     static int mpi_print_mode = 0;
34     static int list_mode = 0;
35    
36     static int parse( gpg_iobuf_t inp, PACKET *pkt, int onlykeypkts,
37     _off_t *retpos, int *skip, gpg_iobuf_t out, int do_skip );
38     static int copy_packet( gpg_iobuf_t inp, gpg_iobuf_t out, int pkttype,
39     unsigned long pktlen );
40     static void skip_packet( gpg_iobuf_t inp, int pkttype, unsigned long pktlen );
41     static void skip_rest( gpg_iobuf_t inp, unsigned long pktlen );
42     static void *read_rest( gpg_iobuf_t inp, size_t pktlen );
43     static int parse_symkeyenc( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
44     PACKET *packet );
45     static int parse_pubkeyenc( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
46     PACKET *packet );
47     static int parse_signature( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
48     PKT_signature *sig );
49     static int parse_onepass_sig( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
50     PKT_onepass_sig *ops );
51     static int parse_key( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
52     byte *hdr, int hdrlen, PACKET *packet );
53     static int parse_user_id( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
54     PACKET *packet );
55     static int parse_attribute( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
56     PACKET *packet );
57     static int parse_comment( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
58     PACKET *packet );
59     static void parse_trust( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
60     PACKET *packet );
61     static int parse_plaintext( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
62     PACKET *packet, int new_ctb);
63     static int parse_compressed( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
64     PACKET *packet, int new_ctb );
65     static int parse_encrypted( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
66     PACKET *packet, int new_ctb);
67     static int parse_mdc( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
68     PACKET *packet, int new_ctb);
69     static int parse_gpg_control( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
70     PACKET *packet );
71    
72     static unsigned short
73     read_16(gpg_iobuf_t inp)
74     {
75     unsigned short a;
76     a = gpg_iobuf_get_noeof(inp) << 8;
77     a |= gpg_iobuf_get_noeof(inp);
78     return a;
79     }
80    
81     static unsigned long
82     read_32(gpg_iobuf_t inp)
83     {
84     unsigned long a;
85     a = gpg_iobuf_get_noeof(inp) << 24;
86     a |= gpg_iobuf_get_noeof(inp) << 16;
87     a |= gpg_iobuf_get_noeof(inp) << 8;
88     a |= gpg_iobuf_get_noeof(inp);
89     return a;
90     }
91    
92     static unsigned long
93     buffer_to_u32( const unsigned char *buffer )
94     {
95     unsigned long a;
96     a = *buffer << 24;
97     a |= buffer[1] << 16;
98     a |= buffer[2] << 8;
99     a |= buffer[3];
100     return a;
101     }
102    
103     int
104     set_packet_list_mode( int mode )
105     {
106     int old = list_mode;
107     list_mode = mode;
108     mpi_print_mode = 0;
109     return old;
110     }
111    
112     static void
113     unknown_pubkey_warning( int algo )
114     {
115     static byte unknown_pubkey_algos[256];
116    
117     algo &= 0xff;
118     if( !unknown_pubkey_algos[algo] ) {
119     unknown_pubkey_algos[algo] = 1;
120     }
121     }
122    
123     static const char *
124     strtimestamp( unsigned long stamp )
125     {
126     static char buffer[11+5];
127     struct tm *tp;
128     time_t atime = stamp;
129    
130     if (atime < 0) {
131     strcpy (buffer, "????" "-??" "-??");
132     }
133     else {
134     tp = gmtime( &atime );
135     sprintf(buffer,"%04d-%02d-%02d",
136     1900+tp->tm_year, tp->tm_mon+1, tp->tm_mday );
137     }
138     return buffer;
139     }
140    
141     static const char *
142     strtimevalue( unsigned long value )
143     {
144     static char buffer[30];
145     unsigned int years, days, hours, minutes;
146    
147     value /= 60;
148     minutes = value % 60;
149     value /= 60;
150     hours = value % 24;
151     value /= 24;
152     days = value % 365;
153     value /= 365;
154     years = value;
155    
156     sprintf(buffer,"%uy%ud%uh%um", years, days, hours, minutes );
157     if( years )
158     return buffer;
159     if( days )
160     return strchr( buffer, 'y' ) + 1;
161     return strchr( buffer, 'd' ) + 1;
162     }
163    
164    
165     static gpg_mpi_t
166     mpi_read( gpg_iobuf_t inp, size_t *ret_n, int flags )
167     {
168     gpg_mpi_t a;
169     int i = 0, j = 0;
170     u32 t;
171     size_t n;
172    
173     a = calloc( 1, sizeof *a );
174     a->nbits = read_16( inp );
175     n = (a->nbits + 7) / 8;
176     a->alloced = n;
177     a->d = calloc( n, 4 );
178     i = 4 - n % 4;
179     i %= 4;
180     j = (n+4-1) / 4;
181     for( ; j > 0; j-- ) {
182     t = 0;
183     for( ; i < 4; i++ ) {
184     t <<= 8;
185     t |= gpg_iobuf_get( inp ) & 0xff;
186     }
187     i = 0;
188     a->d[j-1] = t;
189     }
190     if( *ret_n )
191     *ret_n = n + 2;
192    
193     return a;
194     }
195    
196     void
197     mpi_print( FILE *fp, gpg_mpi_t a, int mode )
198     {
199     int i;
200     for( i = 0; i < a->alloced / 4; i++ )
201     printf( "%08x", a->d[i] );
202     }
203    
204     static void
205     mpi_set_protect_flag( gpg_mpi_t a )
206     {
207     a->flags = 1;
208     }
209    
210     static gpg_mpi_t
211     mpi_set_opaque( gpg_mpi_t a, void *p, int len )
212     {
213     if( !a ) {
214     a = calloc( 1, sizeof *a );
215     }
216    
217     if( a->flags & 4 )
218     safe_free( a->d );
219     else {
220     safe_free( a->d );
221     }
222    
223     a->d = p;
224     a->alloced = 0;
225     a->nlimbs = 0;
226     a->nbits = len;
227     a->flags = 4;
228     return a;
229     }
230    
231     void
232     free_symkey_enc( PKT_symkey_enc *enc )
233     {
234     safe_free(enc);
235     }
236    
237     void
238     free_pubkey_enc( PKT_pubkey_enc *enc )
239     {
240     int n, i;
241     n = pubkey_get_nenc( enc->pubkey_algo );
242     if( !n )
243     safe_free(enc->data[0]);
244     for(i=0; i < n; i++ )
245     safe_free( enc->data[i] );
246     safe_free(enc);
247     }
248    
249     void
250     free_seckey_enc( PKT_signature *sig )
251     {
252     int n, i;
253    
254     n = pubkey_get_nsig( sig->pubkey_algo );
255     if( !n )
256     safe_free(sig->data[0]);
257     for(i=0; i < n; i++ )
258     safe_free( sig->data[i] );
259    
260     safe_free(sig->revkey);
261     safe_free(sig->hashed);
262     safe_free(sig->unhashed);
263     safe_free(sig);
264     }
265    
266    
267    
268     void
269     release_public_key_parts( PKT_public_key *pk )
270     {
271     int n, i;
272     n = pubkey_get_npkey( pk->pubkey_algo );
273     if( !n )
274     safe_free(pk->pkey[0]);
275     for(i=0; i < n; i++ ) {
276     safe_free( pk->pkey[i] );
277     pk->pkey[i] = NULL;
278     }
279     if (pk->prefs) {
280     safe_free (pk->prefs);
281     pk->prefs = NULL;
282     }
283     if( pk->namehash ) {
284     safe_free(pk->namehash);
285     pk->namehash = NULL;
286     }
287     if (pk->user_id) {
288     free_user_id (pk->user_id);
289     pk->user_id = NULL;
290     }
291     if (pk->revkey) {
292     safe_free(pk->revkey);
293     pk->revkey=NULL;
294     pk->numrevkeys=0;
295     }
296     }
297    
298    
299     void
300     free_public_key( PKT_public_key *pk )
301     {
302     release_public_key_parts( pk );
303     safe_free(pk);
304     }
305    
306    
307     int
308     pubkey_get_nenc( int algo )
309     {
310     switch( algo ) {
311     case 1:
312     case 2:
313     case 3: return 1;
314     case 16:
315     case 20: return 2;
316     }
317     return 0;
318     }
319    
320     int
321     pubkey_get_nsig( algo )
322     {
323     switch( algo ) {
324     case 1:
325     case 2:
326     case 3: return 1;
327     case 17:
328     case 16:
329     case 20: return 2;
330     }
331     return 0;
332     }
333    
334     int
335     pubkey_get_npkey( int algo )
336     {
337     if( is_ELGAMAL( algo ) ) return 3;
338     else if ( algo == 17 ) return 4;
339     else if ( is_RSA( algo ) ) return 2;
340     return 0;
341     } /* cdk_pk_get_npkey */
342    
343     int
344     pubkey_get_nskey( int algo )
345     {
346     if ( is_ELGAMAL( algo ) ) return 4;
347     else if ( algo == 17 ) return 5;
348     else if ( is_RSA( algo ) )return 6;
349     return 0;
350     } /* cdk_pk_get_nskey */
351    
352    
353     static subpktarea_t *
354     cp_subpktarea (subpktarea_t *s )
355     {
356     subpktarea_t *d;
357    
358     if( !s )
359     return NULL;
360     d = malloc (sizeof (*d) + s->size - 1 );
361     d->size = s->size;
362     d->len = s->len;
363     memcpy (d->data, s->data, s->len);
364     return d;
365     }
366    
367     /*
368     * Return a copy of the preferences
369     */
370     prefitem_t *
371     copy_prefs (const prefitem_t *prefs)
372     {
373     size_t n;
374     prefitem_t *new;
375    
376     if (!prefs)
377     return NULL;
378    
379     for (n=0; prefs[n].type; n++)
380     ;
381     new = malloc ( sizeof (*new) * (n+1));
382     for (n=0; prefs[n].type; n++) {
383     new[n].type = prefs[n].type;
384     new[n].value = prefs[n].value;
385     }
386     new[n].type = PREFTYPE_NONE;
387     new[n].value = 0;
388    
389     return new;
390     }
391    
392     /****************
393     * Replace all common parts of a sk by the one from the public key.
394     * This is a hack and a better solution will be to just store the real secret
395     * parts somewhere and don't duplicate all the other stuff.
396     */
397     void
398     copy_public_parts_to_secret_key( PKT_public_key *pk, PKT_secret_key *sk )
399     {
400     sk->expiredate = pk->expiredate;
401     sk->pubkey_algo = pk->pubkey_algo;
402     sk->pubkey_usage= pk->pubkey_usage;
403     sk->req_usage = pk->req_usage;
404     sk->req_algo = pk->req_algo;
405     sk->has_expired = pk->has_expired;
406     sk->is_revoked = pk->is_revoked;
407     sk->is_valid = pk->is_valid;
408     sk->main_keyid[0]= pk->main_keyid[0];
409     sk->main_keyid[1]= pk->main_keyid[1];
410     sk->keyid[0] = pk->keyid[0];
411     sk->keyid[1] = pk->keyid[1];
412     }
413    
414     void
415     release_secret_key_parts( PKT_secret_key *sk )
416     {
417     int n, i;
418    
419     n = pubkey_get_nskey( sk->pubkey_algo );
420     if( !n )
421     safe_free(sk->skey[0]);
422     for(i=0; i < n; i++ ) {
423     safe_free( sk->skey[i] );
424     sk->skey[i] = NULL;
425     }
426     }
427    
428     void
429     free_secret_key( PKT_secret_key *sk )
430     {
431     release_secret_key_parts( sk );
432     safe_free(sk);
433     }
434    
435     void
436     free_comment( PKT_comment *rem )
437     {
438     safe_free(rem);
439     }
440    
441     void
442     free_attributes(PKT_user_id *uid)
443     {
444     safe_free(uid->attribs);
445     safe_free(uid->attrib_data);
446    
447     uid->attribs=NULL;
448     uid->attrib_data=NULL;
449     uid->attrib_len=0;
450     }
451    
452     void
453     free_user_id (PKT_user_id *uid)
454     {
455     assert (uid->ref > 0);
456     if (--uid->ref)
457     return;
458    
459     free_attributes(uid);
460    
461     if (uid->prefs)
462     safe_free (uid->prefs);
463     safe_free (uid);
464     }
465    
466     void
467     free_compressed( PKT_compressed *zd )
468     {
469     if( zd->buf ) { /* have to skip some bytes */
470     /* don't have any information about the length, so
471     * we assume this is the last packet */
472     while( gpg_iobuf_read( zd->buf, NULL, 1<<30 ) != -1 )
473     ;
474     }
475     safe_free(zd);
476     }
477    
478     void
479     free_encrypted( PKT_encrypted *ed )
480     {
481     if( ed->buf ) { /* have to skip some bytes */
482     if( gpg_iobuf_in_block_mode(ed->buf) ) {
483     while( gpg_iobuf_read( ed->buf, NULL, 1<<30 ) != -1 )
484     ;
485     }
486     else {
487     while( ed->len ) { /* skip the packet */
488     int n = gpg_iobuf_read( ed->buf, NULL, ed->len );
489     if( n == -1 )
490     ed->len = 0;
491     else
492     ed->len -= n;
493     }
494     }
495     }
496     safe_free(ed);
497     }
498    
499    
500     void
501     free_plaintext( PKT_plaintext *pt )
502     {
503     if( pt->buf ) { /* have to skip some bytes */
504     if( gpg_iobuf_in_block_mode(pt->buf) ) {
505     while( gpg_iobuf_read( pt->buf, NULL, 1<<30 ) != -1 )
506     ;
507     }
508     else {
509     while( pt->len ) { /* skip the packet */
510     int n = gpg_iobuf_read( pt->buf, NULL, pt->len );
511     if( n == -1 )
512     pt->len = 0;
513     else
514     pt->len -= n;
515     }
516     }
517     }
518     safe_free(pt);
519     }
520    
521     /****************
522     * Free the packet in pkt.
523     */
524     void
525     gpg_free_packet( PACKET *pkt )
526     {
527     if( !pkt || !pkt->pkt.generic )
528     return;
529    
530     switch( pkt->pkttype ) {
531     case PKT_SIGNATURE:
532     free_seckey_enc( pkt->pkt.signature );
533     break;
534     case PKT_PUBKEY_ENC:
535     free_pubkey_enc( pkt->pkt.pubkey_enc );
536     break;
537     case PKT_SYMKEY_ENC:
538     free_symkey_enc( pkt->pkt.symkey_enc );
539     break;
540     case PKT_PUBLIC_KEY:
541     case PKT_PUBLIC_SUBKEY:
542     free_public_key( pkt->pkt.public_key );
543     break;
544     case PKT_SECRET_KEY:
545     case PKT_SECRET_SUBKEY:
546     free_secret_key( pkt->pkt.secret_key );
547     break;
548     case PKT_COMMENT:
549     free_comment( pkt->pkt.comment );
550     break;
551     case PKT_USER_ID:
552     free_user_id( pkt->pkt.user_id );
553     break;
554     case PKT_COMPRESSED:
555     free_compressed( pkt->pkt.compressed);
556     break;
557     case PKT_ENCRYPTED:
558     case PKT_ENCRYPTED_MDC:
559     free_encrypted( pkt->pkt.encrypted );
560     break;
561     case PKT_PLAINTEXT:
562     free_plaintext( pkt->pkt.plaintext );
563     break;
564     default:
565     safe_free( pkt->pkt.generic );
566     break;
567     }
568     pkt->pkt.generic = NULL;
569     }
570    
571    
572    
573     /****************
574     * Parse a Packet and return it in packet
575     * Returns: 0 := valid packet in pkt
576     * -1 := no more packets
577     * >0 := error
578     * Note: The function may return an error and a partly valid packet;
579     * caller must free this packet.
580     */
581     int
582     gpg_parse_packet( gpg_iobuf_t inp, PACKET *pkt )
583     {
584     int skip, rc;
585    
586     do {
587     rc = parse( inp, pkt, 0, NULL, &skip, NULL, 0 );
588     } while( skip );
589     return rc;
590     }
591    
592     /****************
593     * Like parse packet, but only return secret or public (sub)key packets.
594     */
595     int
596     search_packet( gpg_iobuf_t inp, PACKET *pkt, _off_t *retpos, int with_uid )
597     {
598     int skip, rc;
599    
600     do {
601     rc = parse( inp, pkt, with_uid?2:1, retpos, &skip, NULL, 0 );
602     } while( skip );
603     return rc;
604     }
605    
606     /****************
607     * Copy all packets from INP to OUT, thereby removing unused spaces.
608     */
609     int
610     copy_all_packets( gpg_iobuf_t inp, gpg_iobuf_t out )
611     {
612     PACKET pkt;
613     int skip, rc=0;
614     do {
615     gpg_init_packet(&pkt);
616     } while( !(rc = parse( inp, &pkt, 0, NULL, &skip, out, 0 )));
617     return rc;
618     }
619    
620     /****************
621     * Copy some packets from INP to OUT, thereby removing unused spaces.
622     * Stop at offset STOPoff (i.e. don't copy packets at this or later offsets)
623     */
624     int
625     copy_some_packets( gpg_iobuf_t inp, gpg_iobuf_t out, _off_t stopoff )
626     {
627     PACKET pkt;
628     int skip, rc=0;
629     do {
630     if( gpg_iobuf_tell(inp) >= stopoff )
631     return 0;
632     gpg_init_packet(&pkt);
633     } while( !(rc = parse( inp, &pkt, 0, NULL, &skip, out, 0 )) );
634     return rc;
635     }
636    
637     /****************
638     * Skip over N packets
639     */
640     int
641     skip_some_packets( gpg_iobuf_t inp, unsigned n )
642     {
643     int skip, rc=0;
644     PACKET pkt;
645    
646     for( ;n && !rc; n--) {
647     gpg_init_packet(&pkt);
648     rc = parse( inp, &pkt, 0, NULL, &skip, NULL, 1 );
649     }
650     return rc;
651     }
652    
653     /****************
654     * Parse packet. Set the variable skip points to 1 if the packet
655     * should be skipped; this is the case if either ONLYKEYPKTS is set
656     * and the parsed packet isn't one or the
657     * packet-type is 0, indicating deleted stuff.
658     * if OUT is not NULL, a special copymode is used.
659     */
660     static int
661     parse( gpg_iobuf_t inp, PACKET *pkt, int onlykeypkts, _off_t *retpos,
662     int *skip, gpg_iobuf_t out, int do_skip
663     )
664     {
665     int rc=0, c, ctb, pkttype, lenbytes;
666     unsigned long pktlen;
667     byte hdr[8];
668     int hdrlen;
669     int new_ctb = 0;
670     int with_uid = (onlykeypkts == 2);
671    
672     *skip = 0;
673     /*assert( !pkt->pkt.generic );*/
674     if( retpos )
675     *retpos = gpg_iobuf_tell(inp);
676    
677     if( (ctb = gpg_iobuf_get(inp)) == -1 ) {
678     rc = -1;
679     goto leave;
680     }
681     hdrlen=0;
682     hdr[hdrlen++] = ctb;
683     if( !(ctb & 0x80) ) {
684     printf("%s: invalid packet (ctb=%02x)\n", gpg_iobuf_where(inp), ctb );
685     rc = G10ERR_INVALID_PACKET;
686     goto leave;
687     }
688     pktlen = 0;
689     new_ctb = !!(ctb & 0x40);
690     if( new_ctb ) {
691     pkttype = ctb & 0x3f;
692     if( (c = gpg_iobuf_get(inp)) == -1 ) {
693     printf("%s: 1st length byte missing\n", gpg_iobuf_where(inp) );
694     rc = G10ERR_INVALID_PACKET;
695     goto leave;
696     }
697     if (pkttype == PKT_COMPRESSED) {
698     gpg_iobuf_set_partial_block_mode(inp, c & 0xff);
699     pktlen = 0;/* to indicate partial length */
700     }
701     else {
702     hdr[hdrlen++] = c;
703     if( c < 192 )
704     pktlen = c;
705     else if( c < 224 ) {
706     pktlen = (c - 192) * 256;
707     if( (c = gpg_iobuf_get(inp)) == -1 ) {
708     printf("%s: 2nd length byte missing\n",
709     gpg_iobuf_where(inp) );
710     rc = G10ERR_INVALID_PACKET;
711     goto leave;
712     }
713     hdr[hdrlen++] = c;
714     pktlen += c + 192;
715     }
716     else if( c == 255 ) {
717     pktlen = (hdr[hdrlen++] = gpg_iobuf_get_noeof(inp)) << 24;
718     pktlen |= (hdr[hdrlen++] = gpg_iobuf_get_noeof(inp)) << 16;
719     pktlen |= (hdr[hdrlen++] = gpg_iobuf_get_noeof(inp)) << 8;
720     if( (c = gpg_iobuf_get(inp)) == -1 ) {
721     printf("%s: 4 byte length invalid\n",
722     gpg_iobuf_where(inp) );
723     rc = G10ERR_INVALID_PACKET;
724     goto leave;
725     }
726     pktlen |= (hdr[hdrlen++] = c );
727     }
728     else { /* partial body length */
729     gpg_iobuf_set_partial_block_mode(inp, c & 0xff);
730     pktlen = 0;/* to indicate partial length */
731     }
732     }
733     }
734     else {
735     pkttype = (ctb>>2)&0xf;
736     lenbytes = ((ctb&3)==3)? 0 : (1<<(ctb & 3));
737     if( !lenbytes ) {
738     pktlen = 0; /* don't know the value */
739     if( pkttype != PKT_COMPRESSED )
740     gpg_iobuf_set_block_mode(inp, 1);
741     }
742     else {
743     for( ; lenbytes; lenbytes-- ) {
744     pktlen <<= 8;
745     pktlen |= hdr[hdrlen++] = gpg_iobuf_get_noeof(inp);
746     }
747     }
748     }
749    
750     if (pktlen == 0xffffffff) {
751     /* with a some probability this is caused by a problem in the
752     * the uncompressing layer - in some error cases it just loops
753     * and spits out 0xff bytes. */
754     printf ("%s: garbled packet detected\n", gpg_iobuf_where(inp) );
755     exit (2);
756     }
757    
758     if( out && pkttype ) {
759     if( gpg_iobuf_write( out, hdr, hdrlen ) == -1 )
760     rc = G10ERR_WRITE_FILE;
761     else
762     rc = copy_packet(inp, out, pkttype, pktlen );
763     goto leave;
764     }
765    
766     if (with_uid && pkttype == PKT_USER_ID)
767     ;
768     else if( do_skip
769     || !pkttype
770     || (onlykeypkts && pkttype != PKT_PUBLIC_SUBKEY
771     && pkttype != PKT_PUBLIC_KEY
772     && pkttype != PKT_SECRET_SUBKEY
773     && pkttype != PKT_SECRET_KEY ) ) {
774     skip_rest(inp, pktlen);
775     *skip = 1;
776     rc = 0;
777     goto leave;
778     }
779    
780     pkt->pkttype = pkttype;
781     rc = G10ERR_UNKNOWN_PACKET; /* default error */
782     switch( pkttype ) {
783     case PKT_PUBLIC_KEY:
784     case PKT_PUBLIC_SUBKEY:
785     pkt->pkt.public_key = calloc(1, sizeof *pkt->pkt.public_key );
786     rc = parse_key(inp, pkttype, pktlen, hdr, hdrlen, pkt );
787     break;
788     case PKT_SECRET_KEY:
789     case PKT_SECRET_SUBKEY:
790     pkt->pkt.secret_key = calloc(1,sizeof *pkt->pkt.secret_key );
791     rc = parse_key(inp, pkttype, pktlen, hdr, hdrlen, pkt );
792     break;
793     case PKT_SYMKEY_ENC:
794     rc = parse_symkeyenc( inp, pkttype, pktlen, pkt );
795     break;
796     case PKT_PUBKEY_ENC:
797     rc = parse_pubkeyenc(inp, pkttype, pktlen, pkt );
798     break;
799     case PKT_SIGNATURE:
800     pkt->pkt.signature = calloc(1,sizeof *pkt->pkt.signature );
801     rc = parse_signature(inp, pkttype, pktlen, pkt->pkt.signature );
802     break;
803     case PKT_ONEPASS_SIG:
804     pkt->pkt.onepass_sig = calloc(1,sizeof *pkt->pkt.onepass_sig );
805     rc = parse_onepass_sig(inp, pkttype, pktlen, pkt->pkt.onepass_sig );
806     break;
807     case PKT_USER_ID:
808     rc = parse_user_id(inp, pkttype, pktlen, pkt );
809     break;
810     case PKT_ATTRIBUTE:
811     pkt->pkttype = pkttype = PKT_USER_ID; /* we store it in the userID */
812     rc = parse_attribute(inp, pkttype, pktlen, pkt);
813     break;
814     case PKT_OLD_COMMENT:
815     case PKT_COMMENT:
816     rc = parse_comment(inp, pkttype, pktlen, pkt);
817     break;
818     case PKT_RING_TRUST:
819     parse_trust(inp, pkttype, pktlen, pkt);
820     rc = 0;
821     break;
822     case PKT_PLAINTEXT:
823     rc = parse_plaintext(inp, pkttype, pktlen, pkt, new_ctb );
824     break;
825     case PKT_COMPRESSED:
826     rc = parse_compressed(inp, pkttype, pktlen, pkt, new_ctb );
827     break;
828     case PKT_ENCRYPTED:
829     case PKT_ENCRYPTED_MDC:
830     rc = parse_encrypted(inp, pkttype, pktlen, pkt, new_ctb );
831     break;
832     case PKT_MDC:
833     rc = parse_mdc(inp, pkttype, pktlen, pkt, new_ctb );
834     break;
835     case PKT_GPG_CONTROL:
836     rc = parse_gpg_control(inp, pkttype, pktlen, pkt );
837     break;
838     default:
839     skip_packet(inp, pkttype, pktlen);
840     break;
841     }
842    
843     leave:
844     if( !rc && gpg_iobuf_error(inp) )
845     rc = G10ERR_INV_KEYRING;
846     return rc;
847     }
848    
849     static void
850     dump_hex_line( int c, int *i )
851     {
852     if( *i && !(*i%8) ) {
853     if( *i && !(*i%24) )
854     printf("\n%4d:", *i );
855     else
856     putchar(' ');
857     }
858     if( c == -1 )
859     printf(" EOF" );
860     else
861     printf(" %02x", c );
862     ++*i;
863     }
864    
865    
866     static int
867     copy_packet( gpg_iobuf_t inp, gpg_iobuf_t out, int pkttype, unsigned long pktlen )
868     {
869     int n;
870     char buf[100];
871    
872     if( gpg_iobuf_in_block_mode(inp) ) {
873     while( (n = gpg_iobuf_read( inp, buf, 100 )) != -1 )
874     if( gpg_iobuf_write(out, buf, n ) )
875     return G10ERR_WRITE_FILE; /* write error */
876     }
877     else if( !pktlen && pkttype == PKT_COMPRESSED ) {
878     printf("copy_packet: compressed!\n");
879     /* compressed packet, copy till EOF */
880     while( (n = gpg_iobuf_read( inp, buf, 100 )) != -1 )
881     if( gpg_iobuf_write(out, buf, n ) )
882     return G10ERR_WRITE_FILE; /* write error */
883     }
884     else {
885     for( ; pktlen; pktlen -= n ) {
886     n = pktlen > 100 ? 100 : pktlen;
887     n = gpg_iobuf_read( inp, buf, n );
888     if( n == -1 )
889     return G10ERR_READ_FILE;
890     if( gpg_iobuf_write(out, buf, n ) )
891     return G10ERR_WRITE_FILE; /* write error */
892     }
893     }
894     return 0;
895     }
896    
897    
898     static void
899     skip_packet( gpg_iobuf_t inp, int pkttype, unsigned long pktlen )
900     {
901     if( list_mode ) {
902     if( pkttype == PKT_MARKER )
903     fputs(":marker packet:\n", stdout );
904     else
905     printf(":unknown packet: type %2d, length %lu\n", pkttype, pktlen);
906     if( pkttype ) {
907     int c, i=0 ;
908     if( pkttype != PKT_MARKER )
909     fputs("dump:", stdout );
910     if( gpg_iobuf_in_block_mode(inp) ) {
911     while( (c=gpg_iobuf_get(inp)) != -1 )
912     dump_hex_line(c, &i);
913     }
914     else {
915     for( ; pktlen; pktlen-- )
916     dump_hex_line(gpg_iobuf_get(inp), &i);
917     }
918     putchar('\n');
919     return;
920     }
921     }
922     skip_rest(inp,pktlen);
923     }
924    
925     static void
926     skip_rest( gpg_iobuf_t inp, unsigned long pktlen )
927     {
928     if( gpg_iobuf_in_block_mode(inp) ) {
929     while( gpg_iobuf_get(inp) != -1 )
930     ;
931     }
932     else {
933     for( ; pktlen; pktlen-- )
934     if( gpg_iobuf_get(inp) == -1 )
935     break;
936     }
937     }
938    
939    
940     static void *
941     read_rest( gpg_iobuf_t inp, size_t pktlen )
942     {
943     byte *p;
944     int i;
945    
946     if( gpg_iobuf_in_block_mode(inp) ) {
947     printf("read_rest: can't store stream data\n");
948     p = NULL;
949     }
950     else {
951     p = malloc( pktlen );
952     for(i=0; pktlen; pktlen--, i++ )
953     p[i] = gpg_iobuf_get(inp);
954     }
955     return p;
956     }
957    
958    
959    
960     static int
961     parse_symkeyenc( gpg_iobuf_t inp, int pkttype, unsigned long pktlen, PACKET *packet )
962     {
963     PKT_symkey_enc *k;
964     int rc = 0;
965     int i, version, s2kmode, cipher_algo, hash_algo, seskeylen, minlen;
966    
967     if( pktlen < 4 ) {
968     printf("packet(%d) too short\n", pkttype);
969     rc = G10ERR_INVALID_PACKET;
970     goto leave;
971     }
972     version = gpg_iobuf_get_noeof(inp); pktlen--;
973     if( version != 4 ) {
974     printf("packet(%d) with unknown version %d\n", pkttype, version);
975     rc = G10ERR_INVALID_PACKET;
976     goto leave;
977     }
978     if( pktlen > 200 ) { /* (we encode the seskeylen in a byte) */
979     printf("packet(%d) too large\n", pkttype);
980     rc = G10ERR_INVALID_PACKET;
981     goto leave;
982     }
983     cipher_algo = gpg_iobuf_get_noeof(inp); pktlen--;
984     s2kmode = gpg_iobuf_get_noeof(inp); pktlen--;
985     hash_algo = gpg_iobuf_get_noeof(inp); pktlen--;
986     switch( s2kmode ) {
987     case 0: /* simple s2k */
988     minlen = 0;
989     break;
990     case 1: /* salted s2k */
991     minlen = 8;
992     break;
993     case 3: /* iterated+salted s2k */
994     minlen = 9;
995     break;
996     default:
997     printf("unknown S2K %d\n", s2kmode );
998     goto leave;
999     }
1000     if( minlen > pktlen ) {
1001     printf("packet with S2K %d too short\n", s2kmode );
1002     rc = G10ERR_INVALID_PACKET;
1003     goto leave;
1004     }
1005     seskeylen = pktlen - minlen;
1006     k = packet->pkt.symkey_enc = calloc(1, sizeof *packet->pkt.symkey_enc
1007     + seskeylen - 1 );
1008     k->version = version;
1009     k->cipher_algo = cipher_algo;
1010     k->s2k.mode = s2kmode;
1011     k->s2k.hash_algo = hash_algo;
1012     if( s2kmode == 1 || s2kmode == 3 ) {
1013     for(i=0; i < 8 && pktlen; i++, pktlen-- )
1014     k->s2k.salt[i] = gpg_iobuf_get_noeof(inp);
1015     }
1016     if( s2kmode == 3 ) {
1017     k->s2k.count = gpg_iobuf_get(inp); pktlen--;
1018     }
1019     k->seskeylen = seskeylen;
1020     for(i=0; i < seskeylen && pktlen; i++, pktlen-- )
1021     k->seskey[i] = gpg_iobuf_get_noeof(inp);
1022     assert( !pktlen );
1023    
1024     if( list_mode ) {
1025     printf(":symkey enc packet: version %d, cipher %d, s2k %d, hash %d\n",
1026     version, cipher_algo, s2kmode, hash_algo);
1027     if( s2kmode == 1 || s2kmode == 3 ) {
1028     printf("\tsalt ");
1029     for(i=0; i < 8; i++ )
1030     printf("%02x", k->s2k.salt[i]);
1031     if( s2kmode == 3 )
1032     printf(", count %lu\n", (ulong)k->s2k.count );
1033     printf("\n");
1034     }
1035     }
1036    
1037     leave:
1038     skip_rest(inp, pktlen);
1039     return rc;
1040     }
1041    
1042     static int
1043     parse_pubkeyenc( gpg_iobuf_t inp, int pkttype, unsigned long pktlen, PACKET *packet )
1044     {
1045     unsigned int n;
1046     int rc = 0;
1047     int i, ndata;
1048     PKT_pubkey_enc *k;
1049    
1050     k = packet->pkt.pubkey_enc = calloc(1, sizeof *packet->pkt.pubkey_enc);
1051     if( pktlen < 12 ) {
1052     printf("packet(%d) too short\n", pkttype);
1053     rc = G10ERR_INVALID_PACKET;
1054     goto leave;
1055     }
1056     k->version = gpg_iobuf_get_noeof(inp); pktlen--;
1057     if( k->version != 2 && k->version != 3 ) {
1058     printf("packet(%d) with unknown version %d\n", pkttype, k->version);
1059     rc = G10ERR_INVALID_PACKET;
1060     goto leave;
1061     }
1062     k->keyid[0] = read_32(inp); pktlen -= 4;
1063     k->keyid[1] = read_32(inp); pktlen -= 4;
1064     k->pubkey_algo = gpg_iobuf_get_noeof(inp); pktlen--;
1065     k->throw_keyid = 0; /* only used as flag for build_packet */
1066     if( list_mode )
1067     printf(":pubkey enc packet: version %d, algo %d, keyid %08lX%08lX\n",
1068     k->version, k->pubkey_algo, (ulong)k->keyid[0], (ulong)k->keyid[1]);
1069    
1070     ndata = pubkey_get_nenc(k->pubkey_algo);
1071     if( !ndata ) {
1072     if( list_mode )
1073     printf("\tunsupported algorithm %d\n", k->pubkey_algo );
1074     unknown_pubkey_warning( k->pubkey_algo );
1075     k->data[0] = NULL; /* no need to store the encrypted data */
1076     }
1077     else {
1078     for( i=0; i < ndata; i++ ) {
1079     n = pktlen;
1080     k->data[i] = mpi_read(inp, &n, 0); pktlen -=n;
1081     if( list_mode ) {
1082     printf("\tdata: ");
1083     mpi_print(stdout, k->data[i], mpi_print_mode );
1084     putchar('\n');
1085     }
1086     if (!k->data[i])
1087     rc = G10ERR_INVALID_PACKET;
1088     }
1089     }
1090    
1091     leave:
1092     skip_rest(inp, pktlen);
1093     return rc;
1094     }
1095    
1096     static void
1097     dump_sig_subpkt( int hashed, int type, int critical,
1098     const byte *buffer, size_t buflen, size_t length )
1099     {
1100     const char *p=NULL;
1101     int i;
1102    
1103     /* The CERT has warning out with explains how to use GNUPG to
1104     * detect the ARRs - we print our old message here when it is a faked
1105     * ARR and add an additional notice */
1106     if ( type == SIGSUBPKT_ARR && !hashed ) {
1107     printf("\tsubpkt %d len %u (additional recipient request)\n"
1108     "WARNING: PGP versions > 5.0 and < 6.5.8 will automagically "
1109     "encrypt to this key and thereby reveal the plaintext to "
1110     "the owner of this ARR key. Detailed info follows:\n",
1111     type, (unsigned)length );
1112     }
1113    
1114    
1115     printf("\t%s%ssubpkt %d len %u (", /*)*/
1116     critical ? "critical ":"",
1117     hashed ? "hashed ":"", type, (unsigned)length );
1118     buffer++;
1119     length--;
1120     if( length > buflen ) {
1121     printf("too short: buffer is only %u)\n", (unsigned)buflen );
1122     return;
1123     }
1124     switch( type ) {
1125     case SIGSUBPKT_SIG_CREATED:
1126     if( length >= 4 )
1127     printf("sig created %s", strtimestamp( buffer_to_u32(buffer) ) );
1128     break;
1129     case SIGSUBPKT_SIG_EXPIRE:
1130     if( length >= 4 )
1131     printf("sig expires after %s",
1132     strtimevalue( buffer_to_u32(buffer) ) );
1133     break;
1134     case SIGSUBPKT_EXPORTABLE:
1135     if( length )
1136     printf("%sexportable", *buffer? "":"not ");
1137     break;
1138     case SIGSUBPKT_TRUST:
1139     if(length!=2)
1140     p="[invalid trust signature]";
1141     else
1142     printf("trust signature of level %d, amount %d",buffer[0],buffer[1]);
1143     break;
1144     case SIGSUBPKT_REGEXP:
1145     if(!length)
1146     p="[invalid regexp]";
1147     else
1148     printf("regular expression: \"%s\"",buffer);
1149     break;
1150     case SIGSUBPKT_REVOCABLE:
1151     if( length )
1152     printf("%srevocable", *buffer? "":"not ");
1153     break;
1154     case SIGSUBPKT_KEY_EXPIRE:
1155     if( length >= 4 )
1156     printf("key expires after %s",
1157     strtimevalue( buffer_to_u32(buffer) ) );
1158     break;
1159     case SIGSUBPKT_PREF_SYM:
1160     fputs("pref-sym-algos:", stdout );
1161     for( i=0; i < length; i++ )
1162     printf(" %d", buffer[i] );
1163     break;
1164     case SIGSUBPKT_REV_KEY:
1165     fputs("revocation key: ", stdout );
1166     if( length < 22 )
1167     p = "[too short]";
1168     else {
1169     printf("c=%02x a=%d f=", buffer[0], buffer[1] );
1170     for( i=2; i < length; i++ )
1171     printf("%02X", buffer[i] );
1172     }
1173     break;
1174     case SIGSUBPKT_ISSUER:
1175     if( length >= 8 )
1176     printf("issuer key ID %08lX%08lX",
1177     (ulong)buffer_to_u32(buffer),
1178     (ulong)buffer_to_u32(buffer+4) );
1179     break;
1180     case SIGSUBPKT_NOTATION:
1181     {
1182     fputs("notation: ", stdout );
1183     if( length < 8 )
1184     p = "[too short]";
1185     else if( !(*buffer & 0x80) )
1186     p = "[not human readable]";
1187     else {
1188     const byte *s = buffer;
1189     size_t n1, n2;
1190    
1191     n1 = (s[4] << 8) | s[5];
1192     n2 = (s[6] << 8) | s[7];
1193     s += 8;
1194     if( 8+n1+n2 != length )
1195     p = "[error]";
1196     else {
1197     print_string( stdout, s, n1, ')' );
1198     putc( '=', stdout );
1199     print_string( stdout, s+n1, n2, ')' );
1200     }
1201     }
1202     }
1203     break;
1204     case SIGSUBPKT_PREF_HASH:
1205     fputs("pref-hash-algos:", stdout );
1206     for( i=0; i < length; i++ )
1207     printf(" %d", buffer[i] );
1208     break;
1209     case SIGSUBPKT_PREF_COMPR:
1210     fputs("pref-zip-algos:", stdout );
1211     for( i=0; i < length; i++ )
1212     printf(" %d", buffer[i] );
1213     break;
1214     case SIGSUBPKT_KS_FLAGS:
1215     fputs("key server preferences:",stdout);
1216     for(i=0;i<length;i++)
1217     printf(" %02X", buffer[i]);
1218     break;
1219     case SIGSUBPKT_PREF_KS:
1220     p = "preferred key server";
1221     break;
1222     case SIGSUBPKT_PRIMARY_UID:
1223     p = "primary user ID";
1224     break;
1225     case SIGSUBPKT_POLICY:
1226     fputs("policy: ", stdout );
1227     print_string( stdout, buffer, length, ')' );
1228     break;
1229     case SIGSUBPKT_KEY_FLAGS:
1230     fputs ( "key flags:", stdout );
1231     for( i=0; i < length; i++ )
1232     printf(" %02X", buffer[i] );
1233     break;
1234     case SIGSUBPKT_SIGNERS_UID:
1235     p = "signer's user ID";
1236     break;
1237     case SIGSUBPKT_REVOC_REASON:
1238     if( length ) {
1239     printf("revocation reason 0x%02x (", *buffer );
1240     print_string( stdout, buffer+1, length-1, ')' );
1241     p = ")";
1242     }
1243     break;
1244     case SIGSUBPKT_ARR:
1245     fputs("Big Brother's key (ignored): ", stdout );
1246     if( length < 22 )
1247     p = "[too short]";
1248     else {
1249     printf("c=%02x a=%d f=", buffer[0], buffer[1] );
1250     for( i=2; i < length; i++ )
1251     printf("%02X", buffer[i] );
1252     }
1253     break;
1254     case SIGSUBPKT_FEATURES:
1255     fputs ( "features:", stdout );
1256     for( i=0; i < length; i++ )
1257     printf(" %02x", buffer[i] );
1258     break;
1259     case SIGSUBPKT_PRIV_VERIFY_CACHE:
1260     p = "obsolete verification cache";
1261     break;
1262     default: p = "?"; break;
1263     }
1264    
1265     printf("%s)\n", p? p: "");
1266     }
1267    
1268     /****************
1269     * Returns: >= 0 offset into buffer
1270     * -1 unknown type
1271     * -2 unsupported type
1272     * -3 subpacket too short
1273     */
1274     int
1275     parse_one_sig_subpkt( const byte *buffer, size_t n, int type )
1276     {
1277     switch( type ) {
1278     case SIGSUBPKT_REV_KEY:
1279     if(n < 22)
1280     break;
1281     return 0;
1282     case SIGSUBPKT_SIG_CREATED:
1283     case SIGSUBPKT_SIG_EXPIRE:
1284     case SIGSUBPKT_KEY_EXPIRE:
1285     if( n < 4 )
1286     break;
1287     return 0;
1288     case SIGSUBPKT_KEY_FLAGS:
1289     case SIGSUBPKT_KS_FLAGS:
1290     case SIGSUBPKT_PREF_SYM:
1291     case SIGSUBPKT_PREF_HASH:
1292     case SIGSUBPKT_PREF_COMPR:
1293     case SIGSUBPKT_POLICY:
1294     case SIGSUBPKT_FEATURES:
1295     return 0;
1296     case SIGSUBPKT_EXPORTABLE:
1297     case SIGSUBPKT_REVOCABLE:
1298     if( !n )
1299     break;
1300     return 0;
1301     case SIGSUBPKT_ISSUER: /* issuer key ID */
1302     if( n < 8 )
1303     break;
1304     return 0;
1305     case SIGSUBPKT_NOTATION:
1306     if( n < 8 ) /* minimum length needed */
1307     break;
1308     return 0;
1309     case SIGSUBPKT_REVOC_REASON:
1310     if( !n )
1311     break;
1312     return 0;
1313     case SIGSUBPKT_PRIMARY_UID:
1314     if ( n != 1 )
1315     break;
1316     return 0;
1317     case SIGSUBPKT_PRIV_VERIFY_CACHE:
1318     /* We used this in gpg 1.0.5 and 1.0.6 to cache signature
1319     * verification results - it is no longer used.
1320     * "GPG" 0x00 <mode> <stat>
1321     * where mode == 1: valid data, stat == 0: invalid signature
1322     * stat == 1: valid signature
1323     * (because we use private data, we check our marker) */
1324     if( n < 6 )
1325     break;
1326     if( buffer[0] != 'G' || buffer[1] != 'P'
1327     || buffer[2] != 'G' || buffer[3] )
1328     return -2;
1329     return 4;
1330     default: return -1;
1331     }
1332     return -3;
1333     }
1334    
1335    
1336     static int
1337     can_handle_critical( const byte *buffer, size_t n, int type )
1338     {
1339     switch( type ) {
1340     case SIGSUBPKT_NOTATION:
1341     if( n >= 8 && (*buffer & 0x80) )
1342     return 1; /* human readable is handled */
1343     return 0;
1344    
1345     case SIGSUBPKT_SIG_CREATED:
1346     case SIGSUBPKT_SIG_EXPIRE:
1347     case SIGSUBPKT_KEY_EXPIRE:
1348     case SIGSUBPKT_EXPORTABLE:
1349     case SIGSUBPKT_REVOCABLE:
1350     case SIGSUBPKT_REV_KEY:
1351     case SIGSUBPKT_ISSUER:/* issuer key ID */
1352     case SIGSUBPKT_PREF_SYM:
1353     case SIGSUBPKT_PREF_HASH:
1354     case SIGSUBPKT_PREF_COMPR:
1355     case SIGSUBPKT_KEY_FLAGS:
1356     case SIGSUBPKT_PRIMARY_UID:
1357     case SIGSUBPKT_FEATURES:
1358     case SIGSUBPKT_POLICY: /* Is it enough to show the policy? */
1359     return 1;
1360    
1361     default:
1362     return 0;
1363     }
1364     }
1365    
1366    
1367     const byte *
1368     enum_sig_subpkt( const subpktarea_t *pktbuf, sigsubpkttype_t reqtype,
1369     size_t *ret_n, int *start, int *critical )
1370     {
1371     const byte *buffer;
1372     int buflen;
1373     int type;
1374     int critical_dummy;
1375     int offset;
1376     size_t n;
1377     int seq = 0;
1378     int reqseq = start? *start: 0;
1379    
1380     if(!critical)
1381     critical=&critical_dummy;
1382    
1383     if( !pktbuf || reqseq == -1 ) {
1384     /* return some value different from NULL to indicate that
1385     * there is no critical bit we do not understand. The caller
1386     * will never use the value. Yes I know, it is an ugly hack */
1387     return reqtype == SIGSUBPKT_TEST_CRITICAL? (const byte*)&pktbuf : NULL;
1388     }
1389     buffer = pktbuf->data;
1390     buflen = pktbuf->len;
1391     while( buflen ) {
1392     n = *buffer++; buflen--;
1393     if( n == 255 ) { /* 4 byte length header */
1394     if( buflen < 4 )
1395     goto too_short;
1396     n = (buffer[0] << 24) | (buffer[1] << 16)
1397     | (buffer[2] << 8) | buffer[3];
1398     buffer += 4;
1399     buflen -= 4;
1400     }
1401     else if( n >= 192 ) { /* 2 byte special encoded length header */
1402     if( buflen < 2 )
1403     goto too_short;
1404     n = (( n - 192 ) << 8) + *buffer + 192;
1405     buffer++;
1406     buflen--;
1407     }
1408     if( buflen < n )
1409     goto too_short;
1410     type = *buffer;
1411     if( type & 0x80 ) {
1412     type &= 0x7f;
1413     *critical = 1;
1414     }
1415     else
1416     *critical = 0;
1417     if( !(++seq > reqseq) )
1418     ;
1419     else if( reqtype == SIGSUBPKT_TEST_CRITICAL ) {
1420     if( *critical ) {
1421     if( n-1 > buflen+1 )
1422     goto too_short;
1423     if( !can_handle_critical(buffer+1, n-1, type ) ) {
1424     printf("subpacket of type %d has critical bit set\n",
1425     type);
1426     if( start )
1427     *start = seq;
1428     return NULL; /* this is an error */
1429     }
1430     }
1431     }
1432     else if( reqtype < 0 ) /* list packets */
1433     dump_sig_subpkt( reqtype == SIGSUBPKT_LIST_HASHED,
1434     type, *critical, buffer, buflen, n );
1435     else if( type == reqtype ) { /* found */
1436     buffer++;
1437     n--;
1438     if( n > buflen )
1439     goto too_short;
1440     if( ret_n )
1441     *ret_n = n;
1442     offset = parse_one_sig_subpkt(buffer, n, type );
1443     switch( offset ) {
1444     case -3:
1445     printf("subpacket of type %d too short\n", type);
1446     return NULL;
1447     case -2:
1448     return NULL;
1449     case -1:
1450     printf( "This is a BUG.\n%s:%d\n", __FILE__, __LINE__ );
1451     exit( -1 );
1452     default:
1453     break;
1454     }
1455     if( start )
1456     *start = seq;
1457     return buffer+offset;
1458     }
1459     buffer += n; buflen -=n;
1460     }
1461     if( reqtype == SIGSUBPKT_TEST_CRITICAL )
1462     return buffer; /* as value true to indicate that there is no */
1463     /* critical bit we don't understand */
1464     if( start )
1465     *start = -1;
1466     return NULL; /* end of packets; not found */
1467    
1468     too_short:
1469     printf("buffer shorter than subpacket\n");
1470     if( start )
1471     *start = -1;
1472     return NULL;
1473     }
1474    
1475    
1476     const byte *
1477     gpg_parse_sig_subpkt (const subpktarea_t *buffer, sigsubpkttype_t reqtype,
1478     size_t *ret_n)
1479     {
1480     return enum_sig_subpkt( buffer, reqtype, ret_n, NULL, NULL );
1481     }
1482    
1483     const byte *
1484     gpg_parse_sig_subpkt2 (PKT_signature *sig, sigsubpkttype_t reqtype,
1485     size_t *ret_n )
1486     {
1487     const byte *p;
1488    
1489     p = gpg_parse_sig_subpkt (sig->hashed, reqtype, ret_n );
1490     if( !p )
1491     p = gpg_parse_sig_subpkt (sig->unhashed, reqtype, ret_n );
1492     return p;
1493     }
1494    
1495     /* Find all revocation keys. Look in hashed area only. */
1496     void parse_revkeys(PKT_signature *sig)
1497     {
1498     struct revocation_key *revkey;
1499     int seq=0;
1500     size_t len;
1501    
1502     if( sig->sig_class != 0x1F )
1503     return;
1504    
1505     while((revkey=
1506     (struct revocation_key *)enum_sig_subpkt(sig->hashed,
1507     SIGSUBPKT_REV_KEY,
1508     &len,&seq,NULL))) {
1509     if( len==sizeof(struct revocation_key) &&
1510     (revkey->rclass&0x80)) /* 0x80 bit must be set */ {
1511     sig->revkey=realloc(sig->revkey,
1512     sizeof(struct revocation_key *)*(sig->numrevkeys+1));
1513     sig->revkey[sig->numrevkeys]=revkey;
1514     sig->numrevkeys++;
1515     }
1516     }
1517     }
1518    
1519     static int
1520     parse_signature( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
1521     PKT_signature *sig )
1522     {
1523     int md5_len=0;
1524     unsigned n;
1525     int is_v4=0;
1526     int rc=0;
1527     int i, ndata;
1528    
1529     if( pktlen < 16 ) {
1530     printf("packet(%d) too short\n", pkttype);
1531     goto leave;
1532     }
1533     sig->version = gpg_iobuf_get_noeof(inp); pktlen--;
1534     if( sig->version == 4 )
1535     is_v4=1;
1536     else if( sig->version != 2 && sig->version != 3 ) {
1537     printf("packet(%d) with unknown version %d\n", pkttype, sig->version);
1538     rc = G10ERR_INVALID_PACKET;
1539     goto leave;
1540     }
1541    
1542     if( !is_v4 ) {
1543     md5_len = gpg_iobuf_get_noeof(inp); pktlen--;
1544     }
1545     sig->sig_class = gpg_iobuf_get_noeof(inp); pktlen--;
1546     if( !is_v4 ) {
1547     sig->timestamp = read_32(inp); pktlen -= 4;
1548     sig->keyid[0] = read_32(inp); pktlen -= 4;
1549     sig->keyid[1] = read_32(inp); pktlen -= 4;
1550     }
1551     sig->pubkey_algo = gpg_iobuf_get_noeof(inp); pktlen--;
1552     sig->digest_algo = gpg_iobuf_get_noeof(inp); pktlen--;
1553     sig->flags.exportable=1;
1554     sig->flags.revocable=1;
1555     if( is_v4 ) { /* read subpackets */
1556     n = read_16(inp); pktlen -= 2; /* length of hashed data */
1557     if( n > 10000 ) {
1558     printf("signature packet: hashed data too long\n");
1559     rc = G10ERR_INVALID_PACKET;
1560     goto leave;
1561     }
1562     if( n ) {
1563     sig->hashed = malloc (sizeof (*sig->hashed) + n - 1 );
1564     sig->hashed->size = n;
1565     sig->hashed->len = n;
1566     if( gpg_iobuf_read (inp, sig->hashed->data, n ) != n ) {
1567     printf ("premature eof while reading "
1568     "hashed signature data\n");
1569     rc = -1;
1570     goto leave;
1571     }
1572     pktlen -= n;
1573     }
1574     n = read_16(inp); pktlen -= 2; /* length of unhashed data */
1575     if( n > 10000 ) {
1576     printf("signature packet: unhashed data too long\n");
1577     rc = G10ERR_INVALID_PACKET;
1578     goto leave;
1579     }
1580     if( n ) {
1581     /* we add 8 extra bytes so that we have space for the signature
1582     * status cache. Well we are wastin this if there is a cache
1583     * packet already, but in the other case it avoids an realloc */
1584     sig->unhashed = malloc (sizeof(*sig->unhashed) + n + 8 - 1 );
1585     sig->unhashed->size = n + 8;
1586     sig->unhashed->len = n;
1587     if( gpg_iobuf_read(inp, sig->unhashed->data, n ) != n ) {
1588     printf("premature eof while reading "
1589     "unhashed signature data\n");
1590     rc = -1;
1591     goto leave;
1592     }
1593     pktlen -= n;
1594     }
1595     }
1596    
1597     if( pktlen < 5 ) { /* sanity check */
1598     printf("packet(%d) too short\n", pkttype);
1599     rc = G10ERR_INVALID_PACKET;
1600     goto leave;
1601     }
1602    
1603     sig->digest_start[0] = gpg_iobuf_get_noeof(inp); pktlen--;
1604     sig->digest_start[1] = gpg_iobuf_get_noeof(inp); pktlen--;
1605    
1606     if( is_v4 && sig->pubkey_algo ) { /*extract required information */
1607     const byte *p;
1608    
1609     /* set sig->flags.unknown_critical if there is a
1610     * critical bit set for packets which we do not understand */
1611     if( !gpg_parse_sig_subpkt (sig->hashed, SIGSUBPKT_TEST_CRITICAL, NULL)
1612     || !gpg_parse_sig_subpkt (sig->unhashed, SIGSUBPKT_TEST_CRITICAL,
1613     NULL) )
1614     {
1615     sig->flags.unknown_critical = 1;
1616     }
1617    
1618     p = gpg_parse_sig_subpkt (sig->hashed, SIGSUBPKT_SIG_CREATED, NULL );
1619     if( !p )
1620     printf("signature packet without timestamp\n");
1621     else
1622     sig->timestamp = buffer_to_u32(p);
1623     p = gpg_parse_sig_subpkt2( sig, SIGSUBPKT_ISSUER, NULL );
1624     if( !p )
1625     printf("signature packet without keyid\n");
1626     else {
1627     sig->keyid[0] = buffer_to_u32(p);
1628     sig->keyid[1] = buffer_to_u32(p+4);
1629     }
1630    
1631     p=gpg_parse_sig_subpkt(sig->hashed,SIGSUBPKT_SIG_EXPIRE,NULL);
1632     if(p)
1633     sig->expiredate=sig->timestamp+buffer_to_u32(p);
1634     if(sig->expiredate && sig->expiredate<=time(NULL))
1635     sig->flags.expired=1;
1636    
1637     p=gpg_parse_sig_subpkt(sig->hashed,SIGSUBPKT_POLICY,NULL);
1638     if(p)
1639     sig->flags.policy_url=1;
1640    
1641     p=gpg_parse_sig_subpkt(sig->hashed,SIGSUBPKT_NOTATION,NULL);
1642     if(p)
1643     sig->flags.notation=1;
1644    
1645     p=gpg_parse_sig_subpkt(sig->hashed,SIGSUBPKT_REVOCABLE,NULL);
1646     if(p && *p==0)
1647     sig->flags.revocable=0;
1648    
1649     /* We accept the exportable subpacket from either the hashed
1650     or unhashed areas as older versions of gpg put it in the
1651     unhashed area. In theory, anyway, we should never see this
1652     packet off of a local keyring. */
1653    
1654     p=gpg_parse_sig_subpkt2(sig,SIGSUBPKT_EXPORTABLE,NULL);
1655     if(p && *p==0)
1656     sig->flags.exportable=0;
1657    
1658     /* Find all revocation keys. */
1659     if(sig->sig_class==0x1F)
1660     parse_revkeys(sig);
1661     }
1662    
1663     if( list_mode ) {
1664     printf(":signature packet: algo %d, keyid %08lX%08lX\n"
1665     "\tversion %d, created %lu, md5len %d, sigclass %02x\n"
1666     "\tdigest algo %d, begin of digest %02x %02x\n",
1667     sig->pubkey_algo,
1668     (ulong)sig->keyid[0], (ulong)sig->keyid[1],
1669     sig->version, (ulong)sig->timestamp, md5_len, sig->sig_class,
1670     sig->digest_algo,
1671     sig->digest_start[0], sig->digest_start[1] );
1672     if( is_v4 ) {
1673     gpg_parse_sig_subpkt (sig->hashed, SIGSUBPKT_LIST_HASHED, NULL );
1674     gpg_parse_sig_subpkt (sig->unhashed, SIGSUBPKT_LIST_UNHASHED, NULL);
1675     }
1676     }
1677    
1678     ndata = pubkey_get_nsig(sig->pubkey_algo);
1679     if( !ndata ) {
1680     if( list_mode )
1681     printf("\tunknown algorithm %d\n", sig->pubkey_algo );
1682     unknown_pubkey_warning( sig->pubkey_algo );
1683     /* we store the plain material in data[0], so that we are able
1684     * to write it back with build_packet() */
1685     sig->data[0] = mpi_set_opaque(NULL, read_rest(inp, pktlen), pktlen );
1686     pktlen = 0;
1687     }
1688     else {
1689     for( i=0; i < ndata; i++ ) {
1690     n = pktlen;
1691     sig->data[i] = mpi_read(inp, &n, 0 );
1692     pktlen -=n;
1693     if( list_mode ) {
1694     printf("\tdata: ");
1695     mpi_print(stdout, sig->data[i], mpi_print_mode );
1696     putchar('\n');
1697     }
1698     if (!sig->data[i])
1699     rc = G10ERR_INVALID_PACKET;
1700     }
1701     }
1702    
1703     leave:
1704     skip_rest(inp, pktlen);
1705     return rc;
1706     }
1707    
1708    
1709     static int
1710     parse_onepass_sig( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
1711     PKT_onepass_sig *ops )
1712     {
1713     int version;
1714     int rc = 0;
1715    
1716     if( pktlen < 13 ) {
1717     printf("packet(%d) too short\n", pkttype);
1718     rc = G10ERR_INVALID_PACKET;
1719     goto leave;
1720     }
1721     version = gpg_iobuf_get_noeof(inp); pktlen--;
1722     if( version != 3 ) {
1723     printf("onepass_sig with unknown version %d\n", version);
1724     rc = G10ERR_INVALID_PACKET;
1725     goto leave;
1726     }
1727     ops->sig_class = gpg_iobuf_get_noeof(inp); pktlen--;
1728     ops->digest_algo = gpg_iobuf_get_noeof(inp); pktlen--;
1729     ops->pubkey_algo = gpg_iobuf_get_noeof(inp); pktlen--;
1730     ops->keyid[0] = read_32(inp); pktlen -= 4;
1731     ops->keyid[1] = read_32(inp); pktlen -= 4;
1732     ops->last = gpg_iobuf_get_noeof(inp); pktlen--;
1733     if( list_mode )
1734     printf(":onepass_sig packet: keyid %08lX%08lX\n"
1735     "\tversion %d, sigclass %02x, digest %d, pubkey %d, last=%d\n",
1736     (ulong)ops->keyid[0], (ulong)ops->keyid[1],
1737     version, ops->sig_class,
1738     ops->digest_algo, ops->pubkey_algo, ops->last );
1739    
1740    
1741     leave:
1742     skip_rest(inp, pktlen);
1743     return rc;
1744     }
1745    
1746    
1747     static int
1748     parse_key( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
1749     byte *hdr, int hdrlen, PACKET *pkt )
1750     {
1751     int i, version, algorithm;
1752     unsigned n;
1753     unsigned long timestamp, expiredate, max_expiredate;
1754     int npkey, nskey;
1755     int is_v4=0;
1756     int rc=0;
1757    
1758     version = gpg_iobuf_get_noeof(inp); pktlen--;
1759     if( pkttype == PKT_PUBLIC_SUBKEY && version == '#' ) {
1760     /* early versions of G10 use old PGP comments packets;
1761     * luckily all those comments are started by a hash */
1762     if( list_mode ) {
1763     printf(":rfc1991 comment packet: \"" );
1764     for( ; pktlen; pktlen-- ) {
1765     int c;
1766     c = gpg_iobuf_get_noeof(inp);
1767     if( c >= ' ' && c <= 'z' )
1768     putchar(c);
1769     else
1770     printf("\\x%02x", c );
1771     }
1772     printf("\"\n");
1773     }
1774     skip_rest(inp, pktlen);
1775     return 0;
1776     }
1777     else if( version == 4 )
1778     is_v4=1;
1779     else if( version != 2 && version != 3 ) {
1780     printf("packet(%d) with unknown version %d\n", pkttype, version);
1781     rc = G10ERR_INVALID_PACKET;
1782     goto leave;
1783     }
1784    
1785     if( pktlen < 11 ) {
1786     printf("packet(%d) too short\n", pkttype);
1787     rc = G10ERR_INVALID_PACKET;
1788     goto leave;
1789     }
1790    
1791     timestamp = read_32(inp); pktlen -= 4;
1792     if( is_v4 ) {
1793     expiredate = 0; /* have to get it from the selfsignature */
1794     max_expiredate = 0;
1795     }
1796     else {
1797     unsigned short ndays;
1798     ndays = read_16(inp); pktlen -= 2;
1799     if( ndays )
1800     expiredate = timestamp + ndays * 86400L;
1801     else
1802     expiredate = 0;
1803    
1804     max_expiredate=expiredate;
1805     }
1806     algorithm = gpg_iobuf_get_noeof(inp); pktlen--;
1807     if( list_mode )
1808     printf(":%s key packet:\n"
1809     "\tversion %d, algo %d, created %lu, expires %lu\n",
1810     pkttype == PKT_PUBLIC_KEY? "public" :
1811     pkttype == PKT_SECRET_KEY? "secret" :
1812     pkttype == PKT_PUBLIC_SUBKEY? "public sub" :
1813     pkttype == PKT_SECRET_SUBKEY? "secret sub" : "??",
1814     version, algorithm, timestamp, expiredate );
1815    
1816     if( pkttype == PKT_SECRET_KEY || pkttype == PKT_SECRET_SUBKEY ) {
1817     PKT_secret_key *sk = pkt->pkt.secret_key;
1818    
1819     sk->timestamp = timestamp;
1820     sk->expiredate = expiredate;
1821     sk->max_expiredate = max_expiredate;
1822     sk->hdrbytes = hdrlen;
1823     sk->version = version;
1824     sk->is_primary = pkttype == PKT_SECRET_KEY;
1825     sk->pubkey_algo = algorithm;
1826     sk->req_usage = 0;
1827     sk->pubkey_usage = 0; /* not yet used */
1828     }
1829     else {
1830     PKT_public_key *pk = pkt->pkt.public_key;
1831    
1832     pk->timestamp = timestamp;
1833     pk->expiredate = expiredate;
1834     pk->max_expiredate = max_expiredate;
1835     pk->hdrbytes = hdrlen;
1836     pk->version = version;
1837     pk->is_primary = pkttype == PKT_PUBLIC_KEY;
1838     pk->pubkey_algo = algorithm;
1839     pk->req_usage = 0;
1840     pk->pubkey_usage = 0; /* not yet used */
1841     pk->is_revoked = 0;
1842     pk->keyid[0] = 0;
1843     pk->keyid[1] = 0;
1844     }
1845     nskey = pubkey_get_nskey( algorithm );
1846     npkey = pubkey_get_npkey( algorithm );
1847     if( !npkey ) {
1848     if( list_mode )
1849     printf("\tunknown algorithm %d\n", algorithm );
1850     unknown_pubkey_warning( algorithm );
1851     }
1852    
1853    
1854     if( pkttype == PKT_SECRET_KEY || pkttype == PKT_SECRET_SUBKEY ) {
1855     PKT_secret_key *sk = pkt->pkt.secret_key;
1856     byte temp[16];
1857     size_t snlen = 0;
1858    
1859     if( !npkey ) {
1860     sk->skey[0] = mpi_set_opaque( NULL,
1861     read_rest(inp, pktlen), pktlen );
1862     pktlen = 0;
1863     goto leave;
1864     }
1865    
1866     for(i=0; i < npkey; i++ ) {
1867     n = pktlen; sk->skey[i] = mpi_read(inp, &n, 0 ); pktlen -=n;
1868     if( list_mode ) {
1869     printf( "\tskey[%d]: ", i);
1870     mpi_print(stdout, sk->skey[i], mpi_print_mode );
1871     putchar('\n');
1872     }
1873     if (!sk->skey[i])
1874     rc = G10ERR_INVALID_PACKET;
1875     }
1876     if (rc) /* one of the MPIs were bad */
1877     goto leave;
1878     sk->protect.algo = gpg_iobuf_get_noeof(inp); pktlen--;
1879     sk->protect.sha1chk = 0;
1880     if( sk->protect.algo ) {
1881     sk->is_protected = 1;
1882     sk->protect.s2k.count = 0;
1883     if( sk->protect.algo == 254 || sk->protect.algo == 255 ) {
1884     if( pktlen < 3 ) {
1885     rc = G10ERR_INVALID_PACKET;
1886     goto leave;
1887     }
1888     sk->protect.sha1chk = (sk->protect.algo == 254);
1889     sk->protect.algo = gpg_iobuf_get_noeof(inp); pktlen--;
1890     /* Note that a sk->protect.algo > 110 is illegal, but
1891     I'm not erroring on it here as otherwise there
1892     would be no way to delete such a key. */
1893     sk->protect.s2k.mode = gpg_iobuf_get_noeof(inp); pktlen--;
1894     sk->protect.s2k.hash_algo = gpg_iobuf_get_noeof(inp); pktlen--;
1895     /* check for the special GNU extension */
1896     if( is_v4 && sk->protect.s2k.mode == 101 ) {
1897     for(i=0; i < 4 && pktlen; i++, pktlen-- )
1898     temp[i] = gpg_iobuf_get_noeof(inp);
1899     if( i < 4 || memcmp( temp, "GNU", 3 ) ) {
1900     if( list_mode )
1901     printf( "\tunknown S2K %d\n",
1902     sk->protect.s2k.mode );
1903     rc = G10ERR_INVALID_PACKET;
1904     goto leave;
1905     }
1906     /* here we know that it is a gnu extension
1907     * What follows is the GNU protection mode:
1908     * All values have special meanings
1909     * and they are mapped in the mode with a base of 1000.
1910     */
1911     sk->protect.s2k.mode = 1000 + temp[3];
1912     }
1913     switch( sk->protect.s2k.mode ) {
1914     case 1:
1915     case 3:
1916     for(i=0; i < 8 && pktlen; i++, pktlen-- )
1917     temp[i] = gpg_iobuf_get_noeof(inp);
1918     memcpy(sk->protect.s2k.salt, temp, 8 );
1919     break;
1920     }
1921     switch( sk->protect.s2k.mode ) {
1922     case 0: if( list_mode ) printf( "\tsimple S2K" );
1923     break;
1924     case 1: if( list_mode ) printf( "\tsalted S2K" );
1925     break;
1926     case 3: if( list_mode ) printf( "\titer+salt S2K" );
1927     break;
1928     case 1001: if( list_mode ) printf( "\tgnu-dummy S2K" );
1929     break;
1930     case 1002: if (list_mode) printf("\tgnu-divert-to-card S2K");
1931     break;
1932     default:
1933     if( list_mode )
1934     printf( "\tunknown %sS2K %d\n",
1935     sk->protect.s2k.mode < 1000? "":"GNU ",
1936     sk->protect.s2k.mode );
1937     rc = G10ERR_INVALID_PACKET;
1938     goto leave;
1939     }
1940    
1941     if( list_mode ) {
1942     printf(", algo: %d,%s hash: %d",
1943     sk->protect.algo,
1944     sk->protect.sha1chk?" SHA1 protection,"
1945     :" simple checksum,",
1946     sk->protect.s2k.hash_algo );
1947     if( sk->protect.s2k.mode == 1
1948     || sk->protect.s2k.mode == 3 ) {
1949     printf(", salt: ");
1950     for(i=0; i < 8; i++ )
1951     printf("%02x", sk->protect.s2k.salt[i]);
1952     }
1953     putchar('\n');
1954     }
1955    
1956     if( sk->protect.s2k.mode == 3 ) {
1957     if( pktlen < 1 ) {
1958     rc = G10ERR_INVALID_PACKET;
1959     goto leave;
1960     }
1961     sk->protect.s2k.count = gpg_iobuf_get(inp);
1962     pktlen--;
1963     if( list_mode )
1964     printf("\tprotect count: %lu\n",
1965     (ulong)sk->protect.s2k.count);
1966     }
1967     else if( sk->protect.s2k.mode == 1002 ) {
1968     /* Read the serial number. */
1969     if (pktlen < 1) {
1970     rc = G10ERR_INVALID_PACKET;
1971     goto leave;
1972     }
1973     snlen = gpg_iobuf_get (inp);
1974     pktlen--;
1975     if (pktlen < snlen || snlen == -1) {
1976     rc = G10ERR_INVALID_PACKET;
1977     goto leave;
1978     }
1979     }
1980     }
1981     /* Note that a sk->protect.algo > 110 is illegal, but I'm
1982     not erroring on it here as otherwise there would be no
1983     way to delete such a key. */
1984     else { /* old version; no S2K, so we set mode to 0, hash MD5 */
1985     sk->protect.s2k.mode = 0;
1986     sk->protect.s2k.hash_algo = DIGEST_ALGO_MD5;
1987     if( list_mode )
1988     printf( "\tprotect algo: %d (hash algo: %d)\n",
1989     sk->protect.algo, sk->protect.s2k.hash_algo );
1990     }
1991     /* It is really ugly that we don't know the size
1992     * of the IV here in cases we are not aware of the algorithm.
1993     * so a
1994     * sk->protect.ivlen = cipher_get_blocksize(sk->protect.algo);
1995     * won't work. The only solution I see is to hardwire it here.
1996     * NOTE: if you change the ivlen above 16, don't forget to
1997     * enlarge temp.
1998     */
1999     switch( sk->protect.algo ) {
2000     case 7: case 8: case 9: /* reserved for AES */
2001     case 10: /* Twofish */
2002     sk->protect.ivlen = 16;
2003     break;
2004     default:
2005     sk->protect.ivlen = 8;
2006     }
2007     if( sk->protect.s2k.mode == 1001 )
2008     sk->protect.ivlen = 0;
2009     else if( sk->protect.s2k.mode == 1002 )
2010     sk->protect.ivlen = snlen < 16? snlen : 16;
2011    
2012     if( pktlen < sk->protect.ivlen ) {
2013     rc = G10ERR_INVALID_PACKET;
2014     goto leave;
2015     }
2016     for(i=0; i < sk->protect.ivlen && pktlen; i++, pktlen-- )
2017     temp[i] = gpg_iobuf_get_noeof(inp);
2018     if( list_mode ) {
2019     printf( sk->protect.s2k.mode == 1002? "\tserial-number: "
2020     : "\tprotect IV: ");
2021     for(i=0; i < sk->protect.ivlen; i++ )
2022     printf(" %02x", temp[i] );
2023     putchar('\n');
2024     }
2025     memcpy( sk->protect.iv, temp, sk->protect.ivlen );
2026     }
2027     else
2028     sk->is_protected = 0;
2029     /* It does not make sense to read it into secure memory.
2030     * If the user is so careless, not to protect his secret key,
2031     * we can assume, that he operates an open system :=(.
2032     * So we put the key into secure memory when we unprotect it. */
2033     if( sk->protect.s2k.mode == 1001
2034     || sk->protect.s2k.mode == 1002 ) {
2035     /* better set some dummy stuff here */
2036     sk->skey[npkey] = mpi_set_opaque(NULL, strdup("dummydata"), 10);
2037     pktlen = 0;
2038     }
2039     else if( is_v4 && sk->is_protected ) {
2040     /* ugly; the length is encrypted too, so we read all
2041     * stuff up to the end of the packet into the first
2042     * skey element */
2043     sk->skey[npkey] = mpi_set_opaque(NULL,
2044     read_rest(inp, pktlen), pktlen );
2045     pktlen = 0;
2046     if( list_mode ) {
2047     printf("\tencrypted stuff follows\n");
2048     }
2049     }
2050     else { /* v3 method: the mpi length is not encrypted */
2051     for(i=npkey; i < nskey; i++ ) {
2052     n = pktlen; sk->skey[i] = mpi_read(inp, &n, 0 ); pktlen -=n;
2053     if( sk->is_protected && sk->skey[i] )
2054     mpi_set_protect_flag(sk->skey[i]);
2055     if( list_mode ) {
2056     printf( "\tskey[%d]: ", i);
2057     if( sk->is_protected )
2058     printf( "[encrypted]\n");
2059     else {
2060     mpi_print(stdout, sk->skey[i], mpi_print_mode );
2061     putchar('\n');
2062     }
2063     }
2064     if (!sk->skey[i])
2065     rc = G10ERR_INVALID_PACKET;
2066     }
2067     if (rc)
2068     goto leave;
2069    
2070     sk->csum = read_16(inp); pktlen -= 2;
2071     if( list_mode ) {
2072     printf("\tchecksum: %04hx\n", sk->csum);
2073     }
2074     }
2075     }
2076     else {
2077     PKT_public_key *pk = pkt->pkt.public_key;
2078    
2079     if( !npkey ) {
2080     pk->pkey[0] = mpi_set_opaque( NULL,
2081     read_rest(inp, pktlen), pktlen );
2082     pktlen = 0;
2083     goto leave;
2084     }
2085    
2086     for(i=0; i < npkey; i++ ) {
2087     n = pktlen; pk->pkey[i] = mpi_read(inp, &n, 0 ); pktlen -=n;
2088     if( list_mode ) {
2089     printf( "\tpkey[%d]: ", i);
2090     mpi_print(stdout, pk->pkey[i], mpi_print_mode );
2091     putchar('\n');
2092     }
2093     if (!pk->pkey[i])
2094     rc = G10ERR_INVALID_PACKET;
2095     }
2096     if (rc)
2097     goto leave;
2098     }
2099    
2100     leave:
2101     skip_rest(inp, pktlen);
2102     return rc;
2103     }
2104    
2105     /* Attribute subpackets have the same format as v4 signature
2106     subpackets. This is not part of OpenPGP, but is done in several
2107     versions of PGP nevertheless. */
2108     int
2109     parse_attribute_subpkts(PKT_user_id *uid)
2110     {
2111     size_t n;
2112     int count=0;
2113     struct user_attribute *attribs=NULL;
2114     const byte *buffer=uid->attrib_data;
2115     int buflen=uid->attrib_len;
2116     byte type;
2117    
2118     safe_free(uid->attribs);
2119    
2120     while(buflen) {
2121     n = *buffer++; buflen--;
2122     if( n == 255 ) { /* 4 byte length header */
2123     if( buflen < 4 )
2124     goto too_short;
2125     n = (buffer[0] << 24) | (buffer[1] << 16)
2126     | (buffer[2] << 8) | buffer[3];
2127     buffer += 4;
2128     buflen -= 4;
2129     }
2130     else if( n >= 192 ) { /* 2 byte special encoded length header */
2131     if( buflen < 2 )
2132     goto too_short;
2133     n = (( n - 192 ) << 8) + *buffer + 192;
2134     buffer++;
2135     buflen--;
2136     }
2137     if( buflen < n )
2138     goto too_short;
2139    
2140     attribs=realloc(attribs,(count+1)*sizeof(struct user_attribute));
2141     memset(&attribs[count],0,sizeof(struct user_attribute));
2142    
2143     type=*buffer;
2144     buffer++;
2145     buflen--;
2146     n--;
2147    
2148     attribs[count].type=type;
2149     attribs[count].data=buffer;
2150     attribs[count].len=n;
2151     buffer+=n;
2152     buflen-=n;
2153     count++;
2154     }
2155    
2156     uid->attribs=attribs;
2157     uid->numattribs=count;
2158     return count;
2159    
2160     too_short:
2161     printf("buffer shorter than attribute subpacket\n");
2162     uid->attribs=attribs;
2163     uid->numattribs=count;
2164     return count;
2165     }
2166    
2167     static void
2168     setup_user_id(PACKET *packet)
2169     {
2170     packet->pkt.user_id->ref = 1;
2171     packet->pkt.user_id->attribs = NULL;
2172     packet->pkt.user_id->attrib_data = NULL;
2173     packet->pkt.user_id->attrib_len = 0;
2174     packet->pkt.user_id->is_primary = 0;
2175     packet->pkt.user_id->is_revoked = 0;
2176     packet->pkt.user_id->is_expired = 0;
2177     packet->pkt.user_id->expiredate = 0;
2178     packet->pkt.user_id->created = 0;
2179     packet->pkt.user_id->help_key_usage = 0;
2180     packet->pkt.user_id->help_key_expire = 0;
2181     packet->pkt.user_id->prefs = NULL;
2182     }
2183    
2184     static int
2185     parse_user_id( gpg_iobuf_t inp, int pkttype, unsigned long pktlen, PACKET *packet )
2186     {
2187     byte *p;
2188    
2189     packet->pkt.user_id = malloc(sizeof *packet->pkt.user_id + pktlen);
2190     packet->pkt.user_id->len = pktlen;
2191    
2192     setup_user_id(packet);
2193    
2194     p = packet->pkt.user_id->name;
2195     for( ; pktlen; pktlen--, p++ )
2196     *p = gpg_iobuf_get_noeof(inp);
2197     *p = 0;
2198    
2199     if( list_mode ) {
2200     int n = packet->pkt.user_id->len;
2201     printf(":user ID packet: \"");
2202     /* fixme: Hey why don't we replace this with print_string?? */
2203     for(p=packet->pkt.user_id->name; n; p++, n-- ) {
2204     if( *p >= ' ' && *p <= 'z' )
2205     putchar(*p);
2206     else
2207     printf("\\x%02x", *p );
2208     }
2209     printf("\"\n");
2210     }
2211     return 0;
2212     }
2213    
2214     /* Returns 0 for error, 1 for valid */
2215     int parse_image_header(const struct user_attribute *attr,byte *type,u32 *len)
2216     {
2217     u16 headerlen;
2218    
2219     if(attr->len<3)
2220     return 0;
2221    
2222     /* For historical reasons (i.e. "oops!"), the header length is
2223     little endian. */
2224     headerlen=(attr->data[1]<<8) | attr->data[0];
2225    
2226     if(headerlen>attr->len)
2227     return 0;
2228    
2229     if(type && attr->len>=4)
2230     {
2231     if(attr->data[2]==1) /* header version 1 */
2232     *type=attr->data[3];
2233     else
2234     *type=0;
2235     }
2236    
2237     *len=attr->len-headerlen;
2238    
2239     if(*len==0)
2240     return 0;
2241    
2242     return 1;
2243     }
2244    
2245     /* style==0 for extension, 1 for name, 2 for MIME type. Remember that
2246     the "name" style string could be used in a user ID name field, so
2247     make sure it is not too big (see
2248     parse-packet.c:parse_attribute). */
2249     char *image_type_to_string(byte type,int style)
2250     {
2251     char *string;
2252    
2253     switch(type) {
2254     case 1: /* jpeg */
2255     if(style==0)
2256     string="jpg";
2257     else if(style==1)
2258     string="jpeg";
2259     else
2260     string="image/jpeg";
2261     break;
2262    
2263     default:
2264     if(style==0)
2265     string="bin";
2266     else if(style==1)
2267     string="unknown";
2268     else
2269     string="image/x-unknown";
2270     break;
2271     }
2272    
2273     return string;
2274     }
2275    
2276     void
2277     make_attribute_uidname(PKT_user_id *uid)
2278     {
2279     if(uid->numattribs<=0)
2280     sprintf(uid->name,"[bad attribute packet of size %lu]",uid->attrib_len);
2281     else if(uid->numattribs>1)
2282     sprintf(uid->name,"[%d attributes of size %lu]",
2283     uid->numattribs,uid->attrib_len);
2284     else {
2285     /* Only one attribute, so list it as the "user id" */
2286    
2287     if(uid->attribs->type==ATTRIB_IMAGE) {
2288     u32 len;
2289     byte type;
2290    
2291     if(parse_image_header(uid->attribs,&type,&len))
2292     sprintf(uid->name,"[%s image of size %lu]",
2293     image_type_to_string(type,1),(ulong)len);
2294     else
2295     sprintf(uid->name,"[invalid image]");
2296     }
2297     else
2298     sprintf(uid->name,"[unknown attribute of size %lu]",
2299     (ulong)uid->attribs->len);
2300     }
2301    
2302     uid->len = strlen(uid->name);
2303     }
2304    
2305     static int
2306     parse_attribute( gpg_iobuf_t inp, int pkttype, unsigned long pktlen, PACKET *packet )
2307     {
2308     byte *p;
2309    
2310     packet->pkt.user_id = malloc(sizeof *packet->pkt.user_id + 70);
2311    
2312     setup_user_id(packet);
2313    
2314     packet->pkt.user_id->attrib_data = malloc(pktlen);
2315     packet->pkt.user_id->attrib_len = pktlen;
2316     p = packet->pkt.user_id->attrib_data;
2317     for( ; pktlen; pktlen--, p++ )
2318     *p = gpg_iobuf_get_noeof(inp);
2319    
2320     /* Now parse out the individual attribute subpackets. This is
2321     somewhat pointless since there is only one currently defined
2322     attribute type (jpeg), but it is correct by the spec. */
2323     parse_attribute_subpkts(packet->pkt.user_id);
2324    
2325     make_attribute_uidname(packet->pkt.user_id);
2326    
2327     if( list_mode ) {
2328     printf(":attribute packet: %s\n", packet->pkt.user_id->name );
2329     }
2330     return 0;
2331     }
2332    
2333    
2334     static int
2335     parse_comment( gpg_iobuf_t inp, int pkttype, unsigned long pktlen, PACKET *packet )
2336     {
2337     byte *p;
2338    
2339     packet->pkt.comment = malloc(sizeof *packet->pkt.comment + pktlen - 1);
2340     packet->pkt.comment->len = pktlen;
2341     p = packet->pkt.comment->data;
2342     for( ; pktlen; pktlen--, p++ )
2343     *p = gpg_iobuf_get_noeof(inp);
2344    
2345     if( list_mode ) {
2346     int n = packet->pkt.comment->len;
2347     printf(":%scomment packet: \"", pkttype == PKT_OLD_COMMENT?
2348     "OpenPGP draft " : "" );
2349     for(p=packet->pkt.comment->data; n; p++, n-- ) {
2350     if( *p >= ' ' && *p <= 'z' )
2351     putchar(*p);
2352     else
2353     printf("\\x%02x", *p );
2354     }
2355     printf("\"\n");
2356     }
2357     return 0;
2358     }
2359    
2360    
2361     static void
2362     parse_trust( gpg_iobuf_t inp, int pkttype, unsigned long pktlen, PACKET *pkt )
2363     {
2364     int c;
2365    
2366     if (pktlen) {
2367     c = gpg_iobuf_get_noeof(inp);
2368     pktlen--;
2369     pkt->pkt.ring_trust = malloc( sizeof *pkt->pkt.ring_trust );
2370     pkt->pkt.ring_trust->trustval = c;
2371     pkt->pkt.ring_trust->sigcache = 0;
2372     if (!c && pktlen==1) {
2373     c = gpg_iobuf_get_noeof (inp);
2374     pktlen--;
2375     /* we require that bit 7 of the sigcache is 0 (easier eof handling)*/
2376     if ( !(c & 0x80) )
2377     pkt->pkt.ring_trust->sigcache = c;
2378     }
2379     if( list_mode )
2380     printf(":trust packet: flag=%02x sigcache=%02x\n",
2381     pkt->pkt.ring_trust->trustval,
2382     pkt->pkt.ring_trust->sigcache);
2383     }
2384     else {
2385     if( list_mode )
2386     printf(":trust packet: empty\n");
2387     }
2388     skip_rest (inp, pktlen);
2389     }
2390    
2391    
2392     static int
2393     parse_plaintext( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
2394     PACKET *pkt, int new_ctb )
2395     {
2396     int rc = 0;
2397     int mode, namelen, partial=0;
2398     PKT_plaintext *pt;
2399     byte *p;
2400     int c, i;
2401    
2402     if( pktlen && pktlen < 6 ) {
2403     printf("packet(%d) too short (%lu)\n", pkttype, (ulong)pktlen);
2404     rc = G10ERR_INVALID_PACKET;
2405     goto leave;
2406     }
2407     /* A packet length of zero indicates partial body length. A zero
2408     data length isn't a zero length packet due to the header (mode,
2409     name, etc), so this is accurate. */
2410     if(pktlen==0)
2411     partial=1;
2412     mode = gpg_iobuf_get_noeof(inp); if( pktlen ) pktlen--;
2413     namelen = gpg_iobuf_get_noeof(inp); if( pktlen ) pktlen--;
2414     pt = pkt->pkt.plaintext = malloc(sizeof *pkt->pkt.plaintext + namelen -1);
2415     pt->new_ctb = new_ctb;
2416     pt->mode = mode;
2417     pt->namelen = namelen;
2418     pt->is_partial = partial;
2419     if( pktlen ) {
2420     for( i=0; pktlen > 4 && i < namelen; pktlen--, i++ )
2421     pt->name[i] = gpg_iobuf_get_noeof(inp);
2422     }
2423     else {
2424     for( i=0; i < namelen; i++ )
2425     if( (c=gpg_iobuf_get(inp)) == -1 )
2426     break;
2427     else
2428     pt->name[i] = c;
2429     }
2430     pt->timestamp = read_32(inp); if( pktlen) pktlen -= 4;
2431     pt->len = pktlen;
2432     pt->buf = inp;
2433     pktlen = 0;
2434    
2435     if( list_mode ) {
2436     printf(":literal data packet:\n"
2437     "\tmode %c, created %lu, name=\"",
2438     mode >= ' ' && mode <'z'? mode : '?',
2439     (ulong)pt->timestamp );
2440     for(p=pt->name,i=0; i < namelen; p++, i++ ) {
2441     if( *p >= ' ' && *p <= 'z' )
2442     putchar(*p);
2443     else
2444     printf("\\x%02x", *p );
2445     }
2446     printf("\",\n\traw data: %lu bytes\n", (ulong)pt->len );
2447     }
2448    
2449     leave:
2450     return rc;
2451     }
2452    
2453    
2454     static int
2455     parse_compressed( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
2456     PACKET *pkt, int new_ctb )
2457     {
2458     PKT_compressed *zd;
2459    
2460     /* pktlen is here 0, but data follows
2461     * (this should be the last object in a file or
2462     * the compress algorithm should know the length)
2463     */
2464     zd = pkt->pkt.compressed = malloc(sizeof *pkt->pkt.compressed );
2465     zd->algorithm = gpg_iobuf_get_noeof(inp);
2466     zd->len = 0; /* not used */
2467     zd->new_ctb = new_ctb;
2468     zd->buf = inp;
2469     if( list_mode )
2470     printf(":compressed packet: algo=%d\n", zd->algorithm);
2471     return 0;
2472     }
2473    
2474    
2475     static int
2476     parse_encrypted( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
2477     PACKET *pkt, int new_ctb )
2478     {
2479     int rc = 0;
2480     PKT_encrypted *ed;
2481     unsigned long orig_pktlen = pktlen;
2482    
2483     ed = pkt->pkt.encrypted = malloc(sizeof *pkt->pkt.encrypted );
2484     ed->len = pktlen;
2485     /* we don't know the extralen which is (cipher_blocksize+2)
2486     because the algorithm ist not specified in this packet.
2487     However, it is only important to know this for some sanity
2488     checks on the packet length - it doesn't matter that we can't
2489     do it */
2490     ed->extralen = 0;
2491     ed->buf = NULL;
2492     ed->new_ctb = new_ctb;
2493     ed->mdc_method = 0;
2494     if( pkttype == PKT_ENCRYPTED_MDC ) {
2495     /* fixme: add some pktlen sanity checks */
2496     int version;
2497    
2498     version = gpg_iobuf_get_noeof(inp);
2499     if (orig_pktlen)
2500     pktlen--;
2501     if( version != 1 ) {
2502     printf("encrypted_mdc packet with unknown version %d\n",
2503     version);
2504     /*skip_rest(inp, pktlen); should we really do this? */
2505     rc = G10ERR_INVALID_PACKET;
2506     goto leave;
2507     }
2508     ed->mdc_method = DIGEST_ALGO_SHA1;
2509     }
2510     if( orig_pktlen && pktlen < 10 ) { /* actually this is blocksize+2 */
2511     printf("packet(%d) too short\n", pkttype);
2512     rc = G10ERR_INVALID_PACKET;
2513     skip_rest(inp, pktlen);
2514     goto leave;
2515     }
2516     if( list_mode ) {
2517     if( orig_pktlen )
2518     printf(":encrypted data packet:\n\tlength: %lu\n", orig_pktlen);
2519     else
2520     printf(":encrypted data packet:\n\tlength: unknown\n");
2521     if( ed->mdc_method )
2522     printf("\tmdc_method: %d\n", ed->mdc_method );
2523     }
2524    
2525     ed->buf = inp;
2526     pktlen = 0;
2527    
2528     leave:
2529     return rc;
2530     }
2531    
2532    
2533     static int
2534     parse_mdc( gpg_iobuf_t inp, int pkttype, unsigned long pktlen,
2535     PACKET *pkt, int new_ctb )
2536     {
2537     int rc = 0;
2538     PKT_mdc *mdc;
2539     byte *p;
2540    
2541     mdc = pkt->pkt.mdc= malloc(sizeof *pkt->pkt.mdc );
2542     if( list_mode )
2543     printf(":mdc packet: length=%lu\n", pktlen);
2544     if( !new_ctb || pktlen != 20 ) {
2545     printf("mdc_packet with invalid encoding\n");
2546     rc = G10ERR_INVALID_PACKET;
2547     goto leave;
2548     }
2549     p = mdc->hash;
2550     for( ; pktlen; pktlen--, p++ )
2551     *p = gpg_iobuf_get_noeof(inp);
2552    
2553     leave:
2554     return rc;
2555     }
2556    
2557    
2558     /*
2559     * This packet is internally generated by PGG (by armor.c) to
2560     * transfer some information to the lower layer. To make sure that
2561     * this packet is really a GPG faked one and not one comming from outside,
2562     * we first check that tehre is a unique tag in it.
2563     * The format of such a control packet is:
2564     * n byte session marker
2565     * 1 byte control type CTRLPKT_xxxxx
2566     * m byte control data
2567     */
2568    
2569     /* Return a string which is used as a kind of process ID */
2570     const byte *
2571     get_session_marker( size_t *rlen )
2572     {
2573     static byte marker[SIZEOF_UNSIGNED_LONG*2];
2574     static int initialized;
2575    
2576     if ( !initialized ) {
2577     volatile ulong aa, bb; /* we really want the uninitialized value */
2578     ulong a, b;
2579    
2580     initialized = 1;
2581     /* also this marker is guessable it is not easy to use this
2582     * for a faked control packet because an attacker does not
2583     * have enough control about the time the verification does
2584     * take place. Of course, we can add just more random but
2585     * than we need the random generator even for verification
2586     * tasks - which does not make sense. */
2587     a = aa ^ (ulong)getpid();
2588     b = bb ^ (ulong)time(NULL);
2589     memcpy( marker, &a, SIZEOF_UNSIGNED_LONG );
2590     memcpy( marker+SIZEOF_UNSIGNED_LONG, &b, SIZEOF_UNSIGNED_LONG );
2591     }
2592     *rlen = sizeof(marker);
2593     return marker;
2594     }
2595    
2596     static int
2597     parse_gpg_control( gpg_iobuf_t inp,
2598     int pkttype, unsigned long pktlen, PACKET *packet )
2599     {
2600     byte *p;
2601     const byte *sesmark;
2602     size_t sesmarklen;
2603     int i;
2604    
2605     if ( list_mode )
2606     printf(":packet 63: length %lu ", pktlen);
2607    
2608     sesmark = get_session_marker ( &sesmarklen );
2609     if ( pktlen < sesmarklen+1 ) /* 1 is for the control bytes */
2610     goto skipit;
2611     for( i=0; i < sesmarklen; i++, pktlen-- ) {
2612     if ( sesmark[i] != gpg_iobuf_get_noeof(inp) )
2613     goto skipit;
2614     }
2615     if ( list_mode )
2616     puts ("- gpg control packet");
2617    
2618     packet->pkt.gpg_control = malloc(sizeof *packet->pkt.gpg_control
2619     + pktlen - 1);
2620     packet->pkt.gpg_control->control = gpg_iobuf_get_noeof(inp); pktlen--;
2621     packet->pkt.gpg_control->datalen = pktlen;
2622     p = packet->pkt.gpg_control->data;
2623     for( ; pktlen; pktlen--, p++ )
2624     *p = gpg_iobuf_get_noeof(inp);
2625    
2626     return 0;
2627    
2628     skipit:
2629     if ( list_mode ) {
2630     int c;
2631    
2632     i=0;
2633     printf("- private (rest length %lu)\n", pktlen);
2634     if( gpg_iobuf_in_block_mode(inp) ) {
2635     while( (c=gpg_iobuf_get(inp)) != -1 )
2636     dump_hex_line(c, &i);
2637     }
2638     else {
2639     for( ; pktlen; pktlen-- )
2640     dump_hex_line(gpg_iobuf_get(inp), &i);
2641     }
2642     putchar('\n');
2643     }
2644     skip_rest(inp,pktlen);
2645     return G10ERR_INVALID_PACKET;
2646     }
2647    
2648    
2649     u32
2650     gpg_keyid_from_pk( PKT_public_key * pk, byte *fprint )
2651     {
2652     gpg_md_t md;
2653     int npkey, pktlen, i;
2654     const byte *mdbuf;
2655    
2656     if( pk->version == 3 && pk->pubkey_algo == PUBKEY_ALGO_RSA )
2657     return pk->pkey[0]->d[0];
2658     else {
2659     md = gpg_md_open( DIGEST_ALGO_SHA1 );
2660     gpg_md_putc( md, 0x99 );
2661     npkey = pubkey_get_npkey( pk->pubkey_algo );
2662     pktlen = 6;
2663     for( i = 0 ; i <npkey; i++ )
2664     pktlen = pktlen + 2 + pk->pkey[i]->alloced;
2665     gpg_md_putc( md, pktlen>>8 );
2666     gpg_md_putc( md, pktlen );
2667     gpg_md_putc( md, 4 );
2668     gpg_md_putc( md, pk->timestamp >> 24 );
2669     gpg_md_putc( md, pk->timestamp >> 16 );
2670     gpg_md_putc( md, pk->timestamp >> 8 );
2671     gpg_md_putc( md, pk->timestamp );
2672     gpg_md_putc( md, pk->pubkey_algo );
2673     for( i=0; i <npkey; i++ ) {
2674     const u32 * d = pk->pkey[i]->d;
2675     int nbits = pk->pkey[i]->nbits,
2676     n = pk->pkey[i]->alloced;
2677     gpg_md_putc( md, nbits >> 8 );
2678     gpg_md_putc( md, nbits );
2679     n = n>4? n/4 : n;
2680     while( n-- ) {
2681     if( pk->pkey[i]->alloced > 3 )
2682     gpg_md_putc( md, d[n] >> 24 );
2683     if( pk->pkey[i]->alloced > 2 )
2684     gpg_md_putc( md, d[n] >> 16 );
2685     if( pk->pkey[i]->alloced > 1 )
2686     gpg_md_putc( md, d[n] >> 8 );
2687     if( pk->pkey[i]->alloced > 0 )
2688     gpg_md_putc( md, d[n] );
2689     }
2690     }
2691     gpg_md_final( md );
2692     mdbuf = gpg_md_read( md );
2693     }
2694     if( mdbuf && fprint )
2695     memcpy( fprint, mdbuf, 20 );
2696     return mdbuf? mdbuf[16] << 24 | mdbuf[17] << 16 | mdbuf[18] << 8 | mdbuf[19] : 0;
2697     }
2698    
2699    
2700     u32
2701     gpg_keyid_from_sk( PKT_secret_key * sk, byte *fprint )
2702     {
2703     PKT_public_key pk;
2704     int npkey = pubkey_get_npkey( sk->pubkey_algo );
2705     int i;
2706    
2707     pk.pubkey_algo = sk->pubkey_algo;
2708     pk.version = sk->version;
2709     pk.timestamp = sk->timestamp;
2710     pk.expiredate = sk->expiredate;
2711     pk.pubkey_algo = sk->pubkey_algo;
2712     for( i=0; i < npkey; i++ )
2713     pk.pkey[i] = sk->skey[i];
2714     return gpg_keyid_from_pk( &pk, fprint );
2715     }
2716    
2717    
2718     /****************
2719     * Read the next keyblock from stream A.
2720     * PENDING_PKT should be initialzed to NULL
2721     * and not chnaged form the caller.
2722     * Retunr: 0 = okay, -1 no more blocks or another errorcode.
2723     */
2724     int
2725     gpg_read_keyblock( gpg_iobuf_t a, PACKET **pending_pkt, gpg_kbnode_t *ret_root )
2726     {
2727     int rc;
2728     PACKET *pkt;
2729     gpg_kbnode_t root = NULL;
2730     int in_cert;
2731    
2732     if( *pending_pkt ) {
2733     root = gpg_new_kbnode( *pending_pkt );
2734     *pending_pkt = NULL;
2735     in_cert = 1;
2736     }
2737     else
2738     in_cert = 0;
2739     pkt = malloc( sizeof *pkt );
2740     gpg_init_packet(pkt);
2741     while( (rc=gpg_parse_packet(a, pkt)) != -1 ) {
2742     if( rc ) { /* ignore errors */
2743     if( rc != G10ERR_UNKNOWN_PACKET ) {
2744     printf("read_block: read error: %d\n", rc );
2745     rc = G10ERR_INV_KEYRING;
2746     goto ready;
2747     }
2748     gpg_free_packet( pkt );
2749     gpg_init_packet(pkt);
2750     continue;
2751     }
2752    
2753     if( !root && pkt->pkttype == PKT_SIGNATURE
2754     && pkt->pkt.signature->sig_class == 0x20 ) {
2755     /* this is a revocation certificate which is handled
2756     * in a special way */
2757     root = gpg_new_kbnode( pkt );
2758     pkt = NULL;
2759     goto ready;
2760     }
2761    
2762     /* make a linked list of all packets */
2763     switch( pkt->pkttype ) {
2764     case PKT_RING_TRUST:
2765     /* skip those packets */
2766     gpg_free_packet( pkt );
2767     gpg_init_packet(pkt);
2768     break;
2769    
2770     case PKT_PUBLIC_KEY:
2771     case PKT_SECRET_KEY:
2772     if( in_cert ) { /* store this packet */
2773     *pending_pkt = pkt;
2774     pkt = NULL;
2775     goto ready;
2776     }
2777     in_cert = 1;
2778     default:
2779     if( in_cert ) {
2780     if( !root )
2781     root = gpg_new_kbnode( pkt );
2782     else
2783     gpg_add_kbnode( root, gpg_new_kbnode( pkt ) );
2784     pkt = malloc( sizeof *pkt );
2785     }
2786     gpg_init_packet(pkt);
2787     break;
2788     }
2789     }
2790     ready:
2791     if( rc == -1 && root )
2792     rc = 0;
2793    
2794     if( rc )
2795     gpg_release_kbnode( root );
2796     else
2797     *ret_root = root;
2798     gpg_free_packet( pkt );
2799     free( pkt );
2800     return rc;
2801     }

[email protected]
ViewVC Help
Powered by ViewVC 1.1.26