Coverage Report

Created: 2024-06-20 06:28

/src/gnutls/lib/algorithms/sign.c
Line
Count
Source (jump to first uncovered line)
1
/*
2
 * Copyright (C) 2011-2012 Free Software Foundation, Inc.
3
 * Copyright (C) 2017 Red Hat, Inc.
4
 *
5
 * Author: Nikos Mavrogiannopoulos
6
 *
7
 * This file is part of GnuTLS.
8
 *
9
 * The GnuTLS is free software; you can redistribute it and/or
10
 * modify it under the terms of the GNU Lesser General Public License
11
 * as published by the Free Software Foundation; either version 2.1 of
12
 * the License, or (at your option) any later version.
13
 *
14
 * This library is distributed in the hope that it will be useful, but
15
 * WITHOUT ANY WARRANTY; without even the implied warranty of
16
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
17
 * Lesser General Public License for more details.
18
 *
19
 * You should have received a copy of the GNU Lesser General Public License
20
 * along with this program.  If not, see <https://www.gnu.org/licenses/>
21
 *
22
 */
23
24
#include "gnutls_int.h"
25
#include "algorithms.h"
26
#include "errors.h"
27
#include "x509/common.h"
28
#include <assert.h>
29
#include "c-strcase.h"
30
#include "pk.h"
31
32
/* signature algorithms;
33
 */
