New CAVS driver from upstream.
[libgcrypt.git] / tests / fipsdrv.c
1 /* fipsdrv.c  -  A driver to help with FIPS CAVS tests.
2    Copyright (C) 2008 Free Software Foundation, Inc.
3
4    This file is part of Libgcrypt.
5   
6    Libgcrypt is free software; you can redistribute it and/or modify
7    it under the terms of the GNU Lesser General Public License as
8    published by the Free Software Foundation; either version 2.1 of
9    the License, or (at your option) any later version.
10   
11    Libgcrypt 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 Lesser General Public License for more details.
15   
16    You should have received a copy of the GNU Lesser General Public
17    License along with this program; if not, see <http://www.gnu.org/licenses/>.
18  */
19
20 #ifdef HAVE_CONFIG_H
21 #include <config.h>
22 #endif
23 #include <stdio.h>
24 #include <stdlib.h>
25 #include <string.h>
26 #include <stdarg.h>
27 #include <errno.h>
28 #include <ctype.h>
29 #ifndef HAVE_W32_SYSTEM
30 # include <signal.h>
31 #endif
32 #include <assert.h>
33 #include <unistd.h>
34
35 #include <gcrypt.h>
36
37 #define PGM "fipsdrv"
38
39 #define my_isascii(c) (!((c) & 0x80))
40 #define digitp(p)   (*(p) >= '0' && *(p) <= '9')
41 #define hexdigitp(a) (digitp (a)                     \
42                       || (*(a) >= 'A' && *(a) <= 'F')  \
43                       || (*(a) >= 'a' && *(a) <= 'f'))
44 #define xtoi_1(p)   (*(p) <= '9'? (*(p)- '0'): \
45                      *(p) <= 'F'? (*(p)-'A'+10):(*(p)-'a'+10))
46 #define xtoi_2(p)   ((xtoi_1(p) * 16) + xtoi_1((p)+1))
47 #define DIM(v)               (sizeof(v)/sizeof((v)[0]))
48 #define DIMof(type,member)   DIM(((type *)0)->member)
49
50
51 /* Verbose mode flag.  */
52 static int verbose;
53
54 /* Binary input flag.  */
55 static int binary_input;
56
57 /* Binary output flag.  */
58 static int binary_output;
59
60 /* Base64 output flag.  */
61 static int base64_output;
62
63 /* We need to know whetehr we are in loop_mode.  */
64 static int loop_mode;
65
66 /* ASN.1 classes.  */
67 enum
68 {
69   UNIVERSAL = 0,
70   APPLICATION = 1,
71   ASNCONTEXT = 2,
72   PRIVATE = 3
73 };
74
75
76 /* ASN.1 tags.  */
77 enum
78 {
79   TAG_NONE = 0,
80   TAG_BOOLEAN = 1,
81   TAG_INTEGER = 2,
82   TAG_BIT_STRING = 3,
83   TAG_OCTET_STRING = 4,
84   TAG_NULL = 5,
85   TAG_OBJECT_ID = 6,
86   TAG_OBJECT_DESCRIPTOR = 7,
87   TAG_EXTERNAL = 8,
88   TAG_REAL = 9,
89   TAG_ENUMERATED = 10,
90   TAG_EMBEDDED_PDV = 11,
91   TAG_UTF8_STRING = 12,
92   TAG_REALTIVE_OID = 13,
93   TAG_SEQUENCE = 16,
94   TAG_SET = 17,
95   TAG_NUMERIC_STRING = 18,
96   TAG_PRINTABLE_STRING = 19,
97   TAG_TELETEX_STRING = 20,
98   TAG_VIDEOTEX_STRING = 21,
99   TAG_IA5_STRING = 22,
100   TAG_UTC_TIME = 23,
101   TAG_GENERALIZED_TIME = 24,
102   TAG_GRAPHIC_STRING = 25,
103   TAG_VISIBLE_STRING = 26,
104   TAG_GENERAL_STRING = 27,
105   TAG_UNIVERSAL_STRING = 28,
106   TAG_CHARACTER_STRING = 29,
107   TAG_BMP_STRING = 30
108 };
109
110 /* ASN.1 Parser object.  */
111 struct tag_info 
112 {
113   int class;             /* Object class.  */
114   unsigned long tag;     /* The tag of the object.  */
115   unsigned long length;  /* Length of the values.  */
116   int nhdr;              /* Length of the header (TL).  */
117   unsigned int ndef:1;   /* The object has an indefinite length.  */
118   unsigned int cons:1;   /* This is a constructed object.  */ 
119 };
120
121
122
123 /* Print a error message and exit the process with an error code.  */
124 static void
125 die (const char *format, ...)
126 {
127   va_list arg_ptr;
128
129   va_start (arg_ptr, format);
130   fputs (PGM ": ", stderr);
131   vfprintf (stderr, format, arg_ptr);
132   va_end (arg_ptr);
133   exit (1);
134 }
135
136
137 static void
138 showhex (const char *prefix, const void *buffer, size_t length)
139 {
140   const unsigned char *p = buffer;
141
142   if (prefix)
143     fprintf (stderr, PGM ": %s: ", prefix);
144   while (length-- )
145     fprintf (stderr, "%02X", *p++);
146   if (prefix)
147     putc ('\n', stderr);
148 }
149
150
151 /* Convert STRING consisting of hex characters into its binary
152    representation and store that at BUFFER.  BUFFER needs to be of
153    LENGTH bytes.  The function checks that the STRING will convert
154    exactly to LENGTH bytes. The string is delimited by either end of
155    string or a white space character.  The function returns -1 on
156    error or the length of the parsed string.  */
157 static int
158 hex2bin (const char *string, void *buffer, size_t length)
159 {
160   int i;
161   const char *s = string;
162
163   for (i=0; i < length; )
164     {
165       if (!hexdigitp (s) || !hexdigitp (s+1))
166         return -1;           /* Invalid hex digits. */
167       ((unsigned char*)buffer)[i++] = xtoi_2 (s);
168       s += 2;
169     }
170   if (*s && (!my_isascii (*s) || !isspace (*s)) )
171     return -1;             /* Not followed by Nul or white space.  */
172   if (i != length)
173     return -1;             /* Not of expected length.  */
174   if (*s)
175     s++; /* Skip the delimiter. */
176   return s - string;
177 }
178
179
180 /* Convert STRING consisting of hex characters into its binary
181    representation and return it as an allocated buffer. The valid
182    length of the buffer is returned at R_LENGTH.  The string is
183    delimited by end of string.  The function returns NULL on
184    error.  */
185 static void *
186 hex2buffer (const char *string, size_t *r_length)
187 {
188   const char *s;
189   unsigned char *buffer;
190   size_t length;
191
192   buffer = gcry_xmalloc (strlen(string)/2+1);
193   length = 0;
194   for (s=string; *s; s +=2 )
195     {
196       if (!hexdigitp (s) || !hexdigitp (s+1))
197         return NULL;           /* Invalid hex digits. */
198       ((unsigned char*)buffer)[length++] = xtoi_2 (s);
199     }
200   *r_length = length;
201   return buffer;
202 }
203
204 /* Read a file from stream FP into a newly allocated buffer and return
205    that buffer.  The valid length of the buffer is stored at R_LENGTH.
206    Returns NULL on failure.  If decode is set, the file is assumed to
207    be hex encoded and the decoded content is returned. */
208 static void *
209 read_file (FILE *fp, int decode, size_t *r_length)
210 {
211   char *buffer;
212   size_t buflen;
213   size_t nread, bufsize = 0;
214
215   *r_length = 0;
216 #define NCHUNK 8192
217 #ifdef HAVE_DOSISH_SYSTEM
218   setmode (fileno(fp), O_BINARY);
219 #endif
220   buffer = NULL;
221   buflen = 0;
222   do 
223     {
224       bufsize += NCHUNK;
225       if (!buffer)
226         buffer = gcry_xmalloc (bufsize);
227       else
228         buffer = gcry_xrealloc (buffer, bufsize);
229       
230       nread = fread (buffer + buflen, 1, NCHUNK, fp);
231       if (nread < NCHUNK && ferror (fp))
232         {
233           gcry_free (buffer);
234           return NULL;
235         }
236       buflen += nread;
237     }
238   while (nread == NCHUNK);
239 #undef NCHUNK
240   if (decode)
241     {
242       const char *s;
243       char *p;
244
245       for (s=buffer,p=buffer,nread=0; nread+1 < buflen; s += 2, nread +=2 )
246         {
247           if (!hexdigitp (s) || !hexdigitp (s+1))
248             {
249               gcry_free (buffer);
250               return NULL;  /* Invalid hex digits. */
251             }
252           *(unsigned char*)p++ = xtoi_2 (s);
253         }
254       if (nread != buflen)
255         {
256           gcry_free (buffer);
257           return NULL;  /* Odd number of hex digits. */
258         }
259       buflen = p - buffer;
260     }
261
262   *r_length = buflen;
263   return buffer;
264 }
265
266 /* Do in-place decoding of base-64 data of LENGTH in BUFFER.  Returns
267    the new length of the buffer.  Dies on error.  */
268 static size_t
269 base64_decode (char *buffer, size_t length)
270 {
271   static unsigned char const asctobin[128] = 
272     {
273       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
274       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
275       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
276       0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x3e, 0xff, 0xff, 0xff, 0x3f,
277       0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0xff, 0xff,
278       0xff, 0xff, 0xff, 0xff, 0xff, 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06,
279       0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11, 0x12,
280       0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0xff, 0xff, 0xff, 0xff, 0xff,
281       0xff, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 0x20, 0x21, 0x22, 0x23, 0x24,
282       0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, 0x30,
283       0x31, 0x32, 0x33, 0xff, 0xff, 0xff, 0xff, 0xff 
284     };
285
286   int idx = 0;
287   unsigned char val = 0;
288   int c = 0;
289   char *d, *s;
290   int lfseen = 1;
291
292   /* Find BEGIN line.  */
293   for (s=buffer; length; length--, s++)
294     {
295       if (lfseen && *s == '-' && length > 11 && !memcmp (s, "-----BEGIN ", 11))
296         {
297           for (; length && *s != '\n'; length--, s++)
298             ;
299           break;
300         } 
301       lfseen = (*s == '\n');
302     }
303
304   /* Decode until pad character or END line.  */
305   for (d=buffer; length; length--, s++)
306     {
307       if (lfseen && *s == '-' && length > 9 && !memcmp (s, "-----END ", 9))
308         break;
309       if ((lfseen = (*s == '\n')) || *s == ' ' || *s == '\r' || *s == '\t')
310         continue;
311       if (*s == '=')
312         {
313           /* Pad character: stop */
314           if (idx == 1)
315             *d++ = val;
316           break;
317         }
318
319       if ( (*s & 0x80) || (c = asctobin[*(unsigned char *)s]) == 0xff)
320         die ("invalid base64 character %02X at pos %d detected\n",
321              *(unsigned char*)s, (int)(s-buffer));
322
323       switch (idx)
324         {
325         case 0:
326           val = c << 2;
327           break;
328         case 1:
329           val |= (c>>4)&3;
330           *d++ = val;
331           val = (c<<4)&0xf0;
332           break;
333         case 2:
334           val |= (c>>2)&15;
335           *d++ = val;
336           val = (c<<6)&0xc0;
337           break;
338         case 3:
339           val |= c&0x3f;
340           *d++ = val;
341           break;
342         }
343       idx = (idx+1) % 4;
344     }
345
346   return d - buffer;
347 }
348
349
350 /* Parse the buffer at the address BUFFER which consists of the number
351    of octets as stored at BUFLEN.  Return the tag and the length part
352    from the TLV triplet.  Update BUFFER and BUFLEN on success.  Checks
353    that the encoded length does not exhaust the length of the provided
354    buffer. */
355 static int 
356 parse_tag (unsigned char const **buffer, size_t *buflen, struct tag_info *ti)
357 {
358   int c;
359   unsigned long tag;
360   const unsigned char *buf = *buffer;
361   size_t length = *buflen;
362
363   ti->length = 0;
364   ti->ndef = 0;
365   ti->nhdr = 0;
366
367   /* Get the tag */
368   if (!length)
369     return -1; /* Premature EOF.  */
370   c = *buf++; length--;
371   ti->nhdr++;
372
373   ti->class = (c & 0xc0) >> 6;
374   ti->cons  = !!(c & 0x20);
375   tag       = (c & 0x1f);
376
377   if (tag == 0x1f)
378     {
379       tag = 0;
380       do
381         {
382           tag <<= 7;
383           if (!length)
384             return -1; /* Premature EOF.  */
385           c = *buf++; length--;
386           ti->nhdr++;
387           tag |= (c & 0x7f);
388         }
389       while ( (c & 0x80) );
390     }
391   ti->tag = tag;
392
393   /* Get the length */
394   if (!length)
395     return -1; /* Premature EOF. */
396   c = *buf++; length--;
397   ti->nhdr++;
398
399   if ( !(c & 0x80) )
400     ti->length = c;
401   else if (c == 0x80)
402     ti->ndef = 1;
403   else if (c == 0xff)
404     return -1; /* Forbidden length value.  */
405   else
406     {
407       unsigned long len = 0;
408       int count = c & 0x7f;
409
410       for (; count; count--)
411         {
412           len <<= 8;
413           if (!length)
414             return -1; /* Premature EOF.  */
415           c = *buf++; length--;
416           ti->nhdr++;
417           len |= (c & 0xff);
418         }
419       ti->length = len;
420     }
421   
422   if (ti->class == UNIVERSAL && !ti->tag)
423     ti->length = 0;
424
425   if (ti->length > length)
426     return -1; /* Data larger than buffer.  */
427   
428   *buffer = buf;
429   *buflen = length;
430   return 0;
431 }
432
433
434 /* Read the file FNAME assuming it is a PEM encoded private key file
435    and return an S-expression.  With SHOW set, the key parameters are
436    printed.  */
437 static gcry_sexp_t
438 read_private_key_file (const char *fname, int show)
439 {
440   gcry_error_t err;
441   FILE *fp;
442   char *buffer;
443   size_t buflen;
444   const unsigned char *der;
445   size_t derlen;
446   struct tag_info ti;
447   gcry_mpi_t keyparms[8];
448   int n_keyparms = 8;
449   int idx;
450   gcry_sexp_t s_key;
451
452   fp = fopen (fname, binary_input?"rb":"r");
453   if (!fp)
454     die ("can't open `%s': %s\n", fname, strerror (errno));
455   buffer = read_file (fp, 0, &buflen);
456   if (!buffer)
457     die ("error reading `%s'\n", fname);
458   fclose (fp);
459
460   buflen = base64_decode (buffer, buflen);
461   
462   /* Parse the ASN.1 structure.  */
463   der = (const unsigned char*)buffer;
464   derlen = buflen;
465   if ( parse_tag (&der, &derlen, &ti)
466        || ti.tag != TAG_SEQUENCE || ti.class || !ti.cons || ti.ndef)
467     goto bad_asn1;
468   if ( parse_tag (&der, &derlen, &ti)
469        || ti.tag != TAG_INTEGER || ti.class || ti.cons || ti.ndef)
470     goto bad_asn1;
471   if (ti.length != 1 || *der)
472     goto bad_asn1;  /* The value of the first integer is no 0. */
473   der += ti.length; derlen -= ti.length;
474
475   for (idx=0; idx < n_keyparms; idx++)
476     {
477       if ( parse_tag (&der, &derlen, &ti)
478            || ti.tag != TAG_INTEGER || ti.class || ti.cons || ti.ndef)
479         goto bad_asn1;
480       if (show)
481         {
482           char prefix[2];
483
484           prefix[0] = idx < 8? "nedpq12u"[idx] : '?';
485           prefix[1] = 0;
486           showhex (prefix, der, ti.length);
487         }
488       err = gcry_mpi_scan (keyparms+idx, GCRYMPI_FMT_USG, der, ti.length,NULL);
489       if (err)
490         die ("error scanning RSA parameter %d: %s\n", idx, gpg_strerror (err));
491       der += ti.length; derlen -= ti.length;
492     }
493   if (idx != n_keyparms)
494     die ("not enough RSA key parameters\n");
495
496   gcry_free (buffer);
497
498   /* Convert from OpenSSL parameter ordering to the OpenPGP order. */
499   /* First check that p < q; if not swap p and q and recompute u.  */ 
500   if (gcry_mpi_cmp (keyparms[3], keyparms[4]) > 0)
501     {
502       gcry_mpi_swap (keyparms[3], keyparms[4]);
503       gcry_mpi_invm (keyparms[7], keyparms[3], keyparms[4]);
504     }
505   
506   /* Build the S-expression.  */
507   err = gcry_sexp_build (&s_key, NULL,
508                          "(private-key(rsa(n%m)(e%m)"
509                          /**/            "(d%m)(p%m)(q%m)(u%m)))",
510                          keyparms[0], keyparms[1], keyparms[2],
511                          keyparms[3], keyparms[4], keyparms[7] );
512   if (err)
513     die ("error building S-expression: %s\n", gpg_strerror (err));
514   
515   for (idx=0; idx < n_keyparms; idx++)
516     gcry_mpi_release (keyparms[idx]);
517   
518   return s_key;
519   
520  bad_asn1:
521   die ("invalid ASN.1 structure in `%s'\n", fname);
522   return NULL; /*NOTREACHED*/
523 }
524
525
526 /* Read the file FNAME assuming it is a PEM encoded public key file
527    and return an S-expression.  With SHOW set, the key parameters are
528    printed.  */
529 static gcry_sexp_t
530 read_public_key_file (const char *fname, int show)
531 {
532   gcry_error_t err;
533   FILE *fp;
534   char *buffer;
535   size_t buflen;
536   const unsigned char *der;
537   size_t derlen;
538   struct tag_info ti;
539   gcry_mpi_t keyparms[2];
540   int n_keyparms = 2;
541   int idx;
542   gcry_sexp_t s_key;
543
544   fp = fopen (fname, binary_input?"rb":"r");
545   if (!fp)
546     die ("can't open `%s': %s\n", fname, strerror (errno));
547   buffer = read_file (fp, 0, &buflen);
548   if (!buffer)
549     die ("error reading `%s'\n", fname);
550   fclose (fp);
551
552   buflen = base64_decode (buffer, buflen);
553   
554   /* Parse the ASN.1 structure.  */
555   der = (const unsigned char*)buffer;
556   derlen = buflen;
557   if ( parse_tag (&der, &derlen, &ti)
558        || ti.tag != TAG_SEQUENCE || ti.class || !ti.cons || ti.ndef)
559     goto bad_asn1;
560   if ( parse_tag (&der, &derlen, &ti)
561        || ti.tag != TAG_SEQUENCE || ti.class || !ti.cons || ti.ndef)
562     goto bad_asn1;
563   /* We skip the description of the key parameters and assume it is RSA.  */
564   der += ti.length; derlen -= ti.length;
565   
566   if ( parse_tag (&der, &derlen, &ti)
567        || ti.tag != TAG_BIT_STRING || ti.class || ti.cons || ti.ndef)
568     goto bad_asn1;
569   if (ti.length < 1 || *der)
570     goto bad_asn1;  /* The number of unused bits needs to be 0. */
571   der += 1; derlen -= 1;
572
573   /* Parse the BIT string.  */
574   if ( parse_tag (&der, &derlen, &ti)
575        || ti.tag != TAG_SEQUENCE || ti.class || !ti.cons || ti.ndef)
576     goto bad_asn1;
577
578   for (idx=0; idx < n_keyparms; idx++)
579     {
580       if ( parse_tag (&der, &derlen, &ti)
581            || ti.tag != TAG_INTEGER || ti.class || ti.cons || ti.ndef)
582         goto bad_asn1;
583       if (show)
584         {
585           char prefix[2];
586
587           prefix[0] = idx < 2? "ne"[idx] : '?';
588           prefix[1] = 0;
589           showhex (prefix, der, ti.length);
590         }
591       err = gcry_mpi_scan (keyparms+idx, GCRYMPI_FMT_USG, der, ti.length,NULL);
592       if (err)
593         die ("error scanning RSA parameter %d: %s\n", idx, gpg_strerror (err));
594       der += ti.length; derlen -= ti.length;
595     }
596   if (idx != n_keyparms)
597     die ("not enough RSA key parameters\n");
598
599   gcry_free (buffer);
600
601   /* Build the S-expression.  */
602   err = gcry_sexp_build (&s_key, NULL,
603                          "(public-key(rsa(n%m)(e%m)))",
604                          keyparms[0], keyparms[1] );
605   if (err)
606     die ("error building S-expression: %s\n", gpg_strerror (err));
607   
608   for (idx=0; idx < n_keyparms; idx++)
609     gcry_mpi_release (keyparms[idx]);
610   
611   return s_key;
612   
613  bad_asn1:
614   die ("invalid ASN.1 structure in `%s'\n", fname);
615   return NULL; /*NOTREACHED*/
616 }
617
618
619
620 /* Read the file FNAME assuming it is a binary signature result and
621    return an an S-expression suitable for gcry_pk_verify.  */
622 static gcry_sexp_t
623 read_sig_file (const char *fname)
624 {
625   gcry_error_t err;
626   FILE *fp;
627   char *buffer;
628   size_t buflen;
629   gcry_mpi_t tmpmpi;
630   gcry_sexp_t s_sig;
631
632   fp = fopen (fname, "rb");
633   if (!fp)
634     die ("can't open `%s': %s\n", fname, strerror (errno));
635   buffer = read_file (fp, 0, &buflen);
636   if (!buffer)
637     die ("error reading `%s'\n", fname);
638   fclose (fp);
639
640   err = gcry_mpi_scan (&tmpmpi, GCRYMPI_FMT_USG, buffer, buflen, NULL);
641   if (!err)
642     err = gcry_sexp_build (&s_sig, NULL,
643                            "(sig-val(rsa(s %m)))", tmpmpi);
644   if (err)
645     die ("error building S-expression: %s\n", gpg_strerror (err));
646   gcry_mpi_release (tmpmpi);
647   gcry_free (buffer);
648
649   return s_sig;
650 }
651
652
653 static void
654 print_buffer (const void *buffer, size_t length)
655 {
656   int writerr = 0;
657
658   if (base64_output)
659     {
660       static const unsigned char bintoasc[64+1] = 
661         ("ABCDEFGHIJKLMNOPQRSTUVWXYZ" 
662          "abcdefghijklmnopqrstuvwxyz" 
663          "0123456789+/"); 
664       const unsigned char *p;
665       unsigned char inbuf[4];
666       char outbuf[4];
667       int idx, quads;
668
669       idx = quads = 0;
670       for (p = buffer; length; p++, length--)
671         {
672           inbuf[idx++] = *p;
673           if (idx > 2)
674             {
675               outbuf[0] = bintoasc[(*inbuf>>2)&077];
676               outbuf[1] = bintoasc[(((*inbuf<<4)&060)
677                                     |((inbuf[1] >> 4)&017))&077];
678               outbuf[2] = bintoasc[(((inbuf[1]<<2)&074)
679                                     |((inbuf[2]>>6)&03))&077];
680               outbuf[3] = bintoasc[inbuf[2]&077];
681               if (fwrite (outbuf, 4, 1, stdout) != 1)
682                 writerr = 1;
683               idx = 0;
684               if (++quads >= (64/4)) 
685                 {
686                   if (fwrite ("\n", 1, 1, stdout) != 1)
687                     writerr = 1;
688                   quads = 0;
689                 }
690             }
691         }
692       if (idx)
693         {
694           outbuf[0] = bintoasc[(*inbuf>>2)&077];
695           if (idx == 1)
696             {
697               outbuf[1] = bintoasc[((*inbuf<<4)&060)&077];
698               outbuf[2] = outbuf[3] = '=';
699             }
700           else 
701             { 
702               outbuf[1] = bintoasc[(((*inbuf<<4)&060)
703                                     |((inbuf[1]>>4)&017))&077];
704               outbuf[2] = bintoasc[((inbuf[1]<<2)&074)&077];
705               outbuf[3] = '=';
706             }
707           if (fwrite (outbuf, 4, 1, stdout) != 1)
708             writerr = 1;
709           quads++;
710         }
711       if (quads && fwrite ("\n", 1, 1, stdout) != 1)
712         writerr = 1;
713     }
714   else if (binary_output)
715     {
716       if (fwrite (buffer, length, 1, stdout) != 1)
717         writerr++;
718     }
719   else
720     {
721       const unsigned char *p = buffer;
722       
723       while (length-- && !ferror (stdout) )
724         printf ("%02X", *p++);
725       if (ferror (stdout))
726         writerr++;
727     }
728   if (!writerr && fflush (stdout) == EOF)
729     writerr++;
730   if (writerr)
731     {
732 #ifndef HAVE_W32_SYSTEM
733       if (loop_mode && errno == EPIPE)
734         loop_mode = 0;
735       else
736 #endif
737         die ("writing output failed: %s\n", strerror (errno));
738     }
739 }
740
741
742
743 static gcry_error_t
744 init_external_rng_test (void **r_context, 
745                     unsigned int flags,
746                     const void *key, size_t keylen,
747                     const void *seed, size_t seedlen,
748                     const void *dt, size_t dtlen)
749 {
750   return gcry_control (58, 
751                        r_context, flags,
752                        key, keylen,
753                        seed, seedlen,
754                        dt, dtlen);
755 }
756
757 static gcry_error_t
758 run_external_rng_test (void *context, void *buffer, size_t buflen)
759 {
760   return gcry_control (59, context, buffer, buflen);
761 }
762
763 static void
764 deinit_external_rng_test (void *context)
765 {
766   gcry_control (60, context);
767 }
768
769
770 /* Given an OpenSSL cipher name NAME, return the Libgcrypt algirithm
771    identified and store the libgcrypt mode at R_MODE.  Returns 0 on
772    error.  */
773 static int 
774 map_openssl_cipher_name (const char *name, int *r_mode)
775 {
776   static struct {
777     const char *name;
778     int algo;
779     int mode;
780   } table[] = 
781     {
782       { "bf-cbc",       GCRY_CIPHER_BLOWFISH, GCRY_CIPHER_MODE_CBC },
783       { "bf",           GCRY_CIPHER_BLOWFISH, GCRY_CIPHER_MODE_CBC },
784       { "bf-cfb",       GCRY_CIPHER_BLOWFISH, GCRY_CIPHER_MODE_CFB },
785       { "bf-ecb",       GCRY_CIPHER_BLOWFISH, GCRY_CIPHER_MODE_ECB },
786       { "bf-ofb",       GCRY_CIPHER_BLOWFISH, GCRY_CIPHER_MODE_OFB },
787
788       { "cast-cbc",     GCRY_CIPHER_CAST5, GCRY_CIPHER_MODE_CBC },
789       { "cast",         GCRY_CIPHER_CAST5, GCRY_CIPHER_MODE_CBC },
790       { "cast5-cbc",    GCRY_CIPHER_CAST5, GCRY_CIPHER_MODE_CBC },
791       { "cast5-cfb",    GCRY_CIPHER_CAST5, GCRY_CIPHER_MODE_CFB },
792       { "cast5-ecb",    GCRY_CIPHER_CAST5, GCRY_CIPHER_MODE_ECB },
793       { "cast5-ofb",    GCRY_CIPHER_CAST5, GCRY_CIPHER_MODE_OFB },
794
795       { "des-cbc",      GCRY_CIPHER_DES, GCRY_CIPHER_MODE_CBC },
796       { "des",          GCRY_CIPHER_DES, GCRY_CIPHER_MODE_CBC },
797       { "des-cfb",      GCRY_CIPHER_DES, GCRY_CIPHER_MODE_CFB },
798       { "des-ofb",      GCRY_CIPHER_DES, GCRY_CIPHER_MODE_OFB },
799       { "des-ecb",      GCRY_CIPHER_DES, GCRY_CIPHER_MODE_ECB },
800
801       { "des-ede3-cbc", GCRY_CIPHER_3DES, GCRY_CIPHER_MODE_CBC },
802       { "des-ede3    ", GCRY_CIPHER_3DES, GCRY_CIPHER_MODE_ECB },
803       { "des3        ", GCRY_CIPHER_3DES, GCRY_CIPHER_MODE_CBC },
804       { "des-ede3-cfb", GCRY_CIPHER_3DES, GCRY_CIPHER_MODE_CFB },
805       { "des-ede3-ofb", GCRY_CIPHER_3DES, GCRY_CIPHER_MODE_OFB },
806
807       { "rc4",          GCRY_CIPHER_ARCFOUR, GCRY_CIPHER_MODE_STREAM },
808
809       { "aes-128-cbc",  GCRY_CIPHER_AES128, GCRY_CIPHER_MODE_CBC },
810       { "aes-128",      GCRY_CIPHER_AES128, GCRY_CIPHER_MODE_CBC },
811       { "aes-128-cfb",  GCRY_CIPHER_AES128, GCRY_CIPHER_MODE_CFB },
812       { "aes-128-ecb",  GCRY_CIPHER_AES128, GCRY_CIPHER_MODE_ECB },
813       { "aes-128-ofb",  GCRY_CIPHER_AES128, GCRY_CIPHER_MODE_OFB },
814
815       { "aes-192-cbc",  GCRY_CIPHER_AES192, GCRY_CIPHER_MODE_CBC },
816       { "aes-192",      GCRY_CIPHER_AES192, GCRY_CIPHER_MODE_CBC },
817       { "aes-192-cfb",  GCRY_CIPHER_AES192, GCRY_CIPHER_MODE_CFB },
818       { "aes-192-ecb",  GCRY_CIPHER_AES192, GCRY_CIPHER_MODE_ECB },
819       { "aes-192-ofb",  GCRY_CIPHER_AES192, GCRY_CIPHER_MODE_OFB },
820       
821       { "aes-256-cbc",  GCRY_CIPHER_AES256, GCRY_CIPHER_MODE_CBC },
822       { "aes-256",      GCRY_CIPHER_AES256, GCRY_CIPHER_MODE_CBC },
823       { "aes-256-cfb",  GCRY_CIPHER_AES256, GCRY_CIPHER_MODE_CFB },
824       { "aes-256-ecb",  GCRY_CIPHER_AES256, GCRY_CIPHER_MODE_ECB },
825       { "aes-256-ofb",  GCRY_CIPHER_AES256, GCRY_CIPHER_MODE_OFB },
826
827       { NULL, 0 , 0 }
828     };
829   int idx;
830
831   for (idx=0; table[idx].name; idx++)
832     if (!strcmp (name, table[idx].name))
833       {
834         *r_mode = table[idx].mode;
835         return table[idx].algo;
836       }
837   *r_mode = 0;
838   return 0;
839 }
840
841
842 \f
843 /* Run an encrypt or decryption operations.  If DATA is NULL the
844    function reads its input in chunks of size DATALEN from fp and
845    processes it and writes it out until EOF.  */
846 static void
847 run_encrypt_decrypt (int encrypt_mode,
848                      int cipher_algo, int cipher_mode, 
849                      const void *iv_buffer, size_t iv_buflen,
850                      const void *key_buffer, size_t key_buflen,
851                      const void *data, size_t datalen, FILE *fp)
852 {
853   gpg_error_t err;
854   gcry_cipher_hd_t hd;
855   void *outbuf;
856   size_t outbuflen;
857   void *inbuf;
858   size_t inbuflen;
859
860   err = gcry_cipher_open (&hd, cipher_algo, cipher_mode, 0);
861   if (err)
862     die ("gcry_cipher_open failed for algo %d, mode %d: %s\n", 
863          cipher_algo, cipher_mode, gpg_strerror (err));
864
865   err = gcry_cipher_setkey (hd, key_buffer, key_buflen);
866   if (err)
867     die ("gcry_cipher_setkey failed with keylen %u: %s\n",
868          (unsigned int)key_buflen, gpg_strerror (err));
869
870   err = gcry_cipher_setiv (hd, iv_buffer, iv_buflen);
871   if (err)
872     die ("gcry_cipher_setiv failed with ivlen %u: %s\n",
873          (unsigned int)iv_buflen, gpg_strerror (err));
874
875   inbuf = data? NULL : gcry_xmalloc (datalen);
876   outbuflen = datalen;
877   outbuf = gcry_xmalloc (outbuflen);
878
879   do
880     {
881       if (inbuf)
882         {
883           int nread = fread (inbuf, 1, datalen, fp);
884           if (nread < (int)datalen && ferror (fp))
885             die ("error reading input\n");
886           data = inbuf;
887           inbuflen = nread;
888         }
889       else
890         inbuflen = datalen;
891
892       if (encrypt_mode)
893         err = gcry_cipher_encrypt (hd, outbuf, outbuflen, data, inbuflen);
894       else
895         err = gcry_cipher_decrypt (hd, outbuf, outbuflen, data, inbuflen);
896       if (err)
897         die ("gcry_cipher_%scrypt failed: %s\n",
898              encrypt_mode? "en":"de", gpg_strerror (err));
899       print_buffer (outbuf, outbuflen);
900     }
901   while (inbuf);
902
903   gcry_cipher_close (hd);
904   gcry_free (outbuf);
905   gcry_free (inbuf);
906 }
907
908
909 \f
910 /* Run a digest operation.  */
911 static void
912 run_digest (int digest_algo,  const void *data, size_t datalen)
913 {
914   gpg_error_t err;
915   gcry_md_hd_t hd;
916   const unsigned char *digest;
917   unsigned int digestlen;
918
919   err = gcry_md_open (&hd, digest_algo, 0);
920   if (err)
921     die ("gcry_md_open failed for algo %d: %s\n", 
922          digest_algo,  gpg_strerror (err));
923
924   gcry_md_write (hd, data, datalen);
925   digest = gcry_md_read (hd, digest_algo);
926   digestlen = gcry_md_get_algo_dlen (digest_algo);
927   print_buffer (digest, digestlen);
928   gcry_md_close (hd);
929 }
930
931 \f
932 /* Run a HMAC operation.  */
933 static void
934 run_hmac (int digest_algo, const void *key, size_t keylen, 
935           const void *data, size_t datalen)
936 {
937   gpg_error_t err;
938   gcry_md_hd_t hd;
939   const unsigned char *digest;
940   unsigned int digestlen;
941
942   err = gcry_md_open (&hd, digest_algo, GCRY_MD_FLAG_HMAC);
943   if (err)
944     die ("gcry_md_open failed for HMAC algo %d: %s\n", 
945          digest_algo,  gpg_strerror (err));
946
947   gcry_md_setkey (hd, key, keylen);
948   if (err)
949     die ("gcry_md_setkey failed for HMAC algo %d: %s\n", 
950          digest_algo,  gpg_strerror (err));
951
952   gcry_md_write (hd, data, datalen);
953   digest = gcry_md_read (hd, digest_algo);
954   digestlen = gcry_md_get_algo_dlen (digest_algo);
955   print_buffer (digest, digestlen);
956   gcry_md_close (hd);
957 }
958
959 \f
960 static size_t
961 compute_tag_length (size_t n)
962 {     
963   int needed = 0;
964
965   if (n < 128)
966     needed += 2; /* Tag and one length byte.  */
967   else if (n < 256)
968     needed += 3; /* Tag, number of length bytes, 1 length byte.  */
969   else if (n < 65536)
970     needed += 4; /* Tag, number of length bytes, 2 length bytes.  */
971   else
972     die ("DER object too long to encode\n");
973
974   return needed;
975 }
976
977 static unsigned char *
978 store_tag_length (unsigned char *p, int tag, size_t n)
979 {     
980   if (tag == TAG_SEQUENCE)
981     tag |= 0x20; /* constructed */
982
983   *p++ = tag;
984   if (n < 128)
985     *p++ = n;
986   else if (n < 256)
987     {
988       *p++ = 0x81;
989       *p++ = n;
990     }
991   else if (n < 65536)
992     {
993       *p++ = 0x82;
994       *p++ = n >> 8;
995       *p++ = n;
996     }
997
998   return p;
999 }
1000
1001
1002 /* Generate an RSA key of size KEYSIZE using the public exponent
1003    PUBEXP and print it to stdout in the OpenSSL format.  The format
1004    is:
1005
1006        SEQUENCE {
1007          INTEGER (0)  -- Unknown constant. 
1008          INTEGER      -- n
1009          INTEGER      -- e
1010          INTEGER      -- d
1011          INTEGER      -- p     
1012          INTEGER      -- q      (with p < q)
1013          INTEGER      -- dmp1 = d mod (p-1)
1014          INTEGER      -- dmq1 = d mod (q-1)
1015          INTEGER      -- u    = p^{-1} mod q
1016        }
1017
1018 */
1019 static void
1020 run_rsa_gen (int keysize, int pubexp)
1021 {
1022   gpg_error_t err;
1023   gcry_sexp_t keyspec, key, l1;
1024   const char keyelems[] = "nedpq..u";
1025   gcry_mpi_t keyparms[8];
1026   size_t     keyparmslen[8];
1027   int idx;
1028   size_t derlen, needed, n;
1029   unsigned char *derbuf, *der;
1030
1031   err = gcry_sexp_build (&keyspec, NULL, 
1032                          "(genkey (rsa (nbits %d)(rsa-use-e %d)))",
1033                          keysize, pubexp);
1034   if (err)
1035     die ("gcry_sexp_build failed for RSA key generation: %s\n",
1036          gpg_strerror (err));
1037
1038   err = gcry_pk_genkey (&key, keyspec);
1039   if (err)
1040     die ("gcry_pk_genkey failed for RSA: %s\n", gpg_strerror (err));
1041   
1042   gcry_sexp_release (keyspec);
1043
1044   l1 = gcry_sexp_find_token (key, "private-key", 0);
1045   if (!l1)
1046     die ("private key not found in genkey result\n");
1047   gcry_sexp_release (key);
1048   key = l1;
1049
1050   l1 = gcry_sexp_find_token (key, "rsa", 0);
1051   if (!l1)
1052     die ("returned private key not formed as expected\n");
1053   gcry_sexp_release (key);
1054   key = l1;
1055
1056   /* Extract the parameters from the S-expression and store them in a
1057      well defined order in KEYPARMS.  */
1058   for (idx=0; idx < DIM(keyparms); idx++) 
1059     {
1060       if (keyelems[idx] == '.')
1061         {
1062           keyparms[idx] = gcry_mpi_new (0);
1063           continue;
1064         }
1065       l1 = gcry_sexp_find_token (key, keyelems+idx, 1);
1066       if (!l1)
1067         die ("no %c parameter in returned private key\n", keyelems[idx]);
1068       keyparms[idx] = gcry_sexp_nth_mpi (l1, 1, GCRYMPI_FMT_USG);
1069       if (!keyparms[idx])
1070         die ("no value for %c parameter in returned private key\n",
1071              keyelems[idx]);
1072       gcry_sexp_release (l1);
1073     }
1074
1075   gcry_sexp_release (key);
1076
1077   /* Check that p < q; if not swap p and q and recompute u.  */ 
1078   if (gcry_mpi_cmp (keyparms[3], keyparms[4]) > 0)
1079     {
1080       gcry_mpi_swap (keyparms[3], keyparms[4]);
1081       gcry_mpi_invm (keyparms[7], keyparms[3], keyparms[4]);
1082     }
1083
1084   /* Compute the additional parameters.  */
1085   gcry_mpi_sub_ui (keyparms[5], keyparms[3], 1);
1086   gcry_mpi_mod (keyparms[5], keyparms[2], keyparms[5]);
1087   gcry_mpi_sub_ui (keyparms[6], keyparms[4], 1);
1088   gcry_mpi_mod (keyparms[6], keyparms[2], keyparms[6]);
1089
1090   /* Compute the length of the DER encoding.  */
1091   needed = compute_tag_length (1) + 1;  
1092   for (idx=0; idx < DIM(keyparms); idx++) 
1093     {
1094       err = gcry_mpi_print (GCRYMPI_FMT_STD, NULL, 0, &n, keyparms[idx]);
1095       if (err)
1096         die ("error formatting parameter: %s\n", gpg_strerror (err));
1097       keyparmslen[idx] = n;
1098       needed += compute_tag_length (n) + n;
1099     }
1100   
1101   /* Store the key parameters. */
1102   derlen = compute_tag_length (needed) + needed;
1103   der = derbuf = gcry_xmalloc (derlen);
1104
1105   der = store_tag_length (der, TAG_SEQUENCE, needed);
1106   der = store_tag_length (der, TAG_INTEGER, 1);
1107   *der++ = 0;
1108   for (idx=0; idx < DIM(keyparms); idx++) 
1109     {
1110       der = store_tag_length (der, TAG_INTEGER, keyparmslen[idx]);
1111       err = gcry_mpi_print (GCRYMPI_FMT_STD, der, 
1112                            keyparmslen[idx], NULL, keyparms[idx]);
1113       if (err)
1114         die ("error formatting parameter: %s\n", gpg_strerror (err));
1115       der += keyparmslen[idx];
1116     }
1117
1118   /* Print the stuff.  */
1119   for (idx=0; idx < DIM(keyparms); idx++) 
1120     gcry_mpi_release (keyparms[idx]);
1121
1122   assert (der - derbuf == derlen);
1123
1124   if (base64_output)
1125     puts ("-----BEGIN RSA PRIVATE KEY-----");
1126   print_buffer (derbuf, derlen);
1127   if (base64_output)
1128     puts ("-----END RSA PRIVATE KEY-----");
1129
1130   gcry_free (derbuf);
1131 }
1132
1133
1134 \f
1135 /* Sign DATA of length DATALEN using the key taken from the PEM
1136    encoded KEYFILE and the hash algorithm HASHALGO.  */
1137 static void
1138 run_rsa_sign (const void *data, size_t datalen,
1139               int hashalgo, int pkcs1, const char *keyfile)
1140
1141 {
1142   gpg_error_t err;
1143   gcry_sexp_t s_data, s_key, s_sig, s_tmp;
1144   gcry_mpi_t sig_mpi = NULL;
1145   unsigned char *outbuf;
1146   size_t outlen;
1147   
1148 /*   showhex ("D", data, datalen); */
1149   if (pkcs1)
1150     {
1151       unsigned char hash[50];
1152       unsigned int hashsize;
1153
1154       hashsize = gcry_md_get_algo_dlen (hashalgo);
1155       if (!hashsize || hashsize > sizeof hash)
1156         die ("digest too long for buffer or unknown hash algorithm\n");
1157       gcry_md_hash_buffer (hashalgo, hash, data, datalen);
1158       err = gcry_sexp_build (&s_data, NULL,
1159                              "(data (flags pkcs1)(hash %s %b))",
1160                              gcry_md_algo_name (hashalgo),
1161                              (int)hashsize, hash);
1162     }
1163   else
1164     {
1165       gcry_mpi_t tmp;
1166
1167       err = gcry_mpi_scan (&tmp, GCRYMPI_FMT_USG, data, datalen,NULL);
1168       if (!err)
1169         {
1170           err = gcry_sexp_build (&s_data, NULL,
1171                                  "(data (flags raw)(value %m))", tmp);
1172           gcry_mpi_release (tmp);
1173         }
1174     }
1175   if (err)
1176     die ("gcry_sexp_build failed for RSA data input: %s\n",
1177          gpg_strerror (err));
1178
1179   s_key = read_private_key_file (keyfile, 0);
1180
1181   err = gcry_pk_sign (&s_sig, s_data, s_key);
1182   if (err)
1183     {
1184       gcry_sexp_release (read_private_key_file (keyfile, 1));
1185       die ("gcry_pk_signed failed (datalen=%d,keyfile=%s): %s\n",
1186            (int)datalen, keyfile, gpg_strerror (err));
1187     }
1188   gcry_sexp_release (s_key);
1189   gcry_sexp_release (s_data);
1190
1191   s_tmp = gcry_sexp_find_token (s_sig, "sig-val", 0);
1192   if (s_tmp)
1193     {
1194       gcry_sexp_release (s_sig);
1195       s_sig = s_tmp;
1196       s_tmp = gcry_sexp_find_token (s_sig, "rsa", 0);
1197       if (s_tmp)
1198         {
1199           gcry_sexp_release (s_sig);
1200           s_sig = s_tmp;
1201           s_tmp = gcry_sexp_find_token (s_sig, "s", 0);
1202           if (s_tmp)
1203             {
1204               gcry_sexp_release (s_sig);
1205               s_sig = s_tmp;
1206               sig_mpi = gcry_sexp_nth_mpi (s_sig, 1, GCRYMPI_FMT_USG);
1207             }
1208         }
1209     }
1210   gcry_sexp_release (s_sig);
1211               
1212   if (!sig_mpi)
1213     die ("no value in returned S-expression\n");
1214   err = gcry_mpi_aprint (GCRYMPI_FMT_STD, &outbuf, &outlen, sig_mpi);
1215   if (err)
1216     die ("gcry_mpi_aprint failed: %s\n", gpg_strerror (err));
1217   gcry_mpi_release (sig_mpi);
1218
1219   print_buffer (outbuf, outlen);
1220   gcry_free (outbuf);
1221 }
1222
1223
1224 \f
1225 /* Verify DATA of length DATALEN using the public key taken from the
1226    PEM encoded KEYFILE and the hash algorithm HASHALGO against the
1227    binary signature in SIGFILE.  */
1228 static void
1229 run_rsa_verify (const void *data, size_t datalen, int hashalgo, int pkcs1,
1230                 const char *keyfile, const char *sigfile)
1231
1232 {
1233   gpg_error_t err;
1234   gcry_sexp_t s_data, s_key, s_sig;
1235   
1236   if (pkcs1)
1237     {
1238       unsigned char hash[64];
1239       unsigned int hashsize;
1240
1241       hashsize = gcry_md_get_algo_dlen (hashalgo);
1242       if (!hashsize || hashsize > sizeof hash)
1243         die ("digest too long for buffer or unknown hash algorithm\n");
1244       gcry_md_hash_buffer (hashalgo, hash, data, datalen);
1245       err = gcry_sexp_build (&s_data, NULL,
1246                              "(data (flags pkcs1)(hash %s %b))",
1247                              gcry_md_algo_name (hashalgo),
1248                              (int)hashsize, hash);
1249     }
1250   else
1251     {
1252       gcry_mpi_t tmp;
1253
1254       err = gcry_mpi_scan (&tmp, GCRYMPI_FMT_USG, data, datalen,NULL);
1255       if (!err)
1256         {
1257           err = gcry_sexp_build (&s_data, NULL,
1258                                  "(data (flags raw)(value %m))", tmp);
1259           gcry_mpi_release (tmp);
1260         }
1261     }
1262   if (err)
1263     die ("gcry_sexp_build failed for RSA data input: %s\n",
1264          gpg_strerror (err));
1265
1266   s_key = read_public_key_file (keyfile, 0);
1267
1268   s_sig = read_sig_file (sigfile);
1269
1270   err = gcry_pk_verify (s_sig, s_data, s_key);
1271   if (!err)
1272     puts ("GOOD signature");
1273   else if (gpg_err_code (err) == GPG_ERR_BAD_SIGNATURE)
1274     puts ("BAD signature");
1275   else
1276     printf ("ERROR (%s)\n", gpg_strerror (err));
1277
1278   gcry_sexp_release (s_sig);
1279   gcry_sexp_release (s_key);
1280   gcry_sexp_release (s_data);
1281 }
1282
1283
1284
1285 \f
1286 static void
1287 usage (int show_help)
1288 {
1289   if (!show_help)
1290     {
1291       fputs ("usage: " PGM 
1292              " [OPTION] [FILE] (try --help for more information)\n", stderr);
1293       exit (2);
1294     }
1295   fputs
1296     ("Usage: " PGM " [OPTIONS] MODE [FILE]\n"
1297      "Run a crypto operation using hex encoded input and output.\n"
1298      "MODE:\n"
1299      "  encrypt, decrypt, digest, random, hmac-sha, rsa-{gen,sign,verify}\n"
1300      "OPTIONS:\n"
1301      "  --verbose        print additional information\n"
1302      "  --binary         input and output is in binary form\n"
1303      "  --no-fips        do not force FIPS mode\n"
1304      "  --key KEY        use the hex encoded KEY\n"
1305      "  --iv IV          use the hex encoded IV\n"
1306      "  --dt DT          use the hex encoded DT for the RNG\n"
1307      "  --algo NAME      use algorithm NAME\n"
1308      "  --keysize N      use a keysize of N bits\n"
1309      "  --signature NAME take signature from file NAME\n"
1310      "  --chunk N        read in chunks of N bytes (implies --binary)\n"
1311      "  --pkcs1          use PKCS#1 encoding\n"
1312      "  --loop           enable random loop mode\n"
1313      "  --progress       print pogress indicators\n"
1314      "  --help           print this text\n"
1315      "With no FILE, or when FILE is -, read standard input.\n"
1316      "Report bugs to " PACKAGE_BUGREPORT ".\n" , stdout);
1317   exit (0);
1318 }
1319
1320 int
1321 main (int argc, char **argv)
1322 {
1323   int last_argc = -1;
1324   gpg_error_t err;
1325   int no_fips = 0;
1326   int progress = 0;
1327   int use_pkcs1 = 0;
1328   const char *mode_string;
1329   const char *key_string = NULL;
1330   const char *iv_string = NULL;
1331   const char *dt_string = NULL;
1332   const char *algo_string = NULL;
1333   const char *keysize_string = NULL;
1334   const char *signature_string = NULL;
1335   FILE *input;
1336   void *data;
1337   size_t datalen;
1338   size_t chunksize = 0;
1339
1340
1341   if (argc)
1342     { argc--; argv++; }
1343
1344   while (argc && last_argc != argc )
1345     {
1346       last_argc = argc;
1347       if (!strcmp (*argv, "--"))
1348         {
1349           argc--; argv++;
1350           break;
1351         }
1352       else if (!strcmp (*argv, "--help"))
1353         {
1354           usage (1);
1355         }
1356       else if (!strcmp (*argv, "--version"))
1357         {
1358           fputs (PGM " (Libgcrypt) " PACKAGE_VERSION "\n", stdout);
1359           exit (0);
1360         }
1361       else if (!strcmp (*argv, "--verbose"))
1362         {
1363           verbose++;
1364           argc--; argv++;
1365         }
1366       else if (!strcmp (*argv, "--binary"))
1367         {
1368           binary_input = binary_output = 1;
1369           argc--; argv++;
1370         }
1371       else if (!strcmp (*argv, "--no-fips"))
1372         {
1373           no_fips++;
1374           argc--; argv++;
1375         }
1376       else if (!strcmp (*argv, "--loop"))
1377         {
1378           loop_mode = 1;
1379           argc--; argv++;
1380         }
1381       else if (!strcmp (*argv, "--progress"))
1382         {
1383           progress = 1;
1384           argc--; argv++;
1385         }
1386       else if (!strcmp (*argv, "--key"))
1387         {
1388           argc--; argv++;
1389           if (!argc)
1390             usage (0);
1391           key_string = *argv;
1392           argc--; argv++;
1393         }
1394       else if (!strcmp (*argv, "--iv"))
1395         {
1396           argc--; argv++;
1397           if (!argc)
1398             usage (0);
1399           iv_string = *argv;
1400           argc--; argv++;
1401         }
1402       else if (!strcmp (*argv, "--dt"))
1403         {
1404           argc--; argv++;
1405           if (!argc)
1406             usage (0);
1407           dt_string = *argv;
1408           argc--; argv++;
1409         }
1410       else if (!strcmp (*argv, "--algo"))
1411         {
1412           argc--; argv++;
1413           if (!argc)
1414             usage (0);
1415           algo_string = *argv;
1416           argc--; argv++;
1417         }
1418       else if (!strcmp (*argv, "--keysize"))
1419         {
1420           argc--; argv++;
1421           if (!argc)
1422             usage (0);
1423           keysize_string = *argv;
1424           argc--; argv++;
1425         }
1426       else if (!strcmp (*argv, "--signature"))
1427         {
1428           argc--; argv++;
1429           if (!argc)
1430             usage (0);
1431           signature_string = *argv;
1432           argc--; argv++;
1433         }
1434       else if (!strcmp (*argv, "--chunk"))
1435         {
1436           argc--; argv++;
1437           if (!argc)
1438             usage (0);
1439           chunksize = atoi (*argv);
1440           binary_input = binary_output = 1;
1441           argc--; argv++;
1442         }
1443       else if (!strcmp (*argv, "--pkcs1"))
1444         {
1445           use_pkcs1 = 1;
1446           argc--; argv++;
1447         }
1448     }          
1449
1450   if (!argc || argc > 2)
1451     usage (0);
1452   mode_string = *argv;
1453   if (argc == 2 && strcmp (argv[1], "-"))
1454     {
1455       input = fopen (argv[1], binary_input? "rb":"r");
1456       if (!input)
1457         die ("can't open `%s': %s\n", argv[1], strerror (errno));
1458     }
1459   else
1460     input = stdin;
1461
1462 #ifndef HAVE_W32_SYSTEM
1463   if (loop_mode)
1464     signal (SIGPIPE, SIG_IGN);
1465 #endif
1466
1467   if (verbose)
1468     fprintf (stderr, PGM ": started (mode=%s)\n", mode_string);
1469
1470   gcry_control (GCRYCTL_SET_VERBOSITY, (int)verbose);
1471   if (!no_fips)
1472     gcry_control (GCRYCTL_FORCE_FIPS_MODE, 0);
1473   if (!gcry_check_version ("1.4.3"))
1474     die ("Libgcrypt is not sufficient enough\n");
1475   if (verbose)
1476     fprintf (stderr, PGM ": using Libgcrypt %s\n", gcry_check_version (NULL));
1477   if (no_fips)
1478     gcry_control (GCRYCTL_DISABLE_SECMEM, 0);
1479   gcry_control (GCRYCTL_INITIALIZATION_FINISHED, 0);
1480
1481   /* Most operations need some input data.  */
1482   if (!chunksize
1483       && strcmp (mode_string, "random")
1484       && strcmp (mode_string, "rsa-gen") )
1485     {
1486       data = read_file (input, !binary_input, &datalen);
1487       if (!data)
1488         die ("error reading%s input\n", binary_input?"":" and decoding");
1489       if (verbose)
1490         fprintf (stderr, PGM ": %u bytes of input data\n", 
1491                  (unsigned int)datalen);
1492     }
1493   else
1494     {
1495       data = NULL;
1496       datalen = 0;
1497     }
1498
1499
1500   if (!strcmp (mode_string, "encrypt") || !strcmp (mode_string, "decrypt"))
1501     {
1502       int cipher_algo, cipher_mode;
1503       void  *iv_buffer, *key_buffer;
1504       size_t iv_buflen,  key_buflen;
1505
1506       if (!algo_string)
1507         die ("option --algo is required in this mode\n");
1508       cipher_algo = map_openssl_cipher_name (algo_string, &cipher_mode);
1509       if (!cipher_algo)
1510         die ("cipher algorithm `%s' is not supported\n", algo_string);
1511       if (!iv_string)
1512         die ("option --iv is required in this mode\n");
1513       iv_buffer = hex2buffer (iv_string, &iv_buflen);
1514       if (!iv_buffer)
1515         die ("invalid value for IV\n");
1516       if (!key_string)
1517         die ("option --key is required in this mode\n");
1518       key_buffer = hex2buffer (key_string, &key_buflen);
1519       if (!key_buffer)
1520         die ("invalid value for KEY\n");
1521
1522       run_encrypt_decrypt ((*mode_string == 'e'),
1523                            cipher_algo, cipher_mode,
1524                            iv_buffer, iv_buflen,
1525                            key_buffer, key_buflen,
1526                            data, data? datalen:chunksize, input);
1527       gcry_free (key_buffer);
1528       gcry_free (iv_buffer);
1529     }
1530   else if (!strcmp (mode_string, "digest"))
1531     {
1532       int algo;
1533
1534       if (!algo_string)
1535         die ("option --algo is required in this mode\n");
1536       algo = gcry_md_map_name (algo_string);
1537       if (!algo)
1538         die ("digest algorithm `%s' is not supported\n", algo_string);
1539
1540       run_digest (algo, data, datalen);
1541     }
1542   else if (!strcmp (mode_string, "random"))
1543     {
1544       void *context;
1545       unsigned char key[16];
1546       unsigned char seed[16];
1547       unsigned char dt[16];
1548       unsigned char buffer[16];
1549       size_t count = 0;
1550
1551       if (hex2bin (key_string, key, 16) < 0 )
1552         die ("value for --key are not 32 hex digits\n");
1553       if (hex2bin (iv_string, seed, 16) < 0 )
1554         die ("value for --iv are not 32 hex digits\n");
1555       if (hex2bin (dt_string, dt, 16) < 0 )
1556         die ("value for --dt are not 32 hex digits\n");
1557
1558       /* The flag value 1 disables the dup check, so that the RNG
1559          returns all generated data.  */
1560       err = init_external_rng_test (&context, 1, key, 16, seed, 16, dt, 16);
1561       if (err)
1562         die ("init external RNG test failed: %s\n", gpg_strerror (err));
1563
1564       do 
1565         {
1566           err = run_external_rng_test (context, buffer, sizeof buffer);
1567           if (err)
1568             die ("running external RNG test failed: %s\n", gpg_strerror (err));
1569           print_buffer (buffer, sizeof buffer);
1570           if (progress)
1571             {
1572               if (!(++count % 1000))
1573                 fprintf (stderr, PGM ": %lu random bytes so far\n", 
1574                          (unsigned long int)count * sizeof buffer);
1575             }
1576         }
1577       while (loop_mode);
1578       
1579       if (progress)
1580         fprintf (stderr, PGM ": %lu random bytes\n",
1581                          (unsigned long int)count * sizeof buffer);
1582
1583       deinit_external_rng_test (context);
1584     }
1585   else if (!strcmp (mode_string, "hmac-sha"))
1586     {
1587       int algo;
1588       void  *key_buffer;
1589       size_t key_buflen;
1590
1591       if (!data)
1592         die ("no data available (do not use --chunk)\n");
1593       if (!algo_string)
1594         die ("option --algo is required in this mode\n");
1595       switch (atoi (algo_string))
1596         {
1597         case 1:   algo = GCRY_MD_SHA1; break;
1598         case 224: algo = GCRY_MD_SHA224; break;
1599         case 256: algo = GCRY_MD_SHA256; break;
1600         case 384: algo = GCRY_MD_SHA384; break;
1601         case 512: algo = GCRY_MD_SHA512; break;
1602         default:  algo = 0; break;
1603         }
1604       if (!algo)
1605         die ("no digest algorithm found for hmac type `%s'\n", algo_string);
1606       if (!key_string)
1607         die ("option --key is required in this mode\n");
1608       key_buffer = hex2buffer (key_string, &key_buflen);
1609       if (!key_buffer)
1610         die ("invalid value for KEY\n");
1611
1612       run_hmac (algo, key_buffer, key_buflen, data, datalen);
1613
1614       gcry_free (key_buffer);
1615     }
1616   else if (!strcmp (mode_string, "rsa-gen"))
1617     {
1618       int keysize;
1619       
1620       if (!binary_output)
1621         base64_output = 1;
1622
1623       keysize = keysize_string? atoi (keysize_string) : 0;
1624       if (keysize < 128 || keysize > 16384)
1625         die ("invalid keysize specified; needs to be 128 .. 16384\n");
1626       run_rsa_gen (keysize, 65537);
1627     }
1628   else if (!strcmp (mode_string, "rsa-sign"))
1629     {
1630       int algo;
1631
1632       if (!key_string)
1633         die ("option --key is required in this mode\n");
1634       if (access (key_string, R_OK))
1635         die ("option --key needs to specify an existing keyfile\n");
1636       if (!algo_string)
1637         die ("option --algo is required in this mode\n");
1638       algo = gcry_md_map_name (algo_string);
1639       if (!algo)
1640         die ("digest algorithm `%s' is not supported\n", algo_string);
1641       if (!data)
1642         die ("no data available (do not use --chunk)\n");
1643
1644       run_rsa_sign (data, datalen, algo, use_pkcs1, key_string);
1645
1646     }
1647   else if (!strcmp (mode_string, "rsa-verify"))
1648     {
1649       int algo;
1650
1651       if (!key_string)
1652         die ("option --key is required in this mode\n");
1653       if (access (key_string, R_OK))
1654         die ("option --key needs to specify an existing keyfile\n");
1655       if (!algo_string)
1656         die ("option --algo is required in this mode\n");
1657       algo = gcry_md_map_name (algo_string);
1658       if (!algo)
1659         die ("digest algorithm `%s' is not supported\n", algo_string);
1660       if (!data)
1661         die ("no data available (do not use --chunk)\n");
1662       if (!signature_string)
1663         die ("option --signature is required in this mode\n");
1664       if (access (signature_string, R_OK))
1665         die ("option --signature needs to specify an existing file\n");
1666
1667       run_rsa_verify (data, datalen, algo, use_pkcs1, key_string,
1668                       signature_string);
1669
1670     }
1671   else
1672     usage (0);
1673
1674   gcry_free (data);
1675
1676   /* Because Libgcrypt does not enforce FIPS mode in all cases we let
1677      the process die if Libgcrypt is not anymore in FIPS mode after
1678      the actual operation.  */
1679   if (!no_fips && !gcry_fips_mode_active ())
1680     die ("FIPS mode is not anymore active\n");
1681
1682   if (verbose)
1683     fputs (PGM ": ready\n", stderr);
1684
1685   return 0;
1686 }
1687