Coverage Report

Created: 2022-12-08 06:09

/src/libgcrypt/cipher/md.c
Line
Count
Source (jump to first uncovered line)
1
/* md.c  -  message digest dispatcher
2
 * Copyright (C) 1998, 1999, 2002, 2003, 2006,
3
 *               2008 Free Software Foundation, Inc.
4
 * Copyright (C) 2013, 2014 g10 Code GmbH
5
 *
6
 * This file is part of Libgcrypt.
7
 *
8
 * Libgcrypt is free software; you can redistribute it and/or modify
9
 * it under the terms of the GNU Lesser general Public License as
10
 * published by the Free Software Foundation; either version 2.1 of
11
 * the License, or (at your option) any later version.
12
 *
13
 * Libgcrypt is distributed in the hope that it will be useful,
14
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16
 * GNU Lesser General Public License for more details.
17
 *
18
 * You should have received a copy of the GNU Lesser General Public
19
 * License along with this program; if not, see <http://www.gnu.org/licenses/>.
20
 */
21
22
#include <config.h>
23
#include <stdio.h>
24
#include <stdlib.h>
25
#include <string.h>
26
#include <errno.h>
27
28
#include "g10lib.h"
29
#include "cipher.h"
30
31
32
/* This is the list of the digest implementations included in
33
   libgcrypt.  */
34
static const gcry_md_spec_t * const digest_list[] =
35
  {
36
#if USE_CRC
37
     &_gcry_digest_spec_crc32,
38
     &_gcry_digest_spec_crc32_rfc1510,
39
     &_gcry_digest_spec_crc24_rfc2440,
40
#endif
41
#if USE_SHA1
42
     &_gcry_digest_spec_sha1,
43
#endif
44
#if USE_SHA256
45
     &_gcry_digest_spec_sha256,
46
     &_gcry_digest_spec_sha224,
47
#endif
48
#if USE_SHA512
49
     &_gcry_digest_spec_sha512,
50
     &_gcry_digest_spec_sha384,
51
     &_gcry_digest_spec_sha512_256,
52
     &_gcry_digest_spec_sha512_224,
53
#endif
54
#if USE_SHA3
55
     &_gcry_digest_spec_sha3_224,
56
     &_gcry_digest_spec_sha3_256,
57
     &_gcry_digest_spec_sha3_384,
58
     &_gcry_digest_spec_sha3_512,
59
     &_gcry_digest_spec_shake128,
60
     &_gcry_digest_spec_shake256,
61
#endif
62
#if USE_GOST_R_3411_94
63
     &_gcry_digest_spec_gost3411_94,
64
     &_gcry_digest_spec_gost3411_cp,
65
#endif
66
#if USE_GOST_R_3411_12
67
     &_gcry_digest_spec_stribog_256,
68
     &_gcry_digest_spec_stribog_512,
69
#endif
70
#if USE_WHIRLPOOL
71
     &_gcry_digest_spec_whirlpool,
72
#endif
73
#if USE_RMD160
74
     &_gcry_digest_spec_rmd160,
75
#endif
76
#if USE_TIGER
77
     &_gcry_digest_spec_tiger,
78
     &_gcry_digest_spec_tiger1,
79
     &_gcry_digest_spec_tiger2,
80
#endif
81
#if USE_MD5
82
     &_gcry_digest_spec_md5,
83
#endif
84
#if USE_MD4
85
     &_gcry_digest_spec_md4,
86
#endif
87
#if USE_MD2
88
     &_gcry_digest_spec_md2,
89
#endif
90
#if USE_BLAKE2
91
     &_gcry_digest_spec_blake2b_512,
92
     &_gcry_digest_spec_blake2b_384,
93
     &_gcry_digest_spec_blake2b_256,
94
     &_gcry_digest_spec_blake2b_160,
95
     &_gcry_digest_spec_blake2s_256,
96
     &_gcry_digest_spec_blake2s_224,
97
     &_gcry_digest_spec_blake2s_160,
98
     &_gcry_digest_spec_blake2s_128,
99
#endif
100
#if USE_SM3
101
     &_gcry_digest_spec_sm3,
102
#endif
103
     NULL
104
  };
105
106
/* Digest implementations starting with index 0 (enum gcry_md_algos) */
107
static const gcry_md_spec_t * const digest_list_algo0[] =
108
  {
109
    NULL, /* GCRY_MD_NONE */
110
#if USE_MD5
111
    &_gcry_digest_spec_md5,
112
#else
113
    NULL,
114
#endif
115
#if USE_SHA1
116
    &_gcry_digest_spec_sha1,
117
#else
118
    NULL,
119
#endif
120
#if USE_RMD160
121
    &_gcry_digest_spec_rmd160,
122
#else
123
    NULL,
124
#endif
125
    NULL, /* Unused index 4 */
126
#if USE_MD2
127
    &_gcry_digest_spec_md2,
128
#else
129
    NULL,
130
#endif
131
#if USE_TIGER
132
    &_gcry_digest_spec_tiger,
133
#else
134
    NULL,
135
#endif
136
    NULL, /* GCRY_MD_HAVAL */
137
#if USE_SHA256
138
    &_gcry_digest_spec_sha256,
139
#else
140
    NULL,
141
#endif
142
#if USE_SHA512
143
    &_gcry_digest_spec_sha384,
144
    &_gcry_digest_spec_sha512,
145
#else
146
    NULL,
147
    NULL,
148
#endif
149
#if USE_SHA256
150
    &_gcry_digest_spec_sha224
151
#else
152
    NULL
153
#endif
154
  };
155
156
/* Digest implementations starting with index 301 (enum gcry_md_algos) */
157
static const gcry_md_spec_t * const digest_list_algo301[] =
158
  {
159
#if USE_MD4
160
    &_gcry_digest_spec_md4,
161
#else
162
    NULL,
163
#endif
164
#if USE_CRC
165
    &_gcry_digest_spec_crc32,
166
    &_gcry_digest_spec_crc32_rfc1510,
167
    &_gcry_digest_spec_crc24_rfc2440,
168
#else
169
    NULL,
170
    NULL,
171
    NULL,
172
#endif
173
#if USE_WHIRLPOOL
174
    &_gcry_digest_spec_whirlpool,
175
#else
176
    NULL,
177
#endif
178
#if USE_TIGER
179
    &_gcry_digest_spec_tiger1,
180
    &_gcry_digest_spec_tiger2,
181
#else
182
    NULL,
183
    NULL,
184
#endif
185
#if USE_GOST_R_3411_94
186
    &_gcry_digest_spec_gost3411_94,
187
#else
188
    NULL,
189
#endif
190
#if USE_GOST_R_3411_12
191
    &_gcry_digest_spec_stribog_256,
192
    &_gcry_digest_spec_stribog_512,
193
#else
194
    NULL,
195
    NULL,
196
#endif
197
#if USE_GOST_R_3411_94
198
    &_gcry_digest_spec_gost3411_cp,
199
#else
200
    NULL,
201
#endif
202
#if USE_SHA3
203
    &_gcry_digest_spec_sha3_224,
204
    &_gcry_digest_spec_sha3_256,
205
    &_gcry_digest_spec_sha3_384,
206
    &_gcry_digest_spec_sha3_512,
207
    &_gcry_digest_spec_shake128,
208
    &_gcry_digest_spec_shake256,
209
#else
210
    NULL,
211
    NULL,
212
    NULL,
213
    NULL,
214
    NULL,
215
    NULL,
216
#endif
217
#if USE_BLAKE2
218
    &_gcry_digest_spec_blake2b_512,
219
    &_gcry_digest_spec_blake2b_384,
220
    &_gcry_digest_spec_blake2b_256,
221
    &_gcry_digest_spec_blake2b_160,
222
    &_gcry_digest_spec_blake2s_256,
223
    &_gcry_digest_spec_blake2s_224,
224
    &_gcry_digest_spec_blake2s_160,
225
    &_gcry_digest_spec_blake2s_128,
226
#else
227
    NULL,
228
    NULL,
229
    NULL,
230
    NULL,
231
    NULL,
232
    NULL,
233
    NULL,
234
    NULL,
235
#endif
236
#if USE_SM3
237
    &_gcry_digest_spec_sm3,
238
#else
239
    NULL,
240
#endif
241
#if USE_SHA512
242
    &_gcry_digest_spec_sha512_256,
243
    &_gcry_digest_spec_sha512_224,
244
#else
245
    NULL,
246
    NULL,
247
#endif
248
  };
