~ubuntu-branches/ubuntu/lucid/openssl/lucid-proposed

« back to all changes in this revision

Viewing changes to fips/rsa/fips_rsastest.c

  • Committer: Bazaar Package Importer
  • Author(s): Kurt Roeckx
  • Date: 2009-06-13 18:15:46 UTC
  • mto: (11.1.5 squeeze)
  • mto: This revision was merged to the branch mainline in revision 34.
  • Revision ID: james.westby@ubuntu.com-20090613181546-vbfntai3b009dl1u
Tags: upstream-0.9.8k
ImportĀ upstreamĀ versionĀ 0.9.8k

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/* fips_rsastest.c */
 
2
/* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
 
3
 * project 2005.
 
4
 */
 
5
/* ====================================================================
 
6
 * Copyright (c) 2005 The OpenSSL Project.  All rights reserved.
 
7
 *
 
8
 * Redistribution and use in source and binary forms, with or without
 
9
 * modification, are permitted provided that the following conditions
 
10
 * are met:
 
11
 *
 
12
 * 1. Redistributions of source code must retain the above copyright
 
13
 *    notice, this list of conditions and the following disclaimer. 
 
14
 *
 
15
 * 2. Redistributions in binary form must reproduce the above copyright
 
16
 *    notice, this list of conditions and the following disclaimer in
 
17
 *    the documentation and/or other materials provided with the
 
18
 *    distribution.
 
19
 *
 
20
 * 3. All advertising materials mentioning features or use of this
 
21
 *    software must display the following acknowledgment:
 
22
 *    "This product includes software developed by the OpenSSL Project
 
23
 *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
 
24
 *
 
25
 * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
 
26
 *    endorse or promote products derived from this software without
 
27
 *    prior written permission. For written permission, please contact
 
28
 *    licensing@OpenSSL.org.
 
29
 *
 
30
 * 5. Products derived from this software may not be called "OpenSSL"
 
31
 *    nor may "OpenSSL" appear in their names without prior written
 
32
 *    permission of the OpenSSL Project.
 
33
 *
 
34
 * 6. Redistributions of any form whatsoever must retain the following
 
35
 *    acknowledgment:
 
36
 *    "This product includes software developed by the OpenSSL Project
 
37
 *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
 
38
 *
 
39
 * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
 
40
 * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 
41
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
 
42
 * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
 
43
 * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 
44
 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
 
45
 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
 
46
 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
 
47
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
 
48
 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
 
49
 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
 
50
 * OF THE POSSIBILITY OF SUCH DAMAGE.
 
51
 * ====================================================================
 
52
 *
 
53
 * This product includes cryptographic software written by Eric Young
 
54
 * (eay@cryptsoft.com).  This product includes software written by Tim
 
55
 * Hudson (tjh@cryptsoft.com).
 
56
 *
 
57
 */
 
58
 
 
59
#include <stdio.h>
 
60
#include <ctype.h>
 
61
#include <string.h>
 
62
#include <openssl/bio.h>
 
63
#include <openssl/evp.h>
 
64
#include <openssl/hmac.h>
 
65
#include <openssl/err.h>
 
66
#include <openssl/rsa.h>
 
67
#include <openssl/bn.h>
 
68
#include <openssl/x509v3.h>
 
69
 
 
70
#ifndef OPENSSL_FIPS
 
71
 
 
72
int main(int argc, char *argv[])
 
73
{
 
74
    printf("No FIPS RSA support\n");
 
75
    return(0);
 
76
}
 
77
 
 
78
#else
 
79
 
 
80
#include "fips_utl.h"
 
81
 
 
82
static int rsa_stest(FILE *out, FILE *in, int Saltlen);
 
83
static int rsa_printsig(FILE *out, RSA *rsa, const EVP_MD *dgst,
 
84
                unsigned char *Msg, long Msglen, int Saltlen);
 
85
 
 
86
int main(int argc, char **argv)
 