34
35
#ifdef ALLOW_SHA1
36
#define SHA1_SECURE_VAL _SECURE
37
#else
38
#define SHA1_SECURE_VAL _INSECURE_FOR_CERTS
39
#endif
40
41
static SYSTEM_CONFIG_OR_CONST gnutls_sign_entry_st sign_algorithms[] = {
42
  /* RSA-PKCS#1 1.5: must be before PSS,
43
   * so that gnutls_pk_to_sign() will return
44
   * these first for backwards compatibility. */
45
  { .name = "RSA-SHA256",
46
    .oid = SIG_RSA_SHA256_OID,
47
    .id = GNUTLS_SIGN_RSA_SHA256,
48
    .pk = GNUTLS_PK_RSA,
49
    .hash = GNUTLS_DIG_SHA256,
50
    .aid = { { 4, 1 }, SIG_SEM_DEFAULT } },
51
  { .name = "RSA-SHA384",
52
    .oid = SIG_RSA_SHA384_OID,
53
    .id = GNUTLS_SIGN_RSA_SHA384,
54
    .pk = GNUTLS_PK_RSA,
55
    .hash = GNUTLS_DIG_SHA384,
56
    .aid = { { 5, 1 }, SIG_SEM_DEFAULT } },
57
  { .name = "RSA-SHA512",
58
    .oid = SIG_RSA_SHA512_OID,
59
    .id = GNUTLS_SIGN_RSA_SHA512,
60
    .pk = GNUTLS_PK_RSA,
61
    .hash = GNUTLS_DIG_SHA512,
62
    .aid = { { 6, 1 }, SIG_SEM_DEFAULT } },
63
64
  /* RSA-PSS */
65
  { .name = "RSA-PSS-SHA256",
66
    .oid = PK_PKIX1_RSA_PSS_OID,
67
    .id = GNUTLS_SIGN_RSA_PSS_SHA256,
68
    .pk = GNUTLS_PK_RSA_PSS,
69
    .priv_pk =
70
      GNUTLS_PK_RSA, /* PKCS#11 doesn't separate RSA from RSA-PSS privkeys */
71
    .hash = GNUTLS_DIG_SHA256,
72
    .flags = GNUTLS_SIGN_FLAG_TLS13_OK,
73
    .aid = { { 8, 9 }, SIG_SEM_DEFAULT } },
74
  { .name = "RSA-PSS-RSAE-SHA256",
75
    .oid = PK_PKIX1_RSA_PSS_OID,
76
    .id = GNUTLS_SIGN_RSA_PSS_RSAE_SHA256,
77
    .pk = GNUTLS_PK_RSA_PSS,
78
    .cert_pk = GNUTLS_PK_RSA,
79
    .priv_pk = GNUTLS_PK_RSA,
80
    .hash = GNUTLS_DIG_SHA256,
81
    .flags = GNUTLS_SIGN_FLAG_TLS13_OK,
82
    .aid = { { 8, 4 }, SIG_SEM_DEFAULT } },
83
  { .name = "RSA-PSS-SHA384",
84
    .oid = PK_PKIX1_RSA_PSS_OID,
85
    .id = GNUTLS_SIGN_RSA_PSS_SHA384,
86
    .pk = GNUTLS_PK_RSA_PSS,
87
    .priv_pk = GNUTLS_PK_RSA,
88
    .hash = GNUTLS_DIG_SHA384,
89
    .flags = GNUTLS_SIGN_FLAG_TLS13_OK,
90
    .aid = { { 8, 0x0A }, SIG_SEM_DEFAULT } },
91
  { .name = "RSA-PSS-RSAE-SHA384",
92
    .oid = PK_PKIX1_RSA_PSS_OID,
93
    .id = GNUTLS_SIGN_RSA_PSS_RSAE_SHA384,
94
    .pk = GNUTLS_PK_RSA_PSS,
95
    .cert_pk = GNUTLS_PK_RSA,
96
    .priv_pk = GNUTLS_PK_RSA,
97
    .hash = GNUTLS_DIG_SHA384,
98
    .flags = GNUTLS_SIGN_FLAG_TLS13_OK,
99
    .aid = { { 8, 5 }, SIG_SEM_DEFAULT } },
100
  { .name = "RSA-PSS-SHA512",
101
    .oid = PK_PKIX1_RSA_PSS_OID,
102
    .id = GNUTLS_SIGN_RSA_PSS_SHA512,
103
    .pk = GNUTLS_PK_RSA_PSS,
104
    .priv_pk = GNUTLS_PK_RSA,
105
    .hash = GNUTLS_DIG_SHA512,
106
    .flags = GNUTLS_SIGN_FLAG_TLS13_OK,
107
    .aid = { { 8, 0x0B }, SIG_SEM_DEFAULT } },
108
  { .name = "RSA-PSS-RSAE-SHA512",
109
    .oid = PK_PKIX1_RSA_PSS_OID,
110
    .id = GNUTLS_SIGN_RSA_PSS_RSAE_SHA512,
111
    .pk = GNUTLS_PK_RSA_PSS,
112
    .cert_pk = GNUTLS_PK_RSA,
113
    .priv_pk = GNUTLS_PK_RSA,
114
    .hash = GNUTLS_DIG_SHA512,
115
    .flags = GNUTLS_SIGN_FLAG_TLS13_OK,
116
    .aid = { { 8, 6 }, SIG_SEM_DEFAULT } },
117
118
  /* Ed25519: The hash algorithm here is set to be SHA512, although that is
119
   * an internal detail of Ed25519; we set it, because CMS/PKCS#7 requires
120
   * that mapping. */
121
  { .name = "EdDSA-Ed25519",
122
    .oid = SIG_EDDSA_SHA512_OID,
123
    .id = GNUTLS_SIGN_EDDSA_ED25519,
124
    .pk = GNUTLS_PK_EDDSA_ED25519,
125
    .hash = GNUTLS_DIG_SHA512,
126
    .flags = GNUTLS_SIGN_FLAG_TLS13_OK,
127
    .aid = { { 8, 7 }, SIG_SEM_DEFAULT } },
128
129
  /* Ed448: The hash algorithm here is set to be SHAKE256, although that is
130
   * an internal detail of Ed448; we set it, because CMS/PKCS#7 requires
131
   * that mapping. */
132
  { .name = "EdDSA-Ed448",
133
    .oid = SIG_ED448_OID,
134
    .id = GNUTLS_SIGN_EDDSA_ED448,
135
    .pk = GNUTLS_PK_EDDSA_ED448,
136
    .hash = GNUTLS_DIG_SHAKE_256,
137
    .flags = GNUTLS_SIGN_FLAG_TLS13_OK,
138
    .aid = { { 8, 8 }, SIG_SEM_DEFAULT },
139
    .hash_output_size = 114 },
140
141
  /* ECDSA */
142
  /* The following three signature algorithms
143
   * have different semantics when used under TLS 1.2
144
   * or TLS 1.3. Under the former they behave as the
145
   * as ECDSA signed by SHAXXX by any curve, but under the
146
   * latter they are restricted to a single curve.
147
   * For this reason the ECDSA-SHAXXX algorithms act
148
   * as an alias to them. */
149
  /* we have intentionally the ECDSA-SHAXXX algorithms first
150
   * so that gnutls_pk_to_sign() will return these. */
151
  { .name = "ECDSA-SHA256",
152
    .oid = "1.2.840.10045.4.3.2",
153
    .id = GNUTLS_SIGN_ECDSA_SHA256,
154
    .pk = GNUTLS_PK_ECDSA,
155
    .hash = GNUTLS_DIG_SHA256,
156
    .aid = { { 4, 3 }, SIG_SEM_PRE_TLS12 } },
157
  { .name = "ECDSA-SHA384",
158
    .oid = "1.2.840.10045.4.3.3",
159
    .id = GNUTLS_SIGN_ECDSA_SHA384,
160
    .pk = GNUTLS_PK_ECDSA,
161
    .hash = GNUTLS_DIG_SHA384,
162
    .aid = { { 5, 3 }, SIG_SEM_PRE_TLS12 } },
163
  { .name = "ECDSA-SHA512",
164
    .oid = "1.2.840.10045.4.3.4",
165
    .id = GNUTLS_SIGN_ECDSA_SHA512,
166
    .pk = GNUTLS_PK_ECDSA,
167
    .hash = GNUTLS_DIG_SHA512,
168
    .aid = { { 6, 3 }, SIG_SEM_PRE_TLS12 } },
169
170
  { .name = "ECDSA-SECP256R1-SHA256",
171
    .id = GNUTLS_SIGN_ECDSA_SECP256R1_SHA256,
172
    .pk = GNUTLS_PK_ECDSA,
173
    .curve = GNUTLS_ECC_CURVE_SECP256R1,
174
    .hash = GNUTLS_DIG_SHA256,
175
    .flags = GNUTLS_SIGN_FLAG_TLS13_OK,
176
    .aid = { { 4, 3 }, SIG_SEM_TLS13 } },
177
  { .name = "ECDSA-SECP384R1-SHA384",
178
    .id = GNUTLS_SIGN_ECDSA_SECP384R1_SHA384,
179
    .pk = GNUTLS_PK_ECDSA,
180
    .curve = GNUTLS_ECC_CURVE_SECP384R1,
181
    .hash = GNUTLS_DIG_SHA384,
182
    .flags = GNUTLS_SIGN_FLAG_TLS13_OK,
183
    .aid = { { 5, 3 }, SIG_SEM_TLS13 } },
184
  { .name = "ECDSA-SECP521R1-SHA512",
185
    .id = GNUTLS_SIGN_ECDSA_SECP521R1_SHA512,
186
    .pk = GNUTLS_PK_ECDSA,
187
    .curve = GNUTLS_ECC_CURVE_SECP521R1,
188
    .hash = GNUTLS_DIG_SHA512,
189
    .flags = GNUTLS_SIGN_FLAG_TLS13_OK,
190
    .aid = { { 6, 3 }, SIG_SEM_TLS13 } },
191
192
  /* ECDSA-SHA3 */
193
  { .name = "ECDSA-SHA3-224",
194
    .oid = SIG_ECDSA_SHA3_224_OID,
195
    .id = GNUTLS_SIGN_ECDSA_SHA3_224,
196
    .pk = GNUTLS_PK_EC,
197
    .hash = GNUTLS_DIG_SHA3_224,
198
    .aid = TLS_SIGN_AID_UNKNOWN },
199
  { .name = "ECDSA-SHA3-256",
200
    .oid = SIG_ECDSA_SHA3_256_OID,
201
    .id = GNUTLS_SIGN_ECDSA_SHA3_256,
202
    .pk = GNUTLS_PK_EC,
203
    .hash = GNUTLS_DIG_SHA3_256,
204
    .aid = TLS_SIGN_AID_UNKNOWN },
205
  { .name = "ECDSA-SHA3-384",
206
    .oid = SIG_ECDSA_SHA3_384_OID,
207
    .id = GNUTLS_SIGN_ECDSA_SHA3_384,
208
    .pk = GNUTLS_PK_EC,
209
    .hash = GNUTLS_DIG_SHA3_384,
210
    .aid = TLS_SIGN_AID_UNKNOWN },
211
  { .name = "ECDSA-SHA3-512",
212
    .oid = SIG_ECDSA_SHA3_512_OID,
213
    .id = GNUTLS_SIGN_ECDSA_SHA3_512,
214
    .pk = GNUTLS_PK_EC,
215
    .hash = GNUTLS_DIG_SHA3_512,
216
    .aid = TLS_SIGN_AID_UNKNOWN },
217
  { .name = "RSA-SHA3-224",
218
    .oid = SIG_RSA_SHA3_224_OID,
219
    .id = GNUTLS_SIGN_RSA_SHA3_224,
220
    .pk = GNUTLS_PK_RSA,
221
    .hash = GNUTLS_DIG_SHA3_224,
222
    .aid = TLS_SIGN_AID_UNKNOWN },
223
  { .name = "RSA-SHA3-256",
224
    .oid = SIG_RSA_SHA3_256_OID,
225
    .id = GNUTLS_SIGN_RSA_SHA3_256,
226
    .pk = GNUTLS_PK_RSA,
227
    .hash = GNUTLS_DIG_SHA3_256,
228
    .aid = TLS_SIGN_AID_UNKNOWN },
229
  { .name = "RSA-SHA3-384",
230
    .oid = SIG_RSA_SHA3_384_OID,
231
    .id = GNUTLS_SIGN_RSA_SHA3_384,
232
    .pk = GNUTLS_PK_RSA,
233
    .hash = GNUTLS_DIG_SHA3_384,
234
    .aid = TLS_SIGN_AID_UNKNOWN },
235
  { .name = "RSA-SHA3-512",
236
    .oid = SIG_RSA_SHA3_512_OID,
237
    .id = GNUTLS_SIGN_RSA_SHA3_512,
238
    .pk = GNUTLS_PK_RSA,
239
    .hash = GNUTLS_DIG_SHA3_512,
240
    .aid = TLS_SIGN_AID_UNKNOWN },
241
242
  /* DSA-SHA3 */
243
  { .name = "DSA-SHA3-224",
244
    .oid = SIG_DSA_SHA3_224_OID,
245
    .id = GNUTLS_SIGN_DSA_SHA3_224,
246
    .pk = GNUTLS_PK_DSA,
247
    .hash = GNUTLS_DIG_SHA3_224,
248
    .aid = TLS_SIGN_AID_UNKNOWN },
249
  { .name = "DSA-SHA3-256",
250
    .oid = SIG_DSA_SHA3_256_OID,
251
    .id = GNUTLS_SIGN_DSA_SHA3_256,
252
    .pk = GNUTLS_PK_DSA,
253
    .hash = GNUTLS_DIG_SHA3_256,
254
    .aid = TLS_SIGN_AID_UNKNOWN },
255
  { .name = "DSA-SHA3-384",
256
    .oid = SIG_DSA_SHA3_384_OID,
257
    .id = GNUTLS_SIGN_DSA_SHA3_384,
258
    .pk = GNUTLS_PK_DSA,
259
    .hash = GNUTLS_DIG_SHA3_384,
260
    .aid = TLS_SIGN_AID_UNKNOWN },
261
  { .name = "DSA-SHA3-512",
262
    .oid = SIG_DSA_SHA3_512_OID,
263
    .id = GNUTLS_SIGN_DSA_SHA3_512,
264
    .pk = GNUTLS_PK_DSA,
265
    .hash = GNUTLS_DIG_SHA3_512,
266
    .aid = TLS_SIGN_AID_UNKNOWN },
267
268
  /* legacy */
269
  { .name = "RSA-RAW",
270
    .oid = NULL,
271
    .id = GNUTLS_SIGN_RSA_RAW,
272
    .pk = GNUTLS_PK_RSA,
273
    .hash = GNUTLS_DIG_UNKNOWN,
274
    .aid = TLS_SIGN_AID_UNKNOWN },
275
  { .name = "RSA-SHA1",
276
    .oid = SIG_RSA_SHA1_OID,
277
    .id = GNUTLS_SIGN_RSA_SHA1,
278
    .pk = GNUTLS_PK_RSA,
279
    .hash = GNUTLS_DIG_SHA1,
280
    .slevel = SHA1_SECURE_VAL,
281
    .aid = { { 2, 1 }, SIG_SEM_DEFAULT } },
282
  { .name = "RSA-SHA1",
283
    .oid = ISO_SIG_RSA_SHA1_OID,
284
    .id = GNUTLS_SIGN_RSA_SHA1,
285
    .pk = GNUTLS_PK_RSA,
286
    .slevel = SHA1_SECURE_VAL,
287
    .hash = GNUTLS_DIG_SHA1,
288
    .aid = { { 2, 1 }, SIG_SEM_DEFAULT } },
289
  { .name = "RSA-SHA224",
290
    .oid = SIG_RSA_SHA224_OID,
291
    .id = GNUTLS_SIGN_RSA_SHA224,
292
    .pk = GNUTLS_PK_RSA,
293
    .hash = GNUTLS_DIG_SHA224,
294
    .aid = TLS_SIGN_AID_UNKNOWN },
295
  { .name = "RSA-RMD160",
296
    .oid = SIG_RSA_RMD160_OID,
297
    .id = GNUTLS_SIGN_RSA_RMD160,
298
    .pk = GNUTLS_PK_RSA,
299
    .hash = GNUTLS_DIG_RMD160,
300
    .slevel = _INSECURE_FOR_CERTS,
301
    .aid = TLS_SIGN_AID_UNKNOWN },
302
  { .name = "DSA-SHA1",
303
    .oid = SIG_DSA_SHA1_OID,
304
    .id = GNUTLS_SIGN_DSA_SHA1,
305
    .pk = GNUTLS_PK_DSA,
306
    .slevel = SHA1_SECURE_VAL,
307
    .hash = GNUTLS_DIG_SHA1,
308
    .aid = { { 2, 2 }, SIG_SEM_PRE_TLS12 } },
309
  { .name = "DSA-SHA1",
310
    .oid = "1.3.14.3.2.27",
311
    .id = GNUTLS_SIGN_DSA_SHA1,
312
    .pk = GNUTLS_PK_DSA,
313
    .hash = GNUTLS_DIG_SHA1,
314
    .slevel = SHA1_SECURE_VAL,
315
    .aid = { { 2, 2 }, SIG_SEM_PRE_TLS12 } },
316
  { .name = "DSA-SHA224",
317
    .oid = SIG_DSA_SHA224_OID,
318
    .id = GNUTLS_SIGN_DSA_SHA224,
319
    .pk = GNUTLS_PK_DSA,
320
    .hash = GNUTLS_DIG_SHA224,
321
    .aid = TLS_SIGN_AID_UNKNOWN },
322
  { .name = "DSA-SHA256",
323
    .oid = SIG_DSA_SHA256_OID,
324
    .id = GNUTLS_SIGN_DSA_SHA256,
325
    .pk = GNUTLS_PK_DSA,
326
    .hash = GNUTLS_DIG_SHA256,
327
    .aid = TLS_SIGN_AID_UNKNOWN },
328
  { .name = "RSA-MD5",
329
    .oid = SIG_RSA_MD5_OID,
330
    .id = GNUTLS_SIGN_RSA_MD5,
331
    .pk = GNUTLS_PK_RSA,
332
    .hash = GNUTLS_DIG_MD5,
333
    .slevel = _INSECURE,
334
    .aid = TLS_SIGN_AID_UNKNOWN },
335
  { .name = "RSA-MD5",
336
    .oid = "1.3.14.3.2.25",
337
    .id = GNUTLS_SIGN_RSA_MD5,
338
    .pk = GNUTLS_PK_RSA,
339
    .hash = GNUTLS_DIG_MD5,
340
    .slevel = _INSECURE,
341
    .aid = TLS_SIGN_AID_UNKNOWN },
342
  { .name = "RSA-MD2",
343
    .oid = SIG_RSA_MD2_OID,
344
    .id = GNUTLS_SIGN_RSA_MD2,
345
    .pk = GNUTLS_PK_RSA,
346
    .hash = GNUTLS_DIG_MD2,
347
    .slevel = _INSECURE,
348
    .aid = TLS_SIGN_AID_UNKNOWN },
349
  { .name = "ECDSA-SHA1",
350
    .oid = "1.2.840.10045.4.1",
351
    .id = GNUTLS_SIGN_ECDSA_SHA1,
352
    .pk = GNUTLS_PK_EC,
353
    .slevel = SHA1_SECURE_VAL,
354
    .hash = GNUTLS_DIG_SHA1,
355
    .aid = { { 2, 3 }, SIG_SEM_DEFAULT } },
356
  { .name = "ECDSA-SHA224",
357
    .oid = "1.2.840.10045.4.3.1",
358
    .id = GNUTLS_SIGN_ECDSA_SHA224,
359
    .pk = GNUTLS_PK_EC,
360
    .hash = GNUTLS_DIG_SHA224,
361
    .aid = TLS_SIGN_AID_UNKNOWN },
362
  /* GOST R 34.10-2012-512 */
363
  { .name = "GOSTR341012-512",
364
    .oid = SIG_GOST_R3410_2012_512_OID,
365
    .id = GNUTLS_SIGN_GOST_512,
366
    .pk = GNUTLS_PK_GOST_12_512,
367
    .hash = GNUTLS_DIG_STREEBOG_512,
368
    .flags = GNUTLS_SIGN_FLAG_CRT_VRFY_REVERSE,
369
    .aid = { { 8, 65 }, SIG_SEM_PRE_TLS12 } },
370
  /* GOST R 34.10-2012-256 */
371
  { .name = "GOSTR341012-256",
372
    .oid = SIG_GOST_R3410_2012_256_OID,
373
    .id = GNUTLS_SIGN_GOST_256,
374
    .pk = GNUTLS_PK_GOST_12_256,
375
    .hash = GNUTLS_DIG_STREEBOG_256,
376
    .flags = GNUTLS_SIGN_FLAG_CRT_VRFY_REVERSE,
377
    .aid = { { 8, 64 }, SIG_SEM_PRE_TLS12 } },
378
  /* GOST R 34.10-2001 */
379
  { .name = "GOSTR341001",
380
    .oid = SIG_GOST_R3410_2001_OID,
381
    .id = GNUTLS_SIGN_GOST_94,
382
    .pk = GNUTLS_PK_GOST_01,
383
    .hash = GNUTLS_DIG_GOSTR_94,
384
    .flags = GNUTLS_SIGN_FLAG_CRT_VRFY_REVERSE,
385
    .aid = TLS_SIGN_AID_UNKNOWN },
386
  /* GOST R 34.10-94 */
387
  { .name = "GOSTR341094",
388
    .oid = SIG_GOST_R3410_94_OID,
389
    .id = 0,
390
    .pk = 0,
391
    .hash = 0,
392
    .aid = TLS_SIGN_AID_UNKNOWN },
393
  { .name = "DSA-SHA384",
394
    .oid = SIG_DSA_SHA384_OID,
395
    .id = GNUTLS_SIGN_DSA_SHA384,
396
    .pk = GNUTLS_PK_DSA,
397
    .hash = GNUTLS_DIG_SHA384,
398
    .aid = TLS_SIGN_AID_UNKNOWN },
399
  { .name = "DSA-SHA512",
400
    .oid = SIG_DSA_SHA512_OID,
401
    .id = GNUTLS_SIGN_DSA_SHA512,
402
    .pk = GNUTLS_PK_DSA,
403
    .hash = GNUTLS_DIG_SHA512,
404
    .aid = TLS_SIGN_AID_UNKNOWN },
405
406
  { .name = 0,
407
    .oid = 0,
408
    .id = 0,
409
    .pk = 0,
410
    .hash = 0,
411
    .aid = TLS_SIGN_AID_UNKNOWN }
412
};
413
414
#define GNUTLS_SIGN_LOOP(b)                                       \
415
0
  do {                                                      \
416
0
    const gnutls_sign_entry_st *p;                    \
417
0
    for (p = sign_algorithms; p->name != NULL; p++) { \
418
0
      b;                                        \
419
0
    }                                                 \
420
0
  } while (0)
