pubkey: Move sexp parsing for gcry_pk_getkey to the modules.
[libgcrypt.git] / cipher / pubkey-util.c
1 /* pubkey-util.c - Supporting functions for all pubkey modules.
2  * Copyright (C) 1998, 1999, 2000, 2002, 2003, 2005,
3  *               2007, 2008, 2011 Free Software Foundation, Inc.
4  * Copyright (C) 2013  g10 Code GmbH
5  *
6  * This file is part of Libgcrypt.
7  *
8  * Libgcrypt is free software; you can redistribute it and/or modify
9  * it under the terms of the GNU Lesser General Public License as
10  * published by the Free Software Foundation; either version 2.1 of
11  * the License, or (at your option) any later version.
12  *
13  * Libgcrypt is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16  * GNU Lesser General Public License for more details.
17  *
18  * You should have received a copy of the GNU Lesser General Public
19  * License along with this program; if not, see <http://www.gnu.org/licenses/>.
20  */
21
22 #include <config.h>
23 #include <stdio.h>
24 #include <stdlib.h>
25 #include <string.h>
26
27 #include "g10lib.h"
28 #include "mpi.h"
29 #include "cipher.h"
30 #include "pubkey-internal.h"
31
32
33
34
35 /* Get the "nbits" parameter from an s-expression of the format:
36  *
37  *   (algo
38  *     (parameter_name_1 ....)
39  *      ....
40  *     (parameter_name_n ....))
41  *
42  * Example:
43  *
44  *   (rsa
45  *     (nbits 4:2048))
46  *
47  * On success the value for nbits is stored at R_NBITS.  If no nbits
48  * parameter is found, the function returns success and stores 0 at
49  * R_NBITS.  For parsing errors the function returns an error code and
50  * stores 0 at R_NBITS.
51  */
52 gpg_err_code_t
53 _gcry_pk_util_get_nbits (gcry_sexp_t list, unsigned int *r_nbits)
54 {
55   char buf[50];
56   const char *s;
57   size_t n;
58
59   *r_nbits = 0;
60
61   list = gcry_sexp_find_token (list, "nbits", 0);
62   if (!list)
63     return 0; /* No NBITS found.  */
64
65   s = gcry_sexp_nth_data (list, 1, &n);
66   if (!s || n >= DIM (buf) - 1 )
67     {
68       /* NBITS given without a cdr.  */
69       gcry_sexp_release (list);
70       return GPG_ERR_INV_OBJ;
71     }
72   memcpy (buf, s, n);
73   buf[n] = 0;
74   *r_nbits = (unsigned int)strtoul (buf, NULL, 0);
75   gcry_sexp_release (list);
76   return 0;
77 }
78
79
80 /* Get the optional "rsa-use-e" parameter from an s-expression of the
81  * format:
82  *
83  *   (algo
84  *     (parameter_name_1 ....)
85  *      ....
86  *     (parameter_name_n ....))
87  *
88  * Example:
89  *
90  *   (rsa
91  *     (nbits 4:2048)
92  *     (rsa-use-e 2:41))
93  *
94  * On success the value for nbits is stored at R_E.  If no rsa-use-e
95  * parameter is found, the function returns success and stores 65537 at
96  * R_E.  For parsing errors the function returns an error code and
97  * stores 0 at R_E.
98  */
99 gpg_err_code_t
100 _gcry_pk_util_get_rsa_use_e (gcry_sexp_t list, unsigned long *r_e)
101 {
102   char buf[50];
103   const char *s;
104   size_t n;
105
106   *r_e = 0;
107
108   list = gcry_sexp_find_token (list, "rsa-use-e", 0);
109   if (!list)
110     {
111       *r_e = 65537; /* Not given, use the value generated by old versions. */
112       return 0;
113     }
114
115   s = gcry_sexp_nth_data (list, 1, &n);
116   if (!s || n >= DIM (buf) - 1 )
117     {
118       /* No value or value too large.  */
119       gcry_sexp_release (list);
120       return GPG_ERR_INV_OBJ;
121     }
122   memcpy (buf, s, n);
123   buf[n] = 0;
124   *r_e = strtoul (buf, NULL, 0);
125   gcry_sexp_release (list);
126   return 0;
127 }