87
        {
 
88
        FILE *in = NULL, *out = NULL;
 
89
 
 
90
        int ret = 1, Saltlen = -1;
 
91
 
 
92
        if(!FIPS_mode_set(1))
 
93
                {
 
94
                do_print_errors();
 
95
                goto end;
 
96
                }
 
97
 
 
98
        if ((argc > 2) && !strcmp("-saltlen", argv[1]))
 
99
                {
 
100
                Saltlen = atoi(argv[2]);
 
101
                if (Saltlen < 0)
 
102
                        {
 
103
                        fprintf(stderr, "FATAL: Invalid salt length\n");
 
104
                        goto end;
 
105
                        }
 
106
                argc -= 2;
 
107
                argv += 2;
 
108
                }
 
109
        else if ((argc > 1) && !strcmp("-x931", argv[1]))
 
110
                {
 
111
                Saltlen = -2;
 
112
                argc--;
 
113
                argv++;
 
114
                }
 
115
 
 
116
        if (argc == 1)
 
117
                in = stdin;
 
118
        else
 
119
                in = fopen(argv[1], "r");
 
120
 
 
121
        if (argc < 2)
 
122
                out = stdout;
 
123
        else
 
124
                out = fopen(argv[2], "w");
 
125
 
 
126
        if (!in)
 
127
                {
 
128
                fprintf(stderr, "FATAL input initialization error\n");
 
129
                goto end;
 
130
                }
 
131
 
 
132
        if (!out)
 
133
                {
 
134
                fprintf(stderr, "FATAL output initialization error\n");
 
135
                goto end;
 
136
                }
 
137
 
 
138
        if (!rsa_stest(out, in, Saltlen))
 
139
                {
 
140
                fprintf(stderr, "FATAL RSASTEST file processing error\n");
 
141
                goto end;
 
142
                }
 
143
        else
 
144
                ret = 0;
 
145
 
 
146
        end:
 
147
 
 
148
        if (ret)
 
149
                do_print_errors();
 
150
 
 
151
        if (in && (in != stdin))
 
152
                fclose(in);
 
153
        if (out && (out != stdout))
 
154
                fclose(out);
 
155
 
 
156
        return ret;
 
157
 
 
158
        }
 
159
 
 
160
#define RSA_TEST_MAXLINELEN     10240
 
161
 
 
162
int rsa_stest(FILE *out, FILE *in, int Saltlen)
 
163
        {
 
164
        char *linebuf, *olinebuf, *p, *q;
 
165
        char *keyword, *value;
 
166
        RSA *rsa = NULL;
 
167
        const EVP_MD *dgst = NULL;
 
168
        unsigned char *Msg = NULL;
 
169
        long Msglen = -1;
 
170
        int keylen = -1, current_keylen = -1;
 
171
        int ret = 0;
 
172
        int lnum = 0;
 
173
 
 
174
        olinebuf = OPENSSL_malloc(RSA_TEST_MAXLINELEN);
 
175
        linebuf = OPENSSL_malloc(RSA_TEST_MAXLINELEN);
 
176
 
 
177
        if (!linebuf || !olinebuf)
 
178
                goto error;
 
179
 
 
180
        while (fgets(olinebuf, RSA_TEST_MAXLINELEN, in))
 
181
                {
 
182
                lnum++;
 
183
                strcpy(linebuf, olinebuf);
 
184
                keyword = linebuf;
 
185
                /* Skip leading space */
 
186
                while (isspace((unsigned char)*keyword))
 
187
                        keyword++;
 
188
 
 
189
                /* Look for = sign */
 
190
                p = strchr(linebuf, '=');
 
191
 
 
192
                /* If no = just copy */
 
193
                if (!p)
 
194
                        {
 
195
                        if (fputs(olinebuf, out) < 0)
 
196
                                goto error;
 
197
                        continue;
 
198
                        }
 
199
 
 
200
                q = p - 1;
 
201
 
 
202
                /* Remove trailing space */
 
203
                while (isspace((unsigned char)*q))
 
204
                        *q-- = 0;
 
205
 
 
206
                *p = 0;
 
207
                value = p + 1;
 
208
 
 
209
                /* Remove leading space from value */
 
210
                while (isspace((unsigned char)*value))
 
211
                        value++;
 
212
 
 
213
                /* Remove trailing space from value */
 
214
                p = value + strlen(value) - 1;
 
215
 
 
216
                while (*p == '\n' || isspace((unsigned char)*p))
 
217
                        *p-- = 0;
 
218
 
 
219
                /* Look for [mod = XXX] for key length */
 
220
 
 
221
                if (!strcmp(keyword, "[mod"))
 
222
                        {
 
223
                        p = value + strlen(value) - 1;
 
224
                        if (*p != ']')
 
225
                                goto parse_error;
 
226
                        *p = 0;
 
227
                        keylen = atoi(value);
 
228
                        if (keylen < 0)
 
229
                                goto parse_error;
 
230
                        }
 
231
                else if (!strcmp(keyword, "SHAAlg"))
 
232
                        {
 
233
                        if (!strcmp(value, "SHA1"))
 
234
                                dgst = EVP_sha1();
 
235
                        else if (!strcmp(value, "SHA224"))
 
236
                                dgst = EVP_sha224();
 
237
                        else if (!strcmp(value, "SHA256"))
 
238
                                dgst = EVP_sha256();
 
239
                        else if (!strcmp(value, "SHA384"))
 
240
                                dgst = EVP_sha384();
 
241
                        else if (!strcmp(value, "SHA512"))
 
242
                                dgst = EVP_sha512();
 
243
                        else
 
244
                                {
 
245
                                fprintf(stderr,
 
246
                                        "FATAL: unsupported algorithm \"%s\"\n",
 
247
                                                                value);
 
248
                                goto parse_error;
 
249
                                }
 
250
                        }
 
251
                else if (!strcmp(keyword, "Msg"))
 
252
                        {
 
253
                        if (Msg)
 
254
                                goto parse_error;
 
255
                        if (strlen(value) & 1)
 
256
                                *(--value) = '0';
 
257
                        Msg = hex2bin_m(value, &Msglen);
 
258
                        if (!Msg)
 
259
                                goto parse_error;
 
260
                        }
 
261
 
 
262
                fputs(olinebuf, out);
 
263
 
 
264
                /* If key length has changed, generate and output public
 
265
                 * key components of new RSA private key.
 
266
                 */
 
267
 
 
268
                if (keylen != current_keylen)
 
269
                        {
 
270
                        BIGNUM *bn_e;
 
271
                        if (rsa)
 
272
                                FIPS_rsa_free(rsa);
 
273
                        rsa = FIPS_rsa_new();
 
274
                        if (!rsa)
 
275
                                goto error;
 
276
                        bn_e = BN_new();
 
277
                        if (!bn_e || !BN_set_word(bn_e, 0x1001))
 
278
                                goto error;
 
279
                        if (!RSA_X931_generate_key_ex(rsa, keylen, bn_e, NULL))
 
280
                                goto error;
 
281
                        BN_free(bn_e);
 
282
                        fputs("n = ", out);
 
283
                        do_bn_print(out, rsa->n);
 
284
                        fputs("\ne = ", out);
 
285
                        do_bn_print(out, rsa->e);
 
286
                        fputs("\n", out);
 
287
                        current_keylen = keylen;
 
288
                        }
 
289
 
 
290
                if (Msg && dgst)
 
291
                        {
 
292
                        if (!rsa_printsig(out, rsa, dgst, Msg, Msglen,
 
293
                                                                Saltlen))
 
294
                                goto error;
 
295
                        OPENSSL_free(Msg);
 
296
                        Msg = NULL;
 
297
                        }
 
298
 
 
299
                }
 
300
 
 
301
        ret = 1;
 
302
 
 
303
        error:
 
304
 
 
305
        if (olinebuf)
 
306
                OPENSSL_free(olinebuf);
 
307
        if (linebuf)
 
308
                OPENSSL_free(linebuf);
 
309
        if (rsa)
 
310
                FIPS_rsa_free(rsa);
 
311
 
 
312
        return ret;
 
313
 
 
314
        parse_error:
 
315
 
 
316
        fprintf(stderr, "FATAL parse error processing line %d\n", lnum);
 
317
 
 
318
        goto error;
 
319
 
 
320
        }
 
