* parse-packet.c (parse_signature): No need to reserve 8 bytes for the
[gnupg.git] / g10 / misc.c
1 /* misc.c -  miscellaneous functions
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 <config.h>
22 #include <stdio.h>
23 #include <stdlib.h>
24 #include <string.h>
25 #include <unistd.h>
26 #include <errno.h>
27 #if defined(__linux__) && defined(__alpha__) && __GLIBC__ < 2
28 #include <asm/sysinfo.h>
29 #include <asm/unistd.h>
30 #endif
31 #ifdef HAVE_SETRLIMIT
32 #include <time.h>
33 #include <sys/time.h>
34 #include <sys/resource.h>
35 #endif
36 #include "util.h"
37 #include "main.h"
38 #include "photoid.h"
39 #include "options.h"
40 #include "i18n.h"
41
42
43 const char *g10m_revision_string(int);
44 const char *g10c_revision_string(int);
45 const char *g10u_revision_string(int);
46
47 #ifdef __GNUC__
48 volatile
49 #endif
50          void
51 pull_in_libs(void)
52 {
53     g10m_revision_string(0);
54     g10c_revision_string(0);
55     g10u_revision_string(0);
56 }
57
58
59 #if defined(__linux__) && defined(__alpha__) && __GLIBC__ < 2
60 static int
61 setsysinfo(unsigned long op, void *buffer, unsigned long size,
62                      int *start, void *arg, unsigned long flag)
63 {
64     return syscall(__NR_osf_setsysinfo, op, buffer, size, start, arg, flag);
65 }
66
67 void
68 trap_unaligned(void)
69 {
70     unsigned int buf[2];
71
72     buf[0] = SSIN_UACPROC;
73     buf[1] = UAC_SIGBUS | UAC_NOPRINT;
74     setsysinfo(SSI_NVPAIRS, buf, 1, 0, 0, 0);
75 }
76 #else
77 void
78 trap_unaligned(void)
79 {  /* dummy */
80 }
81 #endif
82
83
84 int
85 disable_core_dumps()
86 {
87 #ifdef HAVE_DOSISH_SYSTEM
88     return 0;
89 #else
90 #ifdef HAVE_SETRLIMIT
91     struct rlimit limit;
92
93     limit.rlim_cur = 0;
94     limit.rlim_max = 0;
95     if( !setrlimit( RLIMIT_CORE, &limit ) )
96         return 0;
97     if( errno != EINVAL && errno != ENOSYS )
98         log_fatal(_("can't disable core dumps: %s\n"), strerror(errno) );
99 #endif
100     return 1;
101 #endif
102 }
103
104
105
106 u16
107 checksum_u16( unsigned n )
108 {
109     u16 a;
110
111     a  = (n >> 8) & 0xff;
112     a += n & 0xff;
113     return a;
114 }
115
116
117 u16
118 checksum( byte *p, unsigned n )
119 {
120     u16 a;
121
122     for(a=0; n; n-- )
123         a += *p++;
124     return a;
125 }
126
127 u16
128 checksum_mpi( MPI a )
129 {
130     u16 csum;
131     byte *buffer;
132     unsigned nbytes;
133     unsigned nbits;
134
135     buffer = mpi_get_buffer( a, &nbytes, NULL );
136     nbits = mpi_get_nbits(a);
137     csum = checksum_u16( nbits );
138     csum += checksum( buffer, nbytes );
139     m_free( buffer );
140     return csum;
141 }
142
143 u32
144 buffer_to_u32( const byte *buffer )
145 {
146     unsigned long a;
147     a =  *buffer << 24;
148     a |= buffer[1] << 16;
149     a |= buffer[2] << 8;
150     a |= buffer[3];
151     return a;
152 }
153
154
155 static void
156 no_exp_algo(void)
157 {
158     static int did_note = 0;
159
160     if( !did_note ) {
161         did_note = 1;
162         log_info(_("Experimental algorithms should not be used!\n"));
163     }
164 }
165
166 void
167 print_pubkey_algo_note( int algo )
168 {
169     if( algo >= 100 && algo <= 110 )
170         no_exp_algo();
171 }
172
173 void
174 print_cipher_algo_note( int algo )
175 {
176     if( algo >= 100 && algo <= 110 )
177         no_exp_algo();
178     else if(    algo == CIPHER_ALGO_3DES
179              || algo == CIPHER_ALGO_CAST5
180              || algo == CIPHER_ALGO_BLOWFISH
181              || algo == CIPHER_ALGO_TWOFISH
182              || algo == CIPHER_ALGO_RIJNDAEL
183              || algo == CIPHER_ALGO_RIJNDAEL192
184              || algo == CIPHER_ALGO_RIJNDAEL256
185            )
186         ;
187     else {
188         static int did_note = 0;
189
190         if( !did_note ) {
191             did_note = 1;
192             log_info(_("this cipher algorithm is deprecated; "
193                        "please use a more standard one!\n"));
194         }
195     }
196 }
197
198 void
199 print_digest_algo_note( int algo )
200 {
201     if( algo >= 100 && algo <= 110 )
202         no_exp_algo();
203 }
204
205
206 /* Return a string which is used as a kind of process ID */
207 const byte *
208 get_session_marker( size_t *rlen )
209 {
210     static byte marker[SIZEOF_UNSIGNED_LONG*2];
211     static int initialized;
212
213     if ( !initialized ) {
214         volatile ulong aa, bb; /* we really want the uninitialized value */
215         ulong a, b;
216
217         initialized = 1;
218         /* also this marker is guessable it is not easy to use this 
219          * for a faked control packet because an attacker does not
220          * have enough control about the time the verification does 
221          * take place.  Of course, we can add just more random but 
222          * than we need the random generator even for verification
223          * tasks - which does not make sense. */
224         a = aa ^ (ulong)getpid();
225         b = bb ^ (ulong)time(NULL);
226         memcpy( marker, &a, SIZEOF_UNSIGNED_LONG );
227         memcpy( marker+SIZEOF_UNSIGNED_LONG, &b, SIZEOF_UNSIGNED_LONG );
228     }
229     *rlen = sizeof(marker);
230     return marker;
231 }
232
233 /****************
234  * Wrapper around the libgcrypt function with addional checks on
235  * openPGP contraints for the algo ID.
236  */
237 int
238 openpgp_cipher_test_algo( int algo )
239 {
240     if( algo < 0 || algo > 110 )
241         return G10ERR_CIPHER_ALGO;
242     return check_cipher_algo(algo);
243 }
244
245 int
246 openpgp_pk_test_algo( int algo, unsigned int usage_flags )
247 {
248     if( algo < 0 || algo > 110 )
249         return G10ERR_PUBKEY_ALGO;
250     return check_pubkey_algo2( algo, usage_flags );
251 }
252
253 int 
254 openpgp_pk_algo_usage ( int algo )
255 {
256     int use = 0; 
257     
258     /* they are hardwired in gpg 1.0 */
259     switch ( algo ) {    
260       case PUBKEY_ALGO_RSA:
261           use = PUBKEY_USAGE_SIG | PUBKEY_USAGE_ENC;
262           break;
263       case PUBKEY_ALGO_RSA_E:
264           use = PUBKEY_USAGE_ENC;
265           break;
266       case PUBKEY_ALGO_RSA_S:
267           use = PUBKEY_USAGE_SIG;
268           break;
269       case PUBKEY_ALGO_ELGAMAL_E:
270           use = PUBKEY_USAGE_ENC;
271           break;
272       case PUBKEY_ALGO_DSA:  
273           use = PUBKEY_USAGE_SIG;
274           break;
275       case PUBKEY_ALGO_ELGAMAL:
276           use = PUBKEY_USAGE_SIG | PUBKEY_USAGE_ENC;
277           break;
278       default:
279           break;
280     }
281     return use;
282 }
283
284 int
285 openpgp_md_test_algo( int algo )
286 {
287     if( algo < 0 || algo > 110 )
288         return G10ERR_DIGEST_ALGO;
289     return check_digest_algo(algo);
290 }
291
292 #ifdef USE_IDEA
293 /* Special warning for the IDEA cipher */
294 void
295 idea_cipher_warn(int show)
296 {
297   static int warned=0;
298
299   if(!warned || show)
300     {
301       log_info(_("the IDEA cipher plugin is not present\n"));
302       log_info(_("please see http://www.gnupg.org/why-not-idea.html "
303                  "for more information\n"));
304       warned=1;
305     }
306 }
307 #endif
308
309 /* Expand %-strings.  Returns a string which must be m_freed.  Returns
310    NULL if the string cannot be expanded (too large). */
311 char *
312 pct_expando(const char *string,struct expando_args *args)
313 {
314   const char *ch=string;
315   int idx=0,maxlen=0,done=0;
316   u32 pk_keyid[2]={0,0},sk_keyid[2]={0,0};
317   char *ret=NULL;
318
319   if(args->pk)
320     keyid_from_pk(args->pk,pk_keyid);
321
322   if(args->sk)
323     keyid_from_sk(args->sk,sk_keyid);
324
325   /* This is used so that %k works in photoid command strings in
326      --list-secret-keys (which of course has a sk, but no pk). */
327   if(!args->pk && args->sk)
328     keyid_from_sk(args->sk,pk_keyid);
329
330   while(*ch!='\0')
331     {
332       char *str=NULL;
333
334       if(!done)
335         {
336           /* 8192 is way bigger than we'll need here */
337           if(maxlen>=8192)
338             goto fail;
339
340           maxlen+=1024;
341           ret=m_realloc(ret,maxlen);
342         }
343
344       done=0;
345
346       if(*ch=='%')
347         {
348           switch(*(ch+1))
349             {
350             case 's': /* short key id */
351               if(idx+8<maxlen)
352                 {
353                   sprintf(&ret[idx],"%08lX",(ulong)sk_keyid[1]);
354                   idx+=8;
355                   done=1;
356                 }
357               break;
358
359             case 'S': /* long key id */
360               if(idx+16<maxlen)
361                 {
362                   sprintf(&ret[idx],"%08lX%08lX",
363                           (ulong)sk_keyid[0],(ulong)sk_keyid[1]);
364                   idx+=16;
365                   done=1;
366                 }
367               break;
368
369             case 'k': /* short key id */
370               if(idx+8<maxlen)
371                 {
372                   sprintf(&ret[idx],"%08lX",(ulong)pk_keyid[1]);
373                   idx+=8;
374                   done=1;
375                 }
376               break;
377
378             case 'K': /* long key id */
379               if(idx+16<maxlen)
380                 {
381                   sprintf(&ret[idx],"%08lX%08lX",
382                           (ulong)pk_keyid[0],(ulong)pk_keyid[1]);
383                   idx+=16;
384                   done=1;
385                 }
386               break;
387
388             case 'p': /* primary pk fingerprint of a sk */
389             case 'f': /* pk fingerprint */
390             case 'g': /* sk fingerprint */
391               {
392                 byte array[MAX_FINGERPRINT_LEN];
393                 size_t len;
394                 int i;
395
396                 if((*(ch+1))=='p' && args->sk)
397                   {
398                     if(args->sk->is_primary)
399                       fingerprint_from_sk(args->sk,array,&len);
400                     else if(args->sk->main_keyid[0] || args->sk->main_keyid[1])
401                       {
402                         PKT_public_key *pk=
403                           m_alloc_clear(sizeof(PKT_public_key));
404
405                         if(get_pubkey_fast(pk,args->sk->main_keyid)==0)
406                           fingerprint_from_pk(pk,array,&len);
407                         else
408                           memset(array,0,(len=MAX_FINGERPRINT_LEN));
409                         free_public_key(pk);
410                       }
411                     else
412                       memset(array,0,(len=MAX_FINGERPRINT_LEN));
413                   }
414                 else if((*(ch+1))=='f' && args->pk)
415                   fingerprint_from_pk(args->pk,array,&len);
416                 else if((*(ch+1))=='g' && args->sk)
417                   fingerprint_from_sk(args->sk,array,&len);
418                 else
419                   memset(array,0,(len=MAX_FINGERPRINT_LEN));
420
421                 if(idx+(len*2)<maxlen)
422                   {
423                     for(i=0;i<len;i++)
424                       {
425                         sprintf(&ret[idx],"%02X",array[i]);
426                         idx+=2;
427                       }
428                     done=1;
429                   }
430               }
431               break;
432
433             case 't': /* e.g. "jpg" */
434               str=image_type_to_string(args->imagetype,0);
435               /* fall through */
436
437             case 'T': /* e.g. "image/jpeg" */
438               if(str==NULL)
439                 str=image_type_to_string(args->imagetype,2);
440
441               if(idx+strlen(str)<maxlen)
442                 {
443                   strcpy(&ret[idx],str);
444                   idx+=strlen(str);
445                   done=1;
446                 }
447               break;
448
449             case '%':
450               if(idx+1<maxlen)
451                 {
452                   ret[idx++]='%';
453                   ret[idx]='\0';
454                   done=1;
455                 }
456               break;
457
458               /* Any unknown %-keys (like %i, %o, %I, and %O) are
459                  passed through for later expansion.  Note this also
460                  handles the case where the last character in the
461                  string is a '%' - the terminating \0 will end up here
462                  and properly terminate the string. */
463             default:
464               if(idx+2<maxlen)
465                 {
466                   ret[idx++]='%';
467                   ret[idx++]=*(ch+1);
468                   ret[idx]='\0';
469                   done=1;
470                 }
471               break;
472               }
473
474           if(done)
475             ch++;
476         }
477       else
478         {
479           if(idx+1<maxlen)
480             {
481               ret[idx++]=*ch;
482               ret[idx]='\0';
483               done=1;
484             }
485         }
486
487       if(done)
488         ch++;
489     }
490
491   return ret;
492
493  fail:
494   m_free(ret);
495   return NULL;
496 }
497
498 int
499 hextobyte( const char *s )
500 {
501     int c;
502
503     if( *s >= '0' && *s <= '9' )
504         c = 16 * (*s - '0');
505     else if( *s >= 'A' && *s <= 'F' )
506         c = 16 * (10 + *s - 'A');
507     else if( *s >= 'a' && *s <= 'f' )
508         c = 16 * (10 + *s - 'a');
509     else
510         return -1;
511     s++;
512     if( *s >= '0' && *s <= '9' )
513         c += *s - '0';
514     else if( *s >= 'A' && *s <= 'F' )
515         c += 10 + *s - 'A';
516     else if( *s >= 'a' && *s <= 'f' )
517         c += 10 + *s - 'a';
518     else
519         return -1;
520     return c;
521 }
522
523 void
524 deprecated_warning(const char *configname,unsigned int configlineno,
525                    const char *option,const char *repl1,const char *repl2)
526 {
527   if(configname)
528     {
529       if(strncmp("--",option,2)==0)
530         option+=2;
531
532       if(strncmp("--",repl1,2)==0)
533         repl1+=2;
534
535       log_info(_("%s:%d: deprecated option \"%s\"\n"),
536                configname,configlineno,option);
537     }
538   else
539     log_info(_("WARNING: \"%s\" is a deprecated option\n"),option);
540
541   log_info(_("please use \"%s%s\" instead\n"),repl1,repl2);
542 }
543
544 const char *
545 compress_algo_to_string(int algo)
546 {
547   const char *s="?";
548
549   switch(algo)
550     {
551     case 0:
552       s="Uncompressed";
553       break;
554
555     case 1:
556       s="ZIP";
557       break;
558
559     case 2:
560       s="ZLIB";
561       break;
562     }
563
564   return s;
565 }
566
567 int
568 string_to_compress_algo(const char *string)
569 {
570   if(ascii_strcasecmp(string,"uncompressed")==0)
571     return 0;
572   else if(ascii_strcasecmp(string,"zip")==0)
573     return 1;
574   else if(ascii_strcasecmp(string,"zlib")==0)
575     return 2;
576   else if(ascii_strcasecmp(string,"z0")==0)
577     return 0;
578   else if(ascii_strcasecmp(string,"z1")==0)
579     return 1;
580   else if(ascii_strcasecmp(string,"z2")==0)
581     return 2;
582   else
583     return -1;
584 }
585
586 int
587 check_compress_algo(int algo)
588 {
589   if(algo>=0 && algo<=2)
590     return 0;
591
592   return G10ERR_COMPR_ALGO;
593 }
594
595 int
596 default_cipher_algo(void)
597 {
598   if(opt.def_cipher_algo)
599     return opt.def_cipher_algo;
600   else if(opt.personal_cipher_prefs)
601     return opt.personal_cipher_prefs[0].value;
602   else
603     return opt.s2k_cipher_algo;
604 }
605
606 /* There is no default_digest_algo function, but see
607    sign.c:hash_for */
608
609 int
610 default_compress_algo(void)
611 {
612   if(opt.def_compress_algo!=-1)
613     return opt.def_compress_algo;
614   else if(opt.personal_compress_prefs)
615     return opt.personal_compress_prefs[0].value;
616   else
617     return DEFAULT_COMPRESS_ALGO;
618 }
619
620 const char *
621 compliance_option_string(void)
622 {
623   switch(opt.compliance)
624     {
625     case CO_RFC2440:
626       return "--openpgp";
627     case CO_PGP2:
628       return "--pgp2";
629     case CO_PGP6:
630       return "--pgp6";
631     case CO_PGP7:
632       return "--pgp7";
633     case CO_PGP8:
634       return "--pgp8";
635     default:
636       return "???";
637     }
638 }
639
640 static const char *
641 compliance_string(void)
642 {
643   switch(opt.compliance)
644     {
645     case CO_RFC2440:
646       return "OpenPGP";
647     case CO_PGP2:
648       return "PGP 2.x";
649     case CO_PGP6:
650       return "PGP 6.x";
651     case CO_PGP7:
652       return "PGP 7.x";
653     case CO_PGP8:
654       return "PGP 8.x";
655     default:
656       return "???";
657     }
658 }
659
660 void
661 compliance_failure(void)
662 {
663   log_info(_("this message may not be usable by %s\n"),compliance_string());
664   opt.compliance=CO_GNUPG;
665 }
666
667 int
668 parse_options(char *str,unsigned int *options,struct parse_options *opts)
669 {
670   char *tok;
671
672   while((tok=strsep(&str," ,")))
673     {
674       int i,rev=0;
675
676       if(tok[0]=='\0')
677         continue;
678
679       if(ascii_strncasecmp("no-",tok,3)==0)
680         {
681           rev=1;
682           tok+=3;
683         }
684
685       for(i=0;opts[i].name;i++)
686         {
687           if(ascii_strcasecmp(opts[i].name,tok)==0)
688             {
689               if(rev)
690                 *options&=~opts[i].bit;
691               else
692                 *options|=opts[i].bit;
693               break;
694             }
695         }
696
697       if(!opts[i].name)
698         return 0;
699     }
700
701   return 1;
702 }