diff options
Diffstat (limited to 'src/daemon/https/tls/auth_dh_common.c')
-rw-r--r-- | src/daemon/https/tls/auth_dh_common.c | 275 |
1 files changed, 275 insertions, 0 deletions
diff --git a/src/daemon/https/tls/auth_dh_common.c b/src/daemon/https/tls/auth_dh_common.c index 0957f81b..8fc6e391 100644 --- a/src/daemon/https/tls/auth_dh_common.c +++ b/src/daemon/https/tls/auth_dh_common.c | |||
@@ -50,3 +50,278 @@ MHD_gtls_free_dh_info (MHD_gtls_dh_info_st * dh) | |||
50 | MHD__gnutls_free_datum (&dh->public_key); | 50 | MHD__gnutls_free_datum (&dh->public_key); |
51 | } | 51 | } |
52 | 52 | ||
53 | int | ||
54 | MHD_gtls_proc_dh_common_client_kx (MHD_gtls_session_t session, | ||
55 | opaque * data, size_t _data_size, | ||
56 | mpi_t g, mpi_t p) | ||
57 | { | ||
58 | uint16_t n_Y; | ||
59 | size_t _n_Y; | ||
60 | int ret; | ||
61 | ssize_t data_size = _data_size; | ||
62 | |||
63 | |||
64 | DECR_LEN (data_size, 2); | ||
65 | n_Y = MHD_gtls_read_uint16 (&data[0]); | ||
66 | _n_Y = n_Y; | ||
67 | |||
68 | DECR_LEN (data_size, n_Y); | ||
69 | if (MHD_gtls_mpi_scan_nz (&session->key->client_Y, &data[2], &_n_Y)) | ||
70 | { | ||
71 | MHD_gnutls_assert (); | ||
72 | return GNUTLS_E_MPI_SCAN_FAILED; | ||
73 | } | ||
74 | |||
75 | MHD_gtls_dh_set_peer_public (session, session->key->client_Y); | ||
76 | |||
77 | session->key->KEY = | ||
78 | MHD_gtls_calc_dh_key (session->key->client_Y, session->key->dh_secret, p); | ||
79 | |||
80 | if (session->key->KEY == NULL) | ||
81 | { | ||
82 | MHD_gnutls_assert (); | ||
83 | return GNUTLS_E_MEMORY_ERROR; | ||
84 | } | ||
85 | |||
86 | MHD_gtls_mpi_release (&session->key->client_Y); | ||
87 | MHD_gtls_mpi_release (&session->key->dh_secret); | ||
88 | |||
89 | ret = MHD_gtls_mpi_dprint (&session->key->key, session->key->KEY); | ||
90 | |||
91 | MHD_gtls_mpi_release (&session->key->KEY); | ||
92 | |||
93 | if (ret < 0) | ||
94 | { | ||
95 | return ret; | ||
96 | } | ||
97 | |||
98 | return 0; | ||
99 | } | ||
100 | |||
101 | int | ||
102 | MHD_gtls_gen_dh_common_client_kx (MHD_gtls_session_t session, opaque ** data) | ||
103 | { | ||
104 | mpi_t x = NULL, X = NULL; | ||
105 | size_t n_X; | ||
106 | int ret; | ||
107 | |||
108 | *data = NULL; | ||
109 | |||
110 | X = MHD_gtls_calc_dh_secret (&x, session->key->client_g, | ||
111 | session->key->client_p); | ||
112 | if (X == NULL || x == NULL) | ||
113 | { | ||
114 | MHD_gnutls_assert (); | ||
115 | ret = GNUTLS_E_MEMORY_ERROR; | ||
116 | goto error; | ||
117 | } | ||
118 | |||
119 | MHD_gtls_dh_set_secret_bits (session, MHD__gnutls_mpi_get_nbits (x)); | ||
120 | |||
121 | MHD_gtls_mpi_print (NULL, &n_X, X); | ||
122 | (*data) = MHD_gnutls_malloc (n_X + 2); | ||
123 | if (*data == NULL) | ||
124 | { | ||
125 | ret = GNUTLS_E_MEMORY_ERROR; | ||
126 | goto error; | ||
127 | } | ||
128 | |||
129 | MHD_gtls_mpi_print (&(*data)[2], &n_X, X); | ||
130 | MHD_gtls_mpi_release (&X); | ||
131 | |||
132 | MHD_gtls_write_uint16 (n_X, &(*data)[0]); | ||
133 | |||
134 | /* calculate the key after calculating the message */ | ||
135 | session->key->KEY = | ||
136 | MHD_gtls_calc_dh_key (session->key->client_Y, x, session->key->client_p); | ||
137 | |||
138 | MHD_gtls_mpi_release (&x); | ||
139 | if (session->key->KEY == NULL) | ||
140 | { | ||
141 | MHD_gnutls_assert (); | ||
142 | ret = GNUTLS_E_MEMORY_ERROR; | ||
143 | goto error; | ||
144 | } | ||
145 | |||
146 | /* THESE SHOULD BE DISCARDED */ | ||
147 | MHD_gtls_mpi_release (&session->key->client_Y); | ||
148 | MHD_gtls_mpi_release (&session->key->client_p); | ||
149 | MHD_gtls_mpi_release (&session->key->client_g); | ||
150 | |||
151 | ret = MHD_gtls_mpi_dprint (&session->key->key, session->key->KEY); | ||
152 | |||
153 | MHD_gtls_mpi_release (&session->key->KEY); | ||
154 | |||
155 | if (ret < 0) | ||
156 | { | ||
157 | MHD_gnutls_assert (); | ||
158 | goto error; | ||
159 | } | ||
160 | |||
161 | return n_X + 2; | ||
162 | |||
163 | error: | ||
164 | MHD_gtls_mpi_release (&x); | ||
165 | MHD_gtls_mpi_release (&X); | ||
166 | MHD_gnutls_free (*data); | ||
167 | *data = NULL; | ||
168 | return ret; | ||
169 | } | ||
170 | |||
171 | int | ||
172 | MHD_gtls_proc_dh_common_server_kx (MHD_gtls_session_t session, | ||
173 | opaque * data, size_t _data_size, int psk) | ||
174 | { | ||
175 | uint16_t n_Y, n_g, n_p; | ||
176 | size_t _n_Y, _n_g, _n_p; | ||
177 | uint8_t *data_p; | ||
178 | uint8_t *data_g; | ||
179 | uint8_t *data_Y; | ||
180 | int i, bits, psk_size, ret; | ||
181 | ssize_t data_size = _data_size; | ||
182 | |||
183 | i = 0; | ||
184 | |||
185 | if (psk != 0) | ||
186 | { | ||
187 | DECR_LEN (data_size, 2); | ||
188 | psk_size = MHD_gtls_read_uint16 (&data[i]); | ||
189 | DECR_LEN (data_size, psk_size); | ||
190 | i += 2 + psk_size; | ||
191 | } | ||
192 | |||
193 | DECR_LEN (data_size, 2); | ||
194 | n_p = MHD_gtls_read_uint16 (&data[i]); | ||
195 | i += 2; | ||
196 | |||
197 | DECR_LEN (data_size, n_p); | ||
198 | data_p = &data[i]; | ||
199 | i += n_p; | ||
200 | |||
201 | DECR_LEN (data_size, 2); | ||
202 | n_g = MHD_gtls_read_uint16 (&data[i]); | ||
203 | i += 2; | ||
204 | |||
205 | DECR_LEN (data_size, n_g); | ||
206 | data_g = &data[i]; | ||
207 | i += n_g; | ||
208 | |||
209 | DECR_LEN (data_size, 2); | ||
210 | n_Y = MHD_gtls_read_uint16 (&data[i]); | ||
211 | i += 2; | ||
212 | |||
213 | DECR_LEN (data_size, n_Y); | ||
214 | data_Y = &data[i]; | ||
215 | i += n_Y; | ||
216 | |||
217 | _n_Y = n_Y; | ||
218 | _n_g = n_g; | ||
219 | _n_p = n_p; | ||
220 | |||
221 | if (MHD_gtls_mpi_scan_nz (&session->key->client_Y, data_Y, &_n_Y) != 0) | ||
222 | { | ||
223 | MHD_gnutls_assert (); | ||
224 | return GNUTLS_E_MPI_SCAN_FAILED; | ||
225 | } | ||
226 | |||
227 | if (MHD_gtls_mpi_scan_nz (&session->key->client_g, data_g, &_n_g) != 0) | ||
228 | { | ||
229 | MHD_gnutls_assert (); | ||
230 | return GNUTLS_E_MPI_SCAN_FAILED; | ||
231 | } | ||
232 | if (MHD_gtls_mpi_scan_nz (&session->key->client_p, data_p, &_n_p) != 0) | ||
233 | { | ||
234 | MHD_gnutls_assert (); | ||
235 | return GNUTLS_E_MPI_SCAN_FAILED; | ||
236 | } | ||
237 | |||
238 | bits = MHD_gtls_dh_get_allowed_prime_bits (session); | ||
239 | if (bits < 0) | ||
240 | { | ||
241 | MHD_gnutls_assert (); | ||
242 | return bits; | ||
243 | } | ||
244 | |||
245 | if (MHD__gnutls_mpi_get_nbits (session->key->client_p) < (size_t) bits) | ||
246 | { | ||
247 | /* the prime used by the peer is not acceptable | ||
248 | */ | ||
249 | MHD_gnutls_assert (); | ||
250 | return GNUTLS_E_DH_PRIME_UNACCEPTABLE; | ||
251 | } | ||
252 | |||
253 | MHD_gtls_dh_set_group (session, session->key->client_g, | ||
254 | session->key->client_p); | ||
255 | MHD_gtls_dh_set_peer_public (session, session->key->client_Y); | ||
256 | |||
257 | ret = n_Y + n_p + n_g + 6; | ||
258 | if (psk != 0) | ||
259 | ret += 2; | ||
260 | |||
261 | return ret; | ||
262 | } | ||
263 | |||
264 | /* If the psk flag is set, then an empty psk_identity_hint will | ||
265 | * be inserted */ | ||
266 | int | ||
267 | MHD_gtls_dh_common_print_server_kx (MHD_gtls_session_t session, | ||
268 | mpi_t g, mpi_t p, opaque ** data, int psk) | ||
269 | { | ||
270 | mpi_t x, X; | ||
271 | size_t n_X, n_g, n_p; | ||
272 | int ret, data_size, pos; | ||
273 | uint8_t *pdata; | ||
274 | |||
275 | X = MHD_gtls_calc_dh_secret (&x, g, p); | ||
276 | if (X == NULL || x == NULL) | ||
277 | { | ||
278 | MHD_gnutls_assert (); | ||
279 | return GNUTLS_E_MEMORY_ERROR; | ||
280 | } | ||
281 | |||
282 | session->key->dh_secret = x; | ||
283 | MHD_gtls_dh_set_secret_bits (session, MHD__gnutls_mpi_get_nbits (x)); | ||
284 | |||
285 | MHD_gtls_mpi_print (NULL, &n_g, g); | ||
286 | MHD_gtls_mpi_print (NULL, &n_p, p); | ||
287 | MHD_gtls_mpi_print (NULL, &n_X, X); | ||
288 | |||
289 | data_size = n_g + n_p + n_X + 6; | ||
290 | if (psk != 0) | ||
291 | data_size += 2; | ||
292 | |||
293 | (*data) = MHD_gnutls_malloc (data_size); | ||
294 | if (*data == NULL) | ||
295 | { | ||
296 | MHD_gtls_mpi_release (&X); | ||
297 | return GNUTLS_E_MEMORY_ERROR; | ||
298 | } | ||
299 | |||
300 | pos = 0; | ||
301 | pdata = *data; | ||
302 | |||
303 | if (psk != 0) | ||
304 | { | ||
305 | MHD_gtls_write_uint16 (0, &pdata[pos]); | ||
306 | pos += 2; | ||
307 | } | ||
308 | |||
309 | MHD_gtls_mpi_print (&pdata[pos + 2], &n_p, p); | ||
310 | MHD_gtls_write_uint16 (n_p, &pdata[pos]); | ||
311 | |||
312 | pos += n_p + 2; | ||
313 | |||
314 | MHD_gtls_mpi_print (&pdata[pos + 2], &n_g, g); | ||
315 | MHD_gtls_write_uint16 (n_g, &pdata[pos]); | ||
316 | |||
317 | pos += n_g + 2; | ||
318 | |||
319 | MHD_gtls_mpi_print (&pdata[pos + 2], &n_X, X); | ||
320 | MHD_gtls_mpi_release (&X); | ||
321 | |||
322 | MHD_gtls_write_uint16 (n_X, &pdata[pos]); | ||
323 | |||
324 | ret = data_size; | ||
325 | |||
326 | return ret; | ||
327 | } | ||