421
422
#define GNUTLS_SIGN_ALG_LOOP(a)                        \
423
0
  GNUTLS_SIGN_LOOP(if (p->id && p->id == sign) { \
424
0
    a;                                     \
425
0
    break;                                 \
426
0
  })
427
428
/**
429
 * gnutls_sign_get_name:
430
 * @algorithm: is a sign algorithm
431
 *
432
 * Convert a #gnutls_sign_algorithm_t value to a string.
433
 *
434
 * Returns: a string that contains the name of the specified sign
435
 *   algorithm, or %NULL.
436
 **/
437
const char *gnutls_sign_get_name(gnutls_sign_algorithm_t algorithm)
438
0
{
439
0
  gnutls_sign_algorithm_t sign = algorithm;
440
0
  const char *ret = NULL;
441
442
  /* avoid prefix */
443
0
  GNUTLS_SIGN_ALG_LOOP(ret = p->name);
444
445
0
  return ret;
446
0
}
447
448
/**
449
 * gnutls_sign_is_secure:
450
 * @algorithm: is a sign algorithm
451
 *
452
 * Returns: Non-zero if the provided signature algorithm is considered to be secure.
453
 **/
454
unsigned gnutls_sign_is_secure(gnutls_sign_algorithm_t algorithm)
455
0
{
456
0
  return gnutls_sign_is_secure2(algorithm, 0);
457
0
}
458
459
bool _gnutls_sign_is_secure2(const gnutls_sign_entry_st *se, unsigned int flags)
460
0
{
461
0
  if (se->hash != GNUTLS_DIG_UNKNOWN &&
462
0
      _gnutls_digest_is_insecure2(
463
0
        se->hash,
464
0
        flags & GNUTLS_SIGN_FLAG_ALLOW_INSECURE_REVERTIBLE ?
465
0
          GNUTLS_MAC_FLAG_ALLOW_INSECURE_REVERTIBLE :
466
0
          0)) {
467
0
    return gnutls_assert_val(false);
468
0
  }
469
470
0
  return (flags & GNUTLS_SIGN_FLAG_SECURE_FOR_CERTS ?
471
0
      se->slevel == _SECURE :
472
0
      (se->slevel == _SECURE ||
473
0
       se->slevel == _INSECURE_FOR_CERTS)) ||
474
0
         (flags & GNUTLS_SIGN_FLAG_ALLOW_INSECURE_REVERTIBLE &&
475
0
    se->flags & GNUTLS_SIGN_FLAG_INSECURE_REVERTIBLE);
476
0
}
477
478
/* This is only called by cfg_apply in priority.c, in blocklisting mode. */
479
int _gnutls_sign_mark_insecure(gnutls_sign_algorithm_t sign,
480
             hash_security_level_t level)
