a2840eaed0950cbf89dcb6d7a694ec4e270c4c72
[dragonfly.git] / crypto / openssl / crypto / dsa / dsa_ameth.c
1 /*
2  * Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL project
3  * 2006.
4  */
5 /* ====================================================================
6  * Copyright (c) 2006 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 "cryptlib.h"
61 #include <openssl/x509.h>
62 #include <openssl/asn1.h>
63 #include <openssl/dsa.h>
64 #include <openssl/bn.h>
65 #ifndef OPENSSL_NO_CMS
66 # include <openssl/cms.h>
67 #endif
68 #include "asn1_locl.h"
69
70 static int dsa_pub_decode(EVP_PKEY *pkey, X509_PUBKEY *pubkey)
71 {
72     const unsigned char *p, *pm;
73     int pklen, pmlen;
74     int ptype;
75     void *pval;
76     ASN1_STRING *pstr;
77     X509_ALGOR *palg;
78     ASN1_INTEGER *public_key = NULL;
79
80     DSA *dsa = NULL;
81
82     if (!X509_PUBKEY_get0_param(NULL, &p, &pklen, &palg, pubkey))
83         return 0;
84     X509_ALGOR_get0(NULL, &ptype, &pval, palg);
85
86     if (ptype == V_ASN1_SEQUENCE) {
87         pstr = pval;
88         pm = pstr->data;
89         pmlen = pstr->length;
90
91         if (!(dsa = d2i_DSAparams(NULL, &pm, pmlen))) {
92             DSAerr(DSA_F_DSA_PUB_DECODE, DSA_R_DECODE_ERROR);
93             goto err;
94         }
95
96     } else if ((ptype == V_ASN1_NULL) || (ptype == V_ASN1_UNDEF)) {
97         if (!(dsa = DSA_new())) {
98             DSAerr(DSA_F_DSA_PUB_DECODE, ERR_R_MALLOC_FAILURE);
99             goto err;
100         }
101     } else {
102         DSAerr(DSA_F_DSA_PUB_DECODE, DSA_R_PARAMETER_ENCODING_ERROR);
103         goto err;
104     }
105
106     if (!(public_key = d2i_ASN1_INTEGER(NULL, &p, pklen))) {
107         DSAerr(DSA_F_DSA_PUB_DECODE, DSA_R_DECODE_ERROR);
108         goto err;
109     }
110
111     if (!(dsa->pub_key = ASN1_INTEGER_to_BN(public_key, NULL))) {
112         DSAerr(DSA_F_DSA_PUB_DECODE, DSA_R_BN_DECODE_ERROR);
113         goto err;
114     }
115
116     ASN1_INTEGER_free(public_key);
117     EVP_PKEY_assign_DSA(pkey, dsa);
118     return 1;
119
120  err:
121     if (public_key)
122         ASN1_INTEGER_free(public_key);
123     if (dsa)
124         DSA_free(dsa);
125     return 0;
126
127 }
128
129 static int dsa_pub_encode(X509_PUBKEY *pk, const EVP_PKEY *pkey)
130 {
131     DSA *dsa;
132     int ptype;
133     unsigned char *penc = NULL;
134     int penclen;
135     ASN1_STRING *str = NULL;
136
137     dsa = pkey->pkey.dsa;
138     if (pkey->save_parameters && dsa->p && dsa->q && dsa->g) {
139         str = ASN1_STRING_new();
140         if (!str) {
141             DSAerr(DSA_F_DSA_PUB_ENCODE, ERR_R_MALLOC_FAILURE);
142             goto err;
143         }
144         str->length = i2d_DSAparams(dsa, &str->data);
145         if (str->length <= 0) {
146             DSAerr(DSA_F_DSA_PUB_ENCODE, ERR_R_MALLOC_FAILURE);
147             goto err;
148         }
149         ptype = V_ASN1_SEQUENCE;
150     } else
151         ptype = V_ASN1_UNDEF;
152
153     dsa->write_params = 0;
154
155     penclen = i2d_DSAPublicKey(dsa, &penc);
156
157     if (penclen <= 0) {
158         DSAerr(DSA_F_DSA_PUB_ENCODE, ERR_R_MALLOC_FAILURE);
159         goto err;
160     }
161
162     if (X509_PUBKEY_set0_param(pk, OBJ_nid2obj(EVP_PKEY_DSA),
163                                ptype, str, penc, penclen))
164         return 1;
165
166  err:
167     if (penc)
168         OPENSSL_free(penc);
169     if (str)
170         ASN1_STRING_free(str);
171
172     return 0;
173 }
174
175 /*
176  * In PKCS#8 DSA: you just get a private key integer and parameters in the
177  * AlgorithmIdentifier the pubkey must be recalculated.
178  */
179
180 static int dsa_priv_decode(EVP_PKEY *pkey, PKCS8_PRIV_KEY_INFO *p8)
181 {
182     const unsigned char *p, *pm;
183     int pklen, pmlen;
184     int ptype;
185     void *pval;
186     ASN1_STRING *pstr;
187     X509_ALGOR *palg;
188     ASN1_INTEGER *privkey = NULL;
189     BN_CTX *ctx = NULL;
190
191     STACK_OF(ASN1_TYPE) *ndsa = NULL;
192     DSA *dsa = NULL;
193
194     if (!PKCS8_pkey_get0(NULL, &p, &pklen, &palg, p8))
195         return 0;
196     X509_ALGOR_get0(NULL, &ptype, &pval, palg);
197
198     /* Check for broken DSA PKCS#8, UGH! */
199     if (*p == (V_ASN1_SEQUENCE | V_ASN1_CONSTRUCTED)) {
200         ASN1_TYPE *t1, *t2;
201         if (!(ndsa = d2i_ASN1_SEQUENCE_ANY(NULL, &p, pklen)))
202             goto decerr;
203         if (sk_ASN1_TYPE_num(ndsa) != 2)
204             goto decerr;
205         /*-
206          * Handle Two broken types:
207          * SEQUENCE {parameters, priv_key}
208          * SEQUENCE {pub_key, priv_key}
209          */
210
211         t1 = sk_ASN1_TYPE_value(ndsa, 0);
212         t2 = sk_ASN1_TYPE_value(ndsa, 1);
213         if (t1->type == V_ASN1_SEQUENCE) {
214             p8->broken = PKCS8_EMBEDDED_PARAM;
215             pval = t1->value.ptr;
216         } else if (ptype == V_ASN1_SEQUENCE)
217             p8->broken = PKCS8_NS_DB;
218         else
219             goto decerr;
220
221         if (t2->type != V_ASN1_INTEGER)
222             goto decerr;
223
224         privkey = t2->value.integer;
225     } else {
226         const unsigned char *q = p;
227         if (!(privkey = d2i_ASN1_INTEGER(NULL, &p, pklen)))
228             goto decerr;
229         if (privkey->type == V_ASN1_NEG_INTEGER) {
230             p8->broken = PKCS8_NEG_PRIVKEY;
231             ASN1_STRING_clear_free(privkey);
232             if (!(privkey = d2i_ASN1_UINTEGER(NULL, &q, pklen)))
233                 goto decerr;
234         }
235         if (ptype != V_ASN1_SEQUENCE)
236             goto decerr;
237     }
238
239     pstr = pval;
240     pm = pstr->data;
241     pmlen = pstr->length;
242     if (!(dsa = d2i_DSAparams(NULL, &pm, pmlen)))
243         goto decerr;
244     /* We have parameters now set private key */
245     if (!(dsa->priv_key = ASN1_INTEGER_to_BN(privkey, NULL))) {
246         DSAerr(DSA_F_DSA_PRIV_DECODE, DSA_R_BN_ERROR);
247         goto dsaerr;
248     }
249     /* Calculate public key */
250     if (!(dsa->pub_key = BN_new())) {
251         DSAerr(DSA_F_DSA_PRIV_DECODE, ERR_R_MALLOC_FAILURE);
252         goto dsaerr;
253     }
254     if (!(ctx = BN_CTX_new())) {
255         DSAerr(DSA_F_DSA_PRIV_DECODE, ERR_R_MALLOC_FAILURE);
256         goto dsaerr;
257     }
258
259     if (!BN_mod_exp(dsa->pub_key, dsa->g, dsa->priv_key, dsa->p, ctx)) {
260         DSAerr(DSA_F_DSA_PRIV_DECODE, DSA_R_BN_ERROR);
261         goto dsaerr;
262     }
263
264     EVP_PKEY_assign_DSA(pkey, dsa);
265     BN_CTX_free(ctx);
266     if (ndsa)
267         sk_ASN1_TYPE_pop_free(ndsa, ASN1_TYPE_free);
268     else
269         ASN1_STRING_clear_free(privkey);
270
271     return 1;
272
273  decerr:
274     DSAerr(DSA_F_DSA_PRIV_DECODE, EVP_R_DECODE_ERROR);
275  dsaerr:
276     BN_CTX_free(ctx);
277     if (privkey)
278         ASN1_STRING_clear_free(privkey);
279     sk_ASN1_TYPE_pop_free(ndsa, ASN1_TYPE_free);
280     DSA_free(dsa);
281     return 0;
282 }
283
284 static int dsa_priv_encode(PKCS8_PRIV_KEY_INFO *p8, const EVP_PKEY *pkey)
285 {
286     ASN1_STRING *params = NULL;
287     ASN1_INTEGER *prkey = NULL;
288     unsigned char *dp = NULL;
289     int dplen;
290
291     if (!pkey->pkey.dsa || !pkey->pkey.dsa->priv_key) {
292         DSAerr(DSA_F_DSA_PRIV_ENCODE, DSA_R_MISSING_PARAMETERS);
293         goto err;
294     }
295
296     params = ASN1_STRING_new();
297
298     if (!params) {
299         DSAerr(DSA_F_DSA_PRIV_ENCODE, ERR_R_MALLOC_FAILURE);
300         goto err;
301     }
302
303     params->length = i2d_DSAparams(pkey->pkey.dsa, &params->data);
304     if (params->length <= 0) {
305         DSAerr(DSA_F_DSA_PRIV_ENCODE, ERR_R_MALLOC_FAILURE);
306         goto err;
307     }
308     params->type = V_ASN1_SEQUENCE;
309
310     /* Get private key into integer */
311     prkey = BN_to_ASN1_INTEGER(pkey->pkey.dsa->priv_key, NULL);
312
313     if (!prkey) {
314         DSAerr(DSA_F_DSA_PRIV_ENCODE, DSA_R_BN_ERROR);
315         goto err;
316     }
317
318     dplen = i2d_ASN1_INTEGER(prkey, &dp);
319
320     ASN1_STRING_clear_free(prkey);
321
322     if (!PKCS8_pkey_set0(p8, OBJ_nid2obj(NID_dsa), 0,
323                          V_ASN1_SEQUENCE, params, dp, dplen))
324         goto err;
325
326     return 1;
327
328  err:
329     if (dp != NULL)
330         OPENSSL_free(dp);
331     if (params != NULL)
332         ASN1_STRING_free(params);
333     if (prkey != NULL)
334         ASN1_STRING_clear_free(prkey);
335     return 0;
336 }
337
338 static int int_dsa_size(const EVP_PKEY *pkey)
339 {
340     return (DSA_size(pkey->pkey.dsa));
341 }
342
343 static int dsa_bits(const EVP_PKEY *pkey)
344 {
345     return BN_num_bits(pkey->pkey.dsa->p);
346 }
347
348 static int dsa_missing_parameters(const EVP_PKEY *pkey)
349 {
350     DSA *dsa;
351     dsa = pkey->pkey.dsa;
352     if ((dsa->p == NULL) || (dsa->q == NULL) || (dsa->g == NULL))
353         return 1;
354     return 0;
355 }
356
357 static int dsa_copy_parameters(EVP_PKEY *to, const EVP_PKEY *from)
358 {
359     BIGNUM *a;
360
361     if ((a = BN_dup(from->pkey.dsa->p)) == NULL)
362         return 0;
363     if (to->pkey.dsa->p != NULL)
364         BN_free(to->pkey.dsa->p);
365     to->pkey.dsa->p = a;
366
367     if ((a = BN_dup(from->pkey.dsa->q)) == NULL)
368         return 0;
369     if (to->pkey.dsa->q != NULL)
370         BN_free(to->pkey.dsa->q);
371     to->pkey.dsa->q = a;
372
373     if ((a = BN_dup(from->pkey.dsa->g)) == NULL)
374         return 0;
375     if (to->pkey.dsa->g != NULL)
376         BN_free(to->pkey.dsa->g);
377     to->pkey.dsa->g = a;
378     return 1;
379 }
380
381 static int dsa_cmp_parameters(const EVP_PKEY *a, const EVP_PKEY *b)
382 {
383     if (BN_cmp(a->pkey.dsa->p, b->pkey.dsa->p) ||
384         BN_cmp(a->pkey.dsa->q, b->pkey.dsa->q) ||
385         BN_cmp(a->pkey.dsa->g, b->pkey.dsa->g))
386         return 0;
387     else
388         return 1;
389 }
390
391 static int dsa_pub_cmp(const EVP_PKEY *a, const EVP_PKEY *b)
392 {
393     if (BN_cmp(b->pkey.dsa->pub_key, a->pkey.dsa->pub_key) != 0)
394         return 0;
395     else
396         return 1;
397 }
398
399 static void int_dsa_free(EVP_PKEY *pkey)
400 {
401     DSA_free(pkey->pkey.dsa);
402 }
403
404 static void update_buflen(const BIGNUM *b, size_t *pbuflen)
405 {
406     size_t i;
407     if (!b)
408         return;
409     if (*pbuflen < (i = (size_t)BN_num_bytes(b)))
410         *pbuflen = i;
411 }
412
413 static int do_dsa_print(BIO *bp, const DSA *x, int off, int ptype)
414 {
415     unsigned char *m = NULL;
416     int ret = 0;
417     size_t buf_len = 0;
418     const char *ktype = NULL;
419
420     const BIGNUM *priv_key, *pub_key;
421
422     if (ptype == 2)
423         priv_key = x->priv_key;
424     else
425         priv_key = NULL;
426
427     if (ptype > 0)
428         pub_key = x->pub_key;
429     else
430         pub_key = NULL;
431
432     if (ptype == 2)
433         ktype = "Private-Key";
434     else if (ptype == 1)
435         ktype = "Public-Key";
436     else
437         ktype = "DSA-Parameters";
438
439     update_buflen(x->p, &buf_len);
440     update_buflen(x->q, &buf_len);
441     update_buflen(x->g, &buf_len);
442     update_buflen(priv_key, &buf_len);
443     update_buflen(pub_key, &buf_len);
444
445     m = (unsigned char *)OPENSSL_malloc(buf_len + 10);
446     if (m == NULL) {
447         DSAerr(DSA_F_DO_DSA_PRINT, ERR_R_MALLOC_FAILURE);
448         goto err;
449     }
450
451     if (priv_key) {
452         if (!BIO_indent(bp, off, 128))
453             goto err;
454         if (BIO_printf(bp, "%s: (%d bit)\n", ktype, BN_num_bits(x->p))
455             <= 0)
456             goto err;
457     }
458
459     if (!ASN1_bn_print(bp, "priv:", priv_key, m, off))
460         goto err;
461     if (!ASN1_bn_print(bp, "pub: ", pub_key, m, off))
462         goto err;
463     if (!ASN1_bn_print(bp, "P:   ", x->p, m, off))
464         goto err;
465     if (!ASN1_bn_print(bp, "Q:   ", x->q, m, off))
466         goto err;
467     if (!ASN1_bn_print(bp, "G:   ", x->g, m, off))
468         goto err;
469     ret = 1;
470  err:
471     if (m != NULL)
472         OPENSSL_free(m);
473     return (ret);
474 }
475
476 static int dsa_param_decode(EVP_PKEY *pkey,
477                             const unsigned char **pder, int derlen)
478 {
479     DSA *dsa;
480     if (!(dsa = d2i_DSAparams(NULL, pder, derlen))) {
481         DSAerr(DSA_F_DSA_PARAM_DECODE, ERR_R_DSA_LIB);
482         return 0;
483     }
484     EVP_PKEY_assign_DSA(pkey, dsa);
485     return 1;
486 }
487
488 static int dsa_param_encode(const EVP_PKEY *pkey, unsigned char **pder)
489 {
490     return i2d_DSAparams(pkey->pkey.dsa, pder);
491 }
492
493 static int dsa_param_print(BIO *bp, const EVP_PKEY *pkey, int indent,
494                            ASN1_PCTX *ctx)
495 {
496     return do_dsa_print(bp, pkey->pkey.dsa, indent, 0);
497 }
498
499 static int dsa_pub_print(BIO *bp, const EVP_PKEY *pkey, int indent,
500                          ASN1_PCTX *ctx)
501 {
502     return do_dsa_print(bp, pkey->pkey.dsa, indent, 1);
503 }
504
505 static int dsa_priv_print(BIO *bp, const EVP_PKEY *pkey, int indent,
506                           ASN1_PCTX *ctx)
507 {
508     return do_dsa_print(bp, pkey->pkey.dsa, indent, 2);
509 }
510
511 static int old_dsa_priv_decode(EVP_PKEY *pkey,
512                                const unsigned char **pder, int derlen)
513 {
514     DSA *dsa;
515     if (!(dsa = d2i_DSAPrivateKey(NULL, pder, derlen))) {
516         DSAerr(DSA_F_OLD_DSA_PRIV_DECODE, ERR_R_DSA_LIB);
517         return 0;
518     }
519     EVP_PKEY_assign_DSA(pkey, dsa);
520     return 1;
521 }
522
523 static int old_dsa_priv_encode(const EVP_PKEY *pkey, unsigned char **pder)
524 {
525     return i2d_DSAPrivateKey(pkey->pkey.dsa, pder);
526 }
527
528 static int dsa_sig_print(BIO *bp, const X509_ALGOR *sigalg,
529                          const ASN1_STRING *sig, int indent, ASN1_PCTX *pctx)
530 {
531     DSA_SIG *dsa_sig;
532     const unsigned char *p;
533     if (!sig) {
534         if (BIO_puts(bp, "\n") <= 0)
535             return 0;
536         else
537             return 1;
538     }
539     p = sig->data;
540     dsa_sig = d2i_DSA_SIG(NULL, &p, sig->length);
541     if (dsa_sig) {
542         int rv = 0;
543         size_t buf_len = 0;
544         unsigned char *m = NULL;
545         update_buflen(dsa_sig->r, &buf_len);
546         update_buflen(dsa_sig->s, &buf_len);
547         m = OPENSSL_malloc(buf_len + 10);
548         if (m == NULL) {
549             DSAerr(DSA_F_DSA_SIG_PRINT, ERR_R_MALLOC_FAILURE);
550             goto err;
551         }
552
553         if (BIO_write(bp, "\n", 1) != 1)
554             goto err;
555
556         if (!ASN1_bn_print(bp, "r:   ", dsa_sig->r, m, indent))
557             goto err;
558         if (!ASN1_bn_print(bp, "s:   ", dsa_sig->s, m, indent))
559             goto err;
560         rv = 1;
561  err:
562         if (m)
563             OPENSSL_free(m);
564         DSA_SIG_free(dsa_sig);
565         return rv;
566     }
567     return X509_signature_dump(bp, sig, indent);
568 }
569
570 static int dsa_pkey_ctrl(EVP_PKEY *pkey, int op, long arg1, void *arg2)
571 {
572     switch (op) {
573     case ASN1_PKEY_CTRL_PKCS7_SIGN:
574         if (arg1 == 0) {
575             int snid, hnid;
576             X509_ALGOR *alg1, *alg2;
577             PKCS7_SIGNER_INFO_get0_algs(arg2, NULL, &alg1, &alg2);
578             if (alg1 == NULL || alg1->algorithm == NULL)
579                 return -1;
580             hnid = OBJ_obj2nid(alg1->algorithm);
581             if (hnid == NID_undef)
582                 return -1;
583             if (!OBJ_find_sigid_by_algs(&snid, hnid, EVP_PKEY_id(pkey)))
584                 return -1;
585             X509_ALGOR_set0(alg2, OBJ_nid2obj(snid), V_ASN1_UNDEF, 0);
586         }
587         return 1;
588 #ifndef OPENSSL_NO_CMS
589     case ASN1_PKEY_CTRL_CMS_SIGN:
590         if (arg1 == 0) {
591             int snid, hnid;
592             X509_ALGOR *alg1, *alg2;
593             CMS_SignerInfo_get0_algs(arg2, NULL, NULL, &alg1, &alg2);
594             if (alg1 == NULL || alg1->algorithm == NULL)
595                 return -1;
596             hnid = OBJ_obj2nid(alg1->algorithm);
597             if (hnid == NID_undef)
598                 return -1;
599             if (!OBJ_find_sigid_by_algs(&snid, hnid, EVP_PKEY_id(pkey)))
600                 return -1;
601             X509_ALGOR_set0(alg2, OBJ_nid2obj(snid), V_ASN1_UNDEF, 0);
602         }
603         return 1;
604 #endif
605
606     case ASN1_PKEY_CTRL_DEFAULT_MD_NID:
607         *(int *)arg2 = NID_sha1;
608         return 2;
609
610     default:
611         return -2;
612
613     }
614
615 }
616
617 /* NB these are sorted in pkey_id order, lowest first */
618
619 const EVP_PKEY_ASN1_METHOD dsa_asn1_meths[] = {
620
621     {
622      EVP_PKEY_DSA2,
623      EVP_PKEY_DSA,
624      ASN1_PKEY_ALIAS},
625
626     {
627      EVP_PKEY_DSA1,
628      EVP_PKEY_DSA,
629      ASN1_PKEY_ALIAS},
630
631     {
632      EVP_PKEY_DSA4,
633      EVP_PKEY_DSA,
634      ASN1_PKEY_ALIAS},
635
636     {
637      EVP_PKEY_DSA3,
638      EVP_PKEY_DSA,
639      ASN1_PKEY_ALIAS},
640
641     {
642      EVP_PKEY_DSA,
643      EVP_PKEY_DSA,
644      0,
645
646      "DSA",
647      "OpenSSL DSA method",
648
649      dsa_pub_decode,
650      dsa_pub_encode,
651      dsa_pub_cmp,
652      dsa_pub_print,
653
654      dsa_priv_decode,
655      dsa_priv_encode,
656      dsa_priv_print,
657
658      int_dsa_size,
659      dsa_bits,
660
661      dsa_param_decode,
662      dsa_param_encode,
663      dsa_missing_parameters,
664      dsa_copy_parameters,
665      dsa_cmp_parameters,
666      dsa_param_print,
667      dsa_sig_print,
668
669      int_dsa_free,
670      dsa_pkey_ctrl,
671      old_dsa_priv_decode,
672      old_dsa_priv_encode}
673 };