249
250
251
typedef struct gcry_md_list
252
{
253
  const gcry_md_spec_t *spec;
254
  struct gcry_md_list *next;
255
  size_t actual_struct_size;     /* Allocated size of this structure. */
256
  PROPERLY_ALIGNED_TYPE context[1];
257
} GcryDigestEntry;
258
259
/* This structure is put right after the gcry_md_hd_t buffer, so that
260
 * only one memory block is needed. */
261
struct gcry_md_context
262
{
263
  int  magic;
264
  struct {
265
    unsigned int secure:1;
266
    unsigned int finalized:1;
267
    unsigned int bugemu1:1;
268
    unsigned int hmac:1;
269
  } flags;
270
  size_t actual_handle_size;     /* Allocated size of this handle. */
271
  FILE  *debug;
272
  GcryDigestEntry *list;
273
};
274
275
276
97.9k
#define CTX_MAGIC_NORMAL 0x11071961
277
0
#define CTX_MAGIC_SECURE 0x16917011
278
279
static gcry_err_code_t md_enable (gcry_md_hd_t hd, int algo);
280
static void md_close (gcry_md_hd_t a);
281
static void md_write (gcry_md_hd_t a, const void *inbuf, size_t inlen);
282
static byte *md_read( gcry_md_hd_t a, int algo );
283
static int md_get_algo( gcry_md_hd_t a );
284
static int md_digest_length( int algo );
285
static void md_start_debug ( gcry_md_hd_t a, const char *suffix );
286
static void md_stop_debug ( gcry_md_hd_t a );
287
288
289

290
static int
291
map_algo (int algo)
292
108k
{
293
108k
  return algo;
294
108k
}
295
296
297
/* Return the spec structure for the hash algorithm ALGO.  For an
298
   unknown algorithm NULL is returned.  */
299
static const gcry_md_spec_t *
300
spec_from_algo (int algo)
301
108k
{
302
108k
  const gcry_md_spec_t *spec = NULL;
303
304
108k
  algo = map_algo (algo);
305
306
108k
  if (algo >= 0 && algo < DIM(digest_list_algo0))
307
105k
    spec = digest_list_algo0[algo];
308
2.68k
  else if (algo >= 301 && algo < 301 + DIM(digest_list_algo301))
309
2.68k
    spec = digest_list_algo301[algo - 301];
310
311
108k
  if (spec)
312
108k
    gcry_assert (spec->algo == algo);
313
314
0
  return spec;
315
108k
}
316
317
318
/* Lookup a hash's spec by its name.  */
319
static const gcry_md_spec_t *
320
spec_from_name (const char *name)
321
0
{
322
0
  const gcry_md_spec_t *spec;
323
0
  int idx;
324
325
0
  for (idx=0; (spec = digest_list[idx]); idx++)
326
0
    {
327
0
      if (!stricmp (name, spec->name))
328
0
        return spec;
329
0
    }
330
331
0
  return NULL;
332
0
}
333
334
335
/* Lookup a hash's spec by its OID.  */
336
static const gcry_md_spec_t *
337
spec_from_oid (const char *oid)
338
0
{
339
0
  const gcry_md_spec_t *spec;
340
0
  const gcry_md_oid_spec_t *oid_specs;
341
0
  int idx, j;
342
343
0
  for (idx=0; (spec = digest_list[idx]); idx++)
344
0
    {
345
0
      oid_specs = spec->oids;
346
0
      if (oid_specs)
347
0
        {
348
0
          for (j = 0; oid_specs[j].oidstring; j++)
349
0
            if (!stricmp (oid, oid_specs[j].oidstring))
350
0
              return spec;
351
0
        }
352
0
    }
353
354
0
  return NULL;
355
0
}
356
357
358
static const gcry_md_spec_t *
359
search_oid (const char *oid, gcry_md_oid_spec_t *oid_spec)
360
0
{
361
0
  const gcry_md_spec_t *spec;
362
0
  int i;
363
364
0
  if (!oid)
365
0
    return NULL;
366
367
0
  if (!strncmp (oid, "oid.", 4) || !strncmp (oid, "OID.", 4))
368
0
    oid += 4;
369
370
0
  spec = spec_from_oid (oid);
371
0
  if (spec && spec->oids)
372
0
    {
373
0
      for (i = 0; spec->oids[i].oidstring; i++)
374
0
  if (!stricmp (oid, spec->oids[i].oidstring))
375
0
    {
376
0
      if (oid_spec)
377
0
        *oid_spec = spec->oids[i];
378
0
      return spec;
379
0
    }
380
0
    }
381
382
0
  return NULL;
383
0
}
384
385
386
/****************
387
 * Map a string to the digest algo
388
 */
389
int
390
_gcry_md_map_name (const char *string)
391
0
{
392
0
  const gcry_md_spec_t *spec;
393
394
0
  if (!string)
395
0
    return 0;
396
397
  /* If the string starts with a digit (optionally prefixed with
398
     either "OID." or "oid."), we first look into our table of ASN.1
399
     object identifiers to figure out the algorithm */
400
0
  spec = search_oid (string, NULL);
401
0
  if (spec)
402
0
    return spec->algo;
403
404
  /* Not found, search a matching digest name.  */
405
0
  spec = spec_from_name (string);
406
0
  if (spec)
407
0
    return spec->algo;
408
409
0
  return 0;
410
0
}
411
412
413
/****************
414
 * This function simply returns the name of the algorithm or some constant
415
 * string when there is no algo.  It will never return NULL.
416
 * Use  the macro gcry_md_test_algo() to check whether the algorithm
417
 * is valid.
418
 */
419
const char *
420
_gcry_md_algo_name (int algorithm)
421
0
{
422
0
  const gcry_md_spec_t *spec;
423
424
0
  spec = spec_from_algo (algorithm);
425
0
  return spec ? spec->name : "?";
426
0
}
427
428
429
static gcry_err_code_t
430
check_digest_algo (int algorithm)
431
10.1k
{
432
10.1k
  const gcry_md_spec_t *spec;
433
434
10.1k
  spec = spec_from_algo (algorithm);
435
10.1k
  if (spec && !spec->flags.disabled && (spec->flags.fips || !fips_mode ()))
436
10.1k
    return 0;
437
438
0
  return GPG_ERR_DIGEST_ALGO;
439
440
10.1k
}
441
442
443
/****************
444
 * Open a message digest handle for use with algorithm ALGO.
445
 * More algorithms may be added by md_enable(). The initial algorithm
446
 * may be 0.
447
 */
