blob: cad395d70d78e18527866bf1a3f6452c338e4c7c
1 | /* |
2 | * RSA key extract helper |
3 | * |
4 | * Copyright (c) 2015, Intel Corporation |
5 | * Authors: Tadeusz Struk <tadeusz.struk@intel.com> |
6 | * |
7 | * This program is free software; you can redistribute it and/or modify it |
8 | * under the terms of the GNU General Public License as published by the Free |
9 | * Software Foundation; either version 2 of the License, or (at your option) |
10 | * any later version. |
11 | * |
12 | */ |
13 | #include <linux/kernel.h> |
14 | #include <linux/export.h> |
15 | #include <linux/err.h> |
16 | #include <linux/fips.h> |
17 | #include <crypto/internal/rsa.h> |
18 | #include "rsapubkey-asn1.h" |
19 | #include "rsaprivkey-asn1.h" |
20 | |
21 | int rsa_get_n(void *context, size_t hdrlen, unsigned char tag, |
22 | const void *value, size_t vlen) |
23 | { |
24 | struct rsa_key *key = context; |
25 | const u8 *ptr = value; |
26 | size_t n_sz = vlen; |
27 | |
28 | /* invalid key provided */ |
29 | if (!value || !vlen) |
30 | return -EINVAL; |
31 | |
32 | if (fips_enabled) { |
33 | while (n_sz && !*ptr) { |
34 | ptr++; |
35 | n_sz--; |
36 | } |
37 | |
38 | /* In FIPS mode only allow key size 2K and higher */ |
39 | if (n_sz < 256) { |
40 | pr_err("RSA: key size not allowed in FIPS mode\n"); |
41 | return -EINVAL; |
42 | } |
43 | } |
44 | |
45 | key->n = value; |
46 | key->n_sz = vlen; |
47 | |
48 | return 0; |
49 | } |
50 | |
51 | int rsa_get_e(void *context, size_t hdrlen, unsigned char tag, |
52 | const void *value, size_t vlen) |
53 | { |
54 | struct rsa_key *key = context; |
55 | |
56 | /* invalid key provided */ |
57 | if (!value || !key->n_sz || !vlen || vlen > key->n_sz) |
58 | return -EINVAL; |
59 | |
60 | key->e = value; |
61 | key->e_sz = vlen; |
62 | |
63 | return 0; |
64 | } |
65 | |
66 | int rsa_get_d(void *context, size_t hdrlen, unsigned char tag, |
67 | const void *value, size_t vlen) |
68 | { |
69 | struct rsa_key *key = context; |
70 | |
71 | /* invalid key provided */ |
72 | if (!value || !key->n_sz || !vlen || vlen > key->n_sz) |
73 | return -EINVAL; |
74 | |
75 | key->d = value; |
76 | key->d_sz = vlen; |
77 | |
78 | return 0; |
79 | } |
80 | |
81 | int rsa_get_p(void *context, size_t hdrlen, unsigned char tag, |
82 | const void *value, size_t vlen) |
83 | { |
84 | struct rsa_key *key = context; |
85 | |
86 | /* invalid key provided */ |
87 | if (!value || !vlen || vlen > key->n_sz) |
88 | return -EINVAL; |
89 | |
90 | key->p = value; |
91 | key->p_sz = vlen; |
92 | |
93 | return 0; |
94 | } |
95 | |
96 | int rsa_get_q(void *context, size_t hdrlen, unsigned char tag, |
97 | const void *value, size_t vlen) |
98 | { |
99 | struct rsa_key *key = context; |
100 | |
101 | /* invalid key provided */ |
102 | if (!value || !vlen || vlen > key->n_sz) |
103 | return -EINVAL; |
104 | |
105 | key->q = value; |
106 | key->q_sz = vlen; |
107 | |
108 | return 0; |
109 | } |
110 | |
111 | int rsa_get_dp(void *context, size_t hdrlen, unsigned char tag, |
112 | const void *value, size_t vlen) |
113 | { |
114 | struct rsa_key *key = context; |
115 | |
116 | /* invalid key provided */ |
117 | if (!value || !vlen || vlen > key->n_sz) |
118 | return -EINVAL; |
119 | |
120 | key->dp = value; |
121 | key->dp_sz = vlen; |
122 | |
123 | return 0; |
124 | } |
125 | |
126 | int rsa_get_dq(void *context, size_t hdrlen, unsigned char tag, |
127 | const void *value, size_t vlen) |
128 | { |
129 | struct rsa_key *key = context; |
130 | |
131 | /* invalid key provided */ |
132 | if (!value || !vlen || vlen > key->n_sz) |
133 | return -EINVAL; |
134 | |
135 | key->dq = value; |
136 | key->dq_sz = vlen; |
137 | |
138 | return 0; |
139 | } |
140 | |
141 | int rsa_get_qinv(void *context, size_t hdrlen, unsigned char tag, |
142 | const void *value, size_t vlen) |
143 | { |
144 | struct rsa_key *key = context; |
145 | |
146 | /* invalid key provided */ |
147 | if (!value || !vlen || vlen > key->n_sz) |
148 | return -EINVAL; |
149 | |
150 | key->qinv = value; |
151 | key->qinv_sz = vlen; |
152 | |
153 | return 0; |
154 | } |
155 | |
156 | /** |
157 | * rsa_parse_pub_key() - decodes the BER encoded buffer and stores in the |
158 | * provided struct rsa_key, pointers to the raw key as is, |
159 | * so that the caller can copy it or MPI parse it, etc. |
160 | * |
161 | * @rsa_key: struct rsa_key key representation |
162 | * @key: key in BER format |
163 | * @key_len: length of key |
164 | * |
165 | * Return: 0 on success or error code in case of error |
166 | */ |
167 | int rsa_parse_pub_key(struct rsa_key *rsa_key, const void *key, |
168 | unsigned int key_len) |
169 | { |
170 | return asn1_ber_decoder(&rsapubkey_decoder, rsa_key, key, key_len); |
171 | } |
172 | EXPORT_SYMBOL_GPL(rsa_parse_pub_key); |
173 | |
174 | /** |
175 | * rsa_parse_priv_key() - decodes the BER encoded buffer and stores in the |
176 | * provided struct rsa_key, pointers to the raw key |
177 | * as is, so that the caller can copy it or MPI parse it, |
178 | * etc. |
179 | * |
180 | * @rsa_key: struct rsa_key key representation |
181 | * @key: key in BER format |
182 | * @key_len: length of key |
183 | * |
184 | * Return: 0 on success or error code in case of error |
185 | */ |
186 | int rsa_parse_priv_key(struct rsa_key *rsa_key, const void *key, |
187 | unsigned int key_len) |
188 | { |
189 | return asn1_ber_decoder(&rsaprivkey_decoder, rsa_key, key, key_len); |
190 | } |
191 | EXPORT_SYMBOL_GPL(rsa_parse_priv_key); |
192 |