Line data Source code
1 : /*
2 : * Copyright (C) 2013 Red Hat
3 : *
4 : * Author: Nikos Mavrogiannopoulos
5 : *
6 : * This file is part of GnuTLS.
7 : *
8 : * The GnuTLS is free software; you can redistribute it and/or
9 : * modify it under the terms of the GNU Lesser General Public License
10 : * as published by the Free Software Foundation; either version 2.1 of
11 : * the License, or (at your option) any later version.
12 : *
13 : * This library is distributed in the hope that it will be useful, but
14 : * WITHOUT ANY WARRANTY; without even the implied warranty of
15 : * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 : * Lesser General Public License for more details.
17 : *
18 : * You should have received a copy of the GNU Lesser General Public License
19 : * along with this program. If not, see <https://www.gnu.org/licenses/>
20 : *
21 : */
22 :
23 : #include "gnutls_int.h"
24 : #include "errors.h"
25 : #include "fips.h"
26 : #include <cipher_int.h>
27 : #include <datum.h>
28 : #include <gnutls/crypto.h>
29 : #include <gnutls/self-test.h>
30 : #include "errors.h"
31 : #include <gnutls/abstract.h>
32 : #include <pk.h>
33 : #include <debug.h>
34 :
35 : #define DATASTR "Hello there!"
36 : static const gnutls_datum_t signed_data = {
37 : .data = (void *) DATASTR,
38 : .size = sizeof(DATASTR) - 1
39 : };
40 :
41 : static const gnutls_datum_t bad_data = {
42 : .data = (void *) DATASTR,
43 : .size = sizeof(DATASTR) - 2
44 : };
45 :
46 : /* RSA 2048 private key and signature */
47 : static const char rsa_2048_privkey[] =
48 : "-----BEGIN RSA PRIVATE KEY-----\n"
49 : "MIIEogIBAAKCAQEA6yCv+BLrRP/dMPBXJWK21c0aqxIX6JkODL4K+zlyEURt8/Wp\n"
50 : "nw37CJwHD3VrimSnk2SJvBfTNhzYhCsLShDOPvi4qBrLZ1WozjoVJ8tRE4VCcjQJ\n"
51 : "snpJ7ldiV+Eos1Z3FkbV/uQcw5CYCb/TciSukaWlI+G/xas9EOOFt4aELbc1yDe0\n"
52 : "hyfPDtoaKfek4GhT9qT1I8pTC40P9OrA9Jt8lblqxHWwqmdunLTjPjB5zJT6QgI+\n"
53 : "j1xuq7ZOQhveNA/AOyzh574GIpgsuvPPLBQwsCQkscr7cFnCsyOPgYJrQW3De2+l\n"
54 : "wjp2D7gZeeQcFQKazXcFoiqNpJWoBWmU0qqsgwIDAQABAoIBAAghNzRioxPdrO42\n"
55 : "QS0fvqah0tw7Yew+7oduQr7w+4qxTQP0aIsBVr6zdmMIclF0rX6hKUoBoOHsGWho\n"
56 : "fJlw/1CaFPhrBMFr6sxGodigZQtBvkxolDVBmTDOgK39MQUSZke0501K4du5MiiU\n"
57 : "I2F89zQ9//m/onvZMeFVnJf95LAX5qHr/FLARQFtOpgWzcGVxdvJdJlYb1zMUril\n"
58 : "PqyAZXo1j0vgHWwSd54k8mBLus7l8KT57VFce8+9nBPrOrqW4rDVXzs/go3S+kiI\n"
59 : "OyzYeUs9czg1N1e3VhEaC+EdYUawc0ASuEkbsJ53L8pwDvS+2ly2ykYziJp95Fjv\n"
60 : "bzyd1dECgYEA8FzGCxu7A6/ei9Dn0Fmi8Ns/QvEgbdlGw4v4MlXHjrGJYdOB0BwG\n"
61 : "2D2k0ODNYKlUX2J4hi5x8aCH33y/v0EcOHyuqM33vOWBVbdcumCqcOmp341UebAO\n"
62 : "uCPgDJNhjxXaeDVPnizqnOBA1B9sTxwmCOmFIiFRLbR+XluvDh3t8L0CgYEA+my6\n"
63 : "124Rw7kcFx+9JoB/Z+bUJDYpefUT91gBUhhEdEMx5fujhMzAbLpIRjFQq+75Qb7v\n"
64 : "0NyIS09B4oKOqQYzVEJwqKY7H71BTl7QuzJ8Qtuh/DMZsVIt6xpvdeuAKpEOqz44\n"
65 : "ZD3fW1B59A3ja7kqZadCqq2b02UTk+gdeOrYBj8CgYACX3gZDfoHrEnPKY3QUcI5\n"
66 : "DIEQYR8H1phLP+uAW7ZvozMPAy6J5mzu35Tr9vwwExvhITC9amH3l7UfsLSX58Wm\n"
67 : "jRyQUBA9Dir7tKa2tFOab8Qcj+GgnetXSAtjNGVHK1kPzL7vedQLHm+laHYCRe3e\n"
68 : "Mqf80UVi5SBGQDN3OTZrJQKBgEkj2oozDqMwfGDQl0kYfJ2XEFynKQQCrVsva+tT\n"
69 : "RSMDwR4fmcmel5Dp81P08U/WExy9rIM+9duxAVgrs4jwU6uHYCoRqvEBMIK4NJSI\n"
70 : "ETzhsvTa4+UjUF/7L5SsPJmyFiuzl3rHi2W7InNCXyrGQPjBmjoJTJq4SbiIMZtw\n"
71 : "U7m3AoGACG2rE/Ud71kyOJcKwxzEt8kd+2CMuaZeE/xk+3zLSSjXJzKPficogM3I\n"
72 : "K37/N7N0FjhdQ5hRuD3GH1fcjv9AKdGHsH7RuaG+jHTRUjS1glr17SSQzh6xXnWj\n"
73 : "jG0M4UZm5P9STL09nZuWH0wfpr/eg+9+A6yOVfnADI13v+Ygk7k=\n"
74 : "-----END RSA PRIVATE KEY-----\n";
75 :
76 : static const char rsa_2048_sig[] =
77 : "\x7a\xb3\xf8\xb0\xf9\xf0\x52\x88\x37\x17\x97\x9f\xbe\x61\xb4\xd2"
78 : "\x43\x78\x9f\x79\x92\xd0\xad\x08\xdb\xbd\x3c\x72\x7a\xb5\x51\x59"
79 : "\x63\xd6\x7d\xf1\x9c\x1e\x10\x7b\x27\xab\xf8\xd4\x9d\xcd\xc5\xf9"
80 : "\xae\xf7\x09\x6b\x40\x93\xc5\xe9\x1c\x0f\xb4\x82\xa1\x47\x86\x54"
81 : "\x63\xd2\x4d\x40\x9a\x80\xb9\x38\x45\x69\xa2\xd6\x92\xb6\x69\x7f"
82 : "\x3f\xf3\x5b\xa5\x1d\xac\x06\xad\xdf\x4e\xbb\xe6\xda\x68\x0d\xe5"
83 : "\xab\xef\xd2\xf0\xc5\xd8\xc0\xed\x80\xe2\xd4\x76\x98\xec\x44\xa2"
84 : "\xfc\x3f\xce\x2e\x8b\xc4\x4b\xab\xb0\x70\x24\x52\x85\x2a\x36\xcd"
85 : "\x9a\xb5\x05\x00\xea\x98\x7c\x72\x06\x68\xb1\x38\x44\x16\x80\x6a"
86 : "\x3b\x64\x72\xbb\xfd\x4b\xc9\xdd\xda\x2a\x68\xde\x7f\x6e\x48\x28"
87 : "\xc1\x63\x57\x2b\xde\x83\xa3\x27\x34\xd7\xa6\x87\x18\x35\x10\xff"
88 : "\x31\xd9\x47\xc9\x84\x35\xe1\xaa\xe2\xf7\x98\xfa\x19\xd3\xf1\x94"
89 : "\x25\x2a\x96\xe4\xa8\xa7\x05\x10\x93\x87\xde\x96\x85\xe5\x68\xb8"
90 : "\xe5\x4e\xbf\x66\x85\x91\xbd\x52\x5b\x3d\x9f\x1b\x79\xea\xe3\x8b"
91 : "\xef\x62\x18\x39\x7a\x50\x01\x46\x1b\xde\x8d\x37\xbc\x90\x6c\x07"
92 : "\xc0\x07\xed\x60\xce\x2e\x31\xd6\x8f\xe8\x75\xdb\x45\x21\xc6\xcb";
93 :
94 : /* DSA 2048 private key and signature */
95 : static const char dsa_2048_privkey[] =
96 : "-----BEGIN DSA PRIVATE KEY-----\n"
97 : "MIIDTQIBAAKCAQEAh60B6yPMRIT7udq2kKuwnQDohvT1U0w+RJcSr23C05cM/Ovn\n"
98 : "UP/8Rrj6T8K+uYhMbKgLaZiJJW9q04jaPQk0cfUphbLvRjzVHwE/0Bkb+Y1Rv7ni\n"
99 : "Jot2IFMq5iuNraf889PC0WREvFCcIkSFY2Ac4WT7mCcBtfx/raGFXDUjcUrJ0HwZ\n"
100 : "IOhjQDfcXUsztuyYsYA75ociEY8kyDZq/ixyr5++R1VjNf30Re8AbQlXOEGxEN5t\n"
101 : "t+Tvpq8K5L3prQs2KNSzyOUmedjb/ojH4T4qe/RL9EVjjeuIGHDNUT6F197yZ91y\n"
102 : "qLLTf1WjnUyZcKij5rryX0LJBBWawEZjNSHZawIdAMQlyycia4NigCdiDR+QptUn\n"
103 : "2xrj9o14fXkIrXcCggEAXRZm1rbPhsjSTo6cpCVrmDzO1grv83EHiBH4MvRQQnP8\n"
104 : "FpAREsBA5cYju97XvLaLhioZeMjLn08kU7TUbHRUB+ULTuVvE2dQbBpGuKiLRRt9\n"
105 : "6U2T0eD3xGLoM+o8EY/kpqaWGEpZv7hzM9xuo4vy55+viAZgFWULqmltwfG/7w7V\n"
106 : "NXUHNv5H4Ipw//fSDLTPqzUlNqSSswDLz6pCjWEs0rWAqNAMaOiLTz4id9pL48Oe\n"
107 : "oAfpcQR9tgTEnwyXfZBnrJVclHhkHKGeXvU05IgCzpKO76Z5R+By50T0i/JV7vzM\n"
108 : "l2yS9aAl/cprT6U7yI3oU/blldCVNpMcFAFb+fO8DAKCAQBVMo8xptyvQOJeSvbO\n"
109 : "SSYdJ3IiI/0GdkcGWXblWg9z7mrPaWEnT7OquEm/+vYtWd3GHDtyNM+jzsN4Xgjc\n"
110 : "TL3AEd2hLiozJQ1BFKw25VU08UHAYTzUxZhO4Vwtmp46Kwj8YLDQ3NHRWCBxpDQR\n"
111 : "fbiFvyXP+qXap6plMfrydnUD1mae/JSOWOYgdB7tFIehstLxVXx/cAnjwgFU03Df\n"
112 : "grjsad92zA1Hc9wIjbsgAQdTR5DWnFRkRt3UtayBwoyqm6QceZHsv1NAGvkQ4ion\n"
113 : "bEjkHkjF9YCkR9/rspR8cLghRIXMjOpypuSbaRPeeWq0gP2UOxFL/d3iWH0ETr/L\n"
114 : "kTlCAhxYGpVgtfB96qmJukyl9GOGvfkwFTgEyIDoV84M\n"
115 : "-----END DSA PRIVATE KEY-----\n";
116 :
117 : static const char dsa_2048_sig[] =
118 : "\x30\x3d\x02\x1d\x00\xbe\x87\x2f\xcf\xa1\xe4\x86\x5c\x72\x58\x4a"
119 : "\x7b\x8f\x32\x7f\xa5\x1b\xdc\x5c\xae\xda\x98\xea\x15\x32\xed\x0c"
120 : "\x4e\x02\x1c\x4c\x76\x01\x2b\xcd\xb9\x33\x95\xf2\xfa\xde\x56\x01"
121 : "\xb7\xaa\xe4\x5a\x4a\x2e\xf1\x24\x5a\xd1\xb5\x83\x9a\x93\x61";
122 :
123 : /* secp256r1 private key and signature */
124 : static const char ecdsa_secp256r1_privkey[] =
125 : "-----BEGIN EC PRIVATE KEY-----\n"
126 : "MHcCAQEEIPAKWV7+pZe9c5EubMNfAEKWRQtP/MvlO9HehwHmJssNoAoGCCqGSM49\n"
127 : "AwEHoUQDQgAE2CNONRio3ciuXtoomJKs3MdbzLbd44VPhtzJN30VLFm5gvnfiCj2\n"
128 : "zzz7pl9Cv0ECHl6yedNI8QEKdcwCDgEmkQ==\n"
129 : "-----END EC PRIVATE KEY-----\n";
130 :
131 : static const char ecdsa_secp256r1_sig[] =
132 : "\x30\x45\x02\x21\x00\x80\x67\x18\xb9\x72\xc6\x0b\xe1\xc9\x89\x9b"
133 : "\x85\x11\x49\x29\x08\xd9\x86\x76\xcc\xfb\xc1\xf4\xd0\xa2\x5e\xa7"
134 : "\xb9\x12\xfb\x1a\x68\x02\x20\x67\x12\xb1\x89\x9e\x1d\x9d\x5c\x0f"
135 : "\xef\x6e\xa7\x2a\x95\x8c\xfa\x54\x20\x80\xc8\x30\x7c\xff\x06\xbc"
136 : "\xc8\xe2\x9a\x2f\x05\x2f\x67";
137 :
138 : #ifdef ENABLE_NON_SUITEB_CURVES
139 : /* secp192r1 private key and signature */
140 : static const char ecdsa_secp192r1_privkey[] =
141 : "-----BEGIN EC PRIVATE KEY-----"
142 : "MF8CAQEEGLjezFcbgDMeApVrdtZHvu/k1a8/tVZ41KAKBggqhkjOPQMBAaE0AzIA"
143 : "BO1lciKdgxeRH8k64vxcaV1OYIK9akVrW02Dw21MXhRLP0l0wzCw6LGSr5rS6AaL"
144 : "Fg==" "-----END EC PRIVATE KEY-----";
145 :
146 : static const char ecdsa_secp192r1_sig[] =
147 : "\x30\x34\x02\x18\x7c\x43\xe3\xb7\x26\x90\x43\xb5\xf5\x63\x8f\xee"
148 : "\xac\x78\x3d\xac\x35\x35\xd0\x1e\x83\x17\x2b\x64\x02\x18\x14\x6e"
149 : "\x94\xd5\x7e\xac\x43\x42\x0b\x71\x7a\xc8\x29\xe6\xe3\xda\xf2\x95"
150 : "\x0e\xe0\x63\x24\xed\xf2";
151 :
152 : /* secp224r1 private key and signature */
153 : static const char ecdsa_secp224r1_privkey[] =
154 : "-----BEGIN EC PRIVATE KEY-----"
155 : "MGgCAQEEHOKWJFdWdrR/CgVrUeTeawOrJ9GozE9KKx2a8PmgBwYFK4EEACGhPAM6"
156 : "AAQKQj3YpenWT7lFR41SnBvmj/+Bj+kgzQnaF65qWAtPRJsZXFlLTu3/IUNqSRu9"
157 : "DqPsk8xBHAB7pA==" "-----END EC PRIVATE KEY-----";
158 :
159 : static const char ecdsa_secp224r1_sig[] =
160 : "\x30\x3d\x02\x1c\x14\x22\x09\xa1\x51\x33\x37\xfd\x78\x73\xbd\x84"
161 : "\x6e\x76\xa8\x60\x90\xf5\xb6\x57\x34\x25\xe0\x79\xe3\x01\x61\xa9"
162 : "\x02\x1d\x00\xb1\xee\xdb\xae\xb3\xe6\x9c\x04\x68\xd5\xe1\x0d\xb6"
163 : "\xfc\x5c\x45\xc3\x4f\xbf\x2b\xa5\xe0\x89\x37\x84\x04\x82\x5f";
164 : #endif
165 :
166 : /* secp384r1 private key and signature */
167 : static const char ecdsa_secp384r1_privkey[] =
168 : "-----BEGIN EC PRIVATE KEY-----"
169 : "MIGkAgEBBDDevshD6gb+4rZpC9vwFcIwNs4KmGzdqCxyyN40a8uOWRbyf7aHdiSS"
170 : "03oAyKtc4JCgBwYFK4EEACKhZANiAARO1KkPMno2tnNXx1S9EZkp8SOpDCZ4aobH"
171 : "IYv8RHnSmKf8I3OKD6TaoeR+1MwJmNJUH90Bj45WXla68/vsPiFcfVKboxsZYe/n"
172 : "pv8e4ugXagVQVBXNZJ859iYPdJR24vo=" "-----END EC PRIVATE KEY-----";
173 :
174 : static const char ecdsa_secp384r1_sig[] =
175 : "\x30\x65\x02\x31\x00\xa7\x73\x60\x16\xdb\xf9\x1f\xfc\x9e\xd2\x12"
176 : "\x23\xd4\x04\xa7\x31\x1f\x15\x28\xfd\x87\x9c\x2c\xb1\xf3\x38\x35"
177 : "\x23\x3b\x6e\xfe\x6a\x5d\x89\x34\xbe\x02\x82\xc6\x27\xea\x45\x53"
178 : "\xa9\x87\xc5\x31\x0a\x02\x30\x76\x32\x80\x6b\x43\x3c\xb4\xfd\x90"
179 : "\x03\xe0\x1d\x5d\x77\x18\x45\xf6\x71\x29\xa9\x05\x87\x49\x75\x3a"
180 : "\x78\x9c\x49\xe5\x6c\x8e\x18\xcd\x5d\xee\x2c\x6f\x92\xf7\x15\xd3"
181 : "\x38\xd5\xf9\x9b\x9d\x1a\xf4";
182 :
183 : /* secp521r1 private key and signature */
184 : static const char ecdsa_secp521r1_privkey[] =
185 : "-----BEGIN EC PRIVATE KEY-----"
186 : "MIHbAgEBBEGO2n7NN363qSCvJVdlQtCvudtaW4o0fEufXRjE1AsCrle+VXX0Zh0w"
187 : "Y1slSeDHMndpakoiF+XkQ+bhcB867UV6aKAHBgUrgQQAI6GBiQOBhgAEAQb6jDpo"
188 : "byy1tF8Zucg0TMGUzIN2DK+RZJ3QQRdWdirO25OIC3FoFi1Yird6rpoB6HlNyJ7R"
189 : "0bNG9Uv34bSHMn8yAFoiqxUCdJZQbEenMoZsi6COaePe3e0QqvDMr0hEWT23Sr3t"
190 : "LpEV7eZGFfFIJw5wSUp2KOcs+O9WjmoukTWtDKNV"
191 : "-----END EC PRIVATE KEY-----";
192 :
193 : static const char ecdsa_secp521r1_sig[] =
194 : "\x30\x81\x88\x02\x42\x01\x9d\x13\x2e\xc9\x75\x1b\x60\x10\x62\xc5"
195 : "\x0d\xcb\x08\x9e\x86\x01\xd3\xc9\x8c\xee\x2e\x16\x3d\x8c\xc2\x65"
196 : "\x80\xe1\x32\x56\xc3\x02\x9d\xf0\x4a\x89\x8d\x2e\x33\x2a\x90\x4e"
197 : "\x72\x1d\xaa\x84\x14\xe8\xcb\xdf\x7a\x4a\xc9\x67\x2e\xba\xa3\xf2"
198 : "\xc2\x07\xf7\x1b\xa5\x91\xbd\x02\x42\x01\xe3\x32\xd2\x25\xeb\x2e"
199 : "\xaf\xb4\x6c\xc0\xaa\x5c\xc1\x56\x14\x13\x23\x7f\x62\xcf\x4c\xb8"
200 : "\xd1\x96\xe0\x29\x6d\xed\x74\xdd\x23\x64\xf9\x29\x86\x40\x22\x2f"
201 : "\xb6\x8d\x4c\x8e\x0b\x7a\xda\xdb\x03\x44\x01\x9b\x81\x1c\x3c\xab"
202 : "\x78\xee\xf2\xc5\x24\x33\x61\x65\x01\x87\x66";
203 :
204 : /* GOST01 private key */
205 : static const char gost01_privkey[] =
206 : "-----BEGIN PRIVATE KEY-----\n"
207 : "MEUCAQAwHAYGKoUDAgITMBIGByqFAwICIwEGByqFAwICHgEEIgQgdNfuHGmmTdPm\n"
208 : "p5dAa3ea9UYxpdYQPP9lbDwzQwG2bJM=\n"
209 : "-----END PRIVATE KEY-----\n";
210 :
211 : /* GOST12 256 private key */
212 : static const char gost12_256_privkey[] =
213 : "-----BEGIN PRIVATE KEY-----\n"
214 : "MEgCAQAwHwYIKoUDBwEBAQEwEwYHKoUDAgIjAQYIKoUDBwEBAgIEIgQgKOF96tom\n"
215 : "D61rhSnzKjyrmO3fv0gdlHei+6ovrc8SnBk=\n"
216 : "-----END PRIVATE KEY-----\n";
217 :
218 : /* GOST12 512 private key */
219 : static const char gost12_512_privkey[] =
220 : "-----BEGIN PRIVATE KEY-----\n"
221 : "MGoCAQAwIQYIKoUDBwEBAQIwFQYJKoUDBwECAQIBBggqhQMHAQECAwRCBECjFpvp\n"
222 : "B0vdc7u59b99TCNXhHiB69JJtUjvieNkGYJpoaaIvoKZTNCjpSZASsZcQZCHOTof\n"
223 : "hsQ3JCCy4xnd5jWT\n"
224 : "-----END PRIVATE KEY-----\n";
225 :
226 2 : static int test_rsa_enc(gnutls_pk_algorithm_t pk,
227 : unsigned bits, gnutls_digest_algorithm_t ign)
228 : {
229 2 : int ret;
230 2 : gnutls_datum_t enc = { NULL, 0 };
231 2 : gnutls_datum_t dec = { NULL, 0 };
232 2 : gnutls_datum_t raw_rsa_key = { (void*)rsa_2048_privkey, sizeof(rsa_2048_privkey)-1 };
233 2 : gnutls_privkey_t key;
234 2 : gnutls_pubkey_t pub = NULL;
235 2 : unsigned char plaintext2[sizeof(DATASTR) - 1];
236 :
237 2 : ret = gnutls_privkey_init(&key);
238 2 : if (ret < 0)
239 0 : return gnutls_assert_val(ret);
240 :
241 2 : ret = gnutls_pubkey_init(&pub);
242 2 : if (ret < 0) {
243 0 : gnutls_assert();
244 0 : goto cleanup;
245 : }
246 :
247 2 : ret = gnutls_privkey_import_x509_raw(key, &raw_rsa_key, GNUTLS_X509_FMT_PEM, NULL, 0);
248 2 : if (ret < 0) {
249 0 : gnutls_assert();
250 0 : goto cleanup;
251 : }
252 :
253 2 : ret = gnutls_pubkey_import_privkey(pub, key, 0, 0);
254 2 : if (ret < 0) {
255 0 : gnutls_assert();
256 0 : goto cleanup;
257 : }
258 :
259 2 : ret = gnutls_pubkey_encrypt_data(pub, 0, &signed_data, &enc);
260 2 : if (ret < 0) {
261 0 : gnutls_assert();
262 0 : goto cleanup;
263 : }
264 :
265 2 : if (enc.size == signed_data.size && memcmp(signed_data.data, enc.data,
266 : enc.size) == 0) {
267 0 : gnutls_assert();
268 0 : ret = GNUTLS_E_SELF_TEST_ERROR;
269 0 : goto cleanup;
270 : }
271 :
272 2 : ret = gnutls_privkey_decrypt_data(key, 0, &enc, &dec);
273 2 : if (ret < 0) {
274 0 : gnutls_assert();
275 0 : goto cleanup;
276 : }
277 :
278 2 : if (dec.size != signed_data.size
279 2 : || memcmp(dec.data, signed_data.data, dec.size) != 0) {
280 0 : ret = GNUTLS_E_SELF_TEST_ERROR;
281 0 : gnutls_assert();
282 0 : goto cleanup;
283 : }
284 :
285 2 : ret = gnutls_privkey_decrypt_data2(key, 0, &enc, plaintext2,
286 : signed_data.size);
287 2 : if (ret < 0) {
288 0 : gnutls_assert();
289 0 : goto cleanup;
290 : }
291 2 : if (memcmp(plaintext2, signed_data.data, signed_data.size) != 0) {
292 0 : ret = GNUTLS_E_SELF_TEST_ERROR;
293 0 : gnutls_assert();
294 0 : goto cleanup;
295 : }
296 :
297 : ret = 0;
298 2 : cleanup:
299 2 : if (pub != NULL)
300 2 : gnutls_pubkey_deinit(pub);
301 2 : gnutls_privkey_deinit(key);
302 2 : gnutls_free(enc.data);
303 2 : gnutls_free(dec.data);
304 :
305 2 : if (ret == 0)
306 2 : _gnutls_debug_log("%s-%u-enc self test succeeded\n",
307 : gnutls_pk_get_name(pk), bits);
308 : else
309 0 : _gnutls_debug_log("%s-%u-enc self test failed\n",
310 : gnutls_pk_get_name(pk), bits);
311 :
312 : return ret;
313 : }
314 :
315 8 : static int test_sig(gnutls_pk_algorithm_t pk,
316 : unsigned bits, gnutls_sign_algorithm_t sigalgo)
317 : {
318 8 : int ret;
319 8 : gnutls_privkey_t key;
320 8 : gnutls_datum_t raw_key;
321 8 : gnutls_datum_t sig = { NULL, 0 };
322 8 : gnutls_pubkey_t pub = NULL;
323 8 : char param_name[32];
324 8 : unsigned vflags = 0;
325 :
326 8 : if (sigalgo == GNUTLS_SIGN_GOST_94)
327 2 : vflags |= GNUTLS_VERIFY_ALLOW_BROKEN;
328 :
329 8 : ret = gnutls_privkey_init(&key);
330 8 : if (ret < 0)
331 0 : return gnutls_assert_val(ret);
332 :
333 8 : ret = gnutls_pubkey_init(&pub);
334 8 : if (ret < 0) {
335 0 : gnutls_assert();
336 0 : goto cleanup;
337 : }
338 :
339 8 : switch(pk) {
340 0 : case GNUTLS_PK_RSA:
341 0 : raw_key.data = (void*)rsa_2048_privkey;
342 0 : raw_key.size = sizeof(rsa_2048_privkey) - 1;
343 0 : snprintf(param_name, sizeof(param_name), "%u", bits);
344 0 : break;
345 2 : case GNUTLS_PK_RSA_PSS:
346 2 : raw_key.data = (void*)rsa_2048_privkey;
347 2 : raw_key.size = sizeof(rsa_2048_privkey) - 1;
348 2 : snprintf(param_name, sizeof(param_name), "%u", bits);
349 2 : break;
350 0 : case GNUTLS_PK_DSA:
351 0 : raw_key.data = (void*)dsa_2048_privkey;
352 0 : raw_key.size = sizeof(dsa_2048_privkey) - 1;
353 0 : snprintf(param_name, sizeof(param_name), "%u", bits);
354 0 : break;
355 0 : case GNUTLS_PK_ECC:
356 0 : switch(bits) {
357 : #ifdef ENABLE_NON_SUITEB_CURVES
358 : case GNUTLS_CURVE_TO_BITS(GNUTLS_ECC_CURVE_SECP192R1):
359 : raw_key.data = (void*)ecdsa_secp192r1_privkey;
360 : raw_key.size = sizeof(ecdsa_secp192r1_privkey) - 1;
361 : break;
362 : case GNUTLS_CURVE_TO_BITS(GNUTLS_ECC_CURVE_SECP224R1):
363 : raw_key.data = (void*)ecdsa_secp224r1_privkey;
364 : raw_key.size = sizeof(ecdsa_secp224r1_privkey) - 1;
365 : break;
366 : #endif
367 0 : case GNUTLS_CURVE_TO_BITS(GNUTLS_ECC_CURVE_SECP256R1):
368 0 : raw_key.data = (void*)ecdsa_secp256r1_privkey;
369 0 : raw_key.size = sizeof(ecdsa_secp256r1_privkey) - 1;
370 0 : break;
371 0 : case GNUTLS_CURVE_TO_BITS(GNUTLS_ECC_CURVE_SECP384R1):
372 0 : raw_key.data = (void*)ecdsa_secp384r1_privkey;
373 0 : raw_key.size = sizeof(ecdsa_secp384r1_privkey) - 1;
374 0 : break;
375 0 : case GNUTLS_CURVE_TO_BITS(GNUTLS_ECC_CURVE_SECP521R1):
376 0 : raw_key.data = (void*)ecdsa_secp521r1_privkey;
377 0 : raw_key.size = sizeof(ecdsa_secp521r1_privkey) - 1;
378 0 : break;
379 0 : default:
380 0 : gnutls_assert();
381 0 : ret = GNUTLS_E_INTERNAL_ERROR;
382 0 : goto cleanup;
383 : }
384 0 : snprintf(param_name, sizeof(param_name), "%s",
385 0 : gnutls_ecc_curve_get_name(GNUTLS_BITS_TO_CURVE
386 : (bits)));
387 0 : break;
388 2 : case GNUTLS_PK_GOST_01:
389 2 : raw_key.data = (void*)gost01_privkey;
390 2 : raw_key.size = sizeof(gost01_privkey) - 1;
391 2 : snprintf(param_name, sizeof(param_name), "%s",
392 2 : gnutls_ecc_curve_get_name(GNUTLS_BITS_TO_CURVE
393 : (bits)));
394 2 : break;
395 2 : case GNUTLS_PK_GOST_12_256:
396 2 : raw_key.data = (void*)gost12_256_privkey;
397 2 : raw_key.size = sizeof(gost12_256_privkey) - 1;
398 2 : snprintf(param_name, sizeof(param_name), "%s",
399 2 : gnutls_ecc_curve_get_name(GNUTLS_BITS_TO_CURVE
400 : (bits)));
401 2 : break;
402 2 : case GNUTLS_PK_GOST_12_512:
403 2 : raw_key.data = (void*)gost12_512_privkey;
404 2 : raw_key.size = sizeof(gost12_512_privkey) - 1;
405 2 : snprintf(param_name, sizeof(param_name), "%s",
406 2 : gnutls_ecc_curve_get_name(GNUTLS_BITS_TO_CURVE
407 : (bits)));
408 2 : break;
409 0 : default:
410 0 : gnutls_assert();
411 0 : ret = GNUTLS_E_INTERNAL_ERROR;
412 0 : goto cleanup;
413 : }
414 :
415 8 : ret = gnutls_privkey_import_x509_raw(key, &raw_key, GNUTLS_X509_FMT_PEM, NULL, 0);
416 8 : if (ret < 0) {
417 0 : gnutls_assert();
418 0 : goto cleanup;
419 : }
420 :
421 8 : ret = gnutls_pubkey_import_privkey(pub, key, 0, 0);
422 8 : if (ret < 0) {
423 0 : gnutls_assert();
424 0 : goto cleanup;
425 : }
426 :
427 8 : ret = gnutls_privkey_sign_data2(key, sigalgo, 0, &signed_data, &sig);
428 8 : if (ret < 0) {
429 0 : gnutls_assert();
430 0 : goto cleanup;
431 : }
432 :
433 8 : ret =
434 8 : gnutls_pubkey_verify_data2(pub, sigalgo, vflags,
435 : &signed_data, &sig);
436 8 : if (ret < 0) {
437 0 : ret = GNUTLS_E_SELF_TEST_ERROR;
438 0 : gnutls_assert();
439 0 : goto cleanup;
440 : }
441 :
442 8 : ret =
443 8 : gnutls_pubkey_verify_data2(pub, sigalgo, vflags,
444 : &bad_data, &sig);
445 :
446 8 : if (ret != GNUTLS_E_PK_SIG_VERIFY_FAILED) {
447 0 : ret = GNUTLS_E_SELF_TEST_ERROR;
448 0 : gnutls_assert();
449 0 : goto cleanup;
450 : }
451 :
452 : ret = 0;
453 :
454 8 : cleanup:
455 8 : if (pub != NULL)
456 8 : gnutls_pubkey_deinit(pub);
457 8 : gnutls_privkey_deinit(key);
458 8 : gnutls_free(sig.data);
459 :
460 8 : if (ret == 0)
461 8 : _gnutls_debug_log("%s-%s-sig self test succeeded\n",
462 : gnutls_pk_get_name(pk), param_name);
463 : else
464 0 : _gnutls_debug_log("%s-%s-sig self test failed\n",
465 : gnutls_pk_get_name(pk), param_name);
466 :
467 : return ret;
468 : }
469 :
470 10 : static int test_known_sig(gnutls_pk_algorithm_t pk, unsigned bits,
471 : gnutls_digest_algorithm_t dig,
472 : const void *privkey, size_t privkey_size,
473 : const void *stored_sig, size_t stored_sig_size,
474 : gnutls_privkey_flags_t flags)
475 : {
476 10 : int ret;
477 10 : gnutls_datum_t sig = { NULL, 0 };
478 10 : gnutls_datum_t t, ssig;
479 10 : gnutls_pubkey_t pub = NULL;
480 10 : gnutls_privkey_t key;
481 10 : char param_name[32];
482 10 : unsigned vflags = 0;
483 :
484 10 : if (pk == GNUTLS_PK_EC ||
485 10 : pk == GNUTLS_PK_GOST_01 ||
486 4 : pk == GNUTLS_PK_GOST_12_256 ||
487 : pk == GNUTLS_PK_GOST_12_512)
488 : {
489 6 : snprintf(param_name, sizeof(param_name), "%s",
490 6 : gnutls_ecc_curve_get_name(GNUTLS_BITS_TO_CURVE
491 : (bits)));
492 6 : if (dig == GNUTLS_DIG_GOSTR_94)
493 0 : vflags |= GNUTLS_VERIFY_ALLOW_BROKEN;
494 : } else {
495 4 : snprintf(param_name, sizeof(param_name), "%u", bits);
496 : }
497 :
498 10 : ret = gnutls_privkey_init(&key);
499 10 : if (ret < 0)
500 0 : return gnutls_assert_val(ret);
501 :
502 10 : ret = gnutls_pubkey_init(&pub);
503 10 : if (ret < 0) {
504 0 : gnutls_assert();
505 0 : return ret;
506 : }
507 :
508 10 : t.data = (void *) privkey;
509 10 : t.size = privkey_size;
510 :
511 10 : ret =
512 10 : gnutls_privkey_import_x509_raw(key, &t, GNUTLS_X509_FMT_PEM,
513 : NULL, 0);
514 10 : if (ret < 0) {
515 0 : gnutls_assert();
516 0 : goto cleanup;
517 : }
518 :
519 10 : if (pk != (unsigned) gnutls_privkey_get_pk_algorithm(key, NULL)) {
520 0 : ret = GNUTLS_E_SELF_TEST_ERROR;
521 0 : goto cleanup;
522 : }
523 :
524 10 : ret = gnutls_privkey_sign_data(key, dig, flags, &signed_data, &sig);
525 10 : if (ret < 0) {
526 0 : gnutls_assert();
527 0 : goto cleanup;
528 : }
529 :
530 : /* Test if the generated signature matches the stored */
531 10 : ssig.data = (void *) stored_sig;
532 10 : ssig.size = stored_sig_size;
533 :
534 10 : if (sig.size != ssig.size
535 10 : || memcmp(sig.data, ssig.data, sig.size) != 0) {
536 0 : ret = GNUTLS_E_SELF_TEST_ERROR;
537 : #if 0
538 : unsigned i;
539 : fprintf(stderr, "Algorithm: %s-%s\n",
540 : gnutls_pk_get_name(pk), param_name);
541 : fprintf(stderr, "\nstored[%d]: ", ssig.size);
542 : for (i = 0; i < ssig.size; i++)
543 : fprintf(stderr, "\\x%.2x", ssig.data[i]);
544 :
545 : fprintf(stderr, "\ngenerated[%d]: ", sig.size);
546 : for (i = 0; i < sig.size; i++)
547 : fprintf(stderr, "\\x%.2x", sig.data[i]);
548 : fprintf(stderr, "\n");
549 : #endif
550 0 : gnutls_assert();
551 0 : goto cleanup;
552 : }
553 :
554 : /* Test if we can verify the generated signature */
555 :
556 10 : ret = gnutls_pubkey_import_privkey(pub, key, 0, 0);
557 10 : if (ret < 0) {
558 0 : gnutls_assert();
559 0 : goto cleanup;
560 : }
561 :
562 10 : ret =
563 10 : gnutls_pubkey_verify_data2(pub, gnutls_pk_to_sign(pk, dig), vflags,
564 : &signed_data, &sig);
565 10 : if (ret < 0) {
566 0 : ret = GNUTLS_E_SELF_TEST_ERROR;
567 0 : gnutls_assert();
568 0 : goto cleanup;
569 : }
570 :
571 : /* Test if a broken signature will cause verification error */
572 :
573 10 : ret =
574 10 : gnutls_pubkey_verify_data2(pub, gnutls_pk_to_sign(pk, dig), 0,
575 : &bad_data, &sig);
576 :
577 10 : if (ret != GNUTLS_E_PK_SIG_VERIFY_FAILED) {
578 0 : ret = GNUTLS_E_SELF_TEST_ERROR;
579 0 : gnutls_assert();
580 0 : goto cleanup;
581 : }
582 :
583 : ret = 0;
584 :
585 10 : cleanup:
586 10 : gnutls_free(sig.data);
587 10 : if (pub != 0)
588 10 : gnutls_pubkey_deinit(pub);
589 10 : gnutls_privkey_deinit(key);
590 :
591 10 : if (ret == 0)
592 10 : _gnutls_debug_log("%s-%s-known-sig self test succeeded\n",
593 : gnutls_pk_get_name(pk), param_name);
594 : else
595 0 : _gnutls_debug_log("%s-%s-known-sig self test failed\n",
596 : gnutls_pk_get_name(pk), param_name);
597 :
598 : return ret;
599 : }
600 :
601 : #define PK_TEST(pk, func, bits, sigalgo) \
602 : ret = func(pk, bits, sigalgo); \
603 : if (ret < 0) { \
604 : gnutls_assert(); \
605 : goto cleanup; \
606 : }
607 :
608 : #define PK_KNOWN_TEST(pk, bits, dig, pkey, sig, flags) \
609 : ret = test_known_sig(pk, bits, dig, pkey, sizeof(pkey)-1, sig, sizeof(sig)-1, flags); \
610 : if (ret < 0) { \
611 : gnutls_assert(); \
612 : goto cleanup; \
613 : }
614 :
615 :
616 : /* Known answer tests for DH */
617 2 : static int test_dh(void)
618 : {
619 2 : int ret;
620 2 : gnutls_pk_params_st priv;
621 2 : gnutls_pk_params_st pub;
622 2 : gnutls_datum_t out = {NULL, 0};
623 :
624 : /* FFDHE 3072 test vector provided by Stephan Mueller in:
625 : * https://gitlab.com/gnutls/gnutls/-/merge_requests/1342#note_424430996
626 : */
627 2 : static const uint8_t known_dh_k[] = {
628 : 0xec, 0xb3, 0x85, 0x0c, 0x72, 0x55, 0x55, 0xc2, 0x98, 0x36,
629 : 0xbe, 0x75, 0x9e, 0xc9, 0x9d, 0x8b, 0x16, 0xa6, 0xe6, 0x84,
630 : 0x33, 0x12, 0x80, 0x1d, 0xac, 0xde, 0x6a, 0xd7, 0x3b, 0x1e,
631 : 0x15, 0xca, 0x5d, 0x26, 0xb3, 0x0a, 0x35, 0xf4, 0xbb, 0xad,
632 : 0x71, 0xcb, 0x03, 0x1a, 0xcb, 0xfb, 0x83, 0xf0, 0xa8, 0xde,
633 : 0xed, 0x5e, 0x3d, 0x98, 0xd2, 0xb0, 0xef, 0xad, 0xdf, 0x32,
634 : 0xa0, 0x16, 0x7d, 0x0e, 0x29, 0xd8, 0x85, 0xca, 0x12, 0x97,
635 : 0x56, 0xab, 0x6a, 0x26, 0xa4, 0x46, 0x3d, 0x87, 0xd7, 0xe0,
636 : 0xb4, 0x3e, 0x28, 0x75, 0xac, 0x59, 0xc5, 0x71, 0x3a, 0x24,
637 : 0x15, 0x76, 0x98, 0x72, 0x94, 0x2d, 0xd0, 0x0e, 0xbc, 0x9a,
638 : 0x77, 0xd4, 0xe2, 0xb2, 0x76, 0x54, 0x4a, 0x56, 0xbe, 0x0b,
639 : 0x43, 0xf8, 0x21, 0x6f, 0x54, 0x32, 0xde, 0xb7, 0xd5, 0xb7,
640 : 0x08, 0x00, 0xd2, 0x57, 0x8c, 0x0b, 0x8b, 0x02, 0x3e, 0xdb,
641 : 0x72, 0x54, 0x3a, 0xc0, 0x50, 0x66, 0xbc, 0xc9, 0x67, 0xf5,
642 : 0x22, 0x28, 0xf2, 0x3c, 0x51, 0x94, 0x61, 0x26, 0x9a, 0xc6,
643 : 0x42, 0x0e, 0x8b, 0x42, 0xad, 0x79, 0x40, 0xa9, 0x0b, 0xdc,
644 : 0x84, 0xd5, 0x71, 0x83, 0x94, 0xd9, 0x83, 0x2f, 0x08, 0x74,
645 : 0xbc, 0x37, 0x6a, 0x3e, 0x1e, 0xbc, 0xcc, 0x09, 0x23, 0x30,
646 : 0x79, 0x01, 0x39, 0xf6, 0xe3, 0xa8, 0xc0, 0xfa, 0x7e, 0xdb,
647 : 0x0b, 0x71, 0x3e, 0x4f, 0x1f, 0x69, 0x84, 0xa6, 0x58, 0x6c,
648 : 0x36, 0x2c, 0xcc, 0xb4, 0x7c, 0x94, 0xec, 0x06, 0x0b, 0x11,
649 : 0x53, 0x95, 0xe6, 0x05, 0x43, 0xa4, 0xe4, 0xea, 0x1d, 0x4f,
650 : 0xdc, 0xd0, 0x38, 0x0e, 0x32, 0xa1, 0xde, 0xd9, 0x8d, 0xd8,
651 : 0x20, 0xac, 0x04, 0x83, 0xf8, 0x1b, 0x55, 0x52, 0x16, 0x20,
652 : 0xe3, 0x2e, 0x6d, 0x11, 0x15, 0x29, 0x2f, 0x3a, 0x7c, 0x80,
653 : 0x0a, 0x71, 0x3d, 0x31, 0x9c, 0x1b, 0x73, 0x59, 0xe1, 0x0d,
654 : 0x27, 0xc5, 0xc0, 0x6a, 0x72, 0x3a, 0x5b, 0xd6, 0xf6, 0x50,
655 : 0xe6, 0x69, 0x48, 0x1e, 0xfd, 0xeb, 0x4a, 0x47, 0x73, 0xfb,
656 : 0x88, 0x14, 0xea, 0x6d, 0x36, 0xe1, 0x4c, 0x2c, 0xf9, 0x04,
657 : 0xc1, 0xb7, 0x29, 0xfc, 0x5d, 0x02, 0x5d, 0x1c, 0x4d, 0x31,
658 : 0x4a, 0x51, 0x3f, 0xa4, 0x45, 0x19, 0x29, 0xc4, 0x32, 0xa6,
659 : 0x45, 0xdb, 0x94, 0x3a, 0xbd, 0x76, 0x2c, 0xd6, 0x1a, 0xb1,
660 : 0xff, 0xe7, 0x62, 0x75, 0x16, 0xe5, 0x0b, 0xa3, 0x3a, 0x93,
661 : 0x84, 0xd6, 0xad, 0xc2, 0x24, 0x68, 0x3d, 0xd6, 0x07, 0xe4,
662 : 0xbe, 0x5a, 0x49, 0x31, 0x06, 0xad, 0x3f, 0x31, 0x4a, 0x1c,
663 : 0xf7, 0x58, 0xdf, 0x34, 0xcb, 0xc8, 0xa9, 0x07, 0x24, 0x42,
664 : 0x63, 0xa5, 0x8e, 0xdd, 0x37, 0x78, 0x92, 0x68, 0x3f, 0xd8,
665 : 0x2f, 0xea, 0x8c, 0xf1, 0x8e, 0xd4, 0x8b, 0xa7, 0x3f, 0xa0,
666 : 0xfa, 0xaf, 0xf0, 0x35,
667 : };
668 2 : static const uint8_t test_x[] = {
669 : 0x16, 0x5c, 0xa6, 0xe0, 0x9b, 0x87, 0xfa, 0x2d, 0xbc, 0x13,
670 : 0x20, 0xcd, 0xac, 0x4e, 0xcc, 0x60, 0x1e, 0x48, 0xec, 0xbe,
671 : 0x73, 0x0c, 0xa8, 0x6b, 0x6e, 0x2a, 0xee, 0xdd, 0xd8, 0xf3,
672 : 0x2d, 0x5f, 0x75, 0xf3, 0x07, 0x94, 0x88, 0x3d, 0xb1, 0x38,
673 : 0xcf, 0xae, 0x4a, 0xcc, 0xcb, 0x6a, 0x80, 0xbc, 0xeb, 0x3b,
674 : 0xaa, 0x0b, 0x18, 0x74, 0x58, 0x7c, 0x3e, 0x74, 0xef, 0xb6,
675 : 0xd3, 0x15, 0xee, 0x73, 0x29, 0x88, 0x7b, 0x65, 0x02, 0x39,
676 : 0x33, 0xec, 0x22, 0x06, 0x8c, 0x5b, 0xd6, 0x2f, 0x4c, 0xf7,
677 : 0xe0, 0x97, 0x6d, 0x2a, 0x90, 0x36, 0xfe, 0x1a, 0x44, 0x4d,
678 : 0x9d, 0x41, 0x4b, 0xcb, 0xec, 0x25, 0xf4, 0xc3, 0xa5, 0x91,
679 : 0xd0, 0x90, 0xc9, 0x34, 0x7b, 0xba, 0x27, 0x30, 0x5a, 0xa2,
680 : 0x21, 0x58, 0xce, 0x88, 0x25, 0x39, 0xaf, 0xf1, 0x17, 0x02,
681 : 0x12, 0xf8, 0x55, 0xdc, 0xd2, 0x08, 0x5b, 0xd3, 0xc7, 0x8e,
682 : 0xcf, 0x29, 0x85, 0x85, 0xdb, 0x5c, 0x08, 0xc2, 0xd7, 0xb0,
683 : 0x33, 0x0e, 0xe3, 0xb9, 0x2c, 0x1a, 0x1d, 0x4b, 0xe5, 0x76,
684 : 0x8f, 0xd3, 0x14, 0xb6, 0x8c, 0xdc, 0x9a, 0xe8, 0x15, 0x60,
685 : 0x60, 0x5e, 0xaa, 0xf9, 0xfa, 0xa6, 0xb2, 0x4f, 0xff, 0x46,
686 : 0xc1, 0x5e, 0x93, 0x50, 0x90, 0x7e, 0x4c, 0x26, 0xd7, 0xbb,
687 : 0x21, 0x05, 0x3d, 0x27, 0xc5, 0x9b, 0x0d, 0x46, 0x69, 0xe4,
688 : 0x74, 0x87, 0x74, 0x55, 0xee, 0x5f, 0xe5, 0x72, 0x04, 0x46,
689 : 0x1f, 0x2e, 0x55, 0xc7, 0xcc, 0x2b, 0x2b, 0x39, 0x6d, 0x90,
690 : 0x60, 0x31, 0x37, 0x5b, 0x44, 0xde, 0xfd, 0xf2, 0xd1, 0xc6,
691 : 0x9c, 0x12, 0x82, 0xcc, 0x7c, 0xb1, 0x0e, 0xa9, 0x95, 0x9d,
692 : 0xe0, 0xa8, 0x3e, 0xc1, 0xa3, 0x4a, 0x6a, 0x37, 0x59, 0x17,
693 : 0x93, 0x63, 0x1e, 0xbf, 0x04, 0xa3, 0xaa, 0xc0, 0x1d, 0xc4,
694 : 0x6d, 0x7a, 0xdc, 0x69, 0x9c, 0xb0, 0x22, 0x56, 0xd9, 0x76,
695 : 0x92, 0x2d, 0x1e, 0x62, 0xae, 0xfd, 0xd6, 0x9b, 0xfd, 0x08,
696 : 0x2c, 0x95, 0xec, 0xe7, 0x02, 0x43, 0x62, 0x68, 0x1a, 0xaf,
697 : 0x46, 0x59, 0xb7, 0xce, 0x8e, 0x42, 0x24, 0xae, 0xf7, 0x0e,
698 : 0x9a, 0x3b, 0xf8, 0x77, 0xdf, 0x26, 0x85, 0x9f, 0x45, 0xad,
699 : 0x8c, 0xa9, 0x54, 0x9c, 0x46, 0x44, 0xd5, 0x8a, 0xe9, 0xcc,
700 : 0x34, 0x5e, 0xc5, 0xd1, 0x42, 0x6f, 0x44, 0xf3, 0x0f, 0x90,
701 : 0x3a, 0x32, 0x1a, 0x9c, 0x2a, 0x63, 0xec, 0x21, 0xb4, 0xfc,
702 : 0xfa, 0xa5, 0xcf, 0xe7, 0x9e, 0x43, 0xc7, 0x49, 0x56, 0xbc,
703 : 0x50, 0xc5, 0x84, 0xf0, 0x42, 0xc8, 0x6a, 0xf1, 0x78, 0xe4,
704 : 0xaa, 0x06, 0x37, 0xe1, 0x30, 0xf7, 0x65, 0x97, 0xca, 0xfd,
705 : 0x35, 0xfa, 0xeb, 0x48, 0x6d, 0xaa, 0x45, 0x46, 0x9d, 0xbc,
706 : 0x1d, 0x98, 0x17, 0x45, 0xa3, 0xee, 0x21, 0xa0, 0x97, 0x38,
707 : 0x80, 0xc5, 0x28, 0x1f,
708 : };
709 2 : static const uint8_t test_y[] = { /* y=g^x mod p */
710 : 0x93, 0xeb, 0x5c, 0x37, 0x1d, 0x3c, 0x06, 0x6f, 0xbf, 0xbe,
711 : 0x96, 0x51, 0x26, 0x58, 0x81, 0x36, 0xc6, 0x4f, 0x9a, 0x34,
712 : 0xc4, 0xc5, 0xa8, 0xa3, 0x2c, 0x41, 0x76, 0xa8, 0xc6, 0xc0,
713 : 0xa0, 0xc8, 0x51, 0x36, 0xc4, 0x40, 0x4e, 0x2c, 0x69, 0xf7,
714 : 0x51, 0xbb, 0xb0, 0xd6, 0xf5, 0xdb, 0x40, 0x29, 0x50, 0x3b,
715 : 0x8a, 0xf9, 0xf3, 0x53, 0x78, 0xfc, 0x86, 0xe9, 0xf1, 0xe9,
716 : 0xac, 0x85, 0x13, 0x65, 0x62, 0x22, 0x04, 0x1b, 0x14, 0x2a,
717 : 0xf4, 0x8f, 0x2f, 0xf1, 0x2f, 0x81, 0xd6, 0x18, 0x0e, 0x76,
718 : 0x91, 0x43, 0xb2, 0xfc, 0x7c, 0x6f, 0x0c, 0x45, 0x37, 0x31,
719 : 0x31, 0x58, 0x5c, 0xdf, 0x42, 0x24, 0x7a, 0xba, 0x8b, 0x7f,
720 : 0x79, 0x06, 0x07, 0xef, 0xd6, 0x06, 0xeb, 0xcb, 0x3c, 0xbd,
721 : 0xbc, 0xe5, 0xff, 0xfd, 0x62, 0x15, 0x0c, 0x40, 0x46, 0x37,
722 : 0xef, 0xd0, 0xa1, 0xde, 0x63, 0x4f, 0x20, 0x0b, 0x45, 0x7d,
723 : 0x06, 0x77, 0xfd, 0x23, 0xc1, 0x32, 0x8a, 0x89, 0x65, 0x16,
724 : 0xe8, 0x48, 0x12, 0x1c, 0x25, 0x33, 0x2d, 0xbd, 0xd8, 0x9f,
725 : 0x1c, 0x9d, 0xbc, 0xe3, 0x08, 0x60, 0x87, 0x1a, 0xc6, 0x06,
726 : 0x36, 0xd2, 0xac, 0x09, 0x6d, 0x99, 0x02, 0x89, 0xc6, 0x12,
727 : 0x93, 0x8c, 0x4b, 0xd0, 0x7e, 0x36, 0x8a, 0xd6, 0xa0, 0x97,
728 : 0x4f, 0x97, 0x3f, 0x97, 0x0b, 0xfe, 0x05, 0xfc, 0xc8, 0xef,
729 : 0x21, 0x4d, 0x4a, 0x06, 0x6e, 0xb4, 0xa6, 0x4f, 0xe1, 0xdd,
730 : 0x44, 0x06, 0xfa, 0xd5, 0x0e, 0x54, 0xf5, 0x54, 0x3e, 0x8c,
731 : 0xb9, 0x85, 0x86, 0x00, 0x40, 0x98, 0xe7, 0x01, 0xdd, 0x93,
732 : 0x9d, 0x95, 0xea, 0xf0, 0xd3, 0x99, 0x4b, 0xeb, 0xd5, 0x79,
733 : 0x47, 0xa4, 0xad, 0x2a, 0xe0, 0x4d, 0x36, 0x3b, 0x46, 0x10,
734 : 0x96, 0xbb, 0x48, 0xe9, 0xa1, 0x78, 0x01, 0x35, 0x0a, 0x5c,
735 : 0x7b, 0x3f, 0xf5, 0xf7, 0xb1, 0xe3, 0x97, 0x17, 0x4d, 0x76,
736 : 0x10, 0x8d, 0x68, 0x4c, 0x94, 0x7d, 0xee, 0x0e, 0x20, 0x8b,
737 : 0xce, 0x7d, 0x0a, 0xa3, 0x51, 0xfb, 0xe6, 0xcf, 0xf0, 0x0e,
738 : 0x7f, 0x3c, 0xd4, 0xef, 0x56, 0x31, 0xb2, 0x95, 0xf0, 0x5f,
739 : 0x4b, 0x9c, 0x03, 0x9e, 0xae, 0xb1, 0xc1, 0x46, 0xd7, 0xc0,
740 : 0x4f, 0xb0, 0xf6, 0x6c, 0xe1, 0xe9, 0x2a, 0x97, 0xe0, 0x3f,
741 : 0x3a, 0x93, 0x04, 0xcd, 0x41, 0x7d, 0x45, 0x03, 0xb3, 0x40,
742 : 0x20, 0xe6, 0xad, 0x2d, 0xd3, 0xf7, 0x32, 0x7b, 0xcc, 0x4f,
743 : 0x81, 0x18, 0x4c, 0x50, 0x77, 0xc4, 0xb7, 0x6a, 0x4d, 0x05,
744 : 0xd8, 0x6d, 0xbf, 0x6f, 0xba, 0x1d, 0x38, 0x78, 0x87, 0xd2,
745 : 0x8e, 0xc2, 0x6d, 0xb6, 0xed, 0x66, 0x61, 0xa8, 0xb9, 0x19,
746 : 0x0e, 0x93, 0xd1, 0xcd, 0x5b, 0xbe, 0x19, 0x05, 0x52, 0x43,
747 : 0xd6, 0xc1, 0x07, 0x3c, 0x6a, 0x62, 0xbd, 0x33, 0x9b, 0x1b,
748 : 0x02, 0x42, 0x61, 0x14,
749 : };
750 :
751 2 : gnutls_pk_params_init(&priv);
752 2 : gnutls_pk_params_init(&pub);
753 :
754 2 : priv.algo = pub.algo = GNUTLS_PK_DH;
755 :
756 4 : ret = _gnutls_mpi_init_scan(&priv.params[DH_P],
757 2 : gnutls_ffdhe_3072_group_prime.data,
758 2 : gnutls_ffdhe_3072_group_prime.size);
759 2 : if (ret < 0) {
760 0 : gnutls_assert();
761 0 : goto cleanup;
762 : }
763 :
764 4 : ret = _gnutls_mpi_init_scan(&priv.params[DH_G],
765 2 : gnutls_ffdhe_3072_group_generator.data,
766 2 : gnutls_ffdhe_3072_group_generator.size);
767 2 : if (ret < 0) {
768 0 : gnutls_assert();
769 0 : goto cleanup;
770 : }
771 :
772 2 : ret = _gnutls_mpi_init_scan(&priv.params[DH_X], test_x, sizeof(test_x));
773 2 : if (ret < 0) {
774 0 : gnutls_assert();
775 0 : goto cleanup;
776 : }
777 :
778 2 : ret = _gnutls_mpi_init_scan(&pub.params[DH_Y], test_y, sizeof(test_y));
779 2 : if (ret < 0) {
780 0 : gnutls_assert();
781 0 : goto cleanup;
782 : }
783 :
784 : /* check whether Y^X mod p is the expected value */
785 2 : ret = _gnutls_pk_derive(GNUTLS_PK_DH, &out, &priv, &pub);
786 2 : if (ret < 0) {
787 0 : gnutls_assert();
788 0 : goto cleanup;
789 : }
790 :
791 2 : if (sizeof(known_dh_k) != out.size) {
792 0 : ret = GNUTLS_E_SELF_TEST_ERROR;
793 0 : gnutls_assert();
794 0 : goto cleanup;
795 : }
796 :
797 2 : if (memcmp(out.data, known_dh_k, out.size) != 0) {
798 0 : ret = GNUTLS_E_SELF_TEST_ERROR;
799 0 : gnutls_assert();
800 0 : goto cleanup;
801 : }
802 :
803 :
804 : ret = 0;
805 2 : cleanup:
806 2 : _gnutls_mpi_release(&pub.params[DH_Y]);
807 2 : _gnutls_mpi_release(&priv.params[DH_G]);
808 2 : _gnutls_mpi_release(&priv.params[DH_P]);
809 2 : _gnutls_mpi_release(&priv.params[DH_X]);
810 2 : gnutls_free(out.data);
811 :
812 2 : if (ret < 0) {
813 0 : _gnutls_debug_log("DH self test failed\n");
814 : } else {
815 2 : _gnutls_debug_log("DH self test succeeded\n");
816 : }
817 :
818 2 : return ret;
819 : }
820 :
821 : /* Known answer tests for DH */
822 2 : static int test_ecdh(void)
823 : {
824 2 : int ret;
825 2 : gnutls_pk_params_st priv;
826 2 : gnutls_pk_params_st pub;
827 2 : gnutls_datum_t out = {NULL, 0};
828 2 : static const uint8_t known_key[] = {
829 : 0x22, 0x7a, 0x95, 0x98, 0x5f, 0xb1, 0x25, 0x79,
830 : 0xee, 0x07, 0xe3, 0x8b, 0x1a, 0x97, 0x1d, 0x63,
831 : 0x53, 0xa8, 0xbd, 0xde, 0x67, 0x4b, 0xcf, 0xa4,
832 : 0x5f, 0x5e, 0x67, 0x27, 0x6d, 0x86, 0x27, 0x26 };
833 2 : static const uint8_t test_k[] = { /* priv */
834 : 0x52, 0x9c, 0x30, 0xac, 0x6b, 0xce, 0x71, 0x9a,
835 : 0x37, 0xcd, 0x40, 0x93, 0xbf, 0xf0, 0x36, 0x89,
836 : 0x53, 0xcc, 0x0e, 0x17, 0xc6, 0xb6, 0xe2, 0x6a,
837 : 0x3c, 0x2c, 0x51, 0xdb, 0xa6, 0x69, 0x8c, 0xb1 };
838 2 : static const uint8_t test_x[] = {
839 : 0x51, 0x35, 0xd1, 0xd2, 0xb6, 0xad, 0x13, 0xf4,
840 : 0xa2, 0x25, 0xd3, 0x85, 0x83, 0xbe, 0x42, 0x1e,
841 : 0x19, 0x09, 0x54, 0x39, 0x00, 0x46, 0x91, 0x49,
842 : 0x0f, 0x3f, 0xaf, 0x3f, 0x67, 0xda, 0x10, 0x6f };
843 2 : static const uint8_t test_y[] = { /* y=g^x mod p */
844 : 0x07, 0x3a, 0xa1, 0xa2, 0x47, 0x3d, 0xa2, 0x74,
845 : 0x74, 0xc2, 0xde, 0x62, 0xb6, 0xb9, 0x59, 0xc9,
846 : 0x56, 0xf6, 0x9e, 0x17, 0xea, 0xbf, 0x7d, 0xa1,
847 : 0xd7, 0x65, 0xd6, 0x7b, 0xac, 0xca, 0xd5, 0xe3 };
848 2 : gnutls_pk_params_init(&priv);
849 2 : gnutls_pk_params_init(&pub);
850 :
851 2 : priv.curve = GNUTLS_ECC_CURVE_SECP256R1;
852 2 : pub.curve = GNUTLS_ECC_CURVE_SECP256R1;
853 :
854 2 : priv.algo = pub.algo = GNUTLS_PK_EC;
855 :
856 2 : ret = _gnutls_mpi_init_scan(&priv.params[ECC_K], test_k, sizeof(test_k));
857 2 : if (ret < 0) {
858 0 : gnutls_assert();
859 0 : goto cleanup;
860 : }
861 :
862 2 : ret = _gnutls_mpi_init_scan(&priv.params[ECC_X], test_x, sizeof(test_x));
863 2 : if (ret < 0) {
864 0 : gnutls_assert();
865 0 : goto cleanup;
866 : }
867 :
868 2 : ret = _gnutls_mpi_init_scan(&priv.params[ECC_Y], test_y, sizeof(test_y));
869 2 : if (ret < 0) {
870 0 : gnutls_assert();
871 0 : goto cleanup;
872 : }
873 :
874 2 : ret = _gnutls_mpi_init_scan(&pub.params[ECC_X], test_x, sizeof(test_x));
875 2 : if (ret < 0) {
876 0 : gnutls_assert();
877 0 : goto cleanup;
878 : }
879 :
880 2 : ret = _gnutls_mpi_init_scan(&pub.params[ECC_Y], test_y, sizeof(test_y));
881 2 : if (ret < 0) {
882 0 : gnutls_assert();
883 0 : goto cleanup;
884 : }
885 :
886 : /* check whether Y^X mod p is the expected value */
887 2 : ret = _gnutls_pk_derive(GNUTLS_PK_EC, &out, &priv, &pub);
888 2 : if (ret < 0) {
889 0 : gnutls_assert();
890 0 : goto cleanup;
891 : }
892 :
893 2 : if (sizeof(known_key) != out.size) {
894 0 : ret = GNUTLS_E_SELF_TEST_ERROR;
895 0 : gnutls_assert();
896 0 : goto cleanup;
897 : }
898 :
899 2 : if (memcmp(out.data, known_key, out.size) != 0) {
900 0 : ret = GNUTLS_E_SELF_TEST_ERROR;
901 0 : gnutls_assert();
902 0 : goto cleanup;
903 : }
904 :
905 : ret = 0;
906 2 : cleanup:
907 2 : _gnutls_mpi_release(&pub.params[ECC_Y]);
908 2 : _gnutls_mpi_release(&pub.params[ECC_X]);
909 2 : _gnutls_mpi_release(&priv.params[ECC_K]);
910 2 : _gnutls_mpi_release(&priv.params[ECC_X]);
911 2 : _gnutls_mpi_release(&priv.params[ECC_Y]);
912 2 : gnutls_free(out.data);
913 :
914 2 : if (ret < 0) {
915 0 : _gnutls_debug_log("ECDH self test failed\n");
916 : } else {
917 2 : _gnutls_debug_log("ECDH self test succeeded\n");
918 : }
919 :
920 2 : return ret;
921 : }
922 :
923 : /*-
924 : * gnutls_pk_self_test:
925 : * @flags: GNUTLS_SELF_TEST_FLAG flags
926 : * @pk: the algorithm to use
927 : *
928 : * This function will run self tests on the provided public key algorithm.
929 : *
930 : * Returns: Zero or a negative error code on error.
931 : *
932 : * Since: 3.3.0-FIPS140
933 : -*/
934 2 : int gnutls_pk_self_test(unsigned flags, gnutls_pk_algorithm_t pk)
935 : {
936 2 : int ret;
937 :
938 2 : bool is_post = false;
939 2 : bool is_fips140_mode_enabled = false;
940 :
941 2 : if (flags & GNUTLS_SELF_TEST_FLAG_ALL)
942 2 : pk = GNUTLS_PK_UNKNOWN;
943 :
944 2 : if (_gnutls_get_lib_state() == LIB_STATE_SELFTEST)
945 0 : is_post = true;
946 :
947 2 : if (gnutls_fips140_mode_enabled())
948 0 : is_fips140_mode_enabled = true;
949 :
950 2 : switch (pk) {
951 2 : case GNUTLS_PK_UNKNOWN:
952 2 : FALLTHROUGH;
953 : case GNUTLS_PK_DH:
954 2 : ret = test_dh();
955 2 : if (ret < 0) {
956 0 : gnutls_assert();
957 0 : goto cleanup;
958 : }
959 :
960 2 : if (!(flags & GNUTLS_SELF_TEST_FLAG_ALL))
961 : return 0;
962 2 : FALLTHROUGH;
963 : case GNUTLS_PK_RSA:
964 2 : PK_KNOWN_TEST(GNUTLS_PK_RSA, 2048, GNUTLS_DIG_SHA256,
965 2 : rsa_2048_privkey, rsa_2048_sig, 0);
966 :
967 2 : PK_TEST(GNUTLS_PK_RSA, test_rsa_enc, 2048, 0);
968 :
969 2 : if (!(flags & GNUTLS_SELF_TEST_FLAG_ALL))
970 : return 0;
971 :
972 2 : FALLTHROUGH;
973 : case GNUTLS_PK_RSA_PSS:
974 2 : PK_TEST(GNUTLS_PK_RSA_PSS, test_sig, 2048,
975 2 : GNUTLS_SIGN_RSA_PSS_RSAE_SHA256);
976 :
977 2 : if (!(flags & GNUTLS_SELF_TEST_FLAG_ALL))
978 : return 0;
979 :
980 2 : FALLTHROUGH;
981 : case GNUTLS_PK_DSA:
982 2 : if (is_post || !is_fips140_mode_enabled) {
983 2 : PK_KNOWN_TEST(GNUTLS_PK_DSA, 2048, GNUTLS_DIG_SHA256,
984 : dsa_2048_privkey, dsa_2048_sig,
985 : GNUTLS_PRIVKEY_FLAG_REPRODUCIBLE);
986 : } else {
987 0 : PK_TEST(GNUTLS_PK_DSA, test_sig, 2048,
988 2 : GNUTLS_SIGN_DSA_SHA256);
989 : }
990 :
991 2 : if (!(flags & GNUTLS_SELF_TEST_FLAG_ALL))
992 : return 0;
993 :
994 2 : FALLTHROUGH;
995 : case GNUTLS_PK_EC:
996 : /* Test ECDH and ECDSA */
997 2 : ret = test_ecdh();
998 2 : if (ret < 0) {
999 0 : gnutls_assert();
1000 0 : goto cleanup;
1001 : }
1002 :
1003 : /* Test ECDSA */
1004 2 : if (is_post || !is_fips140_mode_enabled) {
1005 2 : PK_KNOWN_TEST(GNUTLS_PK_EC,
1006 : GNUTLS_CURVE_TO_BITS(GNUTLS_ECC_CURVE_SECP256R1),
1007 : GNUTLS_DIG_SHA256, ecdsa_secp256r1_privkey,
1008 : ecdsa_secp256r1_sig, GNUTLS_PRIVKEY_FLAG_REPRODUCIBLE);
1009 : } else {
1010 0 : PK_TEST(GNUTLS_PK_EC, test_sig,
1011 : GNUTLS_CURVE_TO_BITS(GNUTLS_ECC_CURVE_SECP256R1),
1012 2 : GNUTLS_SIGN_ECDSA_SHA256);
1013 : }
1014 :
1015 2 : if (!(flags & GNUTLS_SELF_TEST_FLAG_ALL))
1016 : return 0;
1017 :
1018 2 : if (is_post || !is_fips140_mode_enabled) {
1019 2 : PK_KNOWN_TEST(GNUTLS_PK_EC,
1020 : GNUTLS_CURVE_TO_BITS(GNUTLS_ECC_CURVE_SECP384R1),
1021 : GNUTLS_DIG_SHA384, ecdsa_secp384r1_privkey,
1022 : ecdsa_secp384r1_sig, GNUTLS_PRIVKEY_FLAG_REPRODUCIBLE);
1023 : } else {
1024 0 : PK_TEST(GNUTLS_PK_EC, test_sig,
1025 : GNUTLS_CURVE_TO_BITS(GNUTLS_ECC_CURVE_SECP384R1),
1026 2 : GNUTLS_SIGN_ECDSA_SHA384);
1027 : }
1028 :
1029 2 : if (is_post || !is_fips140_mode_enabled) {
1030 2 : PK_KNOWN_TEST(GNUTLS_PK_EC,
1031 : GNUTLS_CURVE_TO_BITS(GNUTLS_ECC_CURVE_SECP521R1),
1032 : GNUTLS_DIG_SHA512, ecdsa_secp521r1_privkey,
1033 : ecdsa_secp521r1_sig, GNUTLS_PRIVKEY_FLAG_REPRODUCIBLE);
1034 : } else {
1035 0 : PK_TEST(GNUTLS_PK_EC, test_sig,
1036 : GNUTLS_CURVE_TO_BITS(GNUTLS_ECC_CURVE_SECP521R1),
1037 2 : GNUTLS_SIGN_ECDSA_SHA512);
1038 : }
1039 :
1040 : #ifdef ENABLE_NON_SUITEB_CURVES
1041 : if (is_post || !is_fips140_mode_enabled) {
1042 : PK_KNOWN_TEST(GNUTLS_PK_EC,
1043 : GNUTLS_CURVE_TO_BITS(GNUTLS_ECC_CURVE_SECP192R1),
1044 : GNUTLS_DIG_SHA256, ecdsa_secp192r1_privkey,
1045 : ecdsa_secp192r1_sig, GNUTLS_PRIVKEY_FLAG_REPRODUCIBLE);
1046 : } else {
1047 : PK_TEST(GNUTLS_PK_EC, test_sig,
1048 : GNUTLS_CURVE_TO_BITS(GNUTLS_ECC_CURVE_SECP192R1),
1049 : GNUTLS_SIGN_ECDSA_SHA256);
1050 : }
1051 :
1052 : if (is_post || !is_fips140_mode_enabled) {
1053 : PK_KNOWN_TEST(GNUTLS_PK_EC,
1054 : GNUTLS_CURVE_TO_BITS(GNUTLS_ECC_CURVE_SECP224R1),
1055 : GNUTLS_DIG_SHA256, ecdsa_secp224r1_privkey,
1056 : ecdsa_secp224r1_sig, GNUTLS_PRIVKEY_FLAG_REPRODUCIBLE);
1057 : } else {
1058 : PK_TEST(GNUTLS_PK_EC, test_sig,
1059 : GNUTLS_CURVE_TO_BITS(GNUTLS_ECC_CURVE_SECP224R1),
1060 : GNUTLS_SIGN_ECDSA_SHA256);
1061 : }
1062 : #endif
1063 :
1064 :
1065 : #if ENABLE_GOST
1066 2 : FALLTHROUGH;
1067 : case GNUTLS_PK_GOST_01:
1068 2 : PK_TEST(GNUTLS_PK_GOST_01, test_sig,
1069 : GNUTLS_CURVE_TO_BITS(GNUTLS_ECC_CURVE_GOST256CPA),
1070 2 : GNUTLS_SIGN_GOST_94);
1071 :
1072 2 : if (!(flags & GNUTLS_SELF_TEST_FLAG_ALL))
1073 : return 0;
1074 :
1075 2 : FALLTHROUGH;
1076 : case GNUTLS_PK_GOST_12_256:
1077 2 : PK_TEST(GNUTLS_PK_GOST_12_256, test_sig,
1078 : GNUTLS_CURVE_TO_BITS(GNUTLS_ECC_CURVE_GOST256CPA),
1079 2 : GNUTLS_SIGN_GOST_256);
1080 :
1081 2 : if (!(flags & GNUTLS_SELF_TEST_FLAG_ALL))
1082 : return 0;
1083 :
1084 2 : FALLTHROUGH;
1085 : case GNUTLS_PK_GOST_12_512:
1086 2 : PK_TEST(GNUTLS_PK_GOST_12_512, test_sig,
1087 : GNUTLS_CURVE_TO_BITS(GNUTLS_ECC_CURVE_GOST512A),
1088 : GNUTLS_SIGN_GOST_512);
1089 :
1090 : if (!(flags & GNUTLS_SELF_TEST_FLAG_ALL))
1091 : return 0;
1092 : #endif
1093 : break;
1094 : default:
1095 0 : return gnutls_assert_val(GNUTLS_E_NO_SELF_TEST);
1096 : }
1097 :
1098 : ret = 0;
1099 :
1100 : cleanup:
1101 : return ret;
1102 : }
|