448
static gcry_err_code_t
449
md_open (gcry_md_hd_t *h, int algo, unsigned int flags)
450
48.9k
{
451
48.9k
  gcry_err_code_t err = 0;
452
48.9k
  int secure = !!(flags & GCRY_MD_FLAG_SECURE);
453
48.9k
  int hmac =   !!(flags & GCRY_MD_FLAG_HMAC);
454
48.9k
  int bufsize = secure ? 512 : 1024;
455
48.9k
  gcry_md_hd_t hd;
456
48.9k
  size_t n;
457
458
  /* Allocate a memory area to hold the caller visible buffer with it's
459
   * control information and the data required by this module. Set the
460
   * context pointer at the beginning to this area.
461
   * We have to use this strange scheme because we want to hide the
462
   * internal data but have a variable sized buffer.
463
   *
464
   *  +---+------+---........------+-------------+
465
   *  !ctx! bctl !  buffer       ! private     !
466
   *  +---+------+---........------+-------------+
467
   *    !           ^
468
   *    !---------------------------!
469
   *
470
   * We have to make sure that private is well aligned.
471
   */
472
48.9k
  n = offsetof (struct gcry_md_handle, buf) + bufsize;
473
48.9k
  n = ((n + sizeof (PROPERLY_ALIGNED_TYPE) - 1)
474
48.9k
       / sizeof (PROPERLY_ALIGNED_TYPE)) * sizeof (PROPERLY_ALIGNED_TYPE);
475
476
  /* Allocate and set the Context pointer to the private data */
477
48.9k
  if (secure)
478
0
    hd = xtrymalloc_secure (n + sizeof (struct gcry_md_context));
479
48.9k
  else
480
48.9k
    hd = xtrymalloc (n + sizeof (struct gcry_md_context));
481
482
48.9k
  if (! hd)
483
0
    err = gpg_err_code_from_errno (errno);
484
485
48.9k
  if (! err)
486
48.9k
    {
487
48.9k
      struct gcry_md_context *ctx;
488
489
48.9k
      ctx = (void *) (hd->buf - offsetof (struct gcry_md_handle, buf) + n);
490
      /* Setup the globally visible data (bctl in the diagram).*/
491
48.9k
      hd->ctx = ctx;
492
48.9k
      hd->bufsize = n - offsetof (struct gcry_md_handle, buf);
493
48.9k
      hd->bufpos = 0;
494
495
      /* Initialize the private data. */
496
48.9k
      wipememory2 (ctx, 0, sizeof *ctx);
497
48.9k
      ctx->magic = secure ? CTX_MAGIC_SECURE : CTX_MAGIC_NORMAL;
498
48.9k
      ctx->actual_handle_size = n + sizeof (struct gcry_md_context);
499
48.9k
      ctx->flags.secure = secure;
500
48.9k
      ctx->flags.hmac = hmac;
501
48.9k
      ctx->flags.bugemu1 = !!(flags & GCRY_MD_FLAG_BUGEMU1);
502
48.9k
    }
503
504
48.9k
  if (! err)
505
48.9k
    {
506
      /* Hmmm, should we really do that? - yes [-wk] */
507
48.9k
      _gcry_fast_random_poll ();
508
509
48.9k
      if (algo)
510
48.9k
  {
511
48.9k
    err = md_enable (hd, algo);
512
48.9k
    if (err)
513
0
      md_close (hd);
514
48.9k
  }
515
48.9k
    }
516
517
48.9k
  if (! err)
518
48.9k
    *h = hd;
519
520
48.9k
  return err;
521
48.9k
}
522
523
/* Create a message digest object for algorithm ALGO.  FLAGS may be
524
   given as an bitwise OR of the gcry_md_flags values.  ALGO may be
525
   given as 0 if the algorithms to be used are later set using
526
   gcry_md_enable. H is guaranteed to be a valid handle or NULL on
527
   error.  */
528
gcry_err_code_t
529
_gcry_md_open (gcry_md_hd_t *h, int algo, unsigned int flags)
530
48.9k
{
531
48.9k
  gcry_err_code_t rc;
532
48.9k
  gcry_md_hd_t hd;
533
534
48.9k
  if ((flags & ~(GCRY_MD_FLAG_SECURE
535
48.9k
                 | GCRY_MD_FLAG_HMAC
536
48.9k
                 | GCRY_MD_FLAG_BUGEMU1)))
537
0
    rc = GPG_ERR_INV_ARG;
538
48.9k
  else
539
48.9k
    rc = md_open (&hd, algo, flags);
540
541
48.9k
  *h = rc? NULL : hd;
542
48.9k
  return rc;
543
48.9k
}
544
545
546
547
static gcry_err_code_t
548
md_enable (gcry_md_hd_t hd, int algorithm)
549
48.9k
{
550
48.9k
  struct gcry_md_context *h = hd->ctx;
551
48.9k
  const gcry_md_spec_t *spec;
552
48.9k
  GcryDigestEntry *entry;
553
48.9k
  gcry_err_code_t err = 0;
554
555
48.9k
  for (entry = h->list; entry; entry = entry->next)
556
0
    if (entry->spec->algo == algorithm)
557
0
      return 0; /* Already enabled */
558
559
48.9k
  spec = spec_from_algo (algorithm);
560
48.9k
  if (!spec)
561
0
    {
562
0
      log_debug ("md_enable: algorithm %d not available\n", algorithm);
563
0
      err = GPG_ERR_DIGEST_ALGO;
564
0
    }
565
566
48.9k
  if (!err && spec->flags.disabled)
567
0
    err = GPG_ERR_DIGEST_ALGO;
568
569
  /* Any non-FIPS algorithm should go this way */
570
48.9k
  if (!err && !spec->flags.fips && fips_mode ())
571
0
    err = GPG_ERR_DIGEST_ALGO;
572
573
48.9k
  if (!err && h->flags.hmac && spec->read == NULL)
574
0
    {
575
      /* Expandable output function cannot act as part of HMAC. */
576
0
      err = GPG_ERR_DIGEST_ALGO;
577
0
    }
578
579
48.9k
  if (!err)
580
48.9k
    {
581
48.9k
      size_t size = (sizeof (*entry)
582
48.9k
                     + spec->contextsize * (h->flags.hmac? 3 : 1)
583
48.9k
                     - sizeof (entry->context));
584
585
      /* And allocate a new list entry. */
586
48.9k
      if (h->flags.secure)
587
0
  entry = xtrymalloc_secure (size);
588
48.9k
      else
589
48.9k
  entry = xtrymalloc (size);
590
591
48.9k
      if (! entry)
592
0
  err = gpg_err_code_from_errno (errno);
593
48.9k
      else
594
48.9k
  {
595
48.9k
    entry->spec = spec;
596
48.9k
    entry->next = h->list;
597
48.9k
          entry->actual_struct_size = size;
598
48.9k
    h->list = entry;
599
600
    /* And init this instance. */
601
48.9k
    entry->spec->init (entry->context,
602
48.9k
                             h->flags.bugemu1? GCRY_MD_FLAG_BUGEMU1:0);
603
48.9k
  }
604
48.9k
    }
605
606
48.9k
  return err;
607
48.9k
}
608
609
610
gcry_err_code_t
611
_gcry_md_enable (gcry_md_hd_t hd, int algorithm)
612
0
{
613
0
  return md_enable (hd, algorithm);
614
0
}
615
616
617
static gcry_err_code_t
618
md_copy (gcry_md_hd_t ahd, gcry_md_hd_t *b_hd)
619
0
{
620
0
  gcry_err_code_t err = 0;
621
0
  struct gcry_md_context *a = ahd->ctx;
622
0
  struct gcry_md_context *b;
623
0
  GcryDigestEntry *ar, *br;
624
0
  gcry_md_hd_t bhd;
625
0
  size_t n;
626
627
0
  if (ahd->bufpos)
628
0
    md_write (ahd, NULL, 0);
629
630
0
  n = (char *) ahd->ctx - (char *) ahd;
631
0
  if (a->flags.secure)
632
0
    bhd = xtrymalloc_secure (n + sizeof (struct gcry_md_context));
633
0
  else
634
0
    bhd = xtrymalloc (n + sizeof (struct gcry_md_context));
635
636
0
  if (!bhd)
637
0
    {
638
0
      err = gpg_err_code_from_syserror ();
639
0
      goto leave;
640
0
    }
641
642
0
  bhd->ctx = b = (void *) ((char *) bhd + n);
643
  /* No need to copy the buffer due to the write above. */
644
0
  gcry_assert (ahd->bufsize == (n - offsetof (struct gcry_md_handle, buf)));
645
0
  bhd->bufsize = ahd->bufsize;
646
0
  bhd->bufpos = 0;
647
0
  gcry_assert (! ahd->bufpos);
648
0
  memcpy (b, a, sizeof *a);
649
0
  b->list = NULL;
650
0
  b->debug = NULL;
651
652
  /* Copy the complete list of algorithms.  The copied list is
653
     reversed, but that doesn't matter. */
654
0
  for (ar = a->list; ar; ar = ar->next)
655
0
    {
656
0
      if (a->flags.secure)
657
0
        br = xtrymalloc_secure (ar->actual_struct_size);
658
0
      else
659
0
        br = xtrymalloc (ar->actual_struct_size);
660
0
      if (!br)
661
0
        {
662
0
          err = gpg_err_code_from_syserror ();
663
0
          md_close (bhd);
664
0
          goto leave;
665
0
        }
666
667
0
      memcpy (br, ar, ar->actual_struct_size);
668
0
      br->next = b->list;
669
0
      b->list = br;
670
0
    }
671
672
0
  if (a->debug)
673
0
    md_start_debug (bhd, "unknown");
674
675
0
  *b_hd = bhd;
676
677
0
 leave:
678
0
  return err;
679
0
}
680
681
682
gcry_err_code_t
683
_gcry_md_copy (gcry_md_hd_t *handle, gcry_md_hd_t hd)
684
0
{
685
0
  gcry_err_code_t rc;
686
687
0
  rc = md_copy (hd, handle);
688
0
  if (rc)
689
0
    *handle = NULL;
690
0
  return rc;
691
0
}
692
693
694
/*
695
 * Reset all contexts and discard any buffered stuff.  This may be used
696
 * instead of a md_close(); md_open().
697
 */