321
 
 
322
static int rsa_printsig(FILE *out, RSA *rsa, const EVP_MD *dgst,
 
323
                unsigned char *Msg, long Msglen, int Saltlen)
 
324
        {
 
325
        int ret = 0;
 
326
        unsigned char *sigbuf = NULL;
 
327
        int i, siglen;
 
328
        /* EVP_PKEY structure */
 
329
        EVP_PKEY pk;
 
330
        EVP_MD_CTX ctx;
 
331
        pk.type = EVP_PKEY_RSA;
 
332
        pk.pkey.rsa = rsa;
 
333
 
 
334
        siglen = RSA_size(rsa);
 
335
        sigbuf = OPENSSL_malloc(siglen);
 
336
        if (!sigbuf)
 
337
                goto error;
 
338
 
 
339
        EVP_MD_CTX_init(&ctx);
 
340
 
 
341
        if (Saltlen >= 0)
 
342
                {
 
343
                M_EVP_MD_CTX_set_flags(&ctx,
 
344
                        EVP_MD_CTX_FLAG_PAD_PSS | (Saltlen << 16));
 
345
                }
 
346
        else if (Saltlen == -2)
 
347
                M_EVP_MD_CTX_set_flags(&ctx, EVP_MD_CTX_FLAG_PAD_X931);
 
348
        if (!EVP_SignInit_ex(&ctx, dgst, NULL))
 
349
                goto error;
 
350
        if (!EVP_SignUpdate(&ctx, Msg, Msglen))
 
351
                goto error;
 
352
        if (!EVP_SignFinal(&ctx, sigbuf, (unsigned int *)&siglen, &pk))
 
353
                goto error;
 
354
 
 
355
        EVP_MD_CTX_cleanup(&ctx);
 
356
 
 
357
        fputs("S = ", out);
 
358
 
 
359
        for (i = 0; i < siglen; i++)
 
360
                fprintf(out, "%02X", sigbuf[i]);
 
361
 
 
362
        fputs("\n", out);
 
363
 
 
364
        ret = 1;
 
365
 
 
366
        error:
 
367
 
 
368
        return ret;
 
369
        }
 
370
#endif