481
0
{
482
0
#ifndef DISABLE_SYSTEM_CONFIG
483
0
  gnutls_sign_entry_st *p;
484
485
0
  if (unlikely(level == _SECURE))
486
0
    return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
487
488
0
  for (p = sign_algorithms; p->name != NULL; p++) {
489
0
    if (p->id && p->id == sign) {
490
0
      if (p->slevel < level)
491
0
        p->slevel = level;
492
0
      return 0;
493
0
    }
494
0
  }
495
0
#endif
496
0
  return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
497
0
}
498
499
/* This is only called by cfg_apply in priority.c, in allowlisting mode. */
500
void _gnutls_sign_mark_insecure_all(hash_security_level_t level)
501
0
{
502
0
#ifndef DISABLE_SYSTEM_CONFIG
503
0
  gnutls_sign_entry_st *p;
504
505
0
  for (p = sign_algorithms; p->name != NULL; p++) {
506
0
    if (p->slevel < level)
507
0
      p->slevel = level;
508
0
    p->flags |= GNUTLS_SIGN_FLAG_INSECURE_REVERTIBLE;
509
0
  }
510
0
#endif
511
0
}
512
513
int _gnutls_sign_set_secure(gnutls_sign_algorithm_t sign,
514
          hash_security_level_t slevel)