698
void
699
_gcry_md_reset (gcry_md_hd_t a)
700
12.8k
{
701
12.8k
  GcryDigestEntry *r;
702
703
  /* Note: We allow this even in fips non operational mode.  */
704
705
12.8k
  a->bufpos = a->ctx->flags.finalized = 0;
706
707
12.8k
  if (a->ctx->flags.hmac)
708
0
    for (r = a->ctx->list; r; r = r->next)
709
0
      {
710
0
        memcpy (r->context, (char *)r->context + r->spec->contextsize,
711
0
                r->spec->contextsize);
712
0
      }
713
12.8k
  else
714
25.6k
    for (r = a->ctx->list; r; r = r->next)
715
12.8k
      {
716
12.8k
        memset (r->context, 0, r->spec->contextsize);
717
12.8k
        (*r->spec->init) (r->context,
718
12.8k
                          a->ctx->flags.bugemu1? GCRY_MD_FLAG_BUGEMU1:0);
719
12.8k
      }
720
12.8k
}
721
722
723
static void
724
md_close (gcry_md_hd_t a)
725
79.7k
{
726
79.7k
  GcryDigestEntry *r, *r2;
727
728
79.7k
  if (! a)
729
30.8k
    return;
730
48.9k
  if (a->ctx->debug)
731
0
    md_stop_debug (a);
732
97.9k
  for (r = a->ctx->list; r; r = r2)
733
48.9k
    {
734
48.9k
      r2 = r->next;
735
48.9k
      wipememory (r, r->actual_struct_size);
736
48.9k
      xfree (r);
737
48.9k
    }
738
739
48.9k
  wipememory (a, a->ctx->actual_handle_size);
740
48.9k
  xfree(a);
741
48.9k
}
742
743
744
void
745
_gcry_md_close (gcry_md_hd_t hd)
746
79.7k
{
747
  /* Note: We allow this even in fips non operational mode.  */
748
79.7k
  md_close (hd);
749
79.7k
}
750
751
752
static void
753
md_write (gcry_md_hd_t a, const void *inbuf, size_t inlen)
754
99.8k
{
755
99.8k
  GcryDigestEntry *r;
756
757
99.8k
  if (a->ctx->debug)
758
0
    {
759
0
      if (a->bufpos && fwrite (a->buf, a->bufpos, 1, a->ctx->debug) != 1)
760
0
  BUG();
761
0
      if (inlen && fwrite (inbuf, inlen, 1, a->ctx->debug) != 1)
762
0
  BUG();
763
0
    }
764
765
199k
  for (r = a->ctx->list; r; r = r->next)
766
99.8k
    {
767
99.8k
      if (a->bufpos)
768
46.2k
  (*r->spec->write) (r->context, a->buf, a->bufpos);
769
99.8k
      (*r->spec->write) (r->context, inbuf, inlen);
770
99.8k
    }
771
99.8k
  a->bufpos = 0;
772
99.8k
}
773
774
775
/* Note that this function may be used after finalize and read to keep
776
   on writing to the transform function so to mitigate timing
777
   attacks.  */
