source: trunk/third/openssl/apps/rsautl.c @ 15530

Revision 15530, 8.4 KB checked in by ghudson, 23 years ago (diff)
This commit was generated by cvs2svn to compensate for changes in r15529, which included commits to RCS files with non-trunk default branches.
Line 
1/* rsautl.c */
2/* Written by Dr Stephen N Henson (shenson@bigfoot.com) for the OpenSSL
3 * project 2000.
4 */
5/* ====================================================================
6 * Copyright (c) 2000 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#include "apps.h"
59#include <string.h>
60#include <openssl/err.h>
61#include <openssl/pem.h>
62
63#define RSA_SIGN        1
64#define RSA_VERIFY      2
65#define RSA_ENCRYPT     3
66#define RSA_DECRYPT     4
67
68#define KEY_PRIVKEY     1
69#define KEY_PUBKEY      2
70#define KEY_CERT        3
71
72static void usage(void);
73
74#undef PROG
75
76#define PROG rsautl_main
77
78int MAIN(int argc, char **);
79
80int MAIN(int argc, char **argv)
81{
82        BIO *in = NULL, *out = NULL;
83        char *infile = NULL, *outfile = NULL;
84        char *keyfile = NULL;
85        char rsa_mode = RSA_VERIFY, key_type = KEY_PRIVKEY;
86        int keyform = FORMAT_PEM;
87        char need_priv = 0, badarg = 0, rev = 0;
88        char hexdump = 0, asn1parse = 0;
89        X509 *x;
90        EVP_PKEY *pkey = NULL;
91        RSA *rsa = NULL;
92        unsigned char *rsa_in = NULL, *rsa_out = NULL, pad;
93        int rsa_inlen, rsa_outlen = 0;
94        int keysize;
95
96        int ret = 1;
97
98        argc--;
99        argv++;
100
101        if(!bio_err) bio_err = BIO_new_fp(stderr, BIO_NOCLOSE);
102        ERR_load_crypto_strings();
103        OpenSSL_add_all_algorithms();
104        pad = RSA_PKCS1_PADDING;
105       
106        while(argc >= 1)
107        {
108                if (!strcmp(*argv,"-in")) {
109                        if (--argc < 1) badarg = 1;
110                        infile= *(++argv);
111                } else if (!strcmp(*argv,"-out")) {
112                        if (--argc < 1) badarg = 1;
113                        outfile= *(++argv);
114                } else if(!strcmp(*argv, "-inkey")) {
115                        if (--argc < 1) badarg = 1;
116                        keyfile = *(++argv);
117                } else if(!strcmp(*argv, "-pubin")) {
118                        key_type = KEY_PUBKEY;
119                } else if(!strcmp(*argv, "-certin")) {
120                        key_type = KEY_CERT;
121                }
122                else if(!strcmp(*argv, "-asn1parse")) asn1parse = 1;
123                else if(!strcmp(*argv, "-hexdump")) hexdump = 1;
124                else if(!strcmp(*argv, "-raw")) pad = RSA_NO_PADDING;
125                else if(!strcmp(*argv, "-oaep")) pad = RSA_PKCS1_OAEP_PADDING;
126                else if(!strcmp(*argv, "-ssl")) pad = RSA_SSLV23_PADDING;
127                else if(!strcmp(*argv, "-pkcs")) pad = RSA_PKCS1_PADDING;
128                else if(!strcmp(*argv, "-sign")) {
129                        rsa_mode = RSA_SIGN;
130                        need_priv = 1;
131                } else if(!strcmp(*argv, "-verify")) rsa_mode = RSA_VERIFY;
132                else if(!strcmp(*argv, "-rev")) rev = 1;
133                else if(!strcmp(*argv, "-encrypt")) rsa_mode = RSA_ENCRYPT;
134                else if(!strcmp(*argv, "-decrypt")) {
135                        rsa_mode = RSA_DECRYPT;
136                        need_priv = 1;
137                } else badarg = 1;
138                if(badarg) {
139                        usage();
140                        goto end;
141                }
142                argc--;
143                argv++;
144        }
145
146        if(need_priv && (key_type != KEY_PRIVKEY)) {
147                BIO_printf(bio_err, "A private key is needed for this operation\n");
148                goto end;
149        }
150
151/* FIXME: seed PRNG only if needed */
152        app_RAND_load_file(NULL, bio_err, 0);
153       
154        switch(key_type) {
155                case KEY_PRIVKEY:
156                pkey = load_key(bio_err, keyfile, keyform, NULL);
157                break;
158
159                case KEY_PUBKEY:
160                pkey = load_pubkey(bio_err, keyfile, keyform);
161                break;
162
163                case KEY_CERT:
164                x = load_cert(bio_err, keyfile, keyform);
165                if(x) {
166                        pkey = X509_get_pubkey(x);
167                        X509_free(x);
168                }
169                break;
170        }
171
172        if(!pkey) {
173                BIO_printf(bio_err, "Error loading key\n");
174                return 1;
175        }
176
177        rsa = EVP_PKEY_get1_RSA(pkey);
178        EVP_PKEY_free(pkey);
179
180        if(!rsa) {
181                BIO_printf(bio_err, "Error getting RSA key\n");
182                ERR_print_errors(bio_err);
183                goto end;
184        }
185
186
187        if(infile) {
188                if(!(in = BIO_new_file(infile, "rb"))) {
189                        BIO_printf(bio_err, "Error Reading Input File\n");
190                        ERR_print_errors(bio_err);     
191                        goto end;
192                }
193        } else in = BIO_new_fp(stdin, BIO_NOCLOSE);
194
195        if(outfile) {
196                if(!(out = BIO_new_file(outfile, "wb"))) {
197                        BIO_printf(bio_err, "Error Reading Output File\n");
198                        ERR_print_errors(bio_err);     
199                        goto end;
200                }
201        } else {
202                out = BIO_new_fp(stdout, BIO_NOCLOSE);
203#ifdef VMS
204                {
205                    BIO *tmpbio = BIO_new(BIO_f_linebuffer());
206                    out = BIO_push(tmpbio, out);
207                }
208#endif
209        }
210
211        keysize = RSA_size(rsa);
212
213        rsa_in = OPENSSL_malloc(keysize * 2);
214        rsa_out = OPENSSL_malloc(keysize);
215
216        /* Read the input data */
217        rsa_inlen = BIO_read(in, rsa_in, keysize * 2);
218        if(rsa_inlen <= 0) {
219                BIO_printf(bio_err, "Error reading input Data\n");
220                exit(1);
221        }
222        if(rev) {
223                int i;
224                unsigned char ctmp;
225                for(i = 0; i < rsa_inlen/2; i++) {
226                        ctmp = rsa_in[i];
227                        rsa_in[i] = rsa_in[rsa_inlen - 1 - i];
228                        rsa_in[rsa_inlen - 1 - i] = ctmp;
229                }
230        }
231        switch(rsa_mode) {
232
233                case RSA_VERIFY:
234                        rsa_outlen  = RSA_public_decrypt(rsa_inlen, rsa_in, rsa_out, rsa, pad);
235                break;
236
237                case RSA_SIGN:
238                        rsa_outlen  = RSA_private_encrypt(rsa_inlen, rsa_in, rsa_out, rsa, pad);
239                break;
240
241                case RSA_ENCRYPT:
242                        rsa_outlen  = RSA_public_encrypt(rsa_inlen, rsa_in, rsa_out, rsa, pad);
243                break;
244
245                case RSA_DECRYPT:
246                        rsa_outlen  = RSA_private_decrypt(rsa_inlen, rsa_in, rsa_out, rsa, pad);
247                break;
248
249        }
250
251        if(rsa_outlen <= 0) {
252                BIO_printf(bio_err, "RSA operation error\n");
253                ERR_print_errors(bio_err);
254                goto end;
255        }
256        ret = 0;
257        if(asn1parse) {
258                if(!ASN1_parse_dump(out, rsa_out, rsa_outlen, 1, -1)) {
259                        ERR_print_errors(bio_err);
260                }
261        } else if(hexdump) BIO_dump(out, (char *)rsa_out, rsa_outlen);
262        else BIO_write(out, rsa_out, rsa_outlen);
263        end:
264        RSA_free(rsa);
265        BIO_free(in);
266        BIO_free_all(out);
267        if(rsa_in) OPENSSL_free(rsa_in);
268        if(rsa_out) OPENSSL_free(rsa_out);
269        return ret;
270}
271
272static void usage()
273{
274        BIO_printf(bio_err, "Usage: rsautl [options]\n");
275        BIO_printf(bio_err, "-in file        input file\n");
276        BIO_printf(bio_err, "-out file       output file\n");
277        BIO_printf(bio_err, "-inkey file     input key\n");
278        BIO_printf(bio_err, "-pubin          input is an RSA public\n");
279        BIO_printf(bio_err, "-certin         input is a certificate carrying an RSA public key\n");
280        BIO_printf(bio_err, "-ssl            use SSL v2 padding\n");
281        BIO_printf(bio_err, "-raw            use no padding\n");
282        BIO_printf(bio_err, "-pkcs           use PKCS#1 v1.5 padding (default)\n");
283        BIO_printf(bio_err, "-oaep           use PKCS#1 OAEP\n");
284        BIO_printf(bio_err, "-sign           sign with private key\n");
285        BIO_printf(bio_err, "-verify         verify with public key\n");
286        BIO_printf(bio_err, "-encrypt        encrypt with public key\n");
287        BIO_printf(bio_err, "-decrypt        decrypt with private key\n");
288        BIO_printf(bio_err, "-hexdump        hex dump output\n");
289}
290
Note: See TracBrowser for help on using the repository browser.