515
0
{
516
0
#ifndef DISABLE_SYSTEM_CONFIG
517
0
  gnutls_sign_entry_st *p;
518
519
0
  for (p = sign_algorithms; p->name != NULL; p++) {
520
0
    if (p->id && p->id == sign) {
521
0
      if (!(p->flags &
522
0
            GNUTLS_SIGN_FLAG_INSECURE_REVERTIBLE)) {
523
0
        return gnutls_assert_val(
524
0
          GNUTLS_E_INVALID_REQUEST);
525
0
      }
526
0
      p->slevel = slevel;
527
0
      return 0;
528
0
    }
529
0
  }
530
0
#endif
531
0
  return gnutls_assert_val(GNUTLS_E_INVALID_REQUEST);
532
0
}
533
534
/**
535
 * gnutls_sign_is_secure2:
536
 * @algorithm: is a sign algorithm
537
 * @flags: zero or %GNUTLS_SIGN_FLAG_SECURE_FOR_CERTS
538
 *
539
 * Returns: Non-zero if the provided signature algorithm is considered to be secure.
540
 **/
541
unsigned gnutls_sign_is_secure2(gnutls_sign_algorithm_t algorithm,
542
        unsigned int flags)
543
0
{
544
0
  const gnutls_sign_entry_st *se;
545
546
0
  se = _gnutls_sign_to_entry(algorithm);
547
0
  if (se == NULL)
548
0
    return 0;
549
550
0
  return _gnutls_sign_is_secure2(se, flags);
551
0
}
552
553
/**
554
 * gnutls_sign_list:
555
 *
556
 * Get a list of supported public key signature algorithms.
557
 * This function is not thread safe.
558
 *
559
 * Returns: a (0)-terminated list of #gnutls_sign_algorithm_t
560
 *   integers indicating the available ciphers.
561
 *
562
 **/