778
void
779
_gcry_md_write (gcry_md_hd_t hd, const void *inbuf, size_t inlen)
780
99.8k
{
781
99.8k
  md_write (hd, inbuf, inlen);
782
99.8k
}
783
784
785
static void
786
md_final (gcry_md_hd_t a)
787
104k
{
788
104k
  GcryDigestEntry *r;
789
790
104k
  if (a->ctx->flags.finalized)
791
46.9k
    return;
792
793
57.8k
  if (a->bufpos)
794
0
    md_write (a, NULL, 0);
795
796
115k
  for (r = a->ctx->list; r; r = r->next)
797
57.8k
    (*r->spec->final) (r->context);
798
799
57.8k
  a->ctx->flags.finalized = 1;
800
801
57.8k
  if (!a->ctx->flags.hmac)
802
57.8k
    return;
803
804
0
  for (r = a->ctx->list; r; r = r->next)
805
0
    {
806
0
      byte *p;
807
0
      size_t dlen = r->spec->mdlen;
808
0
      byte *hash;
809
0
      gcry_err_code_t err;
810
811
0
      if (r->spec->read == NULL)
812
0
        continue;
813
814
0
      p = r->spec->read (r->context);
815
816
0
      if (a->ctx->flags.secure)
817
0
        hash = xtrymalloc_secure (dlen);
818
0
      else
819
0
        hash = xtrymalloc (dlen);
820
0
      if (!hash)
821
0
        {
822
0
          err = gpg_err_code_from_errno (errno);
823
0
          _gcry_fatal_error (err, NULL);
824
0
        }
825
826
0
      memcpy (hash, p, dlen);
827
0
      memcpy (r->context, (char *)r->context + r->spec->contextsize * 2,
828
0
              r->spec->contextsize);
829
0
      (*r->spec->write) (r->context, hash, dlen);
830
0
      (*r->spec->final) (r->context);
831
0
      xfree (hash);
832
0
    }
833
0
}
834
835
836
static gcry_err_code_t
837
md_setkey (gcry_md_hd_t h, const unsigned char *key, size_t keylen)
838
0
{
839
0
  gcry_err_code_t rc = 0;
840
0
  GcryDigestEntry *r;
841
0
  int algo_had_setkey = 0;
842
843
0
  if (!h->ctx->list)
844
0
    return GPG_ERR_DIGEST_ALGO; /* Might happen if no algo is enabled.  */
845
846
0
  if (h->ctx->flags.hmac)
847
0
    return GPG_ERR_DIGEST_ALGO; /* Tried md_setkey for HMAC md. */
848
849
0
  for (r = h->ctx->list; r; r = r->next)
850
0
    {
851
0
      switch (r->spec->algo)
852
0
  {
853
0
#if USE_BLAKE2
854
  /* TODO? add spec->init_with_key? */
855
0
  case GCRY_MD_BLAKE2B_512:
856
0
  case GCRY_MD_BLAKE2B_384:
857
0
  case GCRY_MD_BLAKE2B_256:
858
0
  case GCRY_MD_BLAKE2B_160:
859
0
  case GCRY_MD_BLAKE2S_256:
860
0
  case GCRY_MD_BLAKE2S_224:
861
0
  case GCRY_MD_BLAKE2S_160:
862
0
  case GCRY_MD_BLAKE2S_128:
863
0
    algo_had_setkey = 1;
864
0
    memset (r->context, 0, r->spec->contextsize);
865
0
    rc = _gcry_blake2_init_with_key (r->context,
866
0
             h->ctx->flags.bugemu1
867
0
               ? GCRY_MD_FLAG_BUGEMU1:0,
868
0
             key, keylen, r->spec->algo);
869
0
    break;
870
0
#endif
871
0
  default:
872
0
    rc = GPG_ERR_DIGEST_ALGO;
873
0
    break;
874
0
  }
875
876
0
      if (rc)
877
0
  break;
878
0
    }
879
880
0
  if (rc && !algo_had_setkey)
881
0
    {
882
      /* None of algorithms had setkey implementation, so contexts were not
883
       * modified. Just return error. */
884
0
      return rc;
885
0
    }
886
0
  else if (rc && algo_had_setkey)
887
0
    {
888
      /* Some of the contexts have been modified, but got error. Reset
889
       * all contexts. */
890
0
      _gcry_md_reset (h);
891
0
      return rc;
892
0
    }
893
894
  /* Successful md_setkey implies reset. */
895
0
  h->bufpos = h->ctx->flags.finalized = 0;
896
897
0
  return 0;
898
0
}
899
900
901
static gcry_err_code_t
902
prepare_macpads (gcry_md_hd_t a, const unsigned char *key, size_t keylen)
903
0
{
904
0
  GcryDigestEntry *r;
905
906
0
  if (!a->ctx->list)
907
0
    return GPG_ERR_DIGEST_ALGO; /* Might happen if no algo is enabled.  */
908
909
0
  if (!a->ctx->flags.hmac)
910
0
    return GPG_ERR_DIGEST_ALGO; /* Tried prepare_macpads for non-HMAC md. */
911
912
0
  for (r = a->ctx->list; r; r = r->next)
913
0
    {
914
0
      const unsigned char *k;
915
0
      size_t k_len;
916
0
      unsigned char *key_allocated = NULL;
917
0
      int macpad_Bsize;
918
0
      int i;
919
920
0
      switch (r->spec->algo)
921
0
        {
922
  /* TODO: add spec->blocksize */
923
0
        case GCRY_MD_SHA3_224:
924
0
          macpad_Bsize = 1152 / 8;
925
0
          break;
926
0
        case GCRY_MD_SHA3_256:
927
0
          macpad_Bsize = 1088 / 8;
928
0
          break;
929
0
        case GCRY_MD_SHA3_384:
930
0
          macpad_Bsize = 832 / 8;
931
0
          break;
932
0
        case GCRY_MD_SHA3_512:
933
0
          macpad_Bsize = 576 / 8;
934
0
          break;
935
0
        case GCRY_MD_SHA384:
936
0
        case GCRY_MD_SHA512:
937
0
        case GCRY_MD_SHA512_256:
938
0
        case GCRY_MD_SHA512_224:
939
0
        case GCRY_MD_BLAKE2B_512:
940
0
        case GCRY_MD_BLAKE2B_384:
941
0
        case GCRY_MD_BLAKE2B_256:
942
0
        case GCRY_MD_BLAKE2B_160:
943
0
          macpad_Bsize = 128;
944
0
          break;
945
0
        case GCRY_MD_GOSTR3411_94:
946
0
        case GCRY_MD_GOSTR3411_CP:
947
0
          macpad_Bsize = 32;
948
0
          break;
949
0
        default:
950
0
          macpad_Bsize = 64;
951
0
          break;
952
0
        }
953
954
0
      if ( keylen > macpad_Bsize )
955
0
        {
956
0
          k = key_allocated = xtrymalloc_secure (r->spec->mdlen);
957
0
          if (!k)
958
0
            return gpg_err_code_from_errno (errno);
959
0
          _gcry_md_hash_buffer (r->spec->algo, key_allocated, key, keylen);
960
0
          k_len = r->spec->mdlen;
961
0
          gcry_assert ( k_len <= macpad_Bsize );
962
0
        }
963
0
      else
964
0
        {
965
0
          k = key;
966
0
          k_len = keylen;
967
0
        }
968
969
0
      (*r->spec->init) (r->context,
970
0
                        a->ctx->flags.bugemu1? GCRY_MD_FLAG_BUGEMU1:0);
971
0
      a->bufpos = 0;
972
0
      for (i=0; i < k_len; i++ )
973
0
        _gcry_md_putc (a, k[i] ^ 0x36);
974
0
      for (; i < macpad_Bsize; i++ )
975
0
        _gcry_md_putc (a, 0x36);
976
0
      (*r->spec->write) (r->context, a->buf, a->bufpos);
977
0
      memcpy ((char *)r->context + r->spec->contextsize, r->context,
978
0
              r->spec->contextsize);
979
980
0
      (*r->spec->init) (r->context,
981
0
                        a->ctx->flags.bugemu1? GCRY_MD_FLAG_BUGEMU1:0);
982
0
      a->bufpos = 0;
983
0
      for (i=0; i < k_len; i++ )
984
0
        _gcry_md_putc (a, k[i] ^ 0x5c);
985
0
      for (; i < macpad_Bsize; i++ )
986
0
        _gcry_md_putc (a, 0x5c);
987
0
      (*r->spec->write) (r->context, a->buf, a->bufpos);
988
0
      memcpy ((char *)r->context + r->spec->contextsize*2, r->context,
989
0
              r->spec->contextsize);
990
991
0
      xfree (key_allocated);
992
0
    }
993
994
0
  a->bufpos = 0;
995
0
  return 0;
996
0
}
997
998
999
gcry_err_code_t
1000
_gcry_md_ctl (gcry_md_hd_t hd, int cmd, void *buffer, size_t buflen)
1001
104k
{
1002
104k
  gcry_err_code_t rc = 0;
1003
1004
104k
  (void)buflen; /* Currently not used.  */
1005
1006
104k
  switch (cmd)
1007
104k
    {
1008
104k
    case GCRYCTL_FINALIZE:
1009
104k
      md_final (hd);
1010
104k
      break;
1011
0
    case GCRYCTL_START_DUMP:
1012
0
      md_start_debug (hd, buffer);
1013
0
      break;
1014
0
    case GCRYCTL_STOP_DUMP:
1015
0
      md_stop_debug ( hd );
1016
0
      break;
1017
0
    default:
1018
0
      rc = GPG_ERR_INV_OP;
1019
104k
    }
1020
104k
  return rc;
1021
104k
}
1022
1023
1024
gcry_err_code_t
1025
_gcry_md_setkey (gcry_md_hd_t hd, const void *key, size_t keylen)
1026
0
{
1027
0
  gcry_err_code_t rc;
1028
1029
0
  if (hd->ctx->flags.hmac)
1030
0
    {
1031
0
      rc = prepare_macpads (hd, key, keylen);
1032
0
      if (!rc)
1033
0
  _gcry_md_reset (hd);
1034
0
    }
1035
0
  else
1036
0
    {
1037
0
      rc = md_setkey (hd, key, keylen);
1038
0
    }
1039
1040
0
  return rc;
1041
0
}
1042
1043
1044
/* The new debug interface.  If SUFFIX is a string it creates an debug
1045
   file for the context HD.  IF suffix is NULL, the file is closed and
1046
   debugging is stopped.  */
1047
void
1048
_gcry_md_debug (gcry_md_hd_t hd, const char *suffix)
1049
0
{
1050
0
  if (suffix)
1051
0
    md_start_debug (hd, suffix);
1052
0
  else
1053
0
    md_stop_debug (hd);
1054
0
}
1055
1056
1057
/****************
1058
 * If ALGO is null get the digest for the used algo (which should be
1059
 * only one)
1060
 */
1061
static byte *
1062
md_read( gcry_md_hd_t a, int algo )
1063
46.9k
{
1064
46.9k
  GcryDigestEntry *r = a->ctx->list;
1065
1066
46.9k
  if (! algo)
1067
46.2k
    {
1068
      /* Return the first algorithm */
1069
46.2k
      if (r)
1070
46.2k
        {
1071
46.2k
          if (r->next)
1072
0
            log_debug ("more than one algorithm in md_read(0)\n");
1073
46.2k
          if (r->spec->read)
1074
46.2k
            return r->spec->read (r->context);
1075
46.2k
        }
1076
46.2k
    }
1077
626
  else
1078
626
    {
1079
626
      for (r = a->ctx->list; r; r = r->next)
1080
626
  if (r->spec->algo == algo)
1081
626
    {
1082
626
      if (r->spec->read)
1083
626
              return r->spec->read (r->context);
1084
0
            break;
1085
626
    }
1086
626
    }
1087
1088
0
  if (r && !r->spec->read)
1089
0
    _gcry_fatal_error (GPG_ERR_DIGEST_ALGO,
1090
0
                       "requested algo has no fixed digest length");
1091
0
  else
1092
0
    _gcry_fatal_error (GPG_ERR_DIGEST_ALGO, "requested algo not in md context");
1093
0
  return NULL;
1094
0
}
1095
1096
1097
/*
1098
 * Read out the complete digest, this function implictly finalizes
1099
 * the hash.
1100
 */
1101
byte *
1102
_gcry_md_read (gcry_md_hd_t hd, int algo)
1103
46.9k
{
1104
  /* This function is expected to always return a digest, thus we
1105
     can't return an error which we actually should do in
1106
     non-operational state.  */
1107
46.9k
  _gcry_md_ctl (hd, GCRYCTL_FINALIZE, NULL, 0);
1108
46.9k
  return md_read (hd, algo);
1109
46.9k
}
1110
1111
1112
/****************
1113
 * If ALGO is null get the digest for the used algo (which should be
1114
 * only one)
1115
 */
1116
static gcry_err_code_t
1117
md_extract(gcry_md_hd_t a, int algo, void *out, size_t outlen)
1118
0
{
1119
0
  GcryDigestEntry *r = a->ctx->list;
1120
1121
0
  if (!algo)
1122
0
    {
1123
      /* Return the first algorithm */
1124
0
      if (r && r->spec->extract)
1125
0
  {
1126
0
    if (r->next)
1127
0
      log_debug ("more than one algorithm in md_extract(0)\n");
1128
0
    r->spec->extract (r->context, out, outlen);
1129
0
    return 0;
1130
0
  }
1131
0
    }
1132
0
  else
1133
0
    {
1134
0
      for (r = a->ctx->list; r; r = r->next)
1135
0
  if (r->spec->algo == algo && r->spec->extract)
1136
0
    {
1137
0
      r->spec->extract (r->context, out, outlen);
1138
0
      return 0;
1139
0
    }
1140
0
    }
1141
1142
0
  return GPG_ERR_DIGEST_ALGO;
1143
0
}
1144
1145
1146
/*
1147
 * Expand the output from XOF class digest, this function implictly finalizes
1148
 * the hash.
1149
 */
1150
gcry_err_code_t
1151
_gcry_md_extract (gcry_md_hd_t hd, int algo, void *out, size_t outlen)
1152
0
{
1153
0
  _gcry_md_ctl (hd, GCRYCTL_FINALIZE, NULL, 0);
1154
0
  return md_extract (hd, algo, out, outlen);
1155
0
}
1156
1157
1158
/*
1159
 * Read out an intermediate digest.  Not yet functional.
1160
 */
1161
gcry_err_code_t
1162
_gcry_md_get (gcry_md_hd_t hd, int algo, byte *buffer, int buflen)
1163
0
{
1164
0
  (void)hd;
1165
0
  (void)algo;
1166
0
  (void)buffer;
1167
0
  (void)buflen;
1168
1169
  /*md_digest ... */
1170
0
  fips_signal_error ("unimplemented function called");
1171
0
  return GPG_ERR_INTERNAL;
1172
0
}
1173
1174
1175
/*
1176
 * Shortcut function to hash a buffer with a given algo. The only
1177
 * guaranteed supported algorithms are RIPE-MD160 and SHA-1. The
1178
 * supplied digest buffer must be large enough to store the resulting
1179
 * hash.  No error is returned, the function will abort on an invalid
1180
 * algo.  DISABLED_ALGOS are ignored here.  */
1181
void
1182
_gcry_md_hash_buffer (int algo, void *digest,
1183
                      const void *buffer, size_t length)
1184
0
{
1185
0
  const gcry_md_spec_t *spec;
1186
1187
0
  spec = spec_from_algo (algo);
1188
0
  if (!spec)
1189
0
    {
1190
0
      log_debug ("md_hash_buffer: algorithm %d not available\n", algo);
1191
0
      return;
1192
0
    }
1193
1194
0
  if (spec->hash_buffers != NULL)
1195
0
    {
1196
0
      gcry_buffer_t iov;
1197
1198
0
      iov.size = 0;
1199
0
      iov.data = (void *)buffer;
1200
0
      iov.off = 0;
1201
0
      iov.len = length;
1202
1203
0
      if (spec->flags.disabled || (!spec->flags.fips && fips_mode ()))
1204
0
        log_bug ("gcry_md_hash_buffer failed for algo %d: %s",
1205
0
                algo, gpg_strerror (gcry_error (GPG_ERR_DIGEST_ALGO)));
1206
1207
0
      spec->hash_buffers (digest, spec->mdlen, &iov, 1);
1208
0
    }
1209
0
  else
1210
0
    {
1211
      /* For the others we do not have a fast function, so we use the
1212
         normal functions. */
1213
0
      gcry_md_hd_t h;
1214
0
      gpg_err_code_t err;
1215
1216
0
      err = md_open (&h, algo, 0);
1217
0
      if (err)
1218
0
        log_bug ("gcry_md_open failed for algo %d: %s",
1219
0
                algo, gpg_strerror (gcry_error(err)));
1220
0
      md_write (h, (byte *) buffer, length);
1221
0
      md_final (h);
1222
0
      memcpy (digest, md_read (h, algo), md_digest_length (algo));
1223
0
      md_close (h);
1224
0
    }
1225
0
}
1226
1227
1228
/* Shortcut function to hash multiple buffers with a given algo.  In
1229
   contrast to gcry_md_hash_buffer, this function returns an error on
1230
   invalid arguments or on other problems; disabled algorithms are
1231
   _not_ ignored but flagged as an error.
1232
1233
   The data to sign is taken from the array IOV which has IOVCNT items.
1234
1235
   The only supported flag in FLAGS is GCRY_MD_FLAG_HMAC which turns
1236
   this function into a HMAC function; the first item in IOV is then
1237
   used as the key.
1238
1239
   On success 0 is returned and resulting hash or HMAC is stored at
1240
   DIGEST. DIGESTLEN may be given as -1, in which case DIGEST must
1241
   have been provided by the caller with an appropriate length.
1242
   DIGESTLEN may also be the appropriate length or, in case of XOF
1243
   algorithms, DIGESTLEN indicates number bytes to extract from XOF
1244
   to DIGEST.  */