563
const gnutls_sign_algorithm_t *gnutls_sign_list(void)
564
0
{
565
0
  static gnutls_sign_algorithm_t supported_sign[MAX_ALGOS + 1] = { 0 };
566
567
0
  if (supported_sign[0] == 0) {
568
0
    int i = 0;
569
570
0
    GNUTLS_SIGN_LOOP(
571
      /* list all algorithms, but not duplicates */
572
0
      if (supported_sign[i] != p->id &&
573
0
          _gnutls_pk_sign_exists(p->id)) {
574
0
        assert(i + 1 < MAX_ALGOS);
575
0
        supported_sign[i++] = p->id;
576
0
        supported_sign[i + 1] = 0;
577
0
      });
578
0
  }
579
580
0
  return supported_sign;
581
0
}
582
583
/**
584
 * gnutls_sign_get_id:
585
 * @name: is a sign algorithm name
586
 *
587
 * The names are compared in a case insensitive way.
588
 *
589
 * Returns: return a #gnutls_sign_algorithm_t value corresponding to
590
 *   the specified algorithm, or %GNUTLS_SIGN_UNKNOWN on error.
591
 **/
592
gnutls_sign_algorithm_t gnutls_sign_get_id(const char *name)
593
0
{
594
0
  gnutls_sign_algorithm_t ret = GNUTLS_SIGN_UNKNOWN;
595
596
0
  GNUTLS_SIGN_LOOP(if (c_strcasecmp(p->name, name) == 0) {
597
0
    ret = p->id;
598
0
    break;
599
0
  });
600
601
0
  return ret;
602
0
}
603
604
const gnutls_sign_entry_st *_gnutls_oid_to_sign_entry(const char *oid)
605
0
{
606
0
  GNUTLS_SIGN_LOOP(if (p->oid && strcmp(oid, p->oid) == 0) { return p; });
607
0
  return NULL;
608
0
}
609
610
/**
611
 * gnutls_oid_to_sign:
612
 * @oid: is an object identifier
613
 *
614
 * Converts a textual object identifier to a #gnutls_sign_algorithm_t value.
615
 *
616
 * Returns: a #gnutls_sign_algorithm_t id of the specified digest
617
 *   algorithm, or %GNUTLS_SIGN_UNKNOWN on failure.
618
 *
619
 * Since: 3.4.3
620
 **/