1245
gpg_err_code_t
1246
_gcry_md_hash_buffers_extract (int algo, unsigned int flags, void *digest,
1247
             int digestlen, const gcry_buffer_t *iov,
1248
             int iovcnt)
1249
0
{
1250
0
  const gcry_md_spec_t *spec;
1251
0
  int hmac;
1252
1253
0
  if (!iov || iovcnt < 0)
1254
0
    return GPG_ERR_INV_ARG;
1255
0
  if (flags & ~(GCRY_MD_FLAG_HMAC))
1256
0
    return GPG_ERR_INV_ARG;
1257
1258
0
  hmac = !!(flags & GCRY_MD_FLAG_HMAC);
1259
0
  if (hmac && iovcnt < 1)
1260
0
    return GPG_ERR_INV_ARG;
1261
1262
0
  spec = spec_from_algo (algo);
1263
0
  if (!spec)
1264
0
    {
1265
0
      log_debug ("md_hash_buffers: algorithm %d not available\n", algo);
1266
0
      return GPG_ERR_DIGEST_ALGO;
1267
0
    }
1268
1269
0
  if (spec->mdlen > 0 && digestlen != -1 && digestlen != spec->mdlen)
1270
0
    return GPG_ERR_DIGEST_ALGO;
1271
0
  if (spec->mdlen == 0 && digestlen == -1)
1272
0
    return GPG_ERR_DIGEST_ALGO;
1273
1274
0
  if (!hmac && spec->hash_buffers)
1275
0
    {
1276
0
      if (spec->flags.disabled || (!spec->flags.fips && fips_mode ()))
1277
0
        return GPG_ERR_DIGEST_ALGO;
1278
1279
0
      spec->hash_buffers (digest, digestlen, iov, iovcnt);
1280
0
    }
1281
0
  else
1282
0
    {
1283
      /* For the others we do not have a fast function, so we use the
1284
         normal functions.  */
1285
0
      gcry_md_hd_t h;
1286
0
      gpg_err_code_t rc;
1287
1288
0
      rc = md_open (&h, algo, (hmac? GCRY_MD_FLAG_HMAC:0));
1289
0
      if (rc)
1290
0
        return rc;
1291
1292
0
      if (hmac)
1293
0
        {
1294
0
          rc = _gcry_md_setkey (h,
1295
0
                                (const char*)iov[0].data + iov[0].off,
1296
0
                                iov[0].len);
1297
0
          if (rc)
1298
0
            {
1299
0
              md_close (h);
1300
0
              return rc;
1301
0
            }
1302
0
          iov++; iovcnt--;
1303
0
        }
1304
0
      for (;iovcnt; iov++, iovcnt--)
1305
0
        md_write (h, (const char*)iov[0].data + iov[0].off, iov[0].len);
1306
0
      md_final (h);
1307
0
      if (spec->mdlen > 0)
1308
0
  memcpy (digest, md_read (h, algo), spec->mdlen);
1309
0
      else if (digestlen > 0)
1310
0
  md_extract (h, algo, digest, digestlen);
1311
0
      md_close (h);
1312
0
    }
1313
1314
0
  return 0;
1315
0
}
1316
1317
1318
/* Shortcut function to hash multiple buffers with a given algo.  In
1319
   contrast to gcry_md_hash_buffer, this function returns an error on
1320
   invalid arguments or on other problems; disabled algorithms are
1321
   _not_ ignored but flagged as an error.
1322
1323
   The data to sign is taken from the array IOV which has IOVCNT items.
1324
1325
   The only supported flag in FLAGS is GCRY_MD_FLAG_HMAC which turns
1326
   this function into a HMAC function; the first item in IOV is then
1327
   used as the key.
1328
1329
   On success 0 is returned and resulting hash or HMAC is stored at
1330
   DIGEST which must have been provided by the caller with an
1331
   appropriate length.  */
1332
gpg_err_code_t
1333
_gcry_md_hash_buffers (int algo, unsigned int flags, void *digest,
1334
           const gcry_buffer_t *iov, int iovcnt)
1335
0
{
1336
0
  return _gcry_md_hash_buffers_extract(algo, flags, digest, -1, iov, iovcnt);
1337
0
}
1338
1339
1340
static int
1341
md_get_algo (gcry_md_hd_t a)
1342
46.2k
{
1343
46.2k
  GcryDigestEntry *r = a->ctx->list;
1344
1345
46.2k
  if (r && r->next)
1346
0
    {
1347
0
      fips_signal_error ("possible usage error");
1348
0
      log_error ("WARNING: more than one algorithm in md_get_algo()\n");
1349
0
    }
1350
46.2k
  return r ? r->spec->algo : 0;
1351
46.2k
}
1352
1353
1354
int
1355
_gcry_md_get_algo (gcry_md_hd_t hd)
1356
46.2k
{
1357
46.2k
  return md_get_algo (hd);
1358
46.2k
}
1359
1360
1361
/****************
1362
 * Return the length of the digest
1363
 */
1364
static int
1365
md_digest_length (int algorithm)
1366
49.3k
{
1367
49.3k
  const gcry_md_spec_t *spec;
1368
1369
49.3k
  spec = spec_from_algo (algorithm);
1370
49.3k
  return spec? spec->mdlen : 0;
1371
49.3k
}
1372
1373
1374
/****************
1375
 * Return the length of the digest in bytes.
1376
 * This function will return 0 in case of errors.
1377
 */
1378
unsigned int
1379
_gcry_md_get_algo_dlen (int algorithm)
1380
49.3k
{
1381
49.3k
  return md_digest_length (algorithm);
1382
49.3k
}
1383
1384
1385
/* Hmmm: add a mode to enumerate the OIDs
1386
 *  to make g10/sig-check.c more portable */
1387
static const byte *
1388
md_asn_oid (int algorithm, size_t *asnlen, size_t *mdlen)
1389
0
{
1390
0
  const gcry_md_spec_t *spec;
1391
0
  const byte *asnoid = NULL;
1392
1393
0
  spec = spec_from_algo (algorithm);
1394
0
  if (spec)
1395
0
    {
1396
0
      if (asnlen)
1397
0
  *asnlen = spec->asnlen;
1398
0
      if (mdlen)
1399
0
  *mdlen = spec->mdlen;
1400
0
      asnoid = spec->asnoid;
1401
0
    }
1402
0
  else
1403
0
    log_bug ("no ASN.1 OID for md algo %d\n", algorithm);
1404
1405
0
  return asnoid;
1406
0
}
1407
1408
1409
/****************
1410
 * Return information about the given cipher algorithm
1411
 * WHAT select the kind of information returned:
1412
 *  GCRYCTL_TEST_ALGO:
1413
 *  Returns 0 when the specified algorithm is available for use.
1414
 *  buffer and nbytes must be zero.
1415
 *  GCRYCTL_GET_ASNOID:
1416
 *  Return the ASNOID of the algorithm in buffer. if buffer is NULL, only
1417
 *  the required length is returned.
1418
 *  GCRYCTL_SELFTEST
1419
 *      Helper for the regression tests - shall not be used by applications.
1420
 *
1421
 * Note:  Because this function is in most cases used to return an
1422
 * integer value, we can make it easier for the caller to just look at
1423
 * the return value.  The caller will in all cases consult the value
1424
 * and thereby detecting whether a error occurred or not (i.e. while checking
1425
 * the block size)
1426
 */
1427
gcry_err_code_t
1428
_gcry_md_algo_info (int algo, int what, void *buffer, size_t *nbytes)
1429
10.1k
{
1430
10.1k
  gcry_err_code_t rc;
1431
1432
10.1k
  switch (what)
1433
10.1k
    {
1434
10.1k
    case GCRYCTL_TEST_ALGO:
1435
10.1k
      if (buffer || nbytes)
1436
0
  rc = GPG_ERR_INV_ARG;
1437
10.1k
      else
1438
10.1k
  rc = check_digest_algo (algo);
1439
10.1k
      break;
1440
1441
0
    case GCRYCTL_GET_ASNOID:
1442
      /* We need to check that the algo is available because
1443
         md_asn_oid would otherwise raise an assertion. */
1444
0
      rc = check_digest_algo (algo);
1445
0
      if (!rc)
1446
0
        {
1447
0
          const char unsigned *asn;
1448
0
          size_t asnlen;
1449
1450
0
          asn = md_asn_oid (algo, &asnlen, NULL);
1451
0
          if (buffer && (*nbytes >= asnlen))
1452
0
            {
1453
0
              memcpy (buffer, asn, asnlen);
1454
0
              *nbytes = asnlen;
1455
0
            }
1456
0
          else if (!buffer && nbytes)
1457
0
            *nbytes = asnlen;
1458
0
          else
1459
0
            {
1460
0
              if (buffer)
1461
0
                rc = GPG_ERR_TOO_SHORT;
1462
0
              else
1463
0
                rc = GPG_ERR_INV_ARG;
1464
0
            }
1465
0
        }
1466
0
      break;
1467
1468
0
    case GCRYCTL_SELFTEST:
1469
      /* Helper function for the regression tests.  */
1470
0
      rc = gpg_err_code (_gcry_md_selftest (algo, nbytes? (int)*nbytes : 0,
1471
0
                                             NULL));
1472
0
      break;
1473
1474
0
    default:
1475
0
      rc = GPG_ERR_INV_OP;
1476
0
      break;
1477
10.1k
  }
1478
1479
10.1k
  return rc;
1480
10.1k
}
1481
1482
1483
static void
1484
md_start_debug ( gcry_md_hd_t md, const char *suffix )
1485
0
{
1486
0
  static int idx=0;
1487
0
  char buf[50];
1488
1489
0
  if (fips_mode ())
1490
0
    return;
1491
1492
0
  if ( md->ctx->debug )
1493
0
    {
1494
0
      log_debug("Oops: md debug already started\n");
1495
0
      return;
1496
0
    }
1497
0
  idx++;
1498
0
  snprintf (buf, DIM(buf)-1, "dbgmd-%05d.%.10s", idx, suffix );
1499
0
  md->ctx->debug = fopen(buf, "w");
1500
0
  if ( !md->ctx->debug )
1501
0
    log_debug("md debug: can't open %s\n", buf );
1502
0
}
1503
1504
1505
static void
1506
md_stop_debug( gcry_md_hd_t md )
1507
0
{
1508
0
  if ( md->ctx->debug )
1509
0
    {
1510
0
      if ( md->bufpos )
1511
0
        md_write ( md, NULL, 0 );
1512
0
      fclose (md->ctx->debug);
1513
0
      md->ctx->debug = NULL;
1514
0
    }
1515
1516
0
  {  /* a kludge to pull in the __muldi3 for Solaris */
1517
0
    volatile u32 a = (u32)(uintptr_t)md;
1518
0
    volatile u64 b = 42;
1519
0
    volatile u64 c;
1520
0
    c = a * b;
1521
0
    (void)c;
1522
0
  }
1523
0
}
1524
1525
1526
1527
/*
1528
 * Return information about the digest handle.
1529
 *  GCRYCTL_IS_SECURE:
1530
 *  Returns 1 when the handle works on secured memory
1531
 *  otherwise 0 is returned.  There is no error return.
1532
 *  GCRYCTL_IS_ALGO_ENABLED:
1533
 *     Returns 1 if the algo is enabled for that handle.
1534
 *     The algo must be passed as the address of an int.
1535
 */
1536
gcry_err_code_t
1537
_gcry_md_info (gcry_md_hd_t h, int cmd, void *buffer, size_t *nbytes)
1538
0
{
1539
0
  gcry_err_code_t rc = 0;
1540
1541
0
  switch (cmd)
1542
0
    {
1543
0
    case GCRYCTL_IS_SECURE:
1544
0
      *nbytes = h->ctx->flags.secure;
1545
0
      break;
1546
1547
0
    case GCRYCTL_IS_ALGO_ENABLED:
1548
0
      {
1549
0
  GcryDigestEntry *r;
1550
0
  int algo;
1551
1552
0
  if ( !buffer || !nbytes || *nbytes != sizeof (int))
1553
0
    rc = GPG_ERR_INV_ARG;
1554
0
  else
1555
0
    {
1556
0
      algo = *(int*)buffer;
1557
1558
0
      *nbytes = 0;
1559
0
      for(r=h->ctx->list; r; r = r->next ) {
1560
0
        if (r->spec->algo == algo)
1561
0
    {
1562
0
      *nbytes = 1;
1563
0
      break;
1564
0
    }
1565
0
      }
1566
0
    }
1567
0
  break;
1568
0
      }
1569
1570
0
  default:
1571
0
    rc = GPG_ERR_INV_OP;
1572
0
  }
1573
1574
0
  return rc;
1575
0
}
1576
1577
1578
/* Explicitly initialize this module.  */
1579
gcry_err_code_t
1580
_gcry_md_init (void)
1581
1
{
1582
1
  return 0;
1583
1
}
1584
1585
1586
int
1587
_gcry_md_is_secure (gcry_md_hd_t a)
1588
0
{
1589
0
  size_t value;
1590
1591
0
  if (_gcry_md_info (a, GCRYCTL_IS_SECURE, NULL, &value))
1592
0
    value = 1; /* It seems to be better to assume secure memory on
1593
                  error. */
1594
0
  return value;
1595
0
}
1596
1597
1598
int
1599
_gcry_md_is_enabled (gcry_md_hd_t a, int algo)
1600
0
{
1601
0
  size_t value;
1602
1603
0
  value = sizeof algo;
1604
0
  if (_gcry_md_info (a, GCRYCTL_IS_ALGO_ENABLED, &algo, &value))
1605
0
    value = 0;
1606
0
  return value;
1607
0
}
1608
1609
1610
/* Run the selftests for digest algorithm ALGO with optional reporting
1611
   function REPORT.  */
1612
gpg_error_t
1613
_gcry_md_selftest (int algo, int extended, selftest_report_func_t report)
1614
0
{
1615
0
  gcry_err_code_t ec = 0;
1616
0
  const gcry_md_spec_t *spec;
1617
1618
0
  spec = spec_from_algo (algo);
1619
0
  if (spec && !spec->flags.disabled
1620
0
      && (spec->flags.fips || !fips_mode ())
1621
0
      && spec->selftest)
1622
0
    ec = spec->selftest (algo, extended, report);
1623
0
  else
1624
0
    {
1625
0
      ec = (spec && spec->selftest) ? GPG_ERR_DIGEST_ALGO
1626
0
        /* */                       : GPG_ERR_NOT_IMPLEMENTED;
1627
0
      if (report)
1628
0
        report ("digest", algo, "module",
1629
0
                spec && !spec->flags.disabled
1630
0
                && (spec->flags.fips || !fips_mode ())?
1631
0
                "no selftest available" :
1632
0
                spec? "algorithm disabled" : "algorithm not found");
1633
0
    }
1634
1635
0
  return gpg_error (ec);
1636
0
}