621
gnutls_sign_algorithm_t gnutls_oid_to_sign(const char *oid)
622
0
{
623
0
  const gnutls_sign_entry_st *se;
624
625
0
  se = _gnutls_oid_to_sign_entry(oid);
626
0
  if (se == NULL) {
627
0
    _gnutls_debug_log("Unknown SIGN OID: '%s'\n", oid);
628
0
    return GNUTLS_SIGN_UNKNOWN;
629
0
  }
630
0
  return se->id;
631
0
}
632
633
const gnutls_sign_entry_st *
634
_gnutls_pk_to_sign_entry(gnutls_pk_algorithm_t pk,
635
       gnutls_digest_algorithm_t hash)
636
0
{
637
0
  GNUTLS_SIGN_LOOP(if (pk == p->pk && hash == p->hash) { return p; });
638
639
0
  return NULL;
640
0
}
641
642
/**
643
 * gnutls_pk_to_sign:
644
 * @pk: is a public key algorithm
645
 * @hash: a hash algorithm
646
 *
647
 * This function maps public key and hash algorithms combinations
648
 * to signature algorithms.
649
 *
650
 * Returns: return a #gnutls_sign_algorithm_t value, or %GNUTLS_SIGN_UNKNOWN on error.
651
 **/
652
gnutls_sign_algorithm_t gnutls_pk_to_sign(gnutls_pk_algorithm_t pk,
653
            gnutls_digest_algorithm_t hash)
654
0
{
655
0
  const gnutls_sign_entry_st *e;
656
657
0
  e = _gnutls_pk_to_sign_entry(pk, hash);
658
0
  if (e == NULL)
659
0
    return GNUTLS_SIGN_UNKNOWN;
660
0
  return e->id;
661
0
}
662
663
/**
664
 * gnutls_sign_get_oid:
665
 * @sign: is a sign algorithm
666
 *
667
 * Convert a #gnutls_sign_algorithm_t value to its object identifier.
668
 *
669
 * Returns: a string that contains the object identifier of the specified sign
670
 *   algorithm, or %NULL.
671
 *
672
 * Since: 3.4.3
673
 **/
674
const char *gnutls_sign_get_oid(gnutls_sign_algorithm_t sign)
675
0
{
676
0
  const char *ret = NULL;
677
678
0
  GNUTLS_SIGN_ALG_LOOP(ret = p->oid);
679
680
0
  return ret;
681
0
}
682
683
/**
684
 * gnutls_sign_get_hash_algorithm:
685
 * @sign: is a signature algorithm
686
 *
687
 * This function returns the digest algorithm corresponding to
688
 * the given signature algorithms.
689
 *
690
 * Since: 3.1.1
691
 *
692
 * Returns: return a #gnutls_digest_algorithm_t value, or %GNUTLS_DIG_UNKNOWN on error.
693
 **/
694
gnutls_digest_algorithm_t
695
gnutls_sign_get_hash_algorithm(gnutls_sign_algorithm_t sign)
696
0
{
697
0
  gnutls_digest_algorithm_t ret = GNUTLS_DIG_UNKNOWN;
698
699
0
  GNUTLS_SIGN_ALG_LOOP(ret = p->hash);
700
701
0
  return ret;
702
0
}
703
704
/**
705
 * gnutls_sign_get_pk_algorithm:
706
 * @sign: is a signature algorithm
707
 *
708
 * This function returns the public key algorithm corresponding to
709
 * the given signature algorithms. Note that there may be multiple
710
 * public key algorithms supporting a particular signature type;
711
 * when dealing with such algorithms use instead gnutls_sign_supports_pk_algorithm().
712
 *
713
 * Since: 3.1.1
714
 *
715
 * Returns: return a #gnutls_pk_algorithm_t value, or %GNUTLS_PK_UNKNOWN on error.
716
 **/
717
gnutls_pk_algorithm_t gnutls_sign_get_pk_algorithm(gnutls_sign_algorithm_t sign)
718
0
{
719
0
  gnutls_pk_algorithm_t ret = GNUTLS_PK_UNKNOWN;
720
721
0
  GNUTLS_SIGN_ALG_LOOP(ret = p->pk);
722
723
0
  return ret;
724
0
}
725
726
/**
727
 * gnutls_sign_supports_pk_algorithm:
728
 * @sign: is a signature algorithm
729
 * @pk: is a public key algorithm
730
 *
731
 * This function returns non-zero if the public key algorithm corresponds to
732
 * the given signature algorithm. That is, if that signature can be generated
733
 * from the given private key algorithm.
734
 *
735
 * Since: 3.6.0
736
 *
737
 * Returns: return non-zero when the provided algorithms are compatible.
738
 **/
739
unsigned gnutls_sign_supports_pk_algorithm(gnutls_sign_algorithm_t sign,
740
             gnutls_pk_algorithm_t pk)
741
0
{
742
0
  const gnutls_sign_entry_st *p;
743
0
  unsigned r;
744
745
0
  for (p = sign_algorithms; p->name != NULL; p++) {
746
0
    if (p->id && p->id == sign) {
747
0
      r = sign_supports_priv_pk_algorithm(p, pk);
748
0
      if (r != 0)
749
0
        return r;
750
0
    }
751
0
  }
752
753
0
  return 0;
754
0
}
755
756
gnutls_sign_algorithm_t _gnutls_tls_aid_to_sign(uint8_t id0, uint8_t id1,
757
            const version_entry_st *ver)
758
0
{
759
0
  gnutls_sign_algorithm_t ret = GNUTLS_SIGN_UNKNOWN;
760
761
0
  if (id0 == 255 && id1 == 255)
762
0
    return ret;
763
764
0
  GNUTLS_SIGN_LOOP(if (p->aid.id[0] == id0 && p->aid.id[1] == id1 &&
765
0
           ((p->aid.tls_sem & ver->tls_sig_sem) != 0)) {
766
0
    ret = p->id;
767
0
    break;
768
0
  });
769
770
0
  return ret;
771
0
}
772
773
/* Returns NULL if a valid AID is not found
774
 */
775
const sign_algorithm_st *_gnutls_sign_to_tls_aid(gnutls_sign_algorithm_t sign)
776
0
{
777
0
  const sign_algorithm_st *ret = NULL;
778
779
0
  GNUTLS_SIGN_ALG_LOOP(ret = &p->aid);
780
781
0
  if (ret != NULL && HAVE_UNKNOWN_SIGAID(ret))
782
0
    return NULL;
783
784
0
  return ret;
785
0
}
786
787
const gnutls_sign_entry_st *_gnutls_sign_to_entry(gnutls_sign_algorithm_t sign)
788
0
{
789
0
  const gnutls_sign_entry_st *ret = NULL;
790
791
0
  GNUTLS_SIGN_ALG_LOOP(ret = p);
792
793
0
  return ret;
794
0
}
795
796
const gnutls_sign_entry_st *
797
_gnutls_tls_aid_to_sign_entry(uint8_t id0, uint8_t id1,
798
            const version_entry_st *ver)
799
0
{
800
0
  if (id0 == 255 && id1 == 255)
801
0
    return NULL;
802
803
0
  GNUTLS_SIGN_LOOP(
804
0
    if (p->aid.id[0] == id0 && p->aid.id[1] == id1 &&
805
0
        ((p->aid.tls_sem & ver->tls_sig_sem) != 0)) { return p; });
806
807
0
  return NULL;
808
0
}
809
810
const gnutls_sign_entry_st *
811
_gnutls13_sign_get_compatible_with_privkey(gnutls_privkey_t privkey)
812
0
{
813
0
  GNUTLS_SIGN_LOOP(if ((p->flags & GNUTLS_SIGN_FLAG_TLS13_OK) &&
814
0
           _gnutls_privkey_compatible_with_sig(
815
0
             privkey, p->id)) { return p; });
816
817
0
  return NULL;
818
0
}
819
820
unsigned _gnutls_sign_get_hash_strength(gnutls_sign_algorithm_t sign)
821
0
{
822
0
  const gnutls_sign_entry_st *se = _gnutls_sign_to_entry(sign);
823
0
  const mac_entry_st *me;
824
0
  unsigned hash_output_size;
825
826
0
  if (unlikely(se == NULL))
827
0
    return 0;
828
829
0
  me = hash_to_entry(se->hash);
830
0
  if (unlikely(me == NULL))
831
0
    return 0;
832
833
0
  if (se->hash_output_size > 0)
834
0
    hash_output_size = se->hash_output_size;
835
0
  else
836
0
    hash_output_size = _gnutls_mac_get_algo_len(me);
837
838
0
  if (me->id == GNUTLS_MAC_SHAKE_128)
839
0
    return MIN(hash_output_size * 8 / 2, 128);
840
0
  else if (me->id == GNUTLS_MAC_SHAKE_256)
841
0
    return MIN(hash_output_size * 8 / 2, 256);
842
843
0
  return hash_output_size * 8 / 2;
844
0
}