|
1 /* |
|
2 * Copyright (c) 2001-2006 Nokia Corporation and/or its subsidiary(-ies). |
|
3 * All rights reserved. |
|
4 * This component and the accompanying materials are made available |
|
5 * under the terms of the License "Eclipse Public License v1.0" |
|
6 * which accompanies this distribution, and is available |
|
7 * at the URL "http://www.eclipse.org/legal/epl-v10.html". |
|
8 * |
|
9 * Initial Contributors: |
|
10 * Nokia Corporation - initial contribution. |
|
11 * |
|
12 * Contributors: |
|
13 * |
|
14 * Description: EAP and WLAN authentication protocols. |
|
15 * |
|
16 */ |
|
17 |
|
18 |
|
19 // This is enumeration of EAPOL source code. |
|
20 #if defined(USE_EAP_MINIMUM_RELEASE_TRACES) |
|
21 #undef EAP_FILE_NUMBER_ENUM |
|
22 #define EAP_FILE_NUMBER_ENUM 135 |
|
23 #undef EAP_FILE_NUMBER_DATE |
|
24 #define EAP_FILE_NUMBER_DATE 1127594498 |
|
25 #endif //#if defined(USE_EAP_MINIMUM_RELEASE_TRACES) |
|
26 |
|
27 |
|
28 |
|
29 #include "eap_am_memory.h" |
|
30 #include "eap_am_export.h" |
|
31 #include "eap_am_tools.h" |
|
32 #include "eap_tools.h" |
|
33 #include "eap_crypto_api.h" |
|
34 #include "abs_tls_base_record.h" |
|
35 #include "tls_base_record.h" |
|
36 #include "tls_record.h" |
|
37 #include "tls_am_services.h" |
|
38 #include "tls_handshake_header.h" |
|
39 #include "tls_peap_types.h" |
|
40 #include "tls_message.h" |
|
41 #include "eap_automatic_variable.h" |
|
42 #include "eap_state_notification.h" |
|
43 #include "eap_type_tls_peap_types.h" |
|
44 #include "eap_header_string.h" |
|
45 |
|
46 #if defined(USE_FAST_EAP_TYPE) |
|
47 #include "eap_fast_tlv_payloads.h" |
|
48 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
49 |
|
50 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
51 #include "tls_extension.h" |
|
52 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
53 |
|
54 //-------------------------------------------------- |
|
55 |
|
56 #define EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(tools, status) \ |
|
57 EAP_STATUS_RETURN(tools, eap_status_return_and_create_tls_protocol_alert((status))) |
|
58 |
|
59 |
|
60 eap_status_e tls_record_c::eap_status_return_and_create_tls_protocol_alert( |
|
61 const eap_status_e status) |
|
62 { |
|
63 if (status != eap_status_ok |
|
64 && status != eap_status_success |
|
65 && status != eap_status_pending_request |
|
66 && status != eap_status_drop_packet_quietly) |
|
67 { |
|
68 (void) create_tls_protocol_alert(tls_alert_description_none, tls_alert_level_none, status); |
|
69 } |
|
70 |
|
71 return EAP_STATUS_RETURN(m_am_tools, status); |
|
72 } |
|
73 |
|
74 //-------------------------------------------------- |
|
75 |
|
76 EAP_FUNC_EXPORT tls_record_c::~tls_record_c() |
|
77 { |
|
78 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
79 |
|
80 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, |
|
81 (EAPL("this = 0x%08x, %s: function: starts: tls_record_c::~tls_record_c(): m_am_tls_services") |
|
82 EAPL(" = 0x%08x (validity %d).\n"), |
|
83 this, |
|
84 (m_is_client == true ? "client": "server"), |
|
85 m_am_tls_services, |
|
86 m_am_tls_services->get_is_valid())); |
|
87 |
|
88 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::~tls_record_c()"); |
|
89 |
|
90 EAP_ASSERT(m_shutdown_was_called == true); |
|
91 |
|
92 completion_action_clenup(); |
|
93 |
|
94 if (m_free_am_tls_services == true) |
|
95 { |
|
96 delete m_am_tls_services; |
|
97 } |
|
98 m_am_tls_services = 0; |
|
99 |
|
100 if (m_free_application == true) |
|
101 { |
|
102 delete m_application; |
|
103 } |
|
104 m_application = 0; |
|
105 |
|
106 reset_block_ciphers(true); |
|
107 reset_block_ciphers(false); |
|
108 |
|
109 reset_stream_ciphers(true); |
|
110 reset_stream_ciphers(false); |
|
111 |
|
112 reset_hmac_algorithms(true); |
|
113 reset_hmac_algorithms(false); |
|
114 |
|
115 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
116 } |
|
117 |
|
118 //-------------------------------------------------- |
|
119 |
|
120 #if defined(_WIN32) && !defined(__GNUC__) |
|
121 #pragma warning( disable : 4355 ) // 'this' : used in base member initializer list |
|
122 #endif |
|
123 |
|
124 EAP_FUNC_EXPORT tls_record_c::tls_record_c( |
|
125 abs_eap_am_tools_c * const tools, ///< tools is pointer to the tools class. @see abs_eap_am_tools_c. |
|
126 tls_am_services_c * const am_tls_services, ///< This is pointer to adaptation module of TLS. |
|
127 const bool free_am_tls_services, |
|
128 tls_base_application_c * const application, ///< application is pointer to application object. |
|
129 const bool free_application, |
|
130 const bool is_client_when_true, ///< Indicates whether this is client (true) or server (false). |
|
131 const eap_type_value_e eap_type, |
|
132 const eap_am_network_id_c * const receive_network_id) |
|
133 : tls_base_record_c(tools /*, partner */) |
|
134 , m_am_tools(tools) |
|
135 , m_am_tls_services(am_tls_services) |
|
136 , m_free_am_tls_services(free_am_tls_services) |
|
137 , m_application(application) |
|
138 , m_free_application(free_application) |
|
139 , m_completion_queue(tools) |
|
140 , m_received_tls_message(tools, this, this, this, is_client_when_true) |
|
141 , m_new_tls_message(tools, this, this, this, is_client_when_true) |
|
142 , m_message_hash_md5(tools) |
|
143 , m_message_hash_sha1(tools) |
|
144 , m_message_hash_md5_certificate_verify(tools) |
|
145 , m_message_hash_sha1_certificate_verify(tools) |
|
146 , m_client_message_hash_md5_finished(tools) |
|
147 , m_client_message_hash_sha1_finished(tools) |
|
148 , m_server_message_hash_md5_finished(tools) |
|
149 , m_server_message_hash_sha1_finished(tools) |
|
150 , m_client_handshake_random_value(tools) |
|
151 , m_server_handshake_random_value(tools) |
|
152 , m_session_id(tools) |
|
153 , m_master_secret(tools) |
|
154 , m_eap_master_session_key(tools, eap_type) |
|
155 , m_new_send_mac_key(tools) |
|
156 , m_new_receive_mac_key(tools) |
|
157 , m_new_send_encryption_key(tools) |
|
158 , m_new_receive_encryption_key(tools) |
|
159 , m_new_send_iv(tools) |
|
160 , m_new_receive_iv(tools) |
|
161 , m_send_mac_key(tools) |
|
162 , m_receive_mac_key(tools) |
|
163 , m_send_encryption_key(tools) |
|
164 , m_receive_encryption_key(tools) |
|
165 , m_send_iv(tools) |
|
166 , m_receive_iv(tools) |
|
167 , m_session_key_seed(tools) |
|
168 , m_mschapv2_challenges(tools) |
|
169 , m_own_private_dhe_key(tools) |
|
170 , m_own_public_dhe_key(tools) |
|
171 , m_peer_public_dhe_key(tools) |
|
172 , m_shared_dh_key(tools) |
|
173 , m_dhe_prime(tools) |
|
174 , m_dhe_group_generator(tools) |
|
175 , m_signed_message_hash(tools) |
|
176 , m_premaster_secret(tools) |
|
177 , m_own_encrypted_premaster_secret(tools) |
|
178 #if defined(USE_FAST_EAP_TYPE) |
|
179 , m_eap_fast_pac_key(tools) |
|
180 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
181 , m_proposed_cipher_suites(tools) |
|
182 , m_proposed_compression_methods(tools) |
|
183 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
184 , m_supported_tls_extensions(tools) |
|
185 , m_received_tls_extensions(tools) |
|
186 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
187 , m_NAI_realm(tools) |
|
188 , m_send_network_id(tools) |
|
189 , m_own_certificate_chain(tools) |
|
190 , m_own_certificate_types(tools) |
|
191 , m_own_certificate_authorities(tools) |
|
192 , m_peer_certificate_chain(tools) |
|
193 , m_peer_certificate_chain_result(eap_status_illegal_certificate) |
|
194 , m_verify_signature(eap_status_authentication_failure) |
|
195 , m_peer_certificate_types(tools) |
|
196 , m_peer_certificate_authorities(tools) |
|
197 , m_resumed_cipher_suite(tls_cipher_suites_none) |
|
198 , m_selected_cipher_suite(tls_cipher_suites_none) |
|
199 , m_selected_compression_method(tls_compression_method_none) |
|
200 , m_receive_cipher_suite(tls_cipher_suites_TLS_NULL_WITH_NULL_NULL) |
|
201 , m_receive_compression_method(tls_compression_method_null) |
|
202 , m_send_cipher_suite(tls_cipher_suites_TLS_NULL_WITH_NULL_NULL) |
|
203 , m_send_compression_method(tls_compression_method_null) |
|
204 , m_send_block_cipher(0) |
|
205 , m_receive_block_cipher(0) |
|
206 , m_send_stream_cipher(0) |
|
207 , m_receive_stream_cipher(0) |
|
208 , m_send_hmac_algorithm(0) |
|
209 , m_receive_hmac_algorithm(0) |
|
210 , m_send_record_sequence_number(0ul) |
|
211 , m_receive_record_sequence_number(0ul) |
|
212 , m_tls_peap_state(tls_peap_state_wait_tls_start) |
|
213 , m_tls_session_type(tls_session_type_none) |
|
214 , m_eap_type(eap_type) |
|
215 , m_peap_version(peap_version_none) |
|
216 , m_tunneled_eap_type_authentication_state(eap_state_none) |
|
217 , m_is_valid(false) |
|
218 , m_is_client(is_client_when_true) |
|
219 , m_allow_message_send(true) |
|
220 , m_already_in_completion_action_check(false) |
|
221 , m_already_in_process_tls_records(false) |
|
222 , m_pending_query_certificate_authorities_and_types(false) |
|
223 , m_pending_query_certificate_chain(false) |
|
224 , m_pending_query_cipher_suites_and_previous_session(false) |
|
225 , m_pending_query_dh_parameters(false) |
|
226 , m_pending_query_realm(false) |
|
227 , m_pending_select_cipher_suite_and_check_session_id(false) |
|
228 , m_pending_verify_certificate_chain(false) |
|
229 , m_pending_rsa_decrypt_with_private_key(false) |
|
230 , m_pending_rsa_encrypt_with_public_key(false) |
|
231 , m_pending_sign_with_private_key(false) |
|
232 , m_pending_verify_with_public_key(false) |
|
233 , m_pending_query_tunnel_PAC(false) |
|
234 , m_tls_peap_test_version(false) |
|
235 , m_key_material_generated(false) |
|
236 , m_tls_peap_server_authenticates_client_policy_flag(true) |
|
237 , m_tls_peap_server_authenticates_client_config_server(true) |
|
238 , m_tls_peap_server_authenticates_client_action(true) |
|
239 , m_tls_peap_server_requested_client_certificate(false) |
|
240 , m_could_send_fatal_alert_message(true) |
|
241 , m_could_send_warning_alert_message(true) |
|
242 , m_force_tls_message_send(false) |
|
243 , m_shutdown_was_called(false) |
|
244 , m_use_separate_tls_record(true) // Some vendors seems to use only separate TLS-records. Windows RAS and FreeRadius works too with this. |
|
245 , m_use_extra_padding_length(false) // It seems that EAP-TLS of Microsoft Windows does not work with extra padding. |
|
246 , m_client_allows_empty_certificate_authorities_list(false) |
|
247 , m_server_sends_empty_certificate_authorities_list(false) |
|
248 , m_use_tppd_tls_peap(true) |
|
249 , m_use_tppd_peapv1_acknowledge_hack(false) |
|
250 , m_server_offers_new_session_id(true) |
|
251 , m_will_receive_new_session_ticket(false) |
|
252 , m_send_piggypacked_eap_identity_request(true) |
|
253 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
254 , m_tls_use_identity_privacy(false) |
|
255 , m_tls_identity_privacy_handshake_state(tls_identity_privacy_handshake_state_none) |
|
256 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
257 #if defined(USE_FAST_EAP_TYPE) |
|
258 , m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP(false) |
|
259 , m_remove_tunnel_pac(false) |
|
260 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
261 { |
|
262 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
263 |
|
264 EAP_TRACE_DEBUG( |
|
265 m_am_tools, |
|
266 TRACE_FLAGS_DEFAULT, |
|
267 (EAPL("TLS: this = 0x%08x, %s: function: starts: tls_record_c::tls_record_c(): "), |
|
268 this, |
|
269 (m_is_client == true ? "client": "server"))); |
|
270 |
|
271 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::tls_record_c()"); |
|
272 |
|
273 if (receive_network_id == 0 |
|
274 || receive_network_id->get_is_valid_data() == false) |
|
275 { |
|
276 // No need to delete anything here because it is done in destructor. |
|
277 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
278 return; |
|
279 } |
|
280 |
|
281 if (m_am_tls_services == 0 |
|
282 || m_am_tls_services->get_is_valid() == false) |
|
283 { |
|
284 EAP_TRACE_ERROR(m_am_tools, TRACE_FLAGS_TLS_PEAP_ERROR, |
|
285 (EAPL("ERROR: %s: function: tls_record_c::tls_record_c() failed,") |
|
286 EAPL(" m_am_tls_services = 0x%08x (validity %d) is invalid.\n"), |
|
287 (m_is_client == true ? "client": "server"), |
|
288 m_am_tls_services, (m_am_tls_services != 0) ? m_am_tls_services->get_is_valid() : false)); |
|
289 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
290 return; |
|
291 } |
|
292 m_am_tls_services->set_tls_am_partner(this); |
|
293 |
|
294 // Here we swap the addresses. |
|
295 eap_am_network_id_c send_network_id( |
|
296 m_am_tools, |
|
297 receive_network_id->get_destination_id(), |
|
298 receive_network_id->get_source_id(), |
|
299 receive_network_id->get_type()); |
|
300 |
|
301 eap_status_e status = m_send_network_id.set_copy_of_network_id(&send_network_id); |
|
302 if (status != eap_status_ok) |
|
303 { |
|
304 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
305 return; |
|
306 } |
|
307 |
|
308 if (get_is_tunneled_tls() == true |
|
309 && m_application == 0) |
|
310 { |
|
311 // Application is required in tunneled mode. |
|
312 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
313 return; |
|
314 } |
|
315 |
|
316 if (m_application != 0) |
|
317 { |
|
318 m_application->set_application_partner(this); |
|
319 } |
|
320 |
|
321 if (m_is_client == false) |
|
322 { |
|
323 set_state(tls_peap_state_wait_handshake_type_client_hello); |
|
324 } |
|
325 |
|
326 set_is_valid(); |
|
327 |
|
328 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
329 } |
|
330 |
|
331 //-------------------------------------------------- |
|
332 |
|
333 EAP_FUNC_EXPORT void tls_record_c::reset_block_ciphers(const bool send_when_true) |
|
334 { |
|
335 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
336 |
|
337 if (send_when_true == true) |
|
338 { |
|
339 delete m_send_block_cipher; |
|
340 m_send_block_cipher = 0; |
|
341 } |
|
342 else |
|
343 { |
|
344 delete m_receive_block_cipher; |
|
345 m_receive_block_cipher = 0; |
|
346 } |
|
347 |
|
348 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
349 } |
|
350 |
|
351 //-------------------------------------------------- |
|
352 |
|
353 EAP_FUNC_EXPORT void tls_record_c::reset_stream_ciphers(const bool send_when_true) |
|
354 { |
|
355 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
356 |
|
357 if (send_when_true == true) |
|
358 { |
|
359 delete m_send_stream_cipher; |
|
360 m_send_stream_cipher = 0; |
|
361 } |
|
362 else |
|
363 { |
|
364 delete m_receive_stream_cipher; |
|
365 m_receive_stream_cipher = 0; |
|
366 } |
|
367 |
|
368 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
369 } |
|
370 |
|
371 //-------------------------------------------------- |
|
372 |
|
373 EAP_FUNC_EXPORT void tls_record_c::reset_hmac_algorithms(const bool send_when_true) |
|
374 { |
|
375 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
376 |
|
377 if (send_when_true == true) |
|
378 { |
|
379 delete m_send_hmac_algorithm; |
|
380 m_send_hmac_algorithm = 0; |
|
381 } |
|
382 else |
|
383 { |
|
384 delete m_receive_hmac_algorithm; |
|
385 m_receive_hmac_algorithm = 0; |
|
386 } |
|
387 |
|
388 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
389 } |
|
390 |
|
391 //-------------------------------------------------- |
|
392 |
|
393 EAP_FUNC_EXPORT void tls_record_c::set_state(const tls_peap_state_e state) |
|
394 { |
|
395 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
396 |
|
397 EAP_TRACE_DEBUG( |
|
398 m_am_tools, |
|
399 TRACE_FLAGS_DEFAULT, |
|
400 (EAPL("TLS: this = 0x%08x, %s: state_function: starts: tls_record_c::set_state() from %s to %s\n"), |
|
401 this, |
|
402 (m_is_client == true ? "client": "server"), |
|
403 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
404 eap_tls_trace_string_c::get_state_string(state))); |
|
405 |
|
406 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::set_state()"); |
|
407 |
|
408 if (m_tls_peap_state != tls_peap_state_failure) |
|
409 { |
|
410 m_tls_peap_state = state; |
|
411 } |
|
412 |
|
413 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
414 } |
|
415 |
|
416 //-------------------------------------------------- |
|
417 |
|
418 EAP_FUNC_EXPORT tls_peap_state_e tls_record_c::get_state() const |
|
419 { |
|
420 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
421 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
422 return m_tls_peap_state; |
|
423 } |
|
424 |
|
425 //-------------------------------------------------- |
|
426 |
|
427 EAP_FUNC_EXPORT bool tls_record_c::verify_state(const tls_peap_state_e state) |
|
428 { |
|
429 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
430 |
|
431 bool are_equal = false; |
|
432 |
|
433 EAP_TRACE_DEBUG( |
|
434 m_am_tools, |
|
435 TRACE_FLAGS_DEFAULT, |
|
436 (EAPL("TLS: %s: state_function: starts: tls_record_c::verify_state(): (current state %s) %s (new state %s)\n"), |
|
437 (m_is_client == true ? "client": "server"), |
|
438 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
439 ((m_tls_peap_state == state) ? "==" : "!="), |
|
440 eap_tls_trace_string_c::get_state_string(state))); |
|
441 |
|
442 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::verify_state()"); |
|
443 |
|
444 if (m_tls_peap_state == state) |
|
445 { |
|
446 are_equal = true; |
|
447 } |
|
448 else |
|
449 { |
|
450 are_equal = false; |
|
451 } |
|
452 |
|
453 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
454 return are_equal; |
|
455 } |
|
456 |
|
457 //-------------------------------------------------- |
|
458 |
|
459 EAP_FUNC_EXPORT void tls_record_c::set_is_valid() |
|
460 { |
|
461 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
462 |
|
463 m_is_valid = true; |
|
464 |
|
465 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
466 } |
|
467 |
|
468 //-------------------------------------------------- |
|
469 |
|
470 EAP_FUNC_EXPORT bool tls_record_c::get_is_tunneled_tls() |
|
471 { |
|
472 return ( |
|
473 m_eap_type == eap_type_peap |
|
474 || m_eap_type == eap_type_ttls |
|
475 #if defined(USE_FAST_EAP_TYPE) |
|
476 || m_eap_type == eap_type_fast |
|
477 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
478 ); |
|
479 } |
|
480 |
|
481 //-------------------------------------------------- |
|
482 |
|
483 EAP_FUNC_EXPORT void tls_record_c::set_peap_version( |
|
484 const peap_version_e peap_version, |
|
485 const bool use_tppd_tls_peap, |
|
486 const bool use_tppd_peapv1_acknowledge_hack) |
|
487 { |
|
488 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
489 |
|
490 m_peap_version = peap_version; |
|
491 |
|
492 m_use_tppd_tls_peap = use_tppd_tls_peap; |
|
493 |
|
494 m_use_tppd_peapv1_acknowledge_hack = use_tppd_peapv1_acknowledge_hack; |
|
495 |
|
496 m_am_tls_services->set_peap_version( |
|
497 peap_version, |
|
498 use_tppd_tls_peap, |
|
499 use_tppd_peapv1_acknowledge_hack); |
|
500 |
|
501 if (m_application != 0) |
|
502 { |
|
503 m_application->set_peap_version( |
|
504 peap_version, |
|
505 use_tppd_tls_peap, |
|
506 use_tppd_peapv1_acknowledge_hack); |
|
507 } |
|
508 |
|
509 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
510 } |
|
511 |
|
512 //-------------------------------------------------- |
|
513 |
|
514 EAP_FUNC_EXPORT eap_status_e tls_record_c::configure() |
|
515 { |
|
516 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
517 |
|
518 EAP_TRACE_DEBUG( |
|
519 m_am_tools, |
|
520 TRACE_FLAGS_DEFAULT, |
|
521 (EAPL("TLS: this = 0x%08x, %s: function: starts: tls_record_c::configure():\n"), |
|
522 this, |
|
523 (m_is_client == true ? "client": "server"))); |
|
524 |
|
525 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::configure()"); |
|
526 |
|
527 eap_status_e status = m_am_tls_services->configure(); |
|
528 if (status != eap_status_ok) |
|
529 { |
|
530 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
531 return EAP_STATUS_RETURN(m_am_tools, status); |
|
532 } |
|
533 |
|
534 //---------------------------------------------------------- |
|
535 |
|
536 { |
|
537 eap_variable_data_c test_version(m_am_tools); |
|
538 |
|
539 status = get_type_partner()->read_configure( |
|
540 cf_str_EAP_TLS_test_version.get_field(), |
|
541 &test_version); |
|
542 if (status == eap_status_ok |
|
543 && test_version.get_is_valid_data() == true |
|
544 && test_version.get_data_length() == sizeof(u32_t) |
|
545 && test_version.get_data(sizeof(u32_t)) != 0) |
|
546 { |
|
547 // This is optional value. |
|
548 u32_t *flag = reinterpret_cast<u32_t *>(test_version.get_data(sizeof(u32_t))); |
|
549 if (flag != 0) |
|
550 { |
|
551 if (*flag == 0) |
|
552 { |
|
553 m_tls_peap_test_version = false; |
|
554 } |
|
555 else |
|
556 { |
|
557 m_tls_peap_test_version = true; |
|
558 } |
|
559 } |
|
560 } |
|
561 |
|
562 status = eap_status_ok; |
|
563 } |
|
564 |
|
565 //---------------------------------------------------------- |
|
566 |
|
567 { |
|
568 eap_variable_data_c use_separate_tls_record(m_am_tools); |
|
569 |
|
570 status = get_type_partner()->read_configure( |
|
571 cf_str_TLS_use_separate_tls_record.get_field(), |
|
572 &use_separate_tls_record); |
|
573 if (status == eap_status_ok |
|
574 && use_separate_tls_record.get_is_valid_data() == true |
|
575 && use_separate_tls_record.get_data_length() == sizeof(u32_t) |
|
576 && use_separate_tls_record.get_data(sizeof(u32_t)) != 0) |
|
577 { |
|
578 // This is optional value. |
|
579 u32_t *flag = reinterpret_cast<u32_t *>( |
|
580 use_separate_tls_record.get_data(sizeof(u32_t))); |
|
581 if (flag != 0) |
|
582 { |
|
583 if (*flag == 0) |
|
584 { |
|
585 m_use_separate_tls_record = false; |
|
586 } |
|
587 else |
|
588 { |
|
589 m_use_separate_tls_record = true; |
|
590 } |
|
591 } |
|
592 } |
|
593 |
|
594 status = eap_status_ok; |
|
595 } |
|
596 |
|
597 //---------------------------------------------------------- |
|
598 |
|
599 if (m_is_client == false) |
|
600 { |
|
601 eap_variable_data_c server_offers_new_session_id(m_am_tools); |
|
602 |
|
603 status = get_type_partner()->read_configure( |
|
604 cf_str_TLS_server_offers_new_session_id.get_field(), |
|
605 &server_offers_new_session_id); |
|
606 if (status == eap_status_ok |
|
607 && server_offers_new_session_id.get_is_valid_data() == true |
|
608 && server_offers_new_session_id.get_data_length() == sizeof(u32_t) |
|
609 && server_offers_new_session_id.get_data(sizeof(u32_t)) != 0) |
|
610 { |
|
611 // This is optional value. |
|
612 u32_t *flag = reinterpret_cast<u32_t *>( |
|
613 server_offers_new_session_id.get_data(sizeof(u32_t))); |
|
614 if (flag != 0) |
|
615 { |
|
616 if (*flag == 0) |
|
617 { |
|
618 m_server_offers_new_session_id = false; |
|
619 } |
|
620 else |
|
621 { |
|
622 m_server_offers_new_session_id = true; |
|
623 } |
|
624 } |
|
625 } |
|
626 |
|
627 status = eap_status_ok; |
|
628 } |
|
629 |
|
630 //---------------------------------------------------------- |
|
631 |
|
632 if (get_is_tunneled_tls() == true) |
|
633 { |
|
634 // Default function in PEAP and TTLS is only client authenticates server. |
|
635 m_tls_peap_server_authenticates_client_config_server = false; |
|
636 } |
|
637 |
|
638 if (m_is_client == false) |
|
639 { |
|
640 eap_variable_data_c server_authenticates_client(m_am_tools); |
|
641 |
|
642 status = get_type_partner()->read_configure( |
|
643 cf_str_TLS_server_authenticates_client.get_field(), |
|
644 &server_authenticates_client); |
|
645 if (status == eap_status_ok |
|
646 && server_authenticates_client.get_is_valid_data() == true |
|
647 && server_authenticates_client.get_data_length() == sizeof(u32_t) |
|
648 && server_authenticates_client.get_data(sizeof(u32_t)) != 0) |
|
649 { |
|
650 // This is optional value. |
|
651 u32_t *flag = reinterpret_cast<u32_t *>( |
|
652 server_authenticates_client.get_data(sizeof(u32_t))); |
|
653 if (flag != 0) |
|
654 { |
|
655 if (*flag == 0) |
|
656 { |
|
657 m_tls_peap_server_authenticates_client_config_server = false; |
|
658 } |
|
659 else |
|
660 { |
|
661 m_tls_peap_server_authenticates_client_config_server = true; |
|
662 } |
|
663 } |
|
664 } |
|
665 |
|
666 if (m_tls_peap_server_authenticates_client_config_server == false) |
|
667 { |
|
668 m_tls_peap_server_authenticates_client_action = false; |
|
669 } |
|
670 |
|
671 status = eap_status_ok; |
|
672 } |
|
673 |
|
674 //---------------------------------------------------------- |
|
675 |
|
676 if (get_is_tunneled_tls() == true) |
|
677 { |
|
678 // Default function in PEAP and TTLS is only client authenticates server. |
|
679 m_tls_peap_server_authenticates_client_policy_flag = false; |
|
680 } |
|
681 |
|
682 if (m_is_client == true) |
|
683 { |
|
684 eap_variable_data_c server_authenticates_client(m_am_tools); |
|
685 |
|
686 status = get_type_partner()->read_configure( |
|
687 cf_str_TLS_server_authenticates_client_policy_in_client.get_field(), |
|
688 &server_authenticates_client); |
|
689 if (status == eap_status_ok |
|
690 && server_authenticates_client.get_is_valid_data() == true |
|
691 && server_authenticates_client.get_data_length() == sizeof(u32_t) |
|
692 && server_authenticates_client.get_data(sizeof(u32_t)) != 0) |
|
693 { |
|
694 // This is optional value. |
|
695 u32_t *flag = reinterpret_cast<u32_t *>( |
|
696 server_authenticates_client.get_data(sizeof(u32_t))); |
|
697 if (flag != 0) |
|
698 { |
|
699 if (*flag == 0) |
|
700 { |
|
701 m_tls_peap_server_authenticates_client_policy_flag = false; |
|
702 } |
|
703 else |
|
704 { |
|
705 m_tls_peap_server_authenticates_client_policy_flag = true; |
|
706 } |
|
707 } |
|
708 } |
|
709 |
|
710 status = eap_status_ok; |
|
711 } |
|
712 else |
|
713 { |
|
714 eap_variable_data_c server_authenticates_client(m_am_tools); |
|
715 |
|
716 status = get_type_partner()->read_configure( |
|
717 cf_str_TLS_server_authenticates_client_policy_in_server.get_field(), |
|
718 &server_authenticates_client); |
|
719 if (status == eap_status_ok |
|
720 && server_authenticates_client.get_is_valid_data() == true |
|
721 && server_authenticates_client.get_data_length() == sizeof(u32_t) |
|
722 && server_authenticates_client.get_data(sizeof(u32_t)) != 0) |
|
723 { |
|
724 // This is optional value. |
|
725 u32_t *flag = reinterpret_cast<u32_t *>( |
|
726 server_authenticates_client.get_data(sizeof(u32_t))); |
|
727 if (flag != 0) |
|
728 { |
|
729 if (*flag == 0) |
|
730 { |
|
731 m_tls_peap_server_authenticates_client_policy_flag = false; |
|
732 } |
|
733 else |
|
734 { |
|
735 m_tls_peap_server_authenticates_client_policy_flag = true; |
|
736 } |
|
737 } |
|
738 } |
|
739 |
|
740 status = eap_status_ok; |
|
741 } |
|
742 |
|
743 //---------------------------------------------------------- |
|
744 |
|
745 if (m_is_client == true) |
|
746 { |
|
747 eap_variable_data_c client_allows_empty_certificate_authorities_list(m_am_tools); |
|
748 |
|
749 status = get_type_partner()->read_configure( |
|
750 cf_str_TLS_client_allows_empty_certificate_authorities_list.get_field(), |
|
751 &client_allows_empty_certificate_authorities_list); |
|
752 if (status == eap_status_ok |
|
753 && client_allows_empty_certificate_authorities_list.get_is_valid_data() == true |
|
754 && client_allows_empty_certificate_authorities_list.get_data_length() == sizeof(u32_t) |
|
755 && client_allows_empty_certificate_authorities_list.get_data(sizeof(u32_t)) != 0) |
|
756 { |
|
757 // This is optional value. |
|
758 u32_t *flag = reinterpret_cast<u32_t *>( |
|
759 client_allows_empty_certificate_authorities_list.get_data(sizeof(u32_t))); |
|
760 if (flag != 0) |
|
761 { |
|
762 if (*flag == 0) |
|
763 { |
|
764 m_client_allows_empty_certificate_authorities_list = false; |
|
765 } |
|
766 else |
|
767 { |
|
768 m_client_allows_empty_certificate_authorities_list = true; |
|
769 } |
|
770 } |
|
771 } |
|
772 |
|
773 status = eap_status_ok; |
|
774 } |
|
775 else |
|
776 { |
|
777 eap_variable_data_c server_sends_empty_certificate_authorities_list(m_am_tools); |
|
778 |
|
779 status = get_type_partner()->read_configure( |
|
780 cf_str_TLS_server_sends_empty_certificate_authorities_list.get_field(), |
|
781 &server_sends_empty_certificate_authorities_list); |
|
782 if (status == eap_status_ok |
|
783 && server_sends_empty_certificate_authorities_list.get_is_valid_data() == true |
|
784 && server_sends_empty_certificate_authorities_list.get_data_length() == sizeof(u32_t) |
|
785 && server_sends_empty_certificate_authorities_list.get_data(sizeof(u32_t)) != 0) |
|
786 { |
|
787 // This is optional value. |
|
788 u32_t *flag = reinterpret_cast<u32_t *>( |
|
789 server_sends_empty_certificate_authorities_list.get_data(sizeof(u32_t))); |
|
790 if (flag != 0) |
|
791 { |
|
792 if (*flag == 0) |
|
793 { |
|
794 m_server_sends_empty_certificate_authorities_list = false; |
|
795 } |
|
796 else |
|
797 { |
|
798 m_server_sends_empty_certificate_authorities_list = true; |
|
799 } |
|
800 } |
|
801 } |
|
802 |
|
803 status = eap_status_ok; |
|
804 } |
|
805 |
|
806 //---------------------------------------------------------- |
|
807 |
|
808 if (m_is_client == false) |
|
809 { |
|
810 eap_variable_data_c send_piggypacked_eap_identity_request(m_am_tools); |
|
811 |
|
812 status = get_type_partner()->read_configure( |
|
813 cf_str_EAP_FAST_send_piggypacked_eap_identity_request.get_field(), |
|
814 &send_piggypacked_eap_identity_request); |
|
815 if (status == eap_status_ok |
|
816 && send_piggypacked_eap_identity_request.get_is_valid_data() == true |
|
817 && send_piggypacked_eap_identity_request.get_data_length() == sizeof(u32_t) |
|
818 && send_piggypacked_eap_identity_request.get_data(sizeof(u32_t)) != 0) |
|
819 { |
|
820 // This is optional value. |
|
821 u32_t *flag = reinterpret_cast<u32_t *>( |
|
822 send_piggypacked_eap_identity_request.get_data(sizeof(u32_t))); |
|
823 if (flag != 0) |
|
824 { |
|
825 if (*flag == 0) |
|
826 { |
|
827 m_send_piggypacked_eap_identity_request = false; |
|
828 } |
|
829 else |
|
830 { |
|
831 m_send_piggypacked_eap_identity_request = true; |
|
832 } |
|
833 } |
|
834 } |
|
835 |
|
836 status = eap_status_ok; |
|
837 } |
|
838 |
|
839 //---------------------------------------------------------- |
|
840 |
|
841 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
842 |
|
843 { |
|
844 eap_variable_data_c tls_use_privacy(m_am_tools); |
|
845 |
|
846 status = get_type_partner()->read_configure( |
|
847 cf_str_EAP_TLS_PEAP_use_identity_privacy.get_field(), |
|
848 &tls_use_privacy); |
|
849 if (status == eap_status_ok |
|
850 && tls_use_privacy.get_is_valid_data() == true |
|
851 && tls_use_privacy.get_data_length() == sizeof(u32_t) |
|
852 && tls_use_privacy.get_data(sizeof(u32_t)) != 0) |
|
853 { |
|
854 // This is optional value. |
|
855 u32_t *flag = reinterpret_cast<u32_t *>( |
|
856 tls_use_privacy.get_data(sizeof(u32_t))); |
|
857 if (flag != 0) |
|
858 { |
|
859 if (*flag == 0) |
|
860 { |
|
861 m_tls_use_identity_privacy = false; |
|
862 } |
|
863 else |
|
864 { |
|
865 m_tls_use_identity_privacy = true; |
|
866 } |
|
867 } |
|
868 } |
|
869 |
|
870 status = eap_status_ok; |
|
871 } |
|
872 |
|
873 if (m_is_client == false) |
|
874 { |
|
875 eap_variable_data_c tls_server_use_privacy(m_am_tools); |
|
876 |
|
877 status = get_type_partner()->read_configure( |
|
878 cf_str_EAP_TLS_PEAP_use_identity_privacy_server.get_field(), |
|
879 &tls_server_use_privacy); |
|
880 if (status == eap_status_ok |
|
881 && tls_server_use_privacy.get_is_valid_data() == true |
|
882 && tls_server_use_privacy.get_data_length() == sizeof(u32_t) |
|
883 && tls_server_use_privacy.get_data(sizeof(u32_t)) != 0) |
|
884 { |
|
885 // This is optional value. |
|
886 u32_t *flag = reinterpret_cast<u32_t *>( |
|
887 tls_server_use_privacy.get_data(sizeof(u32_t))); |
|
888 if (flag != 0) |
|
889 { |
|
890 if (*flag == 0) |
|
891 { |
|
892 m_tls_use_identity_privacy = false; |
|
893 } |
|
894 else |
|
895 { |
|
896 m_tls_use_identity_privacy = true; |
|
897 } |
|
898 } |
|
899 } |
|
900 |
|
901 status = eap_status_ok; |
|
902 } |
|
903 |
|
904 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
905 |
|
906 //---------------------------------------------------------- |
|
907 |
|
908 #if defined(USE_FAST_EAP_TYPE) |
|
909 if (m_eap_type == eap_type_fast) |
|
910 { |
|
911 // Client and server configuration. |
|
912 { |
|
913 eap_variable_data_c provisioning(m_am_tools); |
|
914 |
|
915 status = get_type_partner()->read_configure( |
|
916 cf_str_EAP_FAST_allow_server_unauthenticated_provisioning_mode_ADHP.get_field(), |
|
917 &provisioning); |
|
918 if (status == eap_status_ok |
|
919 && provisioning.get_is_valid_data() == true |
|
920 && provisioning.get_data_length() == sizeof(u32_t) |
|
921 && provisioning.get_data(sizeof(u32_t)) != 0) |
|
922 { |
|
923 // This is optional value. |
|
924 u32_t *flag = reinterpret_cast<u32_t *>( |
|
925 provisioning.get_data(sizeof(u32_t))); |
|
926 if (flag != 0) |
|
927 { |
|
928 if (*flag == 0) |
|
929 { |
|
930 m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP = false; |
|
931 } |
|
932 else |
|
933 { |
|
934 m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP = true; |
|
935 } |
|
936 } |
|
937 } |
|
938 |
|
939 status = eap_status_ok; |
|
940 } |
|
941 |
|
942 { |
|
943 eap_variable_data_c allow_server_authenticated_provisioning_mode(m_am_tools); |
|
944 |
|
945 status = read_configure( |
|
946 cf_str_EAP_FAST_allow_server_authenticated_provisioning_mode.get_field(), |
|
947 &allow_server_authenticated_provisioning_mode); |
|
948 if (status == eap_status_ok |
|
949 && allow_server_authenticated_provisioning_mode.get_is_valid_data() == true |
|
950 && allow_server_authenticated_provisioning_mode.get_data_length() == sizeof(u32_t) |
|
951 && allow_server_authenticated_provisioning_mode.get_data(sizeof(u32_t)) != 0) |
|
952 { |
|
953 // This is optional value. |
|
954 u32_t *flag = reinterpret_cast<u32_t *>( |
|
955 allow_server_authenticated_provisioning_mode.get_data(sizeof(u32_t))); |
|
956 if (flag != 0) |
|
957 { |
|
958 if (*flag == 0) |
|
959 { |
|
960 m_fast_allow_server_authenticated_provisioning_mode = false; |
|
961 } |
|
962 else |
|
963 { |
|
964 m_fast_allow_server_authenticated_provisioning_mode = true; |
|
965 } |
|
966 } |
|
967 } |
|
968 |
|
969 status = eap_status_ok; |
|
970 } |
|
971 |
|
972 } |
|
973 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
974 |
|
975 //---------------------------------------------------------- |
|
976 |
|
977 status = message_hash_init(); |
|
978 if (status != eap_status_ok) |
|
979 { |
|
980 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
981 return EAP_STATUS_RETURN(m_am_tools, status); |
|
982 } |
|
983 |
|
984 //---------------------------------------------------------- |
|
985 |
|
986 if (m_application != 0) |
|
987 { |
|
988 status = m_application->configure(); |
|
989 } |
|
990 else |
|
991 { |
|
992 status = eap_status_ok; |
|
993 } |
|
994 |
|
995 //---------------------------------------------------------- |
|
996 |
|
997 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
998 return EAP_STATUS_RETURN(m_am_tools, status); |
|
999 } |
|
1000 |
|
1001 //-------------------------------------------------- |
|
1002 |
|
1003 EAP_FUNC_EXPORT eap_status_e tls_record_c::shutdown() |
|
1004 { |
|
1005 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1006 |
|
1007 EAP_TRACE_DEBUG( |
|
1008 m_am_tools, |
|
1009 TRACE_FLAGS_DEFAULT, |
|
1010 (EAPL("TLS: this = 0x%08x, %s: function: starts: tls_record_c::shutdown():\n"), |
|
1011 this, |
|
1012 (m_is_client == true ? "client": "server"))); |
|
1013 |
|
1014 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::shutdown()"); |
|
1015 |
|
1016 if (m_shutdown_was_called == true) |
|
1017 { |
|
1018 // Shutdown function was called already. |
|
1019 return EAP_STATUS_RETURN(m_am_tools, eap_status_ok); |
|
1020 } |
|
1021 m_shutdown_was_called = true; |
|
1022 |
|
1023 if (m_tls_peap_state != tls_peap_state_tls_success) |
|
1024 { |
|
1025 set_state(tls_peap_state_failure); |
|
1026 } |
|
1027 |
|
1028 eap_status_e status = eap_status_ok; |
|
1029 |
|
1030 if (m_application != 0) |
|
1031 { |
|
1032 status = m_application->shutdown(); |
|
1033 } |
|
1034 |
|
1035 |
|
1036 if (m_pending_query_certificate_authorities_and_types == true) |
|
1037 { |
|
1038 EAP_TRACE_DEBUG( |
|
1039 m_am_tools, |
|
1040 TRACE_FLAGS_DEFAULT, |
|
1041 (EAPL("TLS: function: tls_record_c::shutdown(): calls cancel_query_certificate_authorities_and_types()\n"))); |
|
1042 |
|
1043 m_am_tls_services->cancel_query_certificate_authorities_and_types(); |
|
1044 m_pending_query_certificate_authorities_and_types = false; |
|
1045 } |
|
1046 |
|
1047 if (m_pending_query_certificate_chain == true) |
|
1048 { |
|
1049 EAP_TRACE_DEBUG( |
|
1050 m_am_tools, |
|
1051 TRACE_FLAGS_DEFAULT, |
|
1052 (EAPL("TLS: function: tls_record_c::shutdown(): calls cancel_query_certificate_chain()\n"))); |
|
1053 |
|
1054 m_am_tls_services->cancel_query_certificate_chain(); |
|
1055 m_pending_query_certificate_chain = false; |
|
1056 } |
|
1057 |
|
1058 if (m_pending_query_cipher_suites_and_previous_session == true) |
|
1059 { |
|
1060 EAP_TRACE_DEBUG( |
|
1061 m_am_tools, |
|
1062 TRACE_FLAGS_DEFAULT, |
|
1063 (EAPL("TLS: function: tls_record_c::shutdown(): calls cancel_query_cipher_suites_and_previous_session()\n"))); |
|
1064 |
|
1065 m_am_tls_services->cancel_query_cipher_suites_and_previous_session(); |
|
1066 m_pending_query_cipher_suites_and_previous_session = false; |
|
1067 } |
|
1068 |
|
1069 if (m_pending_query_dh_parameters == true) |
|
1070 { |
|
1071 EAP_TRACE_DEBUG( |
|
1072 m_am_tools, |
|
1073 TRACE_FLAGS_DEFAULT, |
|
1074 (EAPL("TLS: function: tls_record_c::shutdown(): calls cancel_query_dh_parameters()\n"))); |
|
1075 |
|
1076 m_am_tls_services->cancel_query_dh_parameters(); |
|
1077 m_pending_query_dh_parameters = false; |
|
1078 } |
|
1079 |
|
1080 if (m_pending_query_realm == true) |
|
1081 { |
|
1082 EAP_TRACE_DEBUG( |
|
1083 m_am_tools, |
|
1084 TRACE_FLAGS_DEFAULT, |
|
1085 (EAPL("TLS: function: tls_record_c::shutdown(): calls cancel_query_realm()\n"))); |
|
1086 |
|
1087 m_am_tls_services->cancel_query_realm(); |
|
1088 m_pending_query_realm = false; |
|
1089 } |
|
1090 |
|
1091 if (m_pending_select_cipher_suite_and_check_session_id == true) |
|
1092 { |
|
1093 EAP_TRACE_DEBUG( |
|
1094 m_am_tools, |
|
1095 TRACE_FLAGS_DEFAULT, |
|
1096 (EAPL("TLS: function: tls_record_c::shutdown(): calls cancel_select_cipher_suite_and_check_session_id()\n"))); |
|
1097 |
|
1098 m_am_tls_services->cancel_select_cipher_suite_and_check_session_id(); |
|
1099 m_pending_select_cipher_suite_and_check_session_id = false; |
|
1100 } |
|
1101 |
|
1102 if (m_pending_verify_certificate_chain == true) |
|
1103 { |
|
1104 EAP_TRACE_DEBUG( |
|
1105 m_am_tools, |
|
1106 TRACE_FLAGS_DEFAULT, |
|
1107 (EAPL("TLS: function: tls_record_c::shutdown(): calls cancel_verify_certificate_chain()\n"))); |
|
1108 |
|
1109 m_am_tls_services->cancel_verify_certificate_chain(); |
|
1110 m_pending_verify_certificate_chain = false; |
|
1111 } |
|
1112 |
|
1113 if (m_pending_rsa_decrypt_with_private_key == true) |
|
1114 { |
|
1115 EAP_TRACE_DEBUG( |
|
1116 m_am_tools, |
|
1117 TRACE_FLAGS_DEFAULT, |
|
1118 (EAPL("TLS: function: tls_record_c::shutdown(): calls cancel_rsa_decrypt_with_private_key()\n"))); |
|
1119 |
|
1120 m_am_tls_services->cancel_rsa_decrypt_with_private_key(); |
|
1121 m_pending_rsa_decrypt_with_private_key = false; |
|
1122 } |
|
1123 |
|
1124 if (m_pending_rsa_encrypt_with_public_key == true) |
|
1125 { |
|
1126 EAP_TRACE_DEBUG( |
|
1127 m_am_tools, |
|
1128 TRACE_FLAGS_DEFAULT, |
|
1129 (EAPL("TLS: function: tls_record_c::shutdown(): calls cancel_rsa_encrypt_with_public_key()\n"))); |
|
1130 |
|
1131 m_am_tls_services->cancel_rsa_encrypt_with_public_key(); |
|
1132 m_pending_rsa_encrypt_with_public_key = false; |
|
1133 } |
|
1134 |
|
1135 if (m_pending_sign_with_private_key == true) |
|
1136 { |
|
1137 EAP_TRACE_DEBUG( |
|
1138 m_am_tools, |
|
1139 TRACE_FLAGS_DEFAULT, |
|
1140 (EAPL("TLS: function: tls_record_c::shutdown(): calls cancel_sign_with_private_key()\n"))); |
|
1141 |
|
1142 m_am_tls_services->cancel_sign_with_private_key(); |
|
1143 m_pending_sign_with_private_key = false; |
|
1144 } |
|
1145 |
|
1146 if (m_pending_verify_with_public_key == true) |
|
1147 { |
|
1148 EAP_TRACE_DEBUG( |
|
1149 m_am_tools, |
|
1150 TRACE_FLAGS_DEFAULT, |
|
1151 (EAPL("TLS: function: tls_record_c::shutdown(): calls cancel_verify_with_public_key()\n"))); |
|
1152 |
|
1153 m_am_tls_services->cancel_verify_with_public_key(); |
|
1154 m_pending_verify_with_public_key = false; |
|
1155 } |
|
1156 |
|
1157 if (m_pending_query_tunnel_PAC == true) |
|
1158 { |
|
1159 EAP_TRACE_DEBUG( |
|
1160 m_am_tools, |
|
1161 TRACE_FLAGS_DEFAULT, |
|
1162 (EAPL("TLS: function: tls_record_c::shutdown(): calls cancel_query_tunnel_PAC()\n"))); |
|
1163 |
|
1164 if (m_application != 0) |
|
1165 { |
|
1166 m_application->cancel_query_tunnel_PAC(); |
|
1167 } |
|
1168 m_pending_query_tunnel_PAC = false; |
|
1169 } |
|
1170 |
|
1171 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1172 return EAP_STATUS_RETURN(m_am_tools, status); |
|
1173 } |
|
1174 |
|
1175 //-------------------------------------------------- |
|
1176 |
|
1177 EAP_FUNC_EXPORT eap_status_e tls_record_c::set_nai_realm( |
|
1178 const eap_variable_data_c * const NAI_realm) |
|
1179 { |
|
1180 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1181 |
|
1182 eap_status_e status = m_NAI_realm.set_copy_of_buffer(NAI_realm); |
|
1183 |
|
1184 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1185 return EAP_STATUS_RETURN(m_am_tools, status); |
|
1186 } |
|
1187 |
|
1188 //-------------------------------------------------- |
|
1189 |
|
1190 void tls_record_c::send_error_notification(const eap_status_e error) |
|
1191 { |
|
1192 // Notifies the lower level of an authentication error. |
|
1193 |
|
1194 eap_general_state_variable_e general_state_variable(eap_general_state_authentication_error); |
|
1195 |
|
1196 if (error == eap_status_user_cancel_authentication) |
|
1197 { |
|
1198 general_state_variable = eap_general_state_authentication_cancelled; |
|
1199 } |
|
1200 |
|
1201 eap_state_notification_c notification( |
|
1202 m_am_tools, |
|
1203 &m_send_network_id, |
|
1204 true, |
|
1205 eap_state_notification_eap, |
|
1206 eap_protocol_layer_general, |
|
1207 m_eap_type, |
|
1208 eap_state_none, |
|
1209 general_state_variable, |
|
1210 0, |
|
1211 false); |
|
1212 |
|
1213 notification.set_authentication_error(error); |
|
1214 |
|
1215 get_type_partner()->state_notification(¬ification); |
|
1216 } |
|
1217 |
|
1218 //-------------------------------------------------- |
|
1219 |
|
1220 // |
|
1221 EAP_FUNC_EXPORT eap_status_e tls_record_c::completion_action_add( |
|
1222 tls_completion_action_e action) |
|
1223 { |
|
1224 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1225 |
|
1226 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
1227 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, |
|
1228 (EAPL("TLS: %s: send_function: completion_action_add()\n"), |
|
1229 (m_is_client == true ? "client": "server"))); |
|
1230 |
|
1231 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::completion_action_add()"); |
|
1232 |
|
1233 tls_completion_c *completion_action = new tls_completion_c( |
|
1234 m_am_tools, |
|
1235 action); |
|
1236 |
|
1237 if (completion_action == 0 |
|
1238 || completion_action->get_is_valid() == false) |
|
1239 { |
|
1240 delete completion_action; |
|
1241 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1242 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
1243 } |
|
1244 |
|
1245 // add_object() will delete completion_action if operation fails. |
|
1246 eap_status_e status = m_completion_queue.add_object(completion_action, true); |
|
1247 |
|
1248 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, |
|
1249 (EAPL("TLS: %s: send_function: completion_action_add(): action %s\n"), |
|
1250 (m_is_client == true ? "client": "server"), |
|
1251 completion_action->get_completion_action_string())); |
|
1252 |
|
1253 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1254 return EAP_STATUS_RETURN(m_am_tools, status); |
|
1255 } |
|
1256 |
|
1257 //-------------------------------------------------- |
|
1258 |
|
1259 // |
|
1260 EAP_FUNC_EXPORT eap_status_e tls_record_c::completion_action_clenup() |
|
1261 { |
|
1262 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1263 |
|
1264 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
1265 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, |
|
1266 (EAPL("TLS: %s: send_function: starts: tls_record_c::completion_action_clenup()\n"), |
|
1267 (m_is_client == true ? "client": "server"))); |
|
1268 |
|
1269 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::completion_action_clenup()"); |
|
1270 |
|
1271 eap_status_e final_status = eap_status_ok; |
|
1272 u32_t counter = 0ul; |
|
1273 |
|
1274 while(m_completion_queue.get_object_count() > 0ul) |
|
1275 { |
|
1276 tls_completion_c * const completion_action = m_completion_queue.get_object(0ul); |
|
1277 EAP_UNREFERENCED_PARAMETER(completion_action); // Not referenced without trace. |
|
1278 |
|
1279 EAP_TRACE_DEBUG( |
|
1280 m_am_tools, |
|
1281 TRACE_FLAGS_DEFAULT, |
|
1282 (EAPL("ERROR: TLS: %s: send_function: completion_action_clenup(): ") |
|
1283 EAPL("action[%u] %s not completed.\n"), |
|
1284 (m_is_client == true ? "client": "server"), |
|
1285 counter, |
|
1286 completion_action->get_completion_action_string())); |
|
1287 |
|
1288 final_status = m_completion_queue.remove_object(0ul); |
|
1289 if (final_status != eap_status_ok) |
|
1290 { |
|
1291 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1292 return EAP_STATUS_RETURN(m_am_tools, final_status); |
|
1293 } |
|
1294 |
|
1295 ++counter; |
|
1296 |
|
1297 } // while() |
|
1298 |
|
1299 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1300 return EAP_STATUS_RETURN(m_am_tools, final_status); |
|
1301 } |
|
1302 |
|
1303 //-------------------------------------------------- |
|
1304 |
|
1305 // |
|
1306 EAP_FUNC_EXPORT eap_status_e tls_record_c::completion_action_check() |
|
1307 { |
|
1308 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1309 |
|
1310 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
1311 EAP_TRACE_DEBUG( |
|
1312 m_am_tools, TRACE_FLAGS_DEFAULT, |
|
1313 (EAPL("TLS: %s: send_function: starts: tls_record_c::completion_action_check()\n"), |
|
1314 (m_is_client == true ? "client": "server"))); |
|
1315 |
|
1316 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::completion_action_check()"); |
|
1317 |
|
1318 if (m_already_in_completion_action_check == true) |
|
1319 { |
|
1320 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1321 // This is recursive call of completion_action_check(). |
|
1322 // This MUST return eap_status_ok. Other return values will skip |
|
1323 // further prosessing of completion action list. |
|
1324 EAP_TRACE_DEBUG( |
|
1325 m_am_tools, TRACE_FLAGS_DEFAULT, |
|
1326 (EAPL("TLS: %s: send_function: completion_action_check(): skip recursion\n"), |
|
1327 (m_is_client == true ? "client": "server"))); |
|
1328 return EAP_STATUS_RETURN(m_am_tools, eap_status_ok); |
|
1329 } |
|
1330 m_already_in_completion_action_check = true; |
|
1331 |
|
1332 eap_automatic_simple_value_c<bool> restore_already_in_completion_action_check( |
|
1333 m_am_tools, |
|
1334 &m_already_in_completion_action_check, |
|
1335 false); |
|
1336 |
|
1337 eap_status_e status = eap_status_ok; |
|
1338 bool continue_with_next_action = true; |
|
1339 u32_t counter = 0ul; |
|
1340 |
|
1341 while(continue_with_next_action == true |
|
1342 && m_completion_queue.get_object_count() > 0ul) |
|
1343 { |
|
1344 status = eap_status_ok; |
|
1345 |
|
1346 tls_completion_c * const completion_action = m_completion_queue.get_object(0ul); |
|
1347 |
|
1348 EAP_TRACE_DEBUG( |
|
1349 m_am_tools, |
|
1350 TRACE_FLAGS_DEFAULT, |
|
1351 (EAPL("TLS: %s: send_function: completion_action_check(): action[%d] %s\n"), |
|
1352 (m_is_client == true ? "client": "server"), |
|
1353 counter, |
|
1354 completion_action->get_completion_action_string())); |
|
1355 |
|
1356 switch(completion_action->get_completion_action()) |
|
1357 { |
|
1358 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
1359 case tls_completion_action_create_handshake_type_hello_request: |
|
1360 { |
|
1361 // We must send Handshake/HelloRequest message. |
|
1362 eap_status_e status = create_handshake_type_hello_request(); |
|
1363 if (status != eap_status_ok) |
|
1364 { |
|
1365 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1366 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1367 } |
|
1368 break; |
|
1369 } |
|
1370 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
1371 case tls_completion_action_query_cipher_suites_and_previous_session: |
|
1372 { |
|
1373 m_allow_message_send = false; |
|
1374 |
|
1375 status = m_am_tls_services->query_cipher_suites_and_previous_session(); |
|
1376 |
|
1377 m_allow_message_send = true; |
|
1378 |
|
1379 if (status == eap_status_pending_request) |
|
1380 { |
|
1381 // This is pending query, that will be completed by |
|
1382 // complete_query_cipher_suites_and_previous_session() call. |
|
1383 m_pending_query_cipher_suites_and_previous_session = true; |
|
1384 |
|
1385 // Cannot complete yet. |
|
1386 continue_with_next_action = false; |
|
1387 } |
|
1388 |
|
1389 break; |
|
1390 } |
|
1391 case tls_completion_action_create_handshake_type_client_hello: |
|
1392 { |
|
1393 if (m_pending_query_cipher_suites_and_previous_session == false |
|
1394 && m_proposed_cipher_suites.get_object_count() > 0ul |
|
1395 && m_proposed_compression_methods.get_object_count() > 0ul) |
|
1396 { |
|
1397 // We must send Handshake/ClientHello message. |
|
1398 eap_status_e status = create_handshake_type_client_hello(); |
|
1399 if (status != eap_status_ok) |
|
1400 { |
|
1401 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1402 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1403 } |
|
1404 } |
|
1405 else |
|
1406 { |
|
1407 // Cannot complete yet. |
|
1408 continue_with_next_action = false; |
|
1409 } |
|
1410 break; |
|
1411 } |
|
1412 case tls_completion_action_create_handshake_type_server_hello: |
|
1413 { |
|
1414 if (m_pending_select_cipher_suite_and_check_session_id == false |
|
1415 && m_selected_cipher_suite != tls_cipher_suites_none |
|
1416 && m_selected_compression_method != tls_compression_method_none) |
|
1417 { |
|
1418 // We must send Handshake/ServerHello message. |
|
1419 eap_status_e status = create_handshake_type_server_hello( |
|
1420 static_cast<u8_t>(m_selected_cipher_suite), |
|
1421 static_cast<u8_t>(m_selected_compression_method)); |
|
1422 if (status != eap_status_ok) |
|
1423 { |
|
1424 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1425 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1426 } |
|
1427 } |
|
1428 else |
|
1429 { |
|
1430 // Cannot complete yet. |
|
1431 continue_with_next_action = false; |
|
1432 } |
|
1433 break; |
|
1434 } |
|
1435 case tls_completion_action_create_handshake_type_certificate: |
|
1436 { |
|
1437 if (m_pending_query_certificate_chain == false |
|
1438 && m_pending_verify_certificate_chain == false) |
|
1439 { |
|
1440 // We must send Handshake/Certificate message. |
|
1441 // NOTE m_own_certificate_chain could be empty. |
|
1442 status = create_handshake_type_certificate(&m_own_certificate_chain); |
|
1443 if (status != eap_status_ok) |
|
1444 { |
|
1445 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1446 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1447 } |
|
1448 } |
|
1449 else |
|
1450 { |
|
1451 // Cannot complete yet. |
|
1452 continue_with_next_action = false; |
|
1453 } |
|
1454 break; |
|
1455 } |
|
1456 case tls_completion_action_create_handshake_type_server_key_exchange: |
|
1457 { |
|
1458 if (m_pending_query_dh_parameters == false) |
|
1459 { |
|
1460 if ((cipher_suite_is_TLS_DHE_DSS() == true |
|
1461 || cipher_suite_is_TLS_DHE_RSA() == true |
|
1462 #if defined(USE_FAST_EAP_TYPE) |
|
1463 || (m_eap_type == eap_type_fast |
|
1464 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true |
|
1465 && cipher_suite_is_TLS_DH_anon() == true) |
|
1466 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
1467 ) |
|
1468 && m_dhe_prime.get_is_valid_data() == true |
|
1469 && m_dhe_group_generator.get_is_valid_data() == true) |
|
1470 { |
|
1471 status = generate_dhe_keys(); |
|
1472 if (status != eap_status_ok) |
|
1473 { |
|
1474 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1475 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1476 } |
|
1477 |
|
1478 // We must send Handshake/ServerKeyExchange. |
|
1479 status = create_handshake_type_server_key_exchange(); |
|
1480 if (status == eap_status_pending_request) |
|
1481 { |
|
1482 // This is pending query, that will be completed by |
|
1483 // complete_create_handshake_type_server_key_exchange() call. |
|
1484 } |
|
1485 else if (status == eap_status_completed_request) |
|
1486 { |
|
1487 // This is already completed by |
|
1488 // complete_create_handshake_type_server_key_exchange() call. |
|
1489 status = eap_status_ok; |
|
1490 } |
|
1491 else if (status == eap_status_ok) |
|
1492 { |
|
1493 // This is also an error case, because this call |
|
1494 // is always completed on success. |
|
1495 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1496 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
1497 m_am_tools, |
|
1498 eap_status_process_general_error); |
|
1499 } |
|
1500 else // All other status values means error, because this |
|
1501 // call is always completed on success. |
|
1502 { |
|
1503 // This is an error case. |
|
1504 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1505 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1506 } |
|
1507 } |
|
1508 else |
|
1509 { |
|
1510 // Cannot complete yet. |
|
1511 continue_with_next_action = false; |
|
1512 } |
|
1513 } |
|
1514 else |
|
1515 { |
|
1516 // Cannot complete yet. |
|
1517 continue_with_next_action = false; |
|
1518 } |
|
1519 break; |
|
1520 } |
|
1521 case tls_completion_action_create_handshake_type_certificate_request: |
|
1522 { |
|
1523 if (m_pending_query_certificate_authorities_and_types == false |
|
1524 && m_own_certificate_types.get_object_count() != 0ul |
|
1525 && (m_own_certificate_authorities.get_object_count() != 0ul |
|
1526 || m_server_sends_empty_certificate_authorities_list == false)) |
|
1527 { |
|
1528 // We must send Handshake/CertificateRequest message. |
|
1529 status = create_handshake_type_certificate_request( |
|
1530 &m_own_certificate_types, |
|
1531 &m_own_certificate_authorities); |
|
1532 if (status != eap_status_ok) |
|
1533 { |
|
1534 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1535 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1536 } |
|
1537 } |
|
1538 else |
|
1539 { |
|
1540 // Cannot complete yet. |
|
1541 continue_with_next_action = false; |
|
1542 } |
|
1543 break; |
|
1544 } |
|
1545 case tls_completion_action_create_handshake_type_server_hello_done: |
|
1546 { |
|
1547 status = create_handshake_type_server_hello_done(); |
|
1548 if (status != eap_status_ok) |
|
1549 { |
|
1550 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1551 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1552 } |
|
1553 |
|
1554 break; |
|
1555 } |
|
1556 case tls_completion_action_create_handshake_type_certificate_verify: |
|
1557 { |
|
1558 if (m_pending_query_certificate_chain == false |
|
1559 && m_pending_verify_certificate_chain == false |
|
1560 && m_own_certificate_chain.get_object_count() > 0ul) |
|
1561 { |
|
1562 // We must send Handshake/CertificateVerify. |
|
1563 status = create_handshake_type_certificate_verify(); |
|
1564 if (status == eap_status_pending_request) |
|
1565 { |
|
1566 // This is pending query, that will be completed by |
|
1567 // complete_create_handshake_type_certificate_verify() call. |
|
1568 } |
|
1569 else if (status == eap_status_completed_request) |
|
1570 { |
|
1571 // This is already completed by |
|
1572 // complete_create_handshake_type_certificate_verify() call. |
|
1573 status = eap_status_ok; |
|
1574 } |
|
1575 else if (status == eap_status_ok) |
|
1576 { |
|
1577 // This is also an error case, because this |
|
1578 // call is always completed on success. |
|
1579 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1580 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
1581 m_am_tools, |
|
1582 eap_status_process_general_error); |
|
1583 } |
|
1584 else // All other status values means error, because this |
|
1585 // call is always completed on success. |
|
1586 { |
|
1587 // This is an error case. |
|
1588 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1589 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1590 } |
|
1591 } |
|
1592 else if (m_pending_query_certificate_chain == false |
|
1593 && m_pending_verify_certificate_chain == false |
|
1594 && m_own_certificate_chain.get_object_count() == 0ul) |
|
1595 { |
|
1596 // No user certificate. |
|
1597 } |
|
1598 else |
|
1599 { |
|
1600 // Cannot complete yet. |
|
1601 continue_with_next_action = false; |
|
1602 } |
|
1603 break; |
|
1604 } |
|
1605 case tls_completion_action_create_handshake_type_client_key_exchange: |
|
1606 { |
|
1607 if (m_pending_query_certificate_chain == false |
|
1608 && m_pending_verify_certificate_chain == false) |
|
1609 { |
|
1610 if (cipher_suite_is_TLS_DHE_DSS() == true |
|
1611 || cipher_suite_is_TLS_DHE_RSA() == true |
|
1612 #if defined(USE_FAST_EAP_TYPE) |
|
1613 || (m_eap_type == eap_type_fast |
|
1614 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true |
|
1615 && cipher_suite_is_TLS_DH_anon() == true) |
|
1616 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
1617 ) |
|
1618 { |
|
1619 // DHE parameters should have been received in ServerKeyExchange message. |
|
1620 |
|
1621 if (m_dhe_prime.get_is_valid_data() == true |
|
1622 && m_dhe_group_generator.get_is_valid_data() == true) |
|
1623 { |
|
1624 status = generate_dhe_keys(); |
|
1625 if (status != eap_status_ok) |
|
1626 { |
|
1627 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1628 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
1629 m_am_tools, |
|
1630 status); |
|
1631 } |
|
1632 } |
|
1633 else |
|
1634 { |
|
1635 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1636 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
1637 m_am_tools, |
|
1638 eap_status_authentication_failure); |
|
1639 } |
|
1640 } |
|
1641 else if (cipher_suite_is_TLS_RSA() == true) |
|
1642 { |
|
1643 // Do nothing special. |
|
1644 } |
|
1645 else |
|
1646 { |
|
1647 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1648 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
1649 m_am_tools, |
|
1650 eap_status_not_supported); |
|
1651 } |
|
1652 |
|
1653 // We must generate premaster secret. |
|
1654 status = generate_premaster_secret(); |
|
1655 if (status != eap_status_ok) |
|
1656 { |
|
1657 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1658 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1659 } |
|
1660 |
|
1661 // We must generate master secret. |
|
1662 status = generate_master_secret(); |
|
1663 if (status != eap_status_ok) |
|
1664 { |
|
1665 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1666 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1667 } |
|
1668 |
|
1669 // We must generate the key material. |
|
1670 status = generate_key_material(); |
|
1671 if (status != eap_status_ok) |
|
1672 { |
|
1673 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1674 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1675 } |
|
1676 |
|
1677 // We must send Handshake/ClientKeyExchange. |
|
1678 status = create_handshake_type_client_key_exchange(); |
|
1679 if (status == eap_status_pending_request) |
|
1680 { |
|
1681 // This is pending query, that will be completed by |
|
1682 // complete_create_handshake_type_client_key_exchange() call. |
|
1683 // Cannot complete yet. |
|
1684 continue_with_next_action = false; |
|
1685 } |
|
1686 else if (status == eap_status_completed_request) |
|
1687 { |
|
1688 // This is already completed by |
|
1689 // complete_create_handshake_type_client_key_exchange() call. |
|
1690 status = eap_status_ok; |
|
1691 } |
|
1692 else if (status == eap_status_ok) |
|
1693 { |
|
1694 // NOTE: This is not always an error case. |
|
1695 if (cipher_suite_is_TLS_DHE_DSS() == true |
|
1696 || cipher_suite_is_TLS_DHE_RSA() == true |
|
1697 #if defined(USE_FAST_EAP_TYPE) |
|
1698 || (m_eap_type == eap_type_fast |
|
1699 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true |
|
1700 && cipher_suite_is_TLS_DH_anon() == true) |
|
1701 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
1702 ) |
|
1703 { |
|
1704 // Cipher suites cipher_suite_is_TLS_DHE_DSS() |
|
1705 // and cipher_suite_is_TLS_DHE_RSA() are syncronous. |
|
1706 // Do nothing special. |
|
1707 } |
|
1708 else if (cipher_suite_is_TLS_RSA() == true) |
|
1709 { |
|
1710 // Cipher suites cipher_suite_is_TLS_RSA() are asyncronous |
|
1711 // and they must NOT return eap_status_ok. |
|
1712 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1713 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
1714 m_am_tools, |
|
1715 eap_status_process_general_error); |
|
1716 } |
|
1717 else |
|
1718 { |
|
1719 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1720 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
1721 m_am_tools, |
|
1722 eap_status_not_supported); |
|
1723 } |
|
1724 } |
|
1725 else // All other status values means error, because this |
|
1726 // call is always completed on success. |
|
1727 { |
|
1728 // This is an error case. |
|
1729 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1730 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1731 } |
|
1732 } |
|
1733 else |
|
1734 { |
|
1735 // Cannot complete yet. |
|
1736 continue_with_next_action = false; |
|
1737 } |
|
1738 break; |
|
1739 } |
|
1740 case tls_completion_action_create_handshake_type_finished: |
|
1741 { |
|
1742 // We must send Handshake/Finished. |
|
1743 status = create_handshake_type_finished(); |
|
1744 if (status != eap_status_ok) |
|
1745 { |
|
1746 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1747 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1748 } |
|
1749 break; |
|
1750 } |
|
1751 case tls_completion_action_finish_handshake: |
|
1752 { |
|
1753 // We must finish the handshake. |
|
1754 status = finish_handshake(); |
|
1755 if (status != eap_status_ok) |
|
1756 { |
|
1757 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1758 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1759 } |
|
1760 break; |
|
1761 } |
|
1762 case tls_completion_action_create_change_cipher_spec_type_change_cipher_spec: |
|
1763 { |
|
1764 // We must send ChangeCipherSpec/ChangeCipherSpec. |
|
1765 status = create_change_cipher_spec_type_change_cipher_spec(); |
|
1766 if (status != eap_status_ok) |
|
1767 { |
|
1768 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1769 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1770 } |
|
1771 break; |
|
1772 } |
|
1773 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
1774 case tls_completion_action_create_handshake_type_new_session_ticket: |
|
1775 { |
|
1776 // We must send Hanshake/NewSessionTicket. |
|
1777 status = create_handshake_type_new_session_ticket(); |
|
1778 if (status != eap_status_ok) |
|
1779 { |
|
1780 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1781 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1782 } |
|
1783 break; |
|
1784 } |
|
1785 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
1786 case tls_completion_action_query_dh_parameters: |
|
1787 { |
|
1788 if (m_selected_cipher_suite != tls_cipher_suites_none) |
|
1789 { |
|
1790 EAP_TRACE_DEBUG( |
|
1791 m_am_tools, |
|
1792 TRACE_FLAGS_DEFAULT, |
|
1793 (EAPL("TLS: %s: pki_function: query_dh_parameters()\n"), |
|
1794 (m_is_client == true ? "client": "server"))); |
|
1795 // Note, server does not query DH parametrs from certificate chain, |
|
1796 // instead server should consult it's configuration settings. |
|
1797 status = m_am_tls_services->query_dh_parameters(0, m_selected_cipher_suite); |
|
1798 if (status == eap_status_pending_request) |
|
1799 { |
|
1800 // This is pending query, that will be completed |
|
1801 // by complete_query_dh_parameters() call. |
|
1802 m_pending_query_dh_parameters = true; |
|
1803 } |
|
1804 else if (status == eap_status_completed_request) |
|
1805 { |
|
1806 // This is already completed by complete_query_dh_parameters() call. |
|
1807 status = eap_status_ok; |
|
1808 } |
|
1809 else if (status == eap_status_ok) |
|
1810 { |
|
1811 // This is also an error case, because this call |
|
1812 // is always completed on success. |
|
1813 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1814 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
1815 m_am_tools, |
|
1816 eap_status_process_general_error); |
|
1817 } |
|
1818 else // All other status values means error, because this |
|
1819 // call is always completed on success. |
|
1820 { |
|
1821 // This is an error case. |
|
1822 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1823 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1824 } |
|
1825 } |
|
1826 else |
|
1827 { |
|
1828 // Cannot complete yet. |
|
1829 continue_with_next_action = false; |
|
1830 } |
|
1831 break; |
|
1832 } |
|
1833 case tls_completion_action_process_tls_records: |
|
1834 { |
|
1835 if (are_pending_queries_completed() == eap_status_ok) |
|
1836 { |
|
1837 status = process_tls_records(); |
|
1838 if (status == eap_status_ok) |
|
1839 { |
|
1840 // All pending messages processed. |
|
1841 // Do nothing special. |
|
1842 } |
|
1843 else if (status == eap_status_end_recursion) |
|
1844 { |
|
1845 // Break recursion. |
|
1846 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1847 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, eap_status_ok); |
|
1848 } |
|
1849 else if (status == eap_status_pending_request) |
|
1850 { |
|
1851 // Cannot complete yet. |
|
1852 continue_with_next_action = false; |
|
1853 } |
|
1854 else |
|
1855 { |
|
1856 // This is an error case. |
|
1857 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1858 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1859 } |
|
1860 |
|
1861 if ((get_is_tunneled_tls() == false |
|
1862 && m_tls_peap_state == tls_peap_state_tls_success) |
|
1863 || (get_is_tunneled_tls() == true |
|
1864 && m_tls_peap_state == tls_peap_state_peap_tunnel_ready)) |
|
1865 { |
|
1866 // TLS authentication OK. |
|
1867 // Note PEAP may continue. |
|
1868 EAP_TRACE_DEBUG( |
|
1869 m_am_tools, |
|
1870 TRACE_FLAGS_DEFAULT, |
|
1871 (EAPL("TLS: %s: process_tls_records() returned, ") |
|
1872 EAPL("TLS authentication successfull.\n"), |
|
1873 (m_is_client == true ? "client": "server"))); |
|
1874 } |
|
1875 } |
|
1876 else |
|
1877 { |
|
1878 // Cannot complete yet. |
|
1879 continue_with_next_action = false; |
|
1880 } |
|
1881 break; |
|
1882 } |
|
1883 case tls_completion_action_complete_create_handshake_type_server_key_exchange: |
|
1884 { |
|
1885 if (m_signed_message_hash.get_is_valid_data() == true |
|
1886 #if defined(USE_FAST_EAP_TYPE) |
|
1887 || (m_eap_type == eap_type_fast |
|
1888 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true |
|
1889 && cipher_suite_is_TLS_DH_anon() == true) |
|
1890 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
1891 ) |
|
1892 { |
|
1893 status = complete_create_handshake_type_server_key_exchange(); |
|
1894 if (status != eap_status_ok) |
|
1895 { |
|
1896 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1897 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1898 } |
|
1899 } |
|
1900 else |
|
1901 { |
|
1902 // Cannot complete yet. |
|
1903 continue_with_next_action = false; |
|
1904 } |
|
1905 break; |
|
1906 } |
|
1907 case tls_completion_action_complete_create_handshake_type_certificate_verify: |
|
1908 { |
|
1909 if (m_signed_message_hash.get_is_valid_data() == true |
|
1910 && m_own_certificate_chain.get_object_count() > 0ul) |
|
1911 { |
|
1912 status = complete_create_handshake_type_certificate_verify(); |
|
1913 if (status != eap_status_ok) |
|
1914 { |
|
1915 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1916 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1917 } |
|
1918 } |
|
1919 else if (m_own_certificate_chain.get_object_count() == 0ul) |
|
1920 { |
|
1921 // No user certificate. |
|
1922 } |
|
1923 else |
|
1924 { |
|
1925 // Cannot complete yet. |
|
1926 continue_with_next_action = false; |
|
1927 } |
|
1928 break; |
|
1929 } |
|
1930 case tls_completion_action_complete_create_handshake_type_client_key_exchange: |
|
1931 { |
|
1932 if (cipher_suite_is_TLS_RSA() == true |
|
1933 && m_own_encrypted_premaster_secret.get_is_valid_data() == true |
|
1934 || ((cipher_suite_is_TLS_DHE_DSS() == true |
|
1935 || cipher_suite_is_TLS_DHE_RSA() == true |
|
1936 #if defined(USE_FAST_EAP_TYPE) |
|
1937 || (m_eap_type == eap_type_fast |
|
1938 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true |
|
1939 && cipher_suite_is_TLS_DH_anon() == true) |
|
1940 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
1941 ) |
|
1942 && m_own_encrypted_premaster_secret.get_is_valid_data() == false)) |
|
1943 { |
|
1944 status = complete_create_handshake_type_client_key_exchange(); |
|
1945 if (status != eap_status_ok) |
|
1946 { |
|
1947 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1948 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
1949 } |
|
1950 } |
|
1951 else |
|
1952 { |
|
1953 // Cannot complete yet. |
|
1954 continue_with_next_action = false; |
|
1955 } |
|
1956 break; |
|
1957 } |
|
1958 case tls_completion_action_verify_certificate_chain: |
|
1959 { |
|
1960 if (m_peer_certificate_chain.get_object_count() != 0ul |
|
1961 && m_selected_cipher_suite != tls_cipher_suites_none |
|
1962 && m_pending_query_certificate_chain == false |
|
1963 && m_pending_verify_certificate_chain == false) |
|
1964 { |
|
1965 EAP_TRACE_DEBUG( |
|
1966 m_am_tools, |
|
1967 TRACE_FLAGS_DEFAULT, |
|
1968 (EAPL("TLS: %s: pki_function: verify_certificate_chain()\n"), |
|
1969 (m_is_client == true ? "client": "server"))); |
|
1970 |
|
1971 status = m_am_tls_services->verify_certificate_chain( |
|
1972 &m_peer_certificate_chain, |
|
1973 m_selected_cipher_suite); |
|
1974 if (status == eap_status_pending_request) |
|
1975 { |
|
1976 // This is pending query, that will be completed |
|
1977 // by complete_verify_certificate_chain() call. |
|
1978 m_pending_verify_certificate_chain = true; |
|
1979 } |
|
1980 else if (status == eap_status_completed_request) |
|
1981 { |
|
1982 // This is already completed by complete_verify_certificate_chain() call. |
|
1983 status = eap_status_ok; |
|
1984 } |
|
1985 else if (status == eap_status_ok) |
|
1986 { |
|
1987 // This is also an error case, because this call is |
|
1988 // always completed on success. |
|
1989 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1990 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
1991 m_am_tools, |
|
1992 eap_status_process_general_error); |
|
1993 } |
|
1994 else // All other status values means error, because this |
|
1995 // call is always completed on success. |
|
1996 { |
|
1997 // This is an error case. |
|
1998 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
1999 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
2000 } |
|
2001 } |
|
2002 else |
|
2003 { |
|
2004 // Cannot complete yet. |
|
2005 continue_with_next_action = false; |
|
2006 } |
|
2007 break; |
|
2008 } |
|
2009 case tls_completion_action_check_sent_tls_message: |
|
2010 { |
|
2011 // Note this call will return eap_status_pending_request if any asyncronous call is pending. |
|
2012 status = check_sent_tls_message(); |
|
2013 break; |
|
2014 } |
|
2015 case tls_completion_action_check_tunnel_authentication_runs: |
|
2016 { |
|
2017 // Check we get some tunneled authentication message and tunneled authentication runs or it did finished. |
|
2018 if (m_tunneled_eap_type_authentication_state == eap_state_none) |
|
2019 { |
|
2020 // Here we swap the addresses. |
|
2021 eap_am_network_id_c receive_network_id(m_am_tools, |
|
2022 m_send_network_id.get_destination_id(), |
|
2023 m_send_network_id.get_source_id(), |
|
2024 m_send_network_id.get_type()); |
|
2025 |
|
2026 status = start_peap_tunneled_authentication( |
|
2027 &receive_network_id, |
|
2028 m_received_eap_identifier, |
|
2029 m_tls_session_type); |
|
2030 if (status != eap_status_ok) |
|
2031 { |
|
2032 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2033 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
2034 } |
|
2035 } |
|
2036 break; |
|
2037 } |
|
2038 default: |
|
2039 { |
|
2040 EAP_TRACE_ERROR( |
|
2041 m_am_tools, |
|
2042 TRACE_FLAGS_DEFAULT, |
|
2043 (EAPL("ERROR TLS: %s: send_function: completion_action_check(): ") |
|
2044 EAPL("unhandled action[%u] %s.\n"), |
|
2045 (m_is_client == true ? "client": "server"), |
|
2046 counter, |
|
2047 completion_action->get_completion_action_string())); |
|
2048 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
2049 m_am_tools, |
|
2050 eap_status_not_supported); |
|
2051 } |
|
2052 } // switch() |
|
2053 |
|
2054 if (continue_with_next_action == true |
|
2055 || status == eap_status_pending_request) |
|
2056 { |
|
2057 const tls_completion_c * const removed_completion_action = m_completion_queue.get_object(0ul); |
|
2058 EAP_UNREFERENCED_PARAMETER(removed_completion_action); // Not referenced without trace. |
|
2059 EAP_TRACE_DEBUG( |
|
2060 m_am_tools, |
|
2061 TRACE_FLAGS_DEFAULT, |
|
2062 (EAPL("TLS: %s: encrypt_function: starts: tls_record_c::completion_action_check(): removes action[%d] %s\n"), |
|
2063 (m_is_client == true ? "client": "server"), |
|
2064 0ul, |
|
2065 removed_completion_action->get_completion_action_string())); |
|
2066 |
|
2067 eap_status_e remove_status = m_completion_queue.remove_object(0ul); |
|
2068 if (remove_status != eap_status_ok) |
|
2069 { |
|
2070 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2071 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
2072 } |
|
2073 } |
|
2074 |
|
2075 ++counter; |
|
2076 |
|
2077 } // while() |
|
2078 |
|
2079 if (continue_with_next_action == false) |
|
2080 { |
|
2081 status = eap_status_pending_request; |
|
2082 } |
|
2083 |
|
2084 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2085 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
2086 } |
|
2087 |
|
2088 //-------------------------------------------------- |
|
2089 |
|
2090 // |
|
2091 EAP_FUNC_EXPORT u8_t tls_record_c::get_extra_padding_length( |
|
2092 const u8_t padding_length, |
|
2093 const u32_t block_size) |
|
2094 { |
|
2095 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2096 |
|
2097 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
2098 EAP_TRACE_DEBUG( |
|
2099 m_am_tools, |
|
2100 TRACE_FLAGS_DEFAULT, |
|
2101 (EAPL("TLS: %s: encrypt_function: starts: tls_record_c::get_extra_padding_length()\n"), |
|
2102 (m_is_client == true ? "client": "server"))); |
|
2103 |
|
2104 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::get_extra_padding_length()"); |
|
2105 |
|
2106 crypto_random_c rand(m_am_tools); |
|
2107 |
|
2108 u8_t count = 0ul; |
|
2109 |
|
2110 if (m_use_extra_padding_length == true) |
|
2111 { |
|
2112 eap_status_e status = rand.get_rand_bytes(&count, sizeof(count)); |
|
2113 if (status != eap_status_ok) |
|
2114 { |
|
2115 count = 3ul; |
|
2116 } |
|
2117 } |
|
2118 |
|
2119 u32_t final_padding_length = ((count * block_size) % 0xff) + padding_length; |
|
2120 |
|
2121 count = static_cast<u8_t>((final_padding_length-padding_length) / block_size); |
|
2122 |
|
2123 while (count > 0ul |
|
2124 && (count * block_size)+padding_length > 0xff) |
|
2125 { |
|
2126 --count; |
|
2127 } |
|
2128 |
|
2129 const u8_t final_length = static_cast<u8_t>((count * block_size)+padding_length); |
|
2130 |
|
2131 EAP_TRACE_DEBUG( |
|
2132 m_am_tools, |
|
2133 TRACE_FLAGS_DEFAULT, |
|
2134 (EAPL("TLS: %s: encrypt_function: get_extra_padding_length(): length = %d = 0x%02x\n"), |
|
2135 (m_is_client == true ? "client": "server"), |
|
2136 final_length, |
|
2137 final_length)); |
|
2138 |
|
2139 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2140 return final_length; |
|
2141 } |
|
2142 |
|
2143 //-------------------------------------------------- |
|
2144 |
|
2145 // |
|
2146 EAP_FUNC_EXPORT eap_status_e tls_record_c::apply_send_block_cipher_suite( |
|
2147 eap_variable_data_c * const tls_record_message_buffer, |
|
2148 abs_crypto_cbc_block_algorithm_c * const encrypt, |
|
2149 abs_crypto_hmac_algorithm_c * const mac) |
|
2150 { |
|
2151 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2152 |
|
2153 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
2154 EAP_TRACE_DEBUG( |
|
2155 m_am_tools, |
|
2156 TRACE_FLAGS_DEFAULT, |
|
2157 (EAPL("TLS: %s: send_function: starts: tls_record_c::apply_send_block_cipher_suite(): %s\n"), |
|
2158 (m_is_client == true ? "client": "server"), |
|
2159 eap_tls_trace_string_c::get_cipher_suite_string(m_send_cipher_suite))); |
|
2160 |
|
2161 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::apply_send_block_cipher_suite()"); |
|
2162 |
|
2163 eap_status_e status = eap_status_process_general_error; |
|
2164 |
|
2165 tls_record_header_c tmp_tls_record_header_on_tls_message_buffer( |
|
2166 m_am_tools, |
|
2167 tls_record_message_buffer->get_data(tls_record_header_c::get_header_length()), |
|
2168 tls_record_message_buffer->get_data_length()); |
|
2169 |
|
2170 if (tmp_tls_record_header_on_tls_message_buffer.get_is_valid() == false |
|
2171 || tls_record_message_buffer->get_data_length() |
|
2172 < tmp_tls_record_header_on_tls_message_buffer.get_header_length()) |
|
2173 { |
|
2174 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2175 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
2176 } |
|
2177 |
|
2178 EAP_TRACE_DATA_DEBUG( |
|
2179 m_am_tools, |
|
2180 TRACE_FLAGS_DEFAULT, |
|
2181 (EAPL("m_send_mac_key"), |
|
2182 m_send_mac_key.get_data(m_send_mac_key.get_data_length()), |
|
2183 m_send_mac_key.get_data_length())); |
|
2184 |
|
2185 status = mac->hmac_set_key(&m_send_mac_key); |
|
2186 if (status != eap_status_ok) |
|
2187 { |
|
2188 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2189 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2190 } |
|
2191 if (mac->get_is_valid() == false) |
|
2192 { |
|
2193 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2194 return EAP_STATUS_RETURN(m_am_tools, eap_status_key_error); |
|
2195 } |
|
2196 |
|
2197 u64_t send_record_sequence_number_network_order = eap_htonll(m_send_record_sequence_number); |
|
2198 |
|
2199 EAP_TRACE_DATA_DEBUG( |
|
2200 m_am_tools, |
|
2201 TRACE_FLAGS_DEFAULT, |
|
2202 (EAPL("send_record_sequence_number_network_order"), |
|
2203 &send_record_sequence_number_network_order, |
|
2204 sizeof(send_record_sequence_number_network_order))); |
|
2205 |
|
2206 status = mac->hmac_update( |
|
2207 &send_record_sequence_number_network_order, |
|
2208 sizeof(send_record_sequence_number_network_order)); |
|
2209 if (status != eap_status_ok) |
|
2210 { |
|
2211 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2212 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2213 } |
|
2214 |
|
2215 EAP_TRACE_DATA_DEBUG( |
|
2216 m_am_tools, |
|
2217 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
2218 (EAPL("verified record"), |
|
2219 tls_record_message_buffer->get_data(tls_record_message_buffer->get_data_length()), |
|
2220 tls_record_message_buffer->get_data_length())); |
|
2221 |
|
2222 status = mac->hmac_update( |
|
2223 tls_record_message_buffer->get_data(tls_record_message_buffer->get_data_length()), |
|
2224 tls_record_message_buffer->get_data_length()); |
|
2225 if (status != eap_status_ok) |
|
2226 { |
|
2227 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2228 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2229 } |
|
2230 |
|
2231 eap_variable_data_c mac_data(m_am_tools); |
|
2232 |
|
2233 status = mac_data.set_buffer_length(mac->get_digest_length()); |
|
2234 if (status != eap_status_ok) |
|
2235 { |
|
2236 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2237 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2238 } |
|
2239 mac_data.set_data_length(mac->get_digest_length()); |
|
2240 |
|
2241 u32_t mac_length = mac->get_digest_length(); |
|
2242 |
|
2243 status = mac->hmac_final( |
|
2244 mac_data.get_data(mac_data.get_data_length()), |
|
2245 &mac_length); |
|
2246 if (status != eap_status_ok) |
|
2247 { |
|
2248 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2249 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2250 } |
|
2251 else if (mac_length != mac->get_digest_length()) |
|
2252 { |
|
2253 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2254 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_parameter); |
|
2255 } |
|
2256 |
|
2257 EAP_TRACE_DATA_DEBUG( |
|
2258 m_am_tools, |
|
2259 TRACE_FLAGS_DEFAULT, |
|
2260 (EAPL("send MAC"), |
|
2261 mac_data.get_data(mac_data.get_data_length()), |
|
2262 mac_data.get_data_length())); |
|
2263 |
|
2264 status = tls_record_message_buffer->add_data(&mac_data); |
|
2265 if (status != eap_status_ok) |
|
2266 { |
|
2267 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2268 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2269 } |
|
2270 |
|
2271 // We must get the address of the record header again. A new buffer may be allocated. |
|
2272 tmp_tls_record_header_on_tls_message_buffer.set_header_buffer( |
|
2273 tls_record_message_buffer->get_data(tls_record_header_c::get_header_length()), |
|
2274 tls_record_message_buffer->get_data_length()); |
|
2275 |
|
2276 if (tmp_tls_record_header_on_tls_message_buffer.get_is_valid() == false |
|
2277 || tls_record_message_buffer->get_data_length() |
|
2278 < tmp_tls_record_header_on_tls_message_buffer.get_header_length()) |
|
2279 { |
|
2280 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2281 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
2282 } |
|
2283 |
|
2284 tmp_tls_record_header_on_tls_message_buffer.set_data_length( |
|
2285 static_cast<u16_t>( |
|
2286 tmp_tls_record_header_on_tls_message_buffer.get_data_length() |
|
2287 + mac->get_digest_length())); |
|
2288 |
|
2289 |
|
2290 u32_t padded_data_length = encrypt->aligned_data_length( |
|
2291 tmp_tls_record_header_on_tls_message_buffer.get_data_length()); |
|
2292 u8_t padding_length = static_cast<u8_t>( |
|
2293 padded_data_length-tmp_tls_record_header_on_tls_message_buffer.get_data_length()); |
|
2294 |
|
2295 padding_length = get_extra_padding_length(padding_length, encrypt->get_block_size()); |
|
2296 |
|
2297 eap_variable_data_c padding(m_am_tools); |
|
2298 status = padding.set_buffer_length(padding_length); |
|
2299 if (status != eap_status_ok) |
|
2300 { |
|
2301 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2302 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2303 } |
|
2304 padding.set_data_length(padding_length); |
|
2305 |
|
2306 status = encrypt->add_padding_bytes( |
|
2307 padding.get_data(padding.get_data_length()), |
|
2308 padding.get_data_length(), |
|
2309 static_cast<u8_t>(padding_length-1ul)); |
|
2310 if (status != eap_status_ok) |
|
2311 { |
|
2312 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2313 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2314 } |
|
2315 |
|
2316 status = tls_record_message_buffer->add_data(&padding); |
|
2317 if (status != eap_status_ok) |
|
2318 { |
|
2319 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2320 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2321 } |
|
2322 |
|
2323 // We must get the address of the record header again. A new buffer may be allocated. |
|
2324 tmp_tls_record_header_on_tls_message_buffer.set_header_buffer( |
|
2325 tls_record_message_buffer->get_data(tls_record_header_c::get_header_length()), |
|
2326 tls_record_message_buffer->get_data_length()); |
|
2327 |
|
2328 if (tmp_tls_record_header_on_tls_message_buffer.get_is_valid() == false |
|
2329 || tls_record_message_buffer->get_data_length() |
|
2330 < tmp_tls_record_header_on_tls_message_buffer.get_header_length()) |
|
2331 { |
|
2332 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2333 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
2334 } |
|
2335 |
|
2336 tmp_tls_record_header_on_tls_message_buffer.set_data_length( |
|
2337 static_cast<u16_t>( |
|
2338 tmp_tls_record_header_on_tls_message_buffer.get_data_length() |
|
2339 + padding_length)); |
|
2340 |
|
2341 EAP_TRACE_DATA_DEBUG( |
|
2342 m_am_tools, |
|
2343 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
2344 (EAPL("plain text record"), |
|
2345 tls_record_message_buffer->get_data(tls_record_message_buffer->get_data_length()), |
|
2346 tls_record_message_buffer->get_data_length())); |
|
2347 |
|
2348 status = encrypt->encrypt_data( |
|
2349 tmp_tls_record_header_on_tls_message_buffer.get_data( |
|
2350 tmp_tls_record_header_on_tls_message_buffer.get_data_length()), |
|
2351 tmp_tls_record_header_on_tls_message_buffer.get_data_length()); |
|
2352 if (status != eap_status_ok) |
|
2353 { |
|
2354 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2355 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2356 } |
|
2357 |
|
2358 EAP_TRACE_DATA_DEBUG( |
|
2359 m_am_tools, |
|
2360 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
2361 (EAPL("encrypted record"), |
|
2362 tls_record_message_buffer->get_data(tls_record_message_buffer->get_data_length()), |
|
2363 tls_record_message_buffer->get_data_length())); |
|
2364 |
|
2365 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2366 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2367 } |
|
2368 |
|
2369 //-------------------------------------------------- |
|
2370 |
|
2371 // |
|
2372 EAP_FUNC_EXPORT eap_status_e tls_record_c::apply_receive_block_cipher_suite( |
|
2373 eap_variable_data_c * const tls_record_message_buffer, |
|
2374 abs_crypto_cbc_block_algorithm_c * const encrypt, |
|
2375 abs_crypto_hmac_algorithm_c * const mac) |
|
2376 { |
|
2377 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2378 |
|
2379 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
2380 EAP_TRACE_DEBUG( |
|
2381 m_am_tools, |
|
2382 TRACE_FLAGS_DEFAULT, |
|
2383 (EAPL("TLS: %s: receive_function: starts: tls_record_c::apply_receive_block_cipher_suite(): %s\n"), |
|
2384 (m_is_client == true ? "client": "server"), |
|
2385 eap_tls_trace_string_c::get_cipher_suite_string(m_receive_cipher_suite))); |
|
2386 |
|
2387 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::apply_receive_block_cipher_suite()"); |
|
2388 |
|
2389 eap_status_e status = eap_status_process_general_error; |
|
2390 |
|
2391 tls_record_header_c tmp_tls_record_header_on_tls_message_buffer( |
|
2392 m_am_tools, |
|
2393 tls_record_message_buffer->get_data(tls_record_header_c::get_header_length()), |
|
2394 tls_record_message_buffer->get_data_length()); |
|
2395 |
|
2396 if (tmp_tls_record_header_on_tls_message_buffer.get_is_valid() == false |
|
2397 || tls_record_message_buffer->get_data_length() |
|
2398 < tmp_tls_record_header_on_tls_message_buffer.get_header_length()) |
|
2399 { |
|
2400 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2401 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
2402 } |
|
2403 |
|
2404 EAP_TRACE_DATA_DEBUG( |
|
2405 m_am_tools, |
|
2406 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
2407 (EAPL("encrypted record"), |
|
2408 tls_record_message_buffer->get_data(tls_record_message_buffer->get_data_length()), |
|
2409 tls_record_message_buffer->get_data_length())); |
|
2410 |
|
2411 status = encrypt->decrypt_data( |
|
2412 tmp_tls_record_header_on_tls_message_buffer.get_data( |
|
2413 tmp_tls_record_header_on_tls_message_buffer.get_data_length()), |
|
2414 tmp_tls_record_header_on_tls_message_buffer.get_data_length()); |
|
2415 if (status != eap_status_ok) |
|
2416 { |
|
2417 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2418 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2419 } |
|
2420 |
|
2421 EAP_TRACE_DATA_DEBUG( |
|
2422 m_am_tools, |
|
2423 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
2424 (EAPL("plain text record"), |
|
2425 tls_record_message_buffer->get_data(tls_record_message_buffer->get_data_length()), |
|
2426 tls_record_message_buffer->get_data_length())); |
|
2427 |
|
2428 // We must get the address of the record header again. A new buffer may be allocated. |
|
2429 tmp_tls_record_header_on_tls_message_buffer.set_header_buffer( |
|
2430 tls_record_message_buffer->get_data(tls_record_header_c::get_header_length()), |
|
2431 tls_record_message_buffer->get_data_length()); |
|
2432 |
|
2433 if (tmp_tls_record_header_on_tls_message_buffer.get_is_valid() == false |
|
2434 || tls_record_message_buffer->get_data_length() |
|
2435 < tmp_tls_record_header_on_tls_message_buffer.get_header_length()) |
|
2436 { |
|
2437 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2438 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
2439 } |
|
2440 |
|
2441 u32_t padding_length_offset |
|
2442 = tmp_tls_record_header_on_tls_message_buffer.get_data_length() - 1ul; |
|
2443 const u8_t * const p_padding_length |
|
2444 = tmp_tls_record_header_on_tls_message_buffer.get_data_offset(padding_length_offset, |
|
2445 TLS_PADDINF_LENGTH_FIELD_SIZE); |
|
2446 |
|
2447 if (p_padding_length == 0 |
|
2448 || (*p_padding_length)+1ul > tmp_tls_record_header_on_tls_message_buffer.get_data_length()) |
|
2449 { |
|
2450 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2451 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_padding); |
|
2452 } |
|
2453 |
|
2454 u32_t padding_length = (*p_padding_length) + 1ul; |
|
2455 |
|
2456 const u8_t * const p_padding |
|
2457 = tmp_tls_record_header_on_tls_message_buffer.get_data_offset( |
|
2458 tmp_tls_record_header_on_tls_message_buffer.get_data_length() - padding_length, |
|
2459 padding_length); |
|
2460 if (p_padding == 0) |
|
2461 { |
|
2462 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2463 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_padding); |
|
2464 } |
|
2465 |
|
2466 eap_status_e padding_status = encrypt->check_padding_bytes( |
|
2467 p_padding, |
|
2468 *p_padding_length, |
|
2469 *p_padding_length); |
|
2470 if (padding_status != eap_status_ok) |
|
2471 { |
|
2472 // NOTE, padding_status is checked in the end of this function. |
|
2473 // HMAC is checked always. |
|
2474 // We set the padding length to zero, so the end of the message is used as a MAC. |
|
2475 // This will fail anyway. |
|
2476 // This will make some timing attacks more difficult. |
|
2477 padding_length = 0ul; |
|
2478 } |
|
2479 |
|
2480 |
|
2481 |
|
2482 tmp_tls_record_header_on_tls_message_buffer.set_data_length( |
|
2483 static_cast<u16_t>( |
|
2484 tmp_tls_record_header_on_tls_message_buffer.get_data_length() - padding_length)); |
|
2485 |
|
2486 tls_record_message_buffer->set_data_length( |
|
2487 tls_record_message_buffer->get_data_length() |
|
2488 - padding_length); |
|
2489 |
|
2490 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
2491 |
|
2492 // HMAC-XXX authentication. |
|
2493 |
|
2494 EAP_TRACE_DATA_DEBUG( |
|
2495 m_am_tools, |
|
2496 TRACE_FLAGS_DEFAULT, |
|
2497 (EAPL("m_receive_mac_key"), |
|
2498 m_receive_mac_key.get_data(m_receive_mac_key.get_data_length()), |
|
2499 m_receive_mac_key.get_data_length())); |
|
2500 |
|
2501 status = mac->hmac_set_key(&m_receive_mac_key); |
|
2502 if (status != eap_status_ok) |
|
2503 { |
|
2504 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2505 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2506 } |
|
2507 if (mac->get_is_valid() == false) |
|
2508 { |
|
2509 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2510 return EAP_STATUS_RETURN(m_am_tools, eap_status_key_error); |
|
2511 } |
|
2512 |
|
2513 if (tls_record_message_buffer->get_data_length() |
|
2514 < (tmp_tls_record_header_on_tls_message_buffer.get_data_length() |
|
2515 + tmp_tls_record_header_on_tls_message_buffer.get_header_length())) |
|
2516 { |
|
2517 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2518 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
2519 } |
|
2520 |
|
2521 if (tmp_tls_record_header_on_tls_message_buffer.get_data_length() < mac->get_digest_length()) |
|
2522 { |
|
2523 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2524 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
2525 } |
|
2526 |
|
2527 u32_t start_offset_of_mac |
|
2528 = tmp_tls_record_header_on_tls_message_buffer.get_data_length() |
|
2529 - mac->get_digest_length(); |
|
2530 |
|
2531 const u8_t * const received_mac |
|
2532 = tmp_tls_record_header_on_tls_message_buffer.get_data_offset( |
|
2533 start_offset_of_mac, |
|
2534 mac->get_digest_length()); |
|
2535 if (received_mac == 0) |
|
2536 { |
|
2537 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2538 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
2539 } |
|
2540 |
|
2541 EAP_TRACE_DATA_DEBUG( |
|
2542 m_am_tools, |
|
2543 TRACE_FLAGS_DEFAULT, |
|
2544 (EAPL("received MAC"), |
|
2545 received_mac, |
|
2546 mac->get_digest_length())); |
|
2547 |
|
2548 tmp_tls_record_header_on_tls_message_buffer.set_data_length( |
|
2549 static_cast<u16_t>(tmp_tls_record_header_on_tls_message_buffer.get_data_length() |
|
2550 - mac->get_digest_length())); |
|
2551 |
|
2552 u64_t receive_record_sequence_number_network_order |
|
2553 = eap_htonll(m_receive_record_sequence_number); |
|
2554 |
|
2555 EAP_TRACE_DATA_DEBUG( |
|
2556 m_am_tools, |
|
2557 TRACE_FLAGS_DEFAULT, |
|
2558 (EAPL("receive_record_sequence_number_network_order"), |
|
2559 &receive_record_sequence_number_network_order, |
|
2560 sizeof(receive_record_sequence_number_network_order))); |
|
2561 |
|
2562 status = mac->hmac_update( |
|
2563 &receive_record_sequence_number_network_order, |
|
2564 sizeof(receive_record_sequence_number_network_order)); |
|
2565 if (status != eap_status_ok) |
|
2566 { |
|
2567 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2568 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2569 } |
|
2570 |
|
2571 EAP_TRACE_DATA_DEBUG( |
|
2572 m_am_tools, |
|
2573 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
2574 (EAPL("verified record"), |
|
2575 tmp_tls_record_header_on_tls_message_buffer.get_header_buffer( |
|
2576 tmp_tls_record_header_on_tls_message_buffer.get_header_length() |
|
2577 + tmp_tls_record_header_on_tls_message_buffer.get_data_length()), |
|
2578 tmp_tls_record_header_on_tls_message_buffer.get_header_length() |
|
2579 + tmp_tls_record_header_on_tls_message_buffer.get_data_length())); |
|
2580 |
|
2581 status = mac->hmac_update( |
|
2582 tmp_tls_record_header_on_tls_message_buffer.get_header_buffer( |
|
2583 tmp_tls_record_header_on_tls_message_buffer.get_header_length() |
|
2584 + tmp_tls_record_header_on_tls_message_buffer.get_data_length()), |
|
2585 tmp_tls_record_header_on_tls_message_buffer.get_header_length() |
|
2586 + tmp_tls_record_header_on_tls_message_buffer.get_data_length()); |
|
2587 if (status != eap_status_ok) |
|
2588 { |
|
2589 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2590 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2591 } |
|
2592 |
|
2593 eap_variable_data_c mac_data(m_am_tools); |
|
2594 |
|
2595 status = mac_data.set_buffer_length(mac->get_digest_length()); |
|
2596 if (status != eap_status_ok) |
|
2597 { |
|
2598 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2599 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2600 } |
|
2601 mac_data.set_data_length(mac->get_digest_length()); |
|
2602 |
|
2603 u32_t mac_length = mac->get_digest_length(); |
|
2604 |
|
2605 status = mac->hmac_final( |
|
2606 mac_data.get_data(mac_data.get_data_length()), |
|
2607 &mac_length); |
|
2608 if (status != eap_status_ok) |
|
2609 { |
|
2610 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2611 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2612 } |
|
2613 else if (mac_length != mac->get_digest_length()) |
|
2614 { |
|
2615 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2616 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_parameter); |
|
2617 } |
|
2618 |
|
2619 EAP_TRACE_DATA_DEBUG( |
|
2620 m_am_tools, |
|
2621 TRACE_FLAGS_DEFAULT, |
|
2622 (EAPL("verify MAC"), |
|
2623 mac_data.get_data(mac_data.get_data_length()), |
|
2624 mac_data.get_data_length())); |
|
2625 |
|
2626 if (padding_status != eap_status_ok) |
|
2627 { |
|
2628 EAP_TRACE_ERROR( |
|
2629 m_am_tools, |
|
2630 TRACE_FLAGS_DEFAULT, |
|
2631 (EAPL("TLS: ERROR: %s: receive_function: apply_receive_cipher_suite(): ") |
|
2632 EAPL("padding failed\n"), |
|
2633 (m_is_client == true ? "client": "server"))); |
|
2634 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2635 return EAP_STATUS_RETURN(m_am_tools, padding_status); |
|
2636 } |
|
2637 else if (m_am_tools->memcmp( |
|
2638 mac_data.get_data(mac_data.get_data_length()), |
|
2639 received_mac, |
|
2640 mac_data.get_data_length()) != 0) |
|
2641 { |
|
2642 EAP_TRACE_ERROR( |
|
2643 m_am_tools, |
|
2644 TRACE_FLAGS_DEFAULT, |
|
2645 (EAPL("TLS: ERROR: %s: receive_function: apply_receive_cipher_suite(): MAC failed\n"), |
|
2646 (m_is_client == true ? "client": "server"))); |
|
2647 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2648 return EAP_STATUS_RETURN(m_am_tools, eap_status_authentication_failure); |
|
2649 } |
|
2650 else |
|
2651 { |
|
2652 EAP_TRACE_ALWAYS( |
|
2653 m_am_tools, |
|
2654 TRACE_FLAGS_DEFAULT, |
|
2655 (EAPL("TLS: %s: receive_function: apply_receive_cipher_suite(): MAC OK\n"), |
|
2656 (m_is_client == true ? "client": "server"))); |
|
2657 } |
|
2658 |
|
2659 tls_record_message_buffer->set_data_length( |
|
2660 tls_record_message_buffer->get_data_length() |
|
2661 - mac->get_digest_length()); |
|
2662 |
|
2663 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2664 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2665 } |
|
2666 |
|
2667 //-------------------------------------------------- |
|
2668 |
|
2669 // |
|
2670 EAP_FUNC_EXPORT eap_status_e tls_record_c::apply_send_stream_cipher_suite( |
|
2671 eap_variable_data_c * const tls_record_message_buffer, |
|
2672 abs_crypto_stream_algorithm_c * const encrypt, |
|
2673 abs_crypto_hmac_algorithm_c * const mac) |
|
2674 { |
|
2675 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2676 |
|
2677 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
2678 EAP_TRACE_DEBUG( |
|
2679 m_am_tools, |
|
2680 TRACE_FLAGS_DEFAULT, |
|
2681 (EAPL("TLS: %s: send_function: starts: tls_record_c::apply_send_stream_cipher_suite(): %s\n"), |
|
2682 (m_is_client == true ? "client": "server"), |
|
2683 eap_tls_trace_string_c::get_cipher_suite_string(m_send_cipher_suite))); |
|
2684 |
|
2685 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::apply_send_stream_cipher_suite()"); |
|
2686 |
|
2687 eap_status_e status = eap_status_process_general_error; |
|
2688 |
|
2689 tls_record_header_c tmp_tls_record_header_on_tls_message_buffer( |
|
2690 m_am_tools, |
|
2691 tls_record_message_buffer->get_data(tls_record_header_c::get_header_length()), |
|
2692 tls_record_message_buffer->get_data_length()); |
|
2693 |
|
2694 if (tmp_tls_record_header_on_tls_message_buffer.get_is_valid() == false |
|
2695 || tls_record_message_buffer->get_data_length() |
|
2696 < tmp_tls_record_header_on_tls_message_buffer.get_header_length()) |
|
2697 { |
|
2698 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2699 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
2700 } |
|
2701 |
|
2702 EAP_TRACE_DATA_DEBUG( |
|
2703 m_am_tools, |
|
2704 TRACE_FLAGS_DEFAULT, |
|
2705 (EAPL("m_send_mac_key"), |
|
2706 m_send_mac_key.get_data(m_send_mac_key.get_data_length()), |
|
2707 m_send_mac_key.get_data_length())); |
|
2708 |
|
2709 status = mac->hmac_set_key(&m_send_mac_key); |
|
2710 if (status != eap_status_ok) |
|
2711 { |
|
2712 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2713 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2714 } |
|
2715 if (mac->get_is_valid() == false) |
|
2716 { |
|
2717 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2718 return EAP_STATUS_RETURN(m_am_tools, eap_status_key_error); |
|
2719 } |
|
2720 |
|
2721 u64_t send_record_sequence_number_network_order = eap_htonll(m_send_record_sequence_number); |
|
2722 |
|
2723 EAP_TRACE_DATA_DEBUG( |
|
2724 m_am_tools, |
|
2725 TRACE_FLAGS_DEFAULT, |
|
2726 (EAPL("send_record_sequence_number_network_order"), |
|
2727 &send_record_sequence_number_network_order, |
|
2728 sizeof(send_record_sequence_number_network_order))); |
|
2729 |
|
2730 status = mac->hmac_update( |
|
2731 &send_record_sequence_number_network_order, |
|
2732 sizeof(send_record_sequence_number_network_order)); |
|
2733 if (status != eap_status_ok) |
|
2734 { |
|
2735 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2736 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2737 } |
|
2738 |
|
2739 EAP_TRACE_DATA_DEBUG( |
|
2740 m_am_tools, |
|
2741 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
2742 (EAPL("verified record"), |
|
2743 tls_record_message_buffer->get_data(tls_record_message_buffer->get_data_length()), |
|
2744 tls_record_message_buffer->get_data_length())); |
|
2745 |
|
2746 status = mac->hmac_update( |
|
2747 tls_record_message_buffer->get_data(tls_record_message_buffer->get_data_length()), |
|
2748 tls_record_message_buffer->get_data_length()); |
|
2749 if (status != eap_status_ok) |
|
2750 { |
|
2751 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2752 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2753 } |
|
2754 |
|
2755 eap_variable_data_c mac_data(m_am_tools); |
|
2756 |
|
2757 status = mac_data.set_buffer_length(mac->get_digest_length()); |
|
2758 if (status != eap_status_ok) |
|
2759 { |
|
2760 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2761 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2762 } |
|
2763 mac_data.set_data_length(mac->get_digest_length()); |
|
2764 |
|
2765 u32_t mac_length = mac->get_digest_length(); |
|
2766 |
|
2767 status = mac->hmac_final( |
|
2768 mac_data.get_data(mac_data.get_data_length()), |
|
2769 &mac_length); |
|
2770 if (status != eap_status_ok) |
|
2771 { |
|
2772 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2773 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2774 } |
|
2775 else if (mac_length != mac->get_digest_length()) |
|
2776 { |
|
2777 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2778 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_parameter); |
|
2779 } |
|
2780 |
|
2781 EAP_TRACE_DATA_DEBUG( |
|
2782 m_am_tools, |
|
2783 TRACE_FLAGS_DEFAULT, |
|
2784 (EAPL("send MAC"), |
|
2785 mac_data.get_data(mac_data.get_data_length()), |
|
2786 mac_data.get_data_length())); |
|
2787 |
|
2788 status = tls_record_message_buffer->add_data(&mac_data); |
|
2789 if (status != eap_status_ok) |
|
2790 { |
|
2791 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2792 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2793 } |
|
2794 |
|
2795 // We must get the address of the record header again. A new buffer may be allocated. |
|
2796 tmp_tls_record_header_on_tls_message_buffer.set_header_buffer( |
|
2797 tls_record_message_buffer->get_data(tls_record_header_c::get_header_length()), |
|
2798 tls_record_message_buffer->get_data_length()); |
|
2799 |
|
2800 if (tmp_tls_record_header_on_tls_message_buffer.get_is_valid() == false |
|
2801 || tls_record_message_buffer->get_data_length() |
|
2802 < tmp_tls_record_header_on_tls_message_buffer.get_header_length()) |
|
2803 { |
|
2804 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2805 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
2806 } |
|
2807 |
|
2808 tmp_tls_record_header_on_tls_message_buffer.set_data_length( |
|
2809 static_cast<u16_t>( |
|
2810 tmp_tls_record_header_on_tls_message_buffer.get_data_length() |
|
2811 + mac->get_digest_length())); |
|
2812 |
|
2813 EAP_TRACE_DATA_DEBUG( |
|
2814 m_am_tools, |
|
2815 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
2816 (EAPL("plain text record"), |
|
2817 tls_record_message_buffer->get_data(tls_record_message_buffer->get_data_length()), |
|
2818 tls_record_message_buffer->get_data_length())); |
|
2819 |
|
2820 status = encrypt->encrypt_data( |
|
2821 tmp_tls_record_header_on_tls_message_buffer.get_data( |
|
2822 tmp_tls_record_header_on_tls_message_buffer.get_data_length()), |
|
2823 tmp_tls_record_header_on_tls_message_buffer.get_data_length()); |
|
2824 if (status != eap_status_ok) |
|
2825 { |
|
2826 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2827 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2828 } |
|
2829 |
|
2830 EAP_TRACE_DATA_DEBUG( |
|
2831 m_am_tools, |
|
2832 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
2833 (EAPL("encrypted record"), |
|
2834 tls_record_message_buffer->get_data(tls_record_message_buffer->get_data_length()), |
|
2835 tls_record_message_buffer->get_data_length())); |
|
2836 |
|
2837 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2838 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2839 } |
|
2840 |
|
2841 //-------------------------------------------------- |
|
2842 |
|
2843 // |
|
2844 EAP_FUNC_EXPORT eap_status_e tls_record_c::apply_receive_stream_cipher_suite( |
|
2845 eap_variable_data_c * const tls_record_message_buffer, |
|
2846 abs_crypto_stream_algorithm_c * const encrypt, |
|
2847 abs_crypto_hmac_algorithm_c * const mac) |
|
2848 { |
|
2849 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2850 |
|
2851 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
2852 EAP_TRACE_DEBUG( |
|
2853 m_am_tools, |
|
2854 TRACE_FLAGS_DEFAULT, |
|
2855 (EAPL("TLS: %s: receive_function: starts: tls_record_c::apply_receive_block_cipher_suite(): %s\n"), |
|
2856 (m_is_client == true ? "client": "server"), |
|
2857 eap_tls_trace_string_c::get_cipher_suite_string(m_receive_cipher_suite))); |
|
2858 |
|
2859 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::apply_receive_stream_cipher_suite()"); |
|
2860 |
|
2861 eap_status_e status = eap_status_process_general_error; |
|
2862 |
|
2863 tls_record_header_c tmp_tls_record_header_on_tls_message_buffer( |
|
2864 m_am_tools, |
|
2865 tls_record_message_buffer->get_data(tls_record_header_c::get_header_length()), |
|
2866 tls_record_message_buffer->get_data_length()); |
|
2867 |
|
2868 if (tmp_tls_record_header_on_tls_message_buffer.get_is_valid() == false |
|
2869 || tls_record_message_buffer->get_data_length() |
|
2870 < tmp_tls_record_header_on_tls_message_buffer.get_header_length()) |
|
2871 { |
|
2872 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2873 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
2874 } |
|
2875 |
|
2876 EAP_TRACE_DATA_DEBUG( |
|
2877 m_am_tools, |
|
2878 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
2879 (EAPL("encrypted record"), |
|
2880 tls_record_message_buffer->get_data(tls_record_message_buffer->get_data_length()), |
|
2881 tls_record_message_buffer->get_data_length())); |
|
2882 |
|
2883 status = encrypt->decrypt_data( |
|
2884 tmp_tls_record_header_on_tls_message_buffer.get_data( |
|
2885 tmp_tls_record_header_on_tls_message_buffer.get_data_length()), |
|
2886 tmp_tls_record_header_on_tls_message_buffer.get_data_length()); |
|
2887 if (status != eap_status_ok) |
|
2888 { |
|
2889 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2890 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2891 } |
|
2892 |
|
2893 EAP_TRACE_DATA_DEBUG( |
|
2894 m_am_tools, |
|
2895 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
2896 (EAPL("plain text record"), |
|
2897 tls_record_message_buffer->get_data(tls_record_message_buffer->get_data_length()), |
|
2898 tls_record_message_buffer->get_data_length())); |
|
2899 |
|
2900 tls_record_message_buffer->set_data_length( |
|
2901 tls_record_message_buffer->get_data_length()); |
|
2902 |
|
2903 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
2904 |
|
2905 // HMAC-SHA1 authentication. |
|
2906 |
|
2907 EAP_TRACE_DATA_DEBUG( |
|
2908 m_am_tools, |
|
2909 TRACE_FLAGS_DEFAULT, |
|
2910 (EAPL("m_receive_mac_key"), |
|
2911 m_receive_mac_key.get_data(m_receive_mac_key.get_data_length()), |
|
2912 m_receive_mac_key.get_data_length())); |
|
2913 |
|
2914 status = mac->hmac_set_key(&m_receive_mac_key); |
|
2915 if (status != eap_status_ok) |
|
2916 { |
|
2917 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2918 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2919 } |
|
2920 if (mac->get_is_valid() == false) |
|
2921 { |
|
2922 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2923 return EAP_STATUS_RETURN(m_am_tools, eap_status_key_error); |
|
2924 } |
|
2925 |
|
2926 if (tls_record_message_buffer->get_data_length() |
|
2927 < (tmp_tls_record_header_on_tls_message_buffer.get_data_length() |
|
2928 + tmp_tls_record_header_on_tls_message_buffer.get_header_length())) |
|
2929 { |
|
2930 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2931 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
2932 } |
|
2933 |
|
2934 if (tmp_tls_record_header_on_tls_message_buffer.get_data_length() < mac->get_digest_length()) |
|
2935 { |
|
2936 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2937 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
2938 } |
|
2939 |
|
2940 u32_t start_offset_of_mac |
|
2941 = tmp_tls_record_header_on_tls_message_buffer.get_data_length() |
|
2942 - mac->get_digest_length(); |
|
2943 |
|
2944 const u8_t * const received_mac |
|
2945 = tmp_tls_record_header_on_tls_message_buffer.get_data_offset( |
|
2946 start_offset_of_mac, |
|
2947 mac->get_digest_length()); |
|
2948 if (received_mac == 0) |
|
2949 { |
|
2950 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2951 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
2952 } |
|
2953 |
|
2954 EAP_TRACE_DATA_DEBUG( |
|
2955 m_am_tools, |
|
2956 TRACE_FLAGS_DEFAULT, |
|
2957 (EAPL("received MAC"), |
|
2958 received_mac, |
|
2959 mac->get_digest_length())); |
|
2960 |
|
2961 tmp_tls_record_header_on_tls_message_buffer.set_data_length( |
|
2962 static_cast<u16_t>(tmp_tls_record_header_on_tls_message_buffer.get_data_length() |
|
2963 - mac->get_digest_length())); |
|
2964 |
|
2965 u64_t receive_record_sequence_number_network_order |
|
2966 = eap_htonll(m_receive_record_sequence_number); |
|
2967 |
|
2968 EAP_TRACE_DATA_DEBUG( |
|
2969 m_am_tools, |
|
2970 TRACE_FLAGS_DEFAULT, |
|
2971 (EAPL("receive_record_sequence_number_network_order"), |
|
2972 &receive_record_sequence_number_network_order, |
|
2973 sizeof(receive_record_sequence_number_network_order))); |
|
2974 |
|
2975 status = mac->hmac_update( |
|
2976 &receive_record_sequence_number_network_order, |
|
2977 sizeof(receive_record_sequence_number_network_order)); |
|
2978 if (status != eap_status_ok) |
|
2979 { |
|
2980 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
2981 return EAP_STATUS_RETURN(m_am_tools, status); |
|
2982 } |
|
2983 |
|
2984 EAP_TRACE_DATA_DEBUG( |
|
2985 m_am_tools, |
|
2986 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
2987 (EAPL("verified record"), |
|
2988 tmp_tls_record_header_on_tls_message_buffer.get_header_buffer( |
|
2989 tmp_tls_record_header_on_tls_message_buffer.get_header_length() |
|
2990 + tmp_tls_record_header_on_tls_message_buffer.get_data_length()), |
|
2991 tmp_tls_record_header_on_tls_message_buffer.get_header_length() |
|
2992 + tmp_tls_record_header_on_tls_message_buffer.get_data_length())); |
|
2993 |
|
2994 status = mac->hmac_update( |
|
2995 tmp_tls_record_header_on_tls_message_buffer.get_header_buffer( |
|
2996 tmp_tls_record_header_on_tls_message_buffer.get_header_length() |
|
2997 + tmp_tls_record_header_on_tls_message_buffer.get_data_length()), |
|
2998 tmp_tls_record_header_on_tls_message_buffer.get_header_length() |
|
2999 + tmp_tls_record_header_on_tls_message_buffer.get_data_length()); |
|
3000 if (status != eap_status_ok) |
|
3001 { |
|
3002 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3003 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3004 } |
|
3005 |
|
3006 eap_variable_data_c mac_data(m_am_tools); |
|
3007 |
|
3008 status = mac_data.set_buffer_length(mac->get_digest_length()); |
|
3009 if (status != eap_status_ok) |
|
3010 { |
|
3011 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3012 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3013 } |
|
3014 mac_data.set_data_length(mac->get_digest_length()); |
|
3015 |
|
3016 u32_t mac_length = mac->get_digest_length(); |
|
3017 |
|
3018 status = mac->hmac_final( |
|
3019 mac_data.get_data(mac_data.get_data_length()), |
|
3020 &mac_length); |
|
3021 if (status != eap_status_ok) |
|
3022 { |
|
3023 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3024 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3025 } |
|
3026 else if (mac_length != mac->get_digest_length()) |
|
3027 { |
|
3028 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3029 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_parameter); |
|
3030 } |
|
3031 |
|
3032 EAP_TRACE_DATA_DEBUG( |
|
3033 m_am_tools, |
|
3034 TRACE_FLAGS_DEFAULT, |
|
3035 (EAPL("verify MAC"), |
|
3036 mac_data.get_data(mac_data.get_data_length()), |
|
3037 mac_data.get_data_length())); |
|
3038 |
|
3039 if (m_am_tools->memcmp( |
|
3040 mac_data.get_data(mac_data.get_data_length()), |
|
3041 received_mac, mac_data.get_data_length()) != 0) |
|
3042 { |
|
3043 EAP_TRACE_ERROR( |
|
3044 m_am_tools, |
|
3045 TRACE_FLAGS_DEFAULT, |
|
3046 (EAPL("TLS: %s: receive_function: apply_receive_cipher_suite(): MAC failed\n"), |
|
3047 (m_is_client == true ? "client": "server"))); |
|
3048 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3049 return EAP_STATUS_RETURN(m_am_tools, eap_status_authentication_failure); |
|
3050 } |
|
3051 else |
|
3052 { |
|
3053 EAP_TRACE_ALWAYS( |
|
3054 m_am_tools, |
|
3055 TRACE_FLAGS_DEFAULT, |
|
3056 (EAPL("TLS: %s: receive_function: apply_receive_cipher_suite(): MAC OK\n"), |
|
3057 (m_is_client == true ? "client": "server"))); |
|
3058 } |
|
3059 |
|
3060 tls_record_message_buffer->set_data_length( |
|
3061 tls_record_message_buffer->get_data_length() |
|
3062 - mac->get_digest_length()); |
|
3063 |
|
3064 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3065 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3066 } |
|
3067 |
|
3068 //-------------------------------------------------- |
|
3069 |
|
3070 // |
|
3071 EAP_FUNC_EXPORT eap_status_e tls_record_c::apply_send_cipher_suite( |
|
3072 eap_variable_data_c * const tls_record_message_buffer) |
|
3073 { |
|
3074 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3075 |
|
3076 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
3077 EAP_TRACE_DEBUG( |
|
3078 m_am_tools, |
|
3079 TRACE_FLAGS_DEFAULT, |
|
3080 (EAPL("TLS: %s: send_function: starts: tls_record_c::apply_send_cipher_suite(): %d=%s\n"), |
|
3081 (m_is_client == true ? "client": "server"), |
|
3082 m_send_cipher_suite, |
|
3083 eap_tls_trace_string_c::get_cipher_suite_string(m_send_cipher_suite))); |
|
3084 |
|
3085 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::apply_send_cipher_suite()"); |
|
3086 |
|
3087 eap_status_e status = eap_status_process_general_error; |
|
3088 |
|
3089 tls_record_header_c tmp_tls_record_header_on_tls_message_buffer( |
|
3090 m_am_tools, |
|
3091 tls_record_message_buffer->get_data(tls_record_header_c::get_header_length()), |
|
3092 tls_record_message_buffer->get_data_length()); |
|
3093 |
|
3094 if (tmp_tls_record_header_on_tls_message_buffer.get_is_valid() == false |
|
3095 || tls_record_message_buffer->get_data_length() |
|
3096 < tmp_tls_record_header_on_tls_message_buffer.get_header_length()) |
|
3097 { |
|
3098 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3099 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
3100 } |
|
3101 |
|
3102 if (m_send_cipher_suite != tls_cipher_suites_TLS_NULL_WITH_NULL_NULL) |
|
3103 { |
|
3104 EAP_TRACE_DATA_ALWAYS( |
|
3105 m_am_tools, |
|
3106 TRACE_FLAGS_DEFAULT, |
|
3107 (EAPL("plaintext TLS-record"), |
|
3108 tls_record_message_buffer->get_data(tls_record_message_buffer->get_data_length()), |
|
3109 tls_record_message_buffer->get_data_length())); |
|
3110 } |
|
3111 |
|
3112 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
3113 |
|
3114 /** |
|
3115 * @{ Add compression of data. Well this will be optional very long time. } |
|
3116 */ |
|
3117 if (m_send_compression_method == tls_compression_method_null) |
|
3118 { |
|
3119 // No compression. |
|
3120 status = eap_status_ok; |
|
3121 } |
|
3122 else |
|
3123 { |
|
3124 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3125 return EAP_STATUS_RETURN(m_am_tools, eap_status_not_supported); |
|
3126 } |
|
3127 |
|
3128 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
3129 |
|
3130 if (m_send_cipher_suite == tls_cipher_suites_TLS_NULL_WITH_NULL_NULL) |
|
3131 { |
|
3132 // No authentication. |
|
3133 // No encryption. |
|
3134 |
|
3135 u64_t send_record_sequence_number_network_order = eap_htonll(m_send_record_sequence_number); |
|
3136 EAP_UNREFERENCED_PARAMETER(send_record_sequence_number_network_order); // in release |
|
3137 |
|
3138 EAP_TRACE_DATA_DEBUG( |
|
3139 m_am_tools, |
|
3140 TRACE_FLAGS_DEFAULT, |
|
3141 (EAPL("send_record_sequence_number_network_order"), |
|
3142 &send_record_sequence_number_network_order, |
|
3143 sizeof(send_record_sequence_number_network_order))); |
|
3144 |
|
3145 status = eap_status_ok; |
|
3146 } |
|
3147 else if (cipher_suite_is_3DES_EDE_CBC_SHA(m_send_cipher_suite) == true |
|
3148 || cipher_suite_is_AES_128_CBC_SHA(m_send_cipher_suite) == true) |
|
3149 { |
|
3150 EAP_ASSERT_TOOLS(m_am_tools, m_send_block_cipher != 0); |
|
3151 EAP_ASSERT_TOOLS(m_am_tools, m_send_hmac_algorithm != 0); |
|
3152 |
|
3153 status = apply_send_block_cipher_suite( |
|
3154 tls_record_message_buffer, |
|
3155 m_send_block_cipher, |
|
3156 m_send_hmac_algorithm); |
|
3157 } |
|
3158 else if (cipher_suite_is_RC4_128_MD5(m_send_cipher_suite) == true |
|
3159 || cipher_suite_is_RC4_128_SHA(m_send_cipher_suite) == true) |
|
3160 { |
|
3161 EAP_ASSERT_TOOLS(m_am_tools, m_send_stream_cipher != 0); |
|
3162 EAP_ASSERT_TOOLS(m_am_tools, m_send_hmac_algorithm != 0); |
|
3163 |
|
3164 status = apply_send_stream_cipher_suite( |
|
3165 tls_record_message_buffer, |
|
3166 m_send_stream_cipher, |
|
3167 m_send_hmac_algorithm); |
|
3168 } |
|
3169 else |
|
3170 { |
|
3171 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3172 return EAP_STATUS_RETURN(m_am_tools, eap_status_not_supported); |
|
3173 } |
|
3174 |
|
3175 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
3176 |
|
3177 if (m_send_cipher_suite != tls_cipher_suites_TLS_NULL_WITH_NULL_NULL) |
|
3178 { |
|
3179 m_send_record_sequence_number = m_send_record_sequence_number + 1ul; |
|
3180 } |
|
3181 |
|
3182 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
3183 |
|
3184 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3185 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3186 } |
|
3187 |
|
3188 //-------------------------------------------------- |
|
3189 |
|
3190 // |
|
3191 EAP_FUNC_EXPORT eap_status_e tls_record_c::apply_receive_cipher_suite( |
|
3192 eap_variable_data_c * const tls_record_message_buffer) |
|
3193 { |
|
3194 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3195 |
|
3196 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
3197 EAP_TRACE_DEBUG( |
|
3198 m_am_tools, |
|
3199 TRACE_FLAGS_DEFAULT, |
|
3200 (EAPL("TLS: %s: receive_function: starts: tls_record_c::apply_receive_cipher_suite(): %d=%s\n"), |
|
3201 (m_is_client == true ? "client": "server"), |
|
3202 m_receive_cipher_suite, |
|
3203 eap_tls_trace_string_c::get_cipher_suite_string(m_receive_cipher_suite))); |
|
3204 |
|
3205 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::apply_receive_cipher_suite()"); |
|
3206 |
|
3207 eap_status_e status = eap_status_process_general_error; |
|
3208 |
|
3209 tls_record_header_c tmp_tls_record_header_on_tls_message_buffer( |
|
3210 m_am_tools, |
|
3211 tls_record_message_buffer->get_data(tls_record_header_c::get_header_length()), |
|
3212 tls_record_message_buffer->get_data_length()); |
|
3213 |
|
3214 if (tmp_tls_record_header_on_tls_message_buffer.get_is_valid() == false |
|
3215 || tls_record_message_buffer->get_data_length() |
|
3216 < tmp_tls_record_header_on_tls_message_buffer.get_header_length()) |
|
3217 { |
|
3218 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3219 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
3220 } |
|
3221 |
|
3222 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
3223 |
|
3224 if (m_receive_cipher_suite == tls_cipher_suites_TLS_NULL_WITH_NULL_NULL) |
|
3225 { |
|
3226 // No decryption. |
|
3227 // No authentication. |
|
3228 |
|
3229 u64_t receive_record_sequence_number_network_order |
|
3230 = eap_htonll(m_receive_record_sequence_number); |
|
3231 EAP_UNREFERENCED_PARAMETER(receive_record_sequence_number_network_order); // in release |
|
3232 |
|
3233 EAP_TRACE_DATA_DEBUG( |
|
3234 m_am_tools, |
|
3235 TRACE_FLAGS_DEFAULT, |
|
3236 (EAPL("receive_record_sequence_number_network_order"), |
|
3237 &receive_record_sequence_number_network_order, |
|
3238 sizeof(receive_record_sequence_number_network_order))); |
|
3239 |
|
3240 status = eap_status_ok; |
|
3241 } |
|
3242 else if (cipher_suite_is_3DES_EDE_CBC_SHA(m_receive_cipher_suite) == true |
|
3243 || cipher_suite_is_AES_128_CBC_SHA(m_receive_cipher_suite) == true) |
|
3244 { |
|
3245 status = apply_receive_block_cipher_suite( |
|
3246 tls_record_message_buffer, |
|
3247 m_receive_block_cipher, |
|
3248 m_receive_hmac_algorithm); |
|
3249 } |
|
3250 else if (cipher_suite_is_RC4_128_MD5(m_receive_cipher_suite) == true |
|
3251 || cipher_suite_is_RC4_128_SHA(m_receive_cipher_suite) == true) |
|
3252 { |
|
3253 status = apply_receive_stream_cipher_suite( |
|
3254 tls_record_message_buffer, |
|
3255 m_receive_stream_cipher, |
|
3256 m_receive_hmac_algorithm); |
|
3257 } |
|
3258 else |
|
3259 { |
|
3260 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3261 return EAP_STATUS_RETURN(m_am_tools, eap_status_not_supported); |
|
3262 } |
|
3263 |
|
3264 if (m_receive_cipher_suite != tls_cipher_suites_TLS_NULL_WITH_NULL_NULL) |
|
3265 { |
|
3266 EAP_TRACE_DATA_ALWAYS( |
|
3267 m_am_tools, |
|
3268 TRACE_FLAGS_DEFAULT, |
|
3269 (EAPL("decrypted TLS-record"), |
|
3270 tls_record_message_buffer->get_data(tls_record_message_buffer->get_data_length()), |
|
3271 tls_record_message_buffer->get_data_length())); |
|
3272 } |
|
3273 |
|
3274 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
3275 |
|
3276 /** |
|
3277 * @{ Add de-compression of data. Well this will be optional very long time. } |
|
3278 */ |
|
3279 if (m_send_compression_method == tls_compression_method_null) |
|
3280 { |
|
3281 // No de-compression. |
|
3282 } |
|
3283 else |
|
3284 { |
|
3285 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3286 return EAP_STATUS_RETURN(m_am_tools, eap_status_not_supported); |
|
3287 } |
|
3288 |
|
3289 |
|
3290 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
3291 |
|
3292 if (m_receive_cipher_suite != tls_cipher_suites_TLS_NULL_WITH_NULL_NULL) |
|
3293 { |
|
3294 m_receive_record_sequence_number = m_receive_record_sequence_number + 1ul; |
|
3295 } |
|
3296 |
|
3297 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
3298 |
|
3299 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3300 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3301 } |
|
3302 |
|
3303 //-------------------------------------------------- |
|
3304 |
|
3305 // This is commented in abs_tls_base_application_c. |
|
3306 EAP_FUNC_EXPORT eap_status_e tls_record_c::packet_send( |
|
3307 eap_buf_chain_wr_c * const sent_packet, |
|
3308 const u32_t header_offset, |
|
3309 const u32_t /*data_length*/, |
|
3310 const u32_t /*buffer_length*/) |
|
3311 { |
|
3312 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3313 |
|
3314 EAP_TRACE_DEBUG( |
|
3315 m_am_tools, |
|
3316 TRACE_FLAGS_DEFAULT, |
|
3317 (EAPL("TLS: %s: receive_function: starts: tls_record_c::packet_send(): %d=%s\n"), |
|
3318 (m_is_client == true ? "client": "server"), |
|
3319 m_receive_cipher_suite, |
|
3320 eap_tls_trace_string_c::get_cipher_suite_string(m_receive_cipher_suite))); |
|
3321 |
|
3322 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::packet_send()"); |
|
3323 |
|
3324 eap_status_e status = create_tls_application_data( |
|
3325 sent_packet, |
|
3326 header_offset); |
|
3327 |
|
3328 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3329 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3330 } |
|
3331 |
|
3332 //-------------------------------------------------- |
|
3333 |
|
3334 // This is commented in abs_tls_base_application_c. |
|
3335 EAP_FUNC_EXPORT u32_t tls_record_c::get_header_offset( |
|
3336 u32_t * const MTU_length, |
|
3337 u32_t * const trailer_length) |
|
3338 { |
|
3339 EAP_TRACE_DEBUG( |
|
3340 m_am_tools, |
|
3341 TRACE_FLAGS_DEFAULT, |
|
3342 (EAPL("TLS: %s: receive_function: starts: tls_record_c::get_header_offset()\n"), |
|
3343 (m_is_client == true ? "client": "server"))); |
|
3344 |
|
3345 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::get_header_offset()"); |
|
3346 |
|
3347 if (m_eap_type == eap_type_peap |
|
3348 && m_peap_version == peap_version_0_xp) |
|
3349 { |
|
3350 // PEAPv0 cannot use long tunneled EAP-packets, |
|
3351 // bacause of the inner EAP-packets does not |
|
3352 // have own EAP-header. Long inner EAP-packets will be |
|
3353 // fragmented in outer PEAPv0 application data and that will cause |
|
3354 // wrong EAP-identifier values after reassembly. |
|
3355 u32_t offset = get_type_partner()->get_header_offset( |
|
3356 MTU_length, |
|
3357 trailer_length); |
|
3358 |
|
3359 // Here we try set MTU such the inner EAP-packets does not need fragmentation. |
|
3360 *MTU_length -= (offset |
|
3361 + 4ul*(tls_record_header_c::get_header_length() |
|
3362 + tls_handshake_header_c::get_header_length())); |
|
3363 *trailer_length = 0ul; |
|
3364 |
|
3365 return 0ul; |
|
3366 } |
|
3367 else |
|
3368 { |
|
3369 *MTU_length = EAP_TLS_PEAP_MAX_MESSAGE_LENGTH; |
|
3370 *trailer_length = 0ul; |
|
3371 |
|
3372 return 0ul; |
|
3373 } |
|
3374 } |
|
3375 |
|
3376 //-------------------------------------------------- |
|
3377 |
|
3378 // This is commented in abs_tls_base_application_c. |
|
3379 EAP_FUNC_EXPORT eap_status_e tls_record_c::read_configure( |
|
3380 const eap_configuration_field_c * const field, |
|
3381 eap_variable_data_c * const data) |
|
3382 { |
|
3383 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3384 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3385 |
|
3386 return get_type_partner()->read_configure( |
|
3387 field, |
|
3388 data); |
|
3389 } |
|
3390 |
|
3391 //-------------------------------------------------- |
|
3392 |
|
3393 // This is commented in abs_tls_base_application_c. |
|
3394 EAP_FUNC_EXPORT eap_status_e tls_record_c::write_configure( |
|
3395 const eap_configuration_field_c * const field, |
|
3396 eap_variable_data_c * const data) |
|
3397 { |
|
3398 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3399 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3400 |
|
3401 return get_type_partner()->write_configure( |
|
3402 field, |
|
3403 data); |
|
3404 } |
|
3405 |
|
3406 //-------------------------------------------------- |
|
3407 |
|
3408 // This is commented in abs_tls_base_application_c. |
|
3409 EAP_FUNC_EXPORT void tls_record_c::state_notification( |
|
3410 const abs_eap_state_notification_c * const state) |
|
3411 { |
|
3412 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3413 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3414 |
|
3415 EAP_TRACE_ALWAYS( |
|
3416 m_am_tools, |
|
3417 TRACE_FLAGS_DEFAULT, |
|
3418 (EAPL("this = 0x%08x, %s: starts: tls_record_c::state_notification(): EAP-type 0x%08x: m_tls_session_type=%d=%s, tls_state=%d=%s, notification state=%s\n"), |
|
3419 this, |
|
3420 (m_is_client == true ? "client": "server"), |
|
3421 convert_eap_type_to_u32_t(m_eap_type), |
|
3422 m_tls_session_type, |
|
3423 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type), |
|
3424 m_tls_peap_state, |
|
3425 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
3426 eap_state_notification_c::get_state_string(state->get_protocol_layer(), state->get_current_state()))); |
|
3427 |
|
3428 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::state_notification()"); |
|
3429 |
|
3430 if (state->get_protocol_layer() == eap_protocol_layer_general) |
|
3431 { |
|
3432 if (state->get_current_state() == eap_general_state_authentication_cancelled) |
|
3433 { |
|
3434 // Tunneled EAP-type terminated unsuccessfully. |
|
3435 m_tunneled_eap_type_authentication_state |
|
3436 = static_cast<eap_state_variable_e>(state->get_current_state()); |
|
3437 set_state(tls_peap_state_failure); |
|
3438 } |
|
3439 } |
|
3440 else if (state->get_protocol_layer() == eap_protocol_layer_eap) |
|
3441 { |
|
3442 if (state->get_current_state() == eap_state_authentication_terminated_unsuccessfully |
|
3443 #if defined(USE_EAP_PEAPV1_EXTENSIONS) |
|
3444 || state->get_current_state() == eap_state_authentication_terminated_unsuccessfully_peapv1_extension |
|
3445 #endif //#if defined(USE_EAP_PEAPV1_EXTENSIONS) |
|
3446 ) |
|
3447 { |
|
3448 // Tunneled EAP-type terminated unsuccessfully. |
|
3449 m_tunneled_eap_type_authentication_state |
|
3450 = static_cast<eap_state_variable_e>(state->get_current_state()); |
|
3451 set_state(tls_peap_state_failure); |
|
3452 |
|
3453 // Because we process aplication data, we do not send alert messages anymore. |
|
3454 m_could_send_fatal_alert_message = false; |
|
3455 m_could_send_warning_alert_message = false; |
|
3456 } |
|
3457 else if (state->get_current_state() |
|
3458 == eap_state_authentication_finished_successfully |
|
3459 || state->get_current_state() |
|
3460 == eap_state_tppd_peapv1_authentication_finished_successfully_with_tunneled_eap_success |
|
3461 #if defined(USE_EAP_PEAPV1_EXTENSIONS) |
|
3462 || state->get_current_state() |
|
3463 == eap_state_authentication_finished_successfully_peapv1_extension |
|
3464 #endif //#if defined(USE_EAP_PEAPV1_EXTENSIONS) |
|
3465 ) |
|
3466 { |
|
3467 // Tunneled EAP-type finished successfully. |
|
3468 |
|
3469 if ((m_eap_type == eap_type_peap |
|
3470 && m_peap_version >= peap_version_0_xp |
|
3471 && m_peap_version <= peap_version_2) |
|
3472 || m_eap_type == eap_type_ttls |
|
3473 #if defined(USE_FAST_EAP_TYPE) |
|
3474 || m_eap_type == eap_type_fast |
|
3475 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
3476 ) |
|
3477 { |
|
3478 eap_status_e status = get_type_partner()->set_tls_master_secret( |
|
3479 &m_eap_master_session_key); |
|
3480 if (status != eap_status_ok) |
|
3481 { |
|
3482 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3483 return; |
|
3484 } |
|
3485 |
|
3486 if (m_eap_type == eap_type_ttls |
|
3487 || m_eap_type == eap_type_peap |
|
3488 #if defined(USE_FAST_EAP_TYPE) |
|
3489 || m_eap_type == eap_type_fast |
|
3490 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
3491 ) |
|
3492 { |
|
3493 |
|
3494 tls_identity_privacy_handshake_state_e tmp_identity_privacy_handshake_state = |
|
3495 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
3496 m_tls_identity_privacy_handshake_state; |
|
3497 #else |
|
3498 tls_identity_privacy_handshake_state_none; |
|
3499 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
3500 EAP_UNREFERENCED_PARAMETER(tmp_identity_privacy_handshake_state); |
|
3501 |
|
3502 EAP_TRACE_DEBUG( |
|
3503 m_am_tools, |
|
3504 TRACE_FLAGS_DEFAULT, |
|
3505 (EAPL("%s: state_notification(): TLS/PEAP authentication ") |
|
3506 EAPL("SUCCESS: %s, %s, tunnel %d, tunneling type %s, tunneling version %s, cipher_suite %s, %s\n"), |
|
3507 (m_is_client == true ? "client": "server"), |
|
3508 (m_tls_peap_server_authenticates_client_action == true |
|
3509 ? "mutual": "anonymous client"), |
|
3510 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type), |
|
3511 get_is_tunneled_tls(), |
|
3512 eap_header_string_c::get_eap_type_string(m_eap_type), |
|
3513 eap_tls_trace_string_c::get_peap_version_string(m_peap_version), |
|
3514 eap_tls_trace_string_c::get_cipher_suite_string(m_selected_cipher_suite), |
|
3515 eap_tls_trace_string_c::get_tls_identity_privacy_handshake_state_string(tmp_identity_privacy_handshake_state))); |
|
3516 |
|
3517 eap_status_e save_status = m_am_tls_services->save_tls_session( |
|
3518 &m_session_id, |
|
3519 &m_master_secret, |
|
3520 m_selected_cipher_suite |
|
3521 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
3522 , tls_extension_c::get_tls_extension( |
|
3523 tls_extension_type_session_ticket, |
|
3524 &m_received_tls_extensions, |
|
3525 m_am_tools) |
|
3526 #endif //#if defined(USE_EAP_TLS_SESSION_TICKET) |
|
3527 ); |
|
3528 if (save_status != eap_status_ok) |
|
3529 { |
|
3530 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3531 (void) EAP_STATUS_RETURN(m_am_tools, save_status); |
|
3532 } |
|
3533 } |
|
3534 |
|
3535 } |
|
3536 |
|
3537 m_tunneled_eap_type_authentication_state |
|
3538 = static_cast<eap_state_variable_e>(state->get_current_state()); |
|
3539 set_state(tls_peap_state_tls_success); |
|
3540 } |
|
3541 #if defined(USE_FAST_EAP_TYPE) |
|
3542 else if (m_eap_type == eap_type_fast |
|
3543 && state->get_current_state() == eap_state_inner_eap_method_skipped) |
|
3544 { |
|
3545 m_tunneled_eap_type_authentication_state |
|
3546 = static_cast<eap_state_variable_e>(state->get_current_state()); |
|
3547 } |
|
3548 else if (m_is_client == false |
|
3549 && m_eap_type == eap_type_fast |
|
3550 && state->get_current_state() == eap_state_authentication_wait_eap_fast_empty_acknowledge) |
|
3551 { |
|
3552 set_state(tls_peap_state_wait_tunneled_authentication_start); |
|
3553 } |
|
3554 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
3555 } |
|
3556 else if (state->get_protocol_layer() == eap_protocol_layer_internal_type) |
|
3557 { |
|
3558 |
|
3559 #if defined(EAP_USE_TTLS_PLAIN_MS_CHAP_V2_HACK) |
|
3560 if (state->get_current_state() == tls_peap_state_server_waits_ttls_plain_ms_chap_v2_empty_ack) |
|
3561 { |
|
3562 EAP_TRACE_ALWAYS( |
|
3563 m_am_tools, |
|
3564 TRACE_FLAGS_DEFAULT, |
|
3565 (EAPL("%s: tls_record_c::state_notification(): ") |
|
3566 EAPL("waits TTLS/plain MsChapv2 empty Ack: EAP-type 0x%08x\n"), |
|
3567 (m_is_client == true ? "client": "server"), |
|
3568 convert_eap_type_to_u32_t(m_eap_type))); |
|
3569 } |
|
3570 #endif //#if defined(EAP_USE_TTLS_PLAIN_MS_CHAP_V2_HACK) |
|
3571 |
|
3572 } |
|
3573 |
|
3574 get_type_partner()->state_notification( |
|
3575 state); |
|
3576 } |
|
3577 |
|
3578 //-------------------------------------------------- |
|
3579 |
|
3580 // This is commented in abs_tls_base_application_c. |
|
3581 EAP_FUNC_EXPORT eap_status_e tls_record_c::set_timer( |
|
3582 abs_eap_base_timer_c * const initializer, |
|
3583 const u32_t id, |
|
3584 void * const data, |
|
3585 const u32_t p_time_ms) |
|
3586 { |
|
3587 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3588 |
|
3589 if (get_type_partner() == 0) |
|
3590 { |
|
3591 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3592 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
3593 } |
|
3594 |
|
3595 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3596 return get_type_partner()->set_timer( |
|
3597 initializer, |
|
3598 id, |
|
3599 data, |
|
3600 p_time_ms); |
|
3601 } |
|
3602 |
|
3603 //-------------------------------------------------- |
|
3604 |
|
3605 // This is commented in abs_tls_base_application_c. |
|
3606 EAP_FUNC_EXPORT eap_status_e tls_record_c::cancel_timer( |
|
3607 abs_eap_base_timer_c * const initializer, |
|
3608 const u32_t id) |
|
3609 { |
|
3610 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3611 |
|
3612 if (get_type_partner() == 0) |
|
3613 { |
|
3614 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3615 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
3616 } |
|
3617 |
|
3618 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3619 return get_type_partner()->cancel_timer( |
|
3620 initializer, |
|
3621 id); |
|
3622 } |
|
3623 |
|
3624 //-------------------------------------------------- |
|
3625 |
|
3626 // This is commented in abs_tls_base_application_c. |
|
3627 EAP_FUNC_EXPORT eap_status_e tls_record_c::cancel_all_timers() |
|
3628 { |
|
3629 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3630 |
|
3631 if (get_type_partner() == 0) |
|
3632 { |
|
3633 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3634 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
3635 } |
|
3636 |
|
3637 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3638 return get_type_partner()->cancel_all_timers(); |
|
3639 } |
|
3640 |
|
3641 //-------------------------------------------------- |
|
3642 |
|
3643 // This is commented in abs_tls_base_application_c. |
|
3644 EAP_FUNC_EXPORT eap_status_e tls_record_c::load_module( |
|
3645 const eap_type_value_e type, |
|
3646 const eap_type_value_e tunneling_type, |
|
3647 abs_eap_base_type_c * const partner, |
|
3648 eap_base_type_c ** const eap_type, |
|
3649 const bool is_client_when_true, |
|
3650 const eap_am_network_id_c * const receive_network_id) |
|
3651 { |
|
3652 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3653 |
|
3654 eap_status_e status = get_type_partner()->load_module( |
|
3655 type, |
|
3656 tunneling_type, |
|
3657 partner, |
|
3658 eap_type, |
|
3659 is_client_when_true, |
|
3660 receive_network_id); |
|
3661 |
|
3662 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3663 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3664 } |
|
3665 |
|
3666 // This is commented in abs_tls_base_application_c. |
|
3667 EAP_FUNC_EXPORT eap_status_e tls_record_c::unload_module(const eap_type_value_e type) |
|
3668 { |
|
3669 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3670 |
|
3671 eap_status_e status = get_type_partner()->unload_module(type); |
|
3672 |
|
3673 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3674 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3675 } |
|
3676 |
|
3677 // This is commented in abs_tls_base_application_c. |
|
3678 EAP_FUNC_EXPORT eap_status_e tls_record_c::restart_authentication( |
|
3679 const eap_am_network_id_c * const receive_network_id, |
|
3680 const bool is_client_when_true, |
|
3681 const bool force_clean_restart, |
|
3682 const bool from_timer) |
|
3683 { |
|
3684 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3685 |
|
3686 eap_status_e status = get_type_partner()->restart_authentication( |
|
3687 receive_network_id, |
|
3688 is_client_when_true, |
|
3689 force_clean_restart, |
|
3690 from_timer); |
|
3691 |
|
3692 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3693 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3694 } |
|
3695 |
|
3696 // This is commented in abs_tls_base_application_c. |
|
3697 EAP_FUNC_EXPORT eap_status_e tls_record_c::packet_data_crypto_keys( |
|
3698 const eap_am_network_id_c * const /* send_network_id */, |
|
3699 const eap_master_session_key_c * const master_session_key) |
|
3700 { |
|
3701 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3702 |
|
3703 EAP_TRACE_DEBUG( |
|
3704 m_am_tools, |
|
3705 TRACE_FLAGS_DEFAULT, |
|
3706 (EAPL("TLS: %s: receive_function: starts: tls_record_c::packet_data_crypto_keys()\n"), |
|
3707 (m_is_client == true ? "client": "server"))); |
|
3708 |
|
3709 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::packet_data_crypto_keys()"); |
|
3710 |
|
3711 if ((m_eap_type == eap_type_peap |
|
3712 && (m_peap_version == peap_version_0_xp |
|
3713 || m_peap_version == peap_version_1)) |
|
3714 || m_eap_type == eap_type_ttls) |
|
3715 { |
|
3716 // We do not forward keys to lower layer. |
|
3717 } |
|
3718 #if defined(USE_FAST_EAP_TYPE) |
|
3719 else if (m_eap_type == eap_type_fast) |
|
3720 { |
|
3721 eap_status_e status = m_eap_master_session_key.set_copy_of_buffer( |
|
3722 master_session_key); |
|
3723 if (status != eap_status_ok) |
|
3724 { |
|
3725 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3726 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3727 } |
|
3728 |
|
3729 // NOTE: state_notification() will deliver master_session_key to lower layers. |
|
3730 } |
|
3731 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
3732 else if (m_eap_type == eap_type_peap |
|
3733 && m_peap_version == peap_version_2) |
|
3734 { |
|
3735 eap_status_e status = m_eap_master_session_key.set_copy_of_buffer( |
|
3736 master_session_key); |
|
3737 if (status != eap_status_ok) |
|
3738 { |
|
3739 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3740 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3741 } |
|
3742 |
|
3743 status = get_type_partner()->set_tls_master_secret(&m_eap_master_session_key); |
|
3744 if (status != eap_status_ok) |
|
3745 { |
|
3746 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3747 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3748 } |
|
3749 } |
|
3750 |
|
3751 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3752 return EAP_STATUS_RETURN(m_am_tools, eap_status_ok); |
|
3753 } |
|
3754 |
|
3755 // This is commented in abs_tls_base_application_c. |
|
3756 EAP_FUNC_EXPORT eap_status_e tls_record_c::check_is_valid_eap_type( |
|
3757 const eap_type_value_e eap_type) |
|
3758 { |
|
3759 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3760 |
|
3761 eap_status_e status = get_type_partner()->check_is_valid_eap_type(eap_type); |
|
3762 |
|
3763 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3764 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3765 } |
|
3766 |
|
3767 // This is commented in abs_tls_base_application_c. |
|
3768 EAP_FUNC_EXPORT eap_status_e tls_record_c::get_eap_type_list( |
|
3769 eap_array_c<eap_type_value_e> * const eap_type_list) |
|
3770 { |
|
3771 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3772 |
|
3773 eap_status_e status = get_type_partner()->get_eap_type_list(eap_type_list); |
|
3774 |
|
3775 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3776 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3777 } |
|
3778 |
|
3779 //-------------------------------------------------- |
|
3780 |
|
3781 // |
|
3782 EAP_FUNC_EXPORT eap_status_e tls_record_c::start_tls_peap_authentication( |
|
3783 const eap_variable_data_c * const received_authority_identity_payload |
|
3784 ) |
|
3785 { |
|
3786 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3787 |
|
3788 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
3789 EAP_TRACE_DEBUG( |
|
3790 m_am_tools, |
|
3791 TRACE_FLAGS_DEFAULT, |
|
3792 (EAPL("TLS: %s: message_function: starts: tls_record_c::start_tls_peap_authentication()\n"), |
|
3793 (m_is_client == true ? "client": "server"))); |
|
3794 |
|
3795 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::start_tls_peap_authentication()"); |
|
3796 |
|
3797 eap_status_e status = completion_action_add(tls_completion_action_query_cipher_suites_and_previous_session); |
|
3798 if (status != eap_status_ok) |
|
3799 { |
|
3800 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3801 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3802 } |
|
3803 |
|
3804 set_state(tls_peap_state_wait_handshake_type_server_hello); |
|
3805 |
|
3806 status = completion_action_add(tls_completion_action_create_handshake_type_client_hello); |
|
3807 if (status != eap_status_ok) |
|
3808 { |
|
3809 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3810 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3811 } |
|
3812 |
|
3813 #if defined(USE_FAST_EAP_TYPE) |
|
3814 if (m_eap_type == eap_type_fast) |
|
3815 { |
|
3816 if (m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true) |
|
3817 { |
|
3818 set_tls_session_type(tls_session_type_eap_fast_server_unauthenticated_provisioning_mode_ADHP); |
|
3819 } |
|
3820 else if (received_authority_identity_payload != 0 |
|
3821 && received_authority_identity_payload->get_is_valid_data() == true) |
|
3822 { |
|
3823 eap_fast_variable_data_c in_A_ID_TLV(m_am_tools); |
|
3824 |
|
3825 status = in_A_ID_TLV.set_copy_of_buffer( |
|
3826 received_authority_identity_payload->get_data(), |
|
3827 received_authority_identity_payload->get_data_length()); |
|
3828 if (status != eap_status_ok) |
|
3829 { |
|
3830 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3831 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3832 } |
|
3833 |
|
3834 status = m_application->query_tunnel_PAC( |
|
3835 &in_A_ID_TLV); |
|
3836 if (status == eap_status_pending_request) |
|
3837 { |
|
3838 // This is pending query, that will be completed by |
|
3839 // complete_query_tunnel_PAC() call. |
|
3840 m_pending_query_tunnel_PAC = true; |
|
3841 |
|
3842 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3843 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3844 } |
|
3845 else if (status == eap_status_completed_request) |
|
3846 { |
|
3847 // This is already completed by complete_query_PACs() call. |
|
3848 |
|
3849 status = check_sent_tls_message(); |
|
3850 |
|
3851 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3852 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3853 } |
|
3854 else if (status == eap_status_ok) |
|
3855 { |
|
3856 // This is also an error case, because this call is always completed on success. |
|
3857 status = eap_status_process_general_error; |
|
3858 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3859 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3860 } |
|
3861 else // All other status values means error, because this call is always completed on success. |
|
3862 { |
|
3863 // This is an error case. |
|
3864 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3865 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
3866 } |
|
3867 } |
|
3868 } |
|
3869 #else |
|
3870 EAP_UNREFERENCED_PARAMETER(received_authority_identity_payload); |
|
3871 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
3872 |
|
3873 |
|
3874 status = check_sent_tls_message(); |
|
3875 |
|
3876 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3877 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3878 } |
|
3879 |
|
3880 //-------------------------------------------------- |
|
3881 |
|
3882 // |
|
3883 EAP_FUNC_EXPORT eap_status_e tls_record_c::start_peap_tunneled_authentication( |
|
3884 const eap_am_network_id_c * const receive_network_id, |
|
3885 const u8_t received_eap_identifier, |
|
3886 const tls_session_type_e tls_session_type) |
|
3887 { |
|
3888 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3889 |
|
3890 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
3891 EAP_TRACE_DEBUG( |
|
3892 m_am_tools, |
|
3893 TRACE_FLAGS_DEFAULT, |
|
3894 (EAPL("TLS: %s: message_function: starts: tls_record_c::start_peap_tunneled_authentication()\n"), |
|
3895 (m_is_client == true ? "client": "server"))); |
|
3896 |
|
3897 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::start_peap_tunneled_authentication()"); |
|
3898 |
|
3899 if (m_is_client == true |
|
3900 && verify_state(tls_peap_state_peap_tunnel_ready) == false) |
|
3901 { |
|
3902 EAP_TRACE_ERROR( |
|
3903 m_am_tools, |
|
3904 TRACE_FLAGS_DEFAULT, |
|
3905 (EAPL("ERROR: TLS: %s: function: verify_state(): current state %s != %s\n"), |
|
3906 (m_is_client == true ? "client": "server"), |
|
3907 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
3908 eap_tls_trace_string_c::get_state_string(tls_peap_state_peap_tunnel_ready))); |
|
3909 return EAP_STATUS_RETURN(m_am_tools, eap_status_unexpected_message); |
|
3910 } |
|
3911 else if (m_is_client == false |
|
3912 && verify_state(tls_peap_state_wait_tunneled_authentication_start) == false) |
|
3913 { |
|
3914 EAP_TRACE_ERROR( |
|
3915 m_am_tools, |
|
3916 TRACE_FLAGS_DEFAULT, |
|
3917 (EAPL("ERROR: TLS: %s: function: verify_state(): current state %s != %s\n"), |
|
3918 (m_is_client == true ? "client": "server"), |
|
3919 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
3920 eap_tls_trace_string_c::get_state_string(tls_peap_state_wait_tunneled_authentication_start))); |
|
3921 return EAP_STATUS_RETURN(m_am_tools, eap_status_unexpected_message); |
|
3922 } |
|
3923 |
|
3924 |
|
3925 set_state(tls_peap_state_wait_application_data); |
|
3926 |
|
3927 eap_status_e status = eap_status_process_general_error; |
|
3928 |
|
3929 { |
|
3930 // This must be inside a block. Automatic variable must be restored after |
|
3931 // the start_peap_tunneled_authentication() function call. |
|
3932 eap_automatic_simple_value_c<bool> restore_allow_message_send( |
|
3933 m_am_tools, |
|
3934 &m_allow_message_send, |
|
3935 m_allow_message_send); |
|
3936 |
|
3937 // Packet send is delayed until after the |
|
3938 // m_application->start_peap_tunneled_authentication() function returns. |
|
3939 m_allow_message_send = false; |
|
3940 |
|
3941 status = m_application->start_peap_tunneled_authentication( |
|
3942 receive_network_id, |
|
3943 m_is_client, |
|
3944 received_eap_identifier, |
|
3945 tls_session_type, |
|
3946 m_tls_peap_server_authenticates_client_action); |
|
3947 } |
|
3948 |
|
3949 |
|
3950 { |
|
3951 // Note this call will return eap_status_pending_request |
|
3952 // if any asyncronous call is pending. |
|
3953 eap_status_e send_status = check_sent_tls_message(); |
|
3954 if (send_status != eap_status_ok) |
|
3955 { |
|
3956 status = send_status; |
|
3957 } |
|
3958 } |
|
3959 |
|
3960 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3961 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3962 } |
|
3963 |
|
3964 //-------------------------------------------------- |
|
3965 |
|
3966 EAP_FUNC_EXPORT eap_status_e tls_record_c::allocate_handshake_message_copy( |
|
3967 tls_handshake_message_c ** const tls_handshake_message, |
|
3968 eap_automatic_variable_c<tls_handshake_message_c> * const automatic_tls_handshake_message, |
|
3969 tls_handshake_header_c * const tls_handshake_header) |
|
3970 { |
|
3971 *tls_handshake_message |
|
3972 = new tls_handshake_message_c(m_am_tools, this, m_is_client); |
|
3973 |
|
3974 automatic_tls_handshake_message->set_variable(*tls_handshake_message); |
|
3975 |
|
3976 if (*tls_handshake_message == 0 |
|
3977 || (*tls_handshake_message)->get_is_valid() == false) |
|
3978 { |
|
3979 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3980 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
3981 } |
|
3982 |
|
3983 eap_status_e status = (*tls_handshake_message)->set_handshake_header_copy( |
|
3984 tls_handshake_header); |
|
3985 |
|
3986 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
3987 return EAP_STATUS_RETURN(m_am_tools, status); |
|
3988 } |
|
3989 |
|
3990 //-------------------------------------------------- |
|
3991 |
|
3992 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
3993 |
|
3994 EAP_FUNC_EXPORT eap_status_e tls_record_c::parse_tls_extension_list( |
|
3995 const u32_t handshake_data_length, |
|
3996 u32_t * const data_offset, |
|
3997 const tls_handshake_header_c * const tls_handshake_header, |
|
3998 tls_handshake_message_c * const tls_handshake_message |
|
3999 ) |
|
4000 { |
|
4001 EAP_TRACE_DEBUG( |
|
4002 m_am_tools, |
|
4003 TRACE_FLAGS_DEFAULT, |
|
4004 (EAPL("TLS: %s: receive_function: starts: tls_record_c::parse_tls_extension_list()\n"), |
|
4005 (m_is_client == true ? "client": "server"))); |
|
4006 |
|
4007 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::parse_tls_extension_list()"); |
|
4008 |
|
4009 eap_status_e status(eap_status_ok); |
|
4010 |
|
4011 // This is optional field. |
|
4012 if ((*data_offset)+TLS_EXTENSIONS_LENGTH_FIELD_SIZE <= handshake_data_length) |
|
4013 { |
|
4014 // Extension list is formatted as: |
|
4015 // 0 1 2 3 |
|
4016 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
4017 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
4018 // | extension list length | |
|
4019 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
4020 // | extension 1 type | extension 1 data length | |
|
4021 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
4022 // | extension 1 data ... |
|
4023 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
4024 // | extension 2 type | extension 2 data length | |
|
4025 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
4026 // | extension 2 data ... |
|
4027 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
4028 |
|
4029 u8_t *p_extension_list = tls_handshake_header->get_data_offset( |
|
4030 (*data_offset), |
|
4031 TLS_EXTENSIONS_LENGTH_FIELD_SIZE); |
|
4032 if (p_extension_list == 0) |
|
4033 { |
|
4034 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4035 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4036 } |
|
4037 |
|
4038 (*data_offset) += TLS_EXTENSIONS_LENGTH_FIELD_SIZE; |
|
4039 |
|
4040 u32_t extension_list_length( |
|
4041 eap_read_u16_t_network_order( |
|
4042 p_extension_list, |
|
4043 TLS_EXTENSIONS_LENGTH_FIELD_SIZE)); |
|
4044 |
|
4045 if ((*data_offset)+extension_list_length > handshake_data_length) |
|
4046 { |
|
4047 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4048 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4049 } |
|
4050 |
|
4051 const u32_t offset_end((*data_offset)+extension_list_length); |
|
4052 |
|
4053 EAP_TRACE_DATA_DEBUG( |
|
4054 m_am_tools, |
|
4055 TRACE_FLAGS_DEFAULT, |
|
4056 (EAPL("TLS-handshake extension payload"), |
|
4057 p_extension_list, |
|
4058 TLS_EXTENSIONS_LENGTH_FIELD_SIZE+extension_list_length)); |
|
4059 |
|
4060 if (extension_list_length > 0ul) |
|
4061 { |
|
4062 eap_array_c<tls_extension_c> extensions_array(m_am_tools); |
|
4063 |
|
4064 while((*data_offset) < offset_end) |
|
4065 { |
|
4066 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
4067 |
|
4068 if ((*data_offset)+TLS_EXTENSION_TYPE_FIELD_SIZE > handshake_data_length) |
|
4069 { |
|
4070 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4071 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4072 } |
|
4073 |
|
4074 u8_t *p_extension_type = tls_handshake_header->get_data_offset( |
|
4075 (*data_offset), |
|
4076 TLS_EXTENSION_TYPE_FIELD_SIZE); |
|
4077 if (p_extension_type == 0) |
|
4078 { |
|
4079 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4080 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4081 } |
|
4082 |
|
4083 (*data_offset) += TLS_EXTENSION_TYPE_FIELD_SIZE; |
|
4084 |
|
4085 u16_t extension_type_host( |
|
4086 eap_read_u16_t_network_order( |
|
4087 p_extension_type, |
|
4088 TLS_EXTENSIONS_LENGTH_FIELD_SIZE)); |
|
4089 |
|
4090 tls_extension_type_e extension_type(static_cast<tls_extension_type_e>(extension_type_host)); |
|
4091 |
|
4092 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
4093 |
|
4094 if ((*data_offset)+TLS_EXTENSION_DATA_LENGTH_FIELD_SIZE > handshake_data_length) |
|
4095 { |
|
4096 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4097 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4098 } |
|
4099 |
|
4100 u8_t *p_extension_data_length = tls_handshake_header->get_data_offset( |
|
4101 (*data_offset), |
|
4102 TLS_EXTENSION_DATA_LENGTH_FIELD_SIZE); |
|
4103 if (p_extension_data_length == 0) |
|
4104 { |
|
4105 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4106 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4107 } |
|
4108 |
|
4109 (*data_offset) += TLS_EXTENSION_DATA_LENGTH_FIELD_SIZE; |
|
4110 |
|
4111 u16_t extension_data_length_host( |
|
4112 eap_read_u16_t_network_order( |
|
4113 p_extension_data_length, |
|
4114 TLS_EXTENSION_DATA_LENGTH_FIELD_SIZE)); |
|
4115 |
|
4116 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
4117 |
|
4118 tls_extension_c * const tls_extension = new tls_extension_c(m_am_tools); |
|
4119 |
|
4120 eap_automatic_variable_c<tls_extension_c> |
|
4121 automatic_tls_extension(m_am_tools, tls_extension); |
|
4122 |
|
4123 if (tls_extension == 0 |
|
4124 || tls_extension->get_is_valid() == false) |
|
4125 { |
|
4126 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4127 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
4128 } |
|
4129 |
|
4130 tls_extension->set_type(extension_type); |
|
4131 |
|
4132 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
4133 |
|
4134 if (extension_data_length_host > 0ul) |
|
4135 { |
|
4136 if ((*data_offset)+extension_data_length_host > handshake_data_length) |
|
4137 { |
|
4138 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4139 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4140 } |
|
4141 |
|
4142 const u8_t * const p_extension_data = tls_handshake_header->get_data_offset( |
|
4143 (*data_offset), |
|
4144 extension_data_length_host); |
|
4145 if (p_extension_data == 0) |
|
4146 { |
|
4147 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4148 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4149 } |
|
4150 |
|
4151 status = tls_extension->set_copy_of_buffer(p_extension_data, extension_data_length_host); |
|
4152 if (status != eap_status_ok) |
|
4153 { |
|
4154 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4155 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4156 } |
|
4157 |
|
4158 (*data_offset) += extension_data_length_host; |
|
4159 } |
|
4160 |
|
4161 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
4162 |
|
4163 automatic_tls_extension.do_not_free_variable(); |
|
4164 |
|
4165 // add_object() will delete extension if operation fails. |
|
4166 status = extensions_array.add_object(tls_extension, true); |
|
4167 if (status != eap_status_ok) |
|
4168 { |
|
4169 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4170 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4171 } |
|
4172 |
|
4173 } // while() |
|
4174 |
|
4175 status = tls_handshake_message->set_tls_extensions(&extensions_array); |
|
4176 if (status != eap_status_ok) |
|
4177 { |
|
4178 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4179 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4180 } |
|
4181 } |
|
4182 } |
|
4183 |
|
4184 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4185 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4186 } |
|
4187 |
|
4188 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
4189 |
|
4190 //-------------------------------------------------- |
|
4191 |
|
4192 EAP_FUNC_EXPORT eap_status_e tls_record_c::parse_handshake_type_hello_request( |
|
4193 tls_record_message_c * const received_tls_record_message, |
|
4194 tls_handshake_header_c * const tls_handshake_header, |
|
4195 const u32_t handshake_data_length) |
|
4196 { |
|
4197 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4198 |
|
4199 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
4200 EAP_TRACE_DEBUG( |
|
4201 m_am_tools, |
|
4202 TRACE_FLAGS_DEFAULT, |
|
4203 (EAPL("TLS: %s: parse_function: starts: tls_record_c::parse_handshake_type_hello_request()\n"), |
|
4204 (m_is_client == true ? "client": "server"))); |
|
4205 |
|
4206 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::parse_handshake_type_hello_request()"); |
|
4207 |
|
4208 tls_handshake_message_c *tls_handshake_message = 0; |
|
4209 |
|
4210 eap_automatic_variable_c<tls_handshake_message_c> |
|
4211 automatic_tls_handshake_message(m_am_tools); |
|
4212 |
|
4213 eap_status_e status = allocate_handshake_message_copy( |
|
4214 &tls_handshake_message, |
|
4215 &automatic_tls_handshake_message, |
|
4216 tls_handshake_header); |
|
4217 if (status != eap_status_ok) |
|
4218 { |
|
4219 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4220 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4221 } |
|
4222 |
|
4223 if (handshake_data_length != 0ul) |
|
4224 { |
|
4225 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4226 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_long_message); |
|
4227 } |
|
4228 |
|
4229 if (status == eap_status_ok) |
|
4230 { |
|
4231 // Note the add_handshake_message() frees message in any case. |
|
4232 automatic_tls_handshake_message.do_not_free_variable(); |
|
4233 |
|
4234 status = received_tls_record_message->add_handshake_message(tls_handshake_message, true); |
|
4235 if (status != eap_status_ok) |
|
4236 { |
|
4237 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4238 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4239 } |
|
4240 } |
|
4241 |
|
4242 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4243 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4244 } |
|
4245 |
|
4246 //-------------------------------------------------- |
|
4247 |
|
4248 EAP_FUNC_EXPORT eap_status_e tls_record_c::parse_handshake_type_client_hello( |
|
4249 tls_record_message_c * const received_tls_record_message, |
|
4250 tls_handshake_header_c * const tls_handshake_header, |
|
4251 const u32_t handshake_data_length) |
|
4252 { |
|
4253 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4254 |
|
4255 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
4256 EAP_TRACE_DEBUG( |
|
4257 m_am_tools, |
|
4258 TRACE_FLAGS_DEFAULT, |
|
4259 (EAPL("TLS: %s: parse_function: starts: tls_record_c::parse_handshake_type_client_hello()\n"), |
|
4260 (m_is_client == true ? "client": "server"))); |
|
4261 |
|
4262 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::parse_handshake_type_client_hello()"); |
|
4263 |
|
4264 tls_handshake_message_c *tls_handshake_message = 0; |
|
4265 |
|
4266 eap_automatic_variable_c<tls_handshake_message_c> |
|
4267 automatic_tls_handshake_message(m_am_tools); |
|
4268 |
|
4269 eap_status_e status = allocate_handshake_message_copy( |
|
4270 &tls_handshake_message, |
|
4271 &automatic_tls_handshake_message, |
|
4272 tls_handshake_header); |
|
4273 if (status != eap_status_ok) |
|
4274 { |
|
4275 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4276 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4277 } |
|
4278 |
|
4279 u32_t data_offset = 0ul; |
|
4280 u8_t * const handshake_data = tls_handshake_header->get_data_offset( |
|
4281 data_offset, |
|
4282 tls_handshake_header->get_data_length()); |
|
4283 if (handshake_data == 0) |
|
4284 { |
|
4285 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4286 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4287 } |
|
4288 |
|
4289 //---------------------------------------------------------- |
|
4290 |
|
4291 { |
|
4292 if (data_offset+TLS_VERSION_FIELD_SIZE > handshake_data_length) |
|
4293 { |
|
4294 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4295 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4296 } |
|
4297 |
|
4298 u8_t *p_version = handshake_data; |
|
4299 u16_t version = eap_read_u16_t_network_order(p_version, TLS_VERSION_FIELD_SIZE); |
|
4300 |
|
4301 if (version != tls_version_3_1) |
|
4302 { |
|
4303 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4304 return EAP_STATUS_RETURN(m_am_tools, eap_status_header_corrupted); |
|
4305 } |
|
4306 |
|
4307 data_offset += TLS_VERSION_FIELD_SIZE; |
|
4308 } |
|
4309 |
|
4310 //---------------------------------------------------------- |
|
4311 |
|
4312 { |
|
4313 if (data_offset+TLS_HANDSHAKE_RANDOM_VALUE_SIZE > handshake_data_length) |
|
4314 { |
|
4315 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4316 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4317 } |
|
4318 |
|
4319 u8_t *p_random_value = tls_handshake_header->get_data_offset( |
|
4320 data_offset, |
|
4321 TLS_HANDSHAKE_RANDOM_VALUE_SIZE); |
|
4322 if (p_random_value == 0) |
|
4323 { |
|
4324 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4325 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4326 } |
|
4327 eap_variable_data_c client_random_value(m_am_tools); |
|
4328 status = client_random_value.set_buffer( |
|
4329 p_random_value, |
|
4330 TLS_HANDSHAKE_RANDOM_VALUE_SIZE, |
|
4331 false, |
|
4332 false); |
|
4333 if (status != eap_status_ok) |
|
4334 { |
|
4335 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4336 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4337 } |
|
4338 |
|
4339 status = tls_handshake_message->set_random_value(&client_random_value); |
|
4340 if (status != eap_status_ok) |
|
4341 { |
|
4342 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4343 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4344 } |
|
4345 |
|
4346 data_offset += TLS_HANDSHAKE_RANDOM_VALUE_SIZE; |
|
4347 |
|
4348 EAP_TRACE_DATA_DEBUG( |
|
4349 m_am_tools, |
|
4350 TRACE_FLAGS_DEFAULT, |
|
4351 (EAPL("TLS: parse_handshake_type_client_hello(): m_client_random_value"), |
|
4352 client_random_value.get_data(client_random_value.get_data_length()), |
|
4353 client_random_value.get_data_length())); |
|
4354 } |
|
4355 |
|
4356 //---------------------------------------------------------- |
|
4357 |
|
4358 { |
|
4359 if (data_offset+TLS_SESSION_ID_LENGTH_FIELD_SIZE > handshake_data_length) |
|
4360 { |
|
4361 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4362 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4363 } |
|
4364 |
|
4365 u8_t *p_session_id_length = tls_handshake_header->get_data_offset( |
|
4366 data_offset, |
|
4367 TLS_SESSION_ID_LENGTH_FIELD_SIZE); |
|
4368 if (p_session_id_length == 0) |
|
4369 { |
|
4370 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4371 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4372 } |
|
4373 data_offset += TLS_SESSION_ID_LENGTH_FIELD_SIZE; |
|
4374 |
|
4375 if (data_offset+*p_session_id_length > handshake_data_length) |
|
4376 { |
|
4377 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4378 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4379 } |
|
4380 |
|
4381 if (*p_session_id_length > 0ul) |
|
4382 { |
|
4383 u8_t *p_session_id = tls_handshake_header->get_data_offset( |
|
4384 data_offset, |
|
4385 *p_session_id_length); |
|
4386 if (p_session_id == 0) |
|
4387 { |
|
4388 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4389 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4390 } |
|
4391 |
|
4392 eap_variable_data_c session_id(m_am_tools); |
|
4393 status = session_id.set_buffer(p_session_id, *p_session_id_length, false, false); |
|
4394 if (status != eap_status_ok) |
|
4395 { |
|
4396 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4397 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4398 } |
|
4399 |
|
4400 status = tls_handshake_message->set_session_id(&session_id); |
|
4401 if (status != eap_status_ok) |
|
4402 { |
|
4403 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4404 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4405 } |
|
4406 } |
|
4407 |
|
4408 data_offset += *p_session_id_length; |
|
4409 } |
|
4410 |
|
4411 //---------------------------------------------------------- |
|
4412 |
|
4413 { |
|
4414 if (data_offset+TLS_CIPHER_SUITE_LENGTH_FIELD_SIZE > handshake_data_length) |
|
4415 { |
|
4416 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4417 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4418 } |
|
4419 |
|
4420 u8_t *p_cipher_suite_length_network_order = tls_handshake_header->get_data_offset( |
|
4421 data_offset, |
|
4422 TLS_CIPHER_SUITE_LENGTH_FIELD_SIZE); |
|
4423 if (p_cipher_suite_length_network_order == 0) |
|
4424 { |
|
4425 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4426 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4427 } |
|
4428 u16_t cipher_suite_length = eap_read_u16_t_network_order( |
|
4429 p_cipher_suite_length_network_order, |
|
4430 TLS_CIPHER_SUITE_LENGTH_FIELD_SIZE); |
|
4431 data_offset += TLS_CIPHER_SUITE_LENGTH_FIELD_SIZE; |
|
4432 |
|
4433 if (data_offset+cipher_suite_length > handshake_data_length) |
|
4434 { |
|
4435 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4436 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4437 } |
|
4438 |
|
4439 if ((cipher_suite_length % 2) != 0) |
|
4440 { |
|
4441 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4442 return EAP_STATUS_RETURN(m_am_tools, eap_status_header_corrupted); |
|
4443 } |
|
4444 |
|
4445 if (cipher_suite_length > 0ul) |
|
4446 { |
|
4447 u8_t *p_cipher_suite = tls_handshake_header->get_data_offset( |
|
4448 data_offset, |
|
4449 cipher_suite_length); |
|
4450 if (p_cipher_suite == 0) |
|
4451 { |
|
4452 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4453 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4454 } |
|
4455 |
|
4456 eap_array_c<u16_t> cipher_suites_array(m_am_tools); |
|
4457 |
|
4458 for (u32_t ind = 0ul; ind < cipher_suite_length; ind += 2ul) |
|
4459 { |
|
4460 u16_t * const cipher_suite = new u16_t; |
|
4461 if (cipher_suite == 0) |
|
4462 { |
|
4463 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4464 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
4465 } |
|
4466 |
|
4467 u16_t cipher_suite_host_order = eap_read_u16_t_network_order( |
|
4468 p_cipher_suite, |
|
4469 TLS_CIPHER_SUITE_FIELD_SIZE); |
|
4470 *cipher_suite = cipher_suite_host_order; |
|
4471 |
|
4472 // add_object() will delete cipher_suite if operation fails. |
|
4473 status = cipher_suites_array.add_object(cipher_suite, true); |
|
4474 if (status != eap_status_ok) |
|
4475 { |
|
4476 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4477 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4478 } |
|
4479 |
|
4480 p_cipher_suite += TLS_CIPHER_SUITE_FIELD_SIZE; |
|
4481 } // for() |
|
4482 |
|
4483 status = tls_handshake_message->set_cipher_suites(&cipher_suites_array); |
|
4484 if (status != eap_status_ok) |
|
4485 { |
|
4486 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4487 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4488 } |
|
4489 } |
|
4490 |
|
4491 data_offset += cipher_suite_length; |
|
4492 } |
|
4493 |
|
4494 //---------------------------------------------------------- |
|
4495 |
|
4496 { |
|
4497 if (data_offset+TLS_COMPRESSION_LENGTH_FIELD_SIZE > handshake_data_length) |
|
4498 { |
|
4499 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4500 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4501 } |
|
4502 |
|
4503 u8_t *p_compression_length = tls_handshake_header->get_data_offset( |
|
4504 data_offset, |
|
4505 TLS_COMPRESSION_LENGTH_FIELD_SIZE); |
|
4506 if (p_compression_length == 0) |
|
4507 { |
|
4508 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4509 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4510 } |
|
4511 data_offset += TLS_COMPRESSION_LENGTH_FIELD_SIZE; |
|
4512 |
|
4513 if (data_offset+*p_compression_length > handshake_data_length) |
|
4514 { |
|
4515 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4516 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4517 } |
|
4518 |
|
4519 if (*p_compression_length > 0ul) |
|
4520 { |
|
4521 u8_t *p_compression = tls_handshake_header->get_data_offset( |
|
4522 data_offset, |
|
4523 *p_compression_length); |
|
4524 if (p_compression == 0) |
|
4525 { |
|
4526 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4527 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4528 } |
|
4529 |
|
4530 eap_array_c<u8_t> compression_array(m_am_tools); |
|
4531 |
|
4532 for (u32_t ind = 0ul; ind < *p_compression_length; ind++) |
|
4533 { |
|
4534 u8_t * const compression_value = new u8_t; |
|
4535 if (compression_value == 0) |
|
4536 { |
|
4537 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4538 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
4539 } |
|
4540 *compression_value = *p_compression; |
|
4541 |
|
4542 // add_object() will delete compression_value if operation fails. |
|
4543 status = compression_array.add_object(compression_value, true); |
|
4544 if (status != eap_status_ok) |
|
4545 { |
|
4546 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4547 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4548 } |
|
4549 |
|
4550 p_compression += TLS_COMPRESSION_FIELD_SIZE; |
|
4551 } // for() |
|
4552 |
|
4553 status = tls_handshake_message->set_compression_methods(&compression_array); |
|
4554 if (status != eap_status_ok) |
|
4555 { |
|
4556 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4557 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4558 } |
|
4559 } |
|
4560 |
|
4561 data_offset += *p_compression_length; |
|
4562 } |
|
4563 |
|
4564 //---------------------------------------------------------- |
|
4565 |
|
4566 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
4567 |
|
4568 status = parse_tls_extension_list( |
|
4569 handshake_data_length, |
|
4570 &data_offset, |
|
4571 tls_handshake_header, |
|
4572 tls_handshake_message); |
|
4573 if (status != eap_status_ok) |
|
4574 { |
|
4575 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4576 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4577 } |
|
4578 |
|
4579 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
4580 |
|
4581 //---------------------------------------------------------- |
|
4582 |
|
4583 if (status == eap_status_ok) |
|
4584 { |
|
4585 // Note the add_handshake_message() frees message in any case. |
|
4586 automatic_tls_handshake_message.do_not_free_variable(); |
|
4587 |
|
4588 status = received_tls_record_message->add_handshake_message(tls_handshake_message, true); |
|
4589 if (status != eap_status_ok) |
|
4590 { |
|
4591 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4592 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4593 } |
|
4594 |
|
4595 status = message_hash_init(); |
|
4596 if (status != eap_status_ok) |
|
4597 { |
|
4598 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4599 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4600 } |
|
4601 } |
|
4602 |
|
4603 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4604 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4605 } |
|
4606 |
|
4607 //-------------------------------------------------- |
|
4608 |
|
4609 EAP_FUNC_EXPORT eap_status_e tls_record_c::parse_handshake_type_certificate( |
|
4610 tls_record_message_c * const received_tls_record_message, |
|
4611 tls_handshake_header_c * const tls_handshake_header, |
|
4612 const u32_t handshake_data_length) |
|
4613 { |
|
4614 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4615 |
|
4616 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
4617 EAP_TRACE_DEBUG( |
|
4618 m_am_tools, |
|
4619 TRACE_FLAGS_DEFAULT, |
|
4620 (EAPL("TLS: %s: parse_function: starts: tls_record_c::parse_handshake_type_certificate()\n"), |
|
4621 (m_is_client == true ? "client": "server"))); |
|
4622 |
|
4623 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::parse_handshake_type_certificate()"); |
|
4624 |
|
4625 tls_handshake_message_c *tls_handshake_message = 0; |
|
4626 |
|
4627 eap_automatic_variable_c<tls_handshake_message_c> |
|
4628 automatic_tls_handshake_message(m_am_tools); |
|
4629 |
|
4630 eap_status_e status = allocate_handshake_message_copy( |
|
4631 &tls_handshake_message, |
|
4632 &automatic_tls_handshake_message, |
|
4633 tls_handshake_header); |
|
4634 if (status != eap_status_ok) |
|
4635 { |
|
4636 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4637 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4638 } |
|
4639 |
|
4640 u32_t data_offset = 0ul; |
|
4641 |
|
4642 //---------------------------------------------------------- |
|
4643 |
|
4644 { |
|
4645 if (data_offset+(TLS_CERTIFICATE_LENGTH_FIELD_SIZE) > handshake_data_length) |
|
4646 { |
|
4647 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4648 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4649 } |
|
4650 |
|
4651 u8_t *p_certificate_chain_length = tls_handshake_header->get_data_offset( |
|
4652 data_offset, |
|
4653 (TLS_CERTIFICATE_LENGTH_FIELD_SIZE)); |
|
4654 if (p_certificate_chain_length == 0) |
|
4655 { |
|
4656 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4657 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4658 } |
|
4659 |
|
4660 u32_t certificate_chain_length = |
|
4661 eap_read_u24_t_network_order( |
|
4662 p_certificate_chain_length, |
|
4663 TLS_CERTIFICATE_LENGTH_FIELD_SIZE); |
|
4664 |
|
4665 data_offset += (TLS_CERTIFICATE_LENGTH_FIELD_SIZE); |
|
4666 |
|
4667 if (certificate_chain_length > 0ul) |
|
4668 { |
|
4669 eap_array_c<eap_variable_data_c> certificate_chain(m_am_tools); |
|
4670 u32_t max_data_offset = data_offset + certificate_chain_length; |
|
4671 |
|
4672 for (;data_offset < max_data_offset;) |
|
4673 { |
|
4674 u8_t *p_certificate_length = tls_handshake_header->get_data_offset( |
|
4675 data_offset, |
|
4676 (TLS_CERTIFICATE_LENGTH_FIELD_SIZE)); |
|
4677 if (p_certificate_length == 0) |
|
4678 { |
|
4679 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4680 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4681 } |
|
4682 |
|
4683 u32_t certificate_length = |
|
4684 eap_read_u24_t_network_order( |
|
4685 p_certificate_length, |
|
4686 TLS_CERTIFICATE_LENGTH_FIELD_SIZE); |
|
4687 |
|
4688 data_offset += (TLS_CERTIFICATE_LENGTH_FIELD_SIZE); |
|
4689 |
|
4690 |
|
4691 eap_variable_data_c * const certificate = new eap_variable_data_c(m_am_tools); |
|
4692 |
|
4693 eap_automatic_variable_c<eap_variable_data_c> |
|
4694 automatic_certificate(m_am_tools, certificate); |
|
4695 |
|
4696 if (certificate == 0) |
|
4697 { |
|
4698 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4699 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
4700 } |
|
4701 |
|
4702 |
|
4703 u8_t *p_certificate = tls_handshake_header->get_data_offset( |
|
4704 data_offset, |
|
4705 certificate_length); |
|
4706 if (p_certificate == 0) |
|
4707 { |
|
4708 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4709 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4710 } |
|
4711 |
|
4712 status = certificate->set_copy_of_buffer(p_certificate, certificate_length); |
|
4713 if (status != eap_status_ok) |
|
4714 { |
|
4715 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4716 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
4717 } |
|
4718 |
|
4719 automatic_certificate.do_not_free_variable(); |
|
4720 |
|
4721 // add_object() will delete certificate if operation fails. |
|
4722 status = certificate_chain.add_object(certificate, true); |
|
4723 if (status != eap_status_ok) |
|
4724 { |
|
4725 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4726 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4727 } |
|
4728 |
|
4729 data_offset += certificate_length; |
|
4730 } // for() |
|
4731 |
|
4732 status = tls_handshake_message->set_certificate_chain(&certificate_chain); |
|
4733 if (status != eap_status_ok) |
|
4734 { |
|
4735 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4736 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4737 } |
|
4738 } |
|
4739 |
|
4740 data_offset += certificate_chain_length; |
|
4741 } |
|
4742 |
|
4743 //---------------------------------------------------------- |
|
4744 |
|
4745 if (status == eap_status_ok) |
|
4746 { |
|
4747 // Note the add_handshake_message() frees message in any case. |
|
4748 automatic_tls_handshake_message.do_not_free_variable(); |
|
4749 |
|
4750 status = received_tls_record_message->add_handshake_message(tls_handshake_message, true); |
|
4751 if (status != eap_status_ok) |
|
4752 { |
|
4753 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4754 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4755 } |
|
4756 } |
|
4757 |
|
4758 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4759 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4760 } |
|
4761 |
|
4762 //-------------------------------------------------- |
|
4763 |
|
4764 EAP_FUNC_EXPORT eap_status_e tls_record_c::parse_handshake_type_certificate_request( |
|
4765 tls_record_message_c * const received_tls_record_message, |
|
4766 tls_handshake_header_c * const tls_handshake_header, |
|
4767 const u32_t handshake_data_length) |
|
4768 { |
|
4769 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4770 |
|
4771 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
4772 EAP_TRACE_DEBUG( |
|
4773 m_am_tools, |
|
4774 TRACE_FLAGS_DEFAULT, |
|
4775 (EAPL("TLS: %s: parse_function: starts: tls_record_c::parse_handshake_type_certificate_request()\n"), |
|
4776 (m_is_client == true ? "client": "server"))); |
|
4777 |
|
4778 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::parse_handshake_type_certificate_request()"); |
|
4779 |
|
4780 tls_handshake_message_c *tls_handshake_message = 0; |
|
4781 |
|
4782 eap_automatic_variable_c<tls_handshake_message_c> |
|
4783 automatic_tls_handshake_message(m_am_tools); |
|
4784 |
|
4785 eap_status_e status = allocate_handshake_message_copy( |
|
4786 &tls_handshake_message, |
|
4787 &automatic_tls_handshake_message, |
|
4788 tls_handshake_header); |
|
4789 if (status != eap_status_ok) |
|
4790 { |
|
4791 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4792 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4793 } |
|
4794 |
|
4795 u32_t data_offset = 0ul; |
|
4796 |
|
4797 //---------------------------------------------------------- |
|
4798 |
|
4799 { |
|
4800 if (data_offset+TLS_CERTIFICATE_TYPE_LENGTH_FIELD_SIZE > handshake_data_length) |
|
4801 { |
|
4802 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4803 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4804 } |
|
4805 |
|
4806 u8_t *p_certificate_type_length = tls_handshake_header->get_data_offset( |
|
4807 data_offset, |
|
4808 TLS_CERTIFICATE_TYPE_LENGTH_FIELD_SIZE); |
|
4809 if (p_certificate_type_length == 0) |
|
4810 { |
|
4811 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4812 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4813 } |
|
4814 data_offset += TLS_CERTIFICATE_TYPE_LENGTH_FIELD_SIZE; |
|
4815 |
|
4816 if (data_offset+*p_certificate_type_length > handshake_data_length) |
|
4817 { |
|
4818 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4819 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4820 } |
|
4821 |
|
4822 if (*p_certificate_type_length > 0ul) |
|
4823 { |
|
4824 u8_t *p_certificate_type = tls_handshake_header->get_data_offset( |
|
4825 data_offset, |
|
4826 *p_certificate_type_length); |
|
4827 if (p_certificate_type == 0) |
|
4828 { |
|
4829 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4830 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4831 } |
|
4832 |
|
4833 eap_array_c<u8_t> certificate_type_array(m_am_tools); |
|
4834 |
|
4835 for (u32_t ind = 0ul; ind < *p_certificate_type_length; ind++) |
|
4836 { |
|
4837 u8_t * const certificate_type_value = new u8_t; |
|
4838 if (certificate_type_value == 0) |
|
4839 { |
|
4840 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4841 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
4842 } |
|
4843 *certificate_type_value = *p_certificate_type; |
|
4844 |
|
4845 // add_object() will delete certificate_type_value if operation fails. |
|
4846 status = certificate_type_array.add_object(certificate_type_value, true); |
|
4847 if (status != eap_status_ok) |
|
4848 { |
|
4849 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4850 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4851 } |
|
4852 |
|
4853 p_certificate_type += TLS_CERTIFICATE_TYPE_FIELD_SIZE; |
|
4854 } // for() |
|
4855 |
|
4856 status = tls_handshake_message->set_certificate_types(&certificate_type_array); |
|
4857 if (status != eap_status_ok) |
|
4858 { |
|
4859 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4860 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4861 } |
|
4862 } |
|
4863 |
|
4864 data_offset += *p_certificate_type_length; |
|
4865 } |
|
4866 |
|
4867 //---------------------------------------------------------- |
|
4868 |
|
4869 { |
|
4870 if (data_offset+TLS_CERTIFICATE_AUTHORITIES_LENGTH_FIELD_SIZE > handshake_data_length) |
|
4871 { |
|
4872 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4873 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4874 } |
|
4875 |
|
4876 u8_t *p_certificate_authorities_length = tls_handshake_header->get_data_offset( |
|
4877 data_offset, |
|
4878 TLS_CERTIFICATE_AUTHORITIES_LENGTH_FIELD_SIZE); |
|
4879 if (p_certificate_authorities_length == 0) |
|
4880 { |
|
4881 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4882 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4883 } |
|
4884 |
|
4885 u32_t certificate_authorities_length = |
|
4886 eap_read_u16_t_network_order( |
|
4887 p_certificate_authorities_length, |
|
4888 TLS_CERTIFICATE_AUTHORITIES_LENGTH_FIELD_SIZE); |
|
4889 |
|
4890 data_offset += TLS_CERTIFICATE_AUTHORITIES_LENGTH_FIELD_SIZE; |
|
4891 |
|
4892 if (certificate_authorities_length > 0ul) |
|
4893 { |
|
4894 eap_array_c<eap_variable_data_c> certificate_authorities(m_am_tools); |
|
4895 u32_t max_data_offset = data_offset + certificate_authorities_length; |
|
4896 |
|
4897 for (;data_offset < max_data_offset;) |
|
4898 { |
|
4899 u8_t *p_certificate_authority_length = tls_handshake_header->get_data_offset( |
|
4900 data_offset, |
|
4901 TLS_CERTIFICATE_AUTHORITIES_LENGTH_FIELD_SIZE); |
|
4902 if (p_certificate_authority_length == 0) |
|
4903 { |
|
4904 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4905 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4906 } |
|
4907 |
|
4908 u32_t certificate_authority_length = |
|
4909 eap_read_u16_t_network_order( |
|
4910 p_certificate_authority_length, |
|
4911 TLS_CERTIFICATE_AUTHORITIES_LENGTH_FIELD_SIZE); |
|
4912 |
|
4913 data_offset += TLS_CERTIFICATE_AUTHORITIES_LENGTH_FIELD_SIZE; |
|
4914 |
|
4915 { |
|
4916 eap_variable_data_c * const certificate_authority |
|
4917 = new eap_variable_data_c(m_am_tools); |
|
4918 |
|
4919 eap_automatic_variable_c<eap_variable_data_c> |
|
4920 automatic_certificate_authority(m_am_tools, certificate_authority); |
|
4921 |
|
4922 if (certificate_authority == 0) |
|
4923 { |
|
4924 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4925 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
4926 } |
|
4927 |
|
4928 |
|
4929 u8_t *p_certificate_authority = tls_handshake_header->get_data_offset( |
|
4930 data_offset, |
|
4931 certificate_authority_length); |
|
4932 if (p_certificate_authority == 0) |
|
4933 { |
|
4934 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4935 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
4936 } |
|
4937 |
|
4938 status = certificate_authority->set_copy_of_buffer( |
|
4939 p_certificate_authority, |
|
4940 certificate_authority_length); |
|
4941 if (status != eap_status_ok) |
|
4942 { |
|
4943 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4944 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
4945 } |
|
4946 |
|
4947 automatic_certificate_authority.do_not_free_variable(); |
|
4948 |
|
4949 // add_object() will delete certificate_authority if operation fails. |
|
4950 status = certificate_authorities.add_object(certificate_authority, true); |
|
4951 if (status != eap_status_ok) |
|
4952 { |
|
4953 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4954 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4955 } |
|
4956 } |
|
4957 |
|
4958 data_offset += certificate_authority_length; |
|
4959 } // for() |
|
4960 |
|
4961 status = tls_handshake_message->set_certificate_authorities(&certificate_authorities); |
|
4962 if (status != eap_status_ok) |
|
4963 { |
|
4964 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4965 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4966 } |
|
4967 } |
|
4968 |
|
4969 data_offset += certificate_authorities_length; |
|
4970 } |
|
4971 |
|
4972 //---------------------------------------------------------- |
|
4973 |
|
4974 if (status == eap_status_ok) |
|
4975 { |
|
4976 // Note the add_handshake_message() frees message in any case. |
|
4977 automatic_tls_handshake_message.do_not_free_variable(); |
|
4978 |
|
4979 status = received_tls_record_message->add_handshake_message(tls_handshake_message, true); |
|
4980 if (status != eap_status_ok) |
|
4981 { |
|
4982 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4983 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4984 } |
|
4985 } |
|
4986 |
|
4987 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4988 return EAP_STATUS_RETURN(m_am_tools, status); |
|
4989 } |
|
4990 |
|
4991 //-------------------------------------------------- |
|
4992 |
|
4993 EAP_FUNC_EXPORT eap_status_e tls_record_c::parse_handshake_type_server_hello_done( |
|
4994 tls_record_message_c * const received_tls_record_message, |
|
4995 tls_handshake_header_c * const tls_handshake_header, |
|
4996 const u32_t /* handshake_data_length */) |
|
4997 { |
|
4998 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
4999 |
|
5000 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
5001 EAP_TRACE_DEBUG( |
|
5002 m_am_tools, |
|
5003 TRACE_FLAGS_DEFAULT, |
|
5004 (EAPL("TLS: %s: parse_function: starts: tls_record_c::parse_handshake_type_server_hello_done()\n"), |
|
5005 (m_is_client == true ? "client": "server"))); |
|
5006 |
|
5007 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::parse_handshake_type_server_hello_done()"); |
|
5008 |
|
5009 tls_handshake_message_c *tls_handshake_message = 0; |
|
5010 |
|
5011 eap_automatic_variable_c<tls_handshake_message_c> |
|
5012 automatic_tls_handshake_message(m_am_tools); |
|
5013 |
|
5014 eap_status_e status = allocate_handshake_message_copy( |
|
5015 &tls_handshake_message, |
|
5016 &automatic_tls_handshake_message, |
|
5017 tls_handshake_header); |
|
5018 if (status != eap_status_ok) |
|
5019 { |
|
5020 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5021 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5022 } |
|
5023 |
|
5024 if (tls_handshake_header->get_data_length() > 0ul) |
|
5025 { |
|
5026 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5027 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_long_message); |
|
5028 } |
|
5029 |
|
5030 //---------------------------------------------------------- |
|
5031 |
|
5032 if (status == eap_status_ok) |
|
5033 { |
|
5034 // Note the add_handshake_message() frees message in any case. |
|
5035 automatic_tls_handshake_message.do_not_free_variable(); |
|
5036 |
|
5037 status = received_tls_record_message->add_handshake_message(tls_handshake_message, true); |
|
5038 if (status != eap_status_ok) |
|
5039 { |
|
5040 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5041 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5042 } |
|
5043 } |
|
5044 |
|
5045 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5046 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5047 } |
|
5048 |
|
5049 //-------------------------------------------------- |
|
5050 |
|
5051 EAP_FUNC_EXPORT eap_status_e tls_record_c::parse_handshake_type_server_hello( |
|
5052 tls_record_message_c * const received_tls_record_message, |
|
5053 tls_handshake_header_c * const tls_handshake_header, |
|
5054 const u32_t handshake_data_length) |
|
5055 { |
|
5056 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5057 |
|
5058 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
5059 EAP_TRACE_DEBUG( |
|
5060 m_am_tools, |
|
5061 TRACE_FLAGS_DEFAULT, |
|
5062 (EAPL("TLS: %s: parse_function: starts: tls_record_c::parse_handshake_type_server_hello()\n"), |
|
5063 (m_is_client == true ? "client": "server"))); |
|
5064 |
|
5065 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::parse_handshake_type_server_hello()"); |
|
5066 |
|
5067 tls_handshake_message_c *tls_handshake_message = 0; |
|
5068 |
|
5069 eap_automatic_variable_c<tls_handshake_message_c> |
|
5070 automatic_tls_handshake_message(m_am_tools); |
|
5071 |
|
5072 eap_status_e status = allocate_handshake_message_copy( |
|
5073 &tls_handshake_message, |
|
5074 &automatic_tls_handshake_message, |
|
5075 tls_handshake_header); |
|
5076 if (status != eap_status_ok) |
|
5077 { |
|
5078 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5079 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5080 } |
|
5081 |
|
5082 u32_t data_offset = 0ul; |
|
5083 |
|
5084 u8_t * handshake_data = tls_handshake_header->get_data_offset( |
|
5085 data_offset, |
|
5086 tls_handshake_header->get_data_length()); |
|
5087 if (handshake_data == 0) |
|
5088 { |
|
5089 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5090 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5091 } |
|
5092 |
|
5093 //---------------------------------------------------------- |
|
5094 |
|
5095 { |
|
5096 if (data_offset+TLS_VERSION_FIELD_SIZE > handshake_data_length) |
|
5097 { |
|
5098 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5099 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5100 } |
|
5101 |
|
5102 u8_t *p_version = handshake_data; |
|
5103 u16_t version = eap_read_u16_t_network_order(p_version, TLS_VERSION_FIELD_SIZE); |
|
5104 |
|
5105 if (version != tls_version_3_1) |
|
5106 { |
|
5107 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5108 return EAP_STATUS_RETURN(m_am_tools, eap_status_header_corrupted); |
|
5109 } |
|
5110 |
|
5111 data_offset += TLS_VERSION_FIELD_SIZE; |
|
5112 } |
|
5113 |
|
5114 //---------------------------------------------------------- |
|
5115 |
|
5116 { |
|
5117 if (data_offset+TLS_HANDSHAKE_RANDOM_VALUE_SIZE > handshake_data_length) |
|
5118 { |
|
5119 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5120 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5121 } |
|
5122 |
|
5123 u8_t *p_random_value = tls_handshake_header->get_data_offset( |
|
5124 data_offset, |
|
5125 TLS_HANDSHAKE_RANDOM_VALUE_SIZE); |
|
5126 if (p_random_value == 0) |
|
5127 { |
|
5128 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5129 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5130 } |
|
5131 eap_variable_data_c server_random_value(m_am_tools); |
|
5132 status = server_random_value.set_buffer( |
|
5133 p_random_value, |
|
5134 TLS_HANDSHAKE_RANDOM_VALUE_SIZE, |
|
5135 false, |
|
5136 false); |
|
5137 if (status != eap_status_ok) |
|
5138 { |
|
5139 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5140 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5141 } |
|
5142 |
|
5143 status = tls_handshake_message->set_random_value(&server_random_value); |
|
5144 if (status != eap_status_ok) |
|
5145 { |
|
5146 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5147 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5148 } |
|
5149 |
|
5150 data_offset += TLS_HANDSHAKE_RANDOM_VALUE_SIZE; |
|
5151 |
|
5152 EAP_TRACE_DATA_DEBUG( |
|
5153 m_am_tools, |
|
5154 TRACE_FLAGS_DEFAULT, |
|
5155 (EAPL("TLS: parse_handshake_type_server_hello(): m_server_random_value"), |
|
5156 server_random_value.get_data(server_random_value.get_data_length()), |
|
5157 server_random_value.get_data_length())); |
|
5158 } |
|
5159 |
|
5160 //---------------------------------------------------------- |
|
5161 |
|
5162 { |
|
5163 if (data_offset+TLS_SESSION_ID_LENGTH_FIELD_SIZE > handshake_data_length) |
|
5164 { |
|
5165 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5166 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5167 } |
|
5168 |
|
5169 u8_t *p_session_id_length = tls_handshake_header->get_data_offset( |
|
5170 data_offset, |
|
5171 TLS_SESSION_ID_LENGTH_FIELD_SIZE); |
|
5172 if (p_session_id_length == 0) |
|
5173 { |
|
5174 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5175 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5176 } |
|
5177 data_offset += TLS_SESSION_ID_LENGTH_FIELD_SIZE; |
|
5178 |
|
5179 if (data_offset+*p_session_id_length > handshake_data_length) |
|
5180 { |
|
5181 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5182 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5183 } |
|
5184 |
|
5185 if (*p_session_id_length > 0ul) |
|
5186 { |
|
5187 u8_t *p_session_id = tls_handshake_header->get_data_offset( |
|
5188 data_offset, |
|
5189 *p_session_id_length); |
|
5190 if (p_session_id == 0) |
|
5191 { |
|
5192 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5193 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5194 } |
|
5195 |
|
5196 eap_variable_data_c session_id(m_am_tools); |
|
5197 status = session_id.set_buffer(p_session_id, *p_session_id_length, false, false); |
|
5198 if (status != eap_status_ok) |
|
5199 { |
|
5200 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5201 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5202 } |
|
5203 |
|
5204 status = tls_handshake_message->set_session_id(&session_id); |
|
5205 if (status != eap_status_ok) |
|
5206 { |
|
5207 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5208 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5209 } |
|
5210 |
|
5211 EAP_TRACE_DATA_DEBUG( |
|
5212 m_am_tools, |
|
5213 TRACE_FLAGS_DEFAULT, |
|
5214 (EAPL("TLS: parse_handshake_type_server_hello(): session_id"), |
|
5215 session_id.get_data(session_id.get_data_length()), |
|
5216 session_id.get_data_length())); |
|
5217 } |
|
5218 |
|
5219 data_offset += *p_session_id_length; |
|
5220 } |
|
5221 |
|
5222 //---------------------------------------------------------- |
|
5223 |
|
5224 { |
|
5225 if (data_offset+TLS_CIPHER_SUITE_FIELD_SIZE > handshake_data_length) |
|
5226 { |
|
5227 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5228 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5229 } |
|
5230 |
|
5231 u8_t *p_cipher_suite_network_order = tls_handshake_header->get_data_offset( |
|
5232 data_offset, |
|
5233 TLS_CIPHER_SUITE_FIELD_SIZE); |
|
5234 if (p_cipher_suite_network_order == 0) |
|
5235 { |
|
5236 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5237 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5238 } |
|
5239 u16_t cipher_suite |
|
5240 = eap_read_u16_t_network_order( |
|
5241 p_cipher_suite_network_order, |
|
5242 TLS_CIPHER_SUITE_FIELD_SIZE); |
|
5243 |
|
5244 status = tls_handshake_message->set_selected_cipher_suite( |
|
5245 static_cast<tls_cipher_suites_e>(cipher_suite)); |
|
5246 if (status != eap_status_ok) |
|
5247 { |
|
5248 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5249 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5250 } |
|
5251 |
|
5252 EAP_TRACE_DATA_DEBUG( |
|
5253 m_am_tools, |
|
5254 TRACE_FLAGS_DEFAULT, |
|
5255 (EAPL("TLS: parse_handshake_type_server_hello(): cipher_suite"), |
|
5256 &cipher_suite, |
|
5257 sizeof(cipher_suite))); |
|
5258 |
|
5259 data_offset += TLS_CIPHER_SUITE_FIELD_SIZE; |
|
5260 } |
|
5261 |
|
5262 //---------------------------------------------------------- |
|
5263 |
|
5264 { |
|
5265 if (data_offset+TLS_COMPRESSION_METHOD_FIELD_SIZE > handshake_data_length) |
|
5266 { |
|
5267 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5268 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5269 } |
|
5270 |
|
5271 u8_t *p_compression = tls_handshake_header->get_data_offset( |
|
5272 data_offset, |
|
5273 TLS_COMPRESSION_METHOD_FIELD_SIZE); |
|
5274 if (p_compression == 0) |
|
5275 { |
|
5276 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5277 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5278 } |
|
5279 |
|
5280 status = tls_handshake_message->set_selected_compression_method( |
|
5281 static_cast<tls_compression_method_e>(*p_compression)); |
|
5282 if (status != eap_status_ok) |
|
5283 { |
|
5284 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5285 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5286 } |
|
5287 |
|
5288 EAP_TRACE_DATA_DEBUG( |
|
5289 m_am_tools, |
|
5290 TRACE_FLAGS_DEFAULT, |
|
5291 (EAPL("TLS: parse_handshake_type_server_hello(): p_compression"), |
|
5292 p_compression, |
|
5293 sizeof(*p_compression))); |
|
5294 |
|
5295 data_offset += TLS_COMPRESSION_METHOD_FIELD_SIZE; |
|
5296 } |
|
5297 |
|
5298 //---------------------------------------------------------- |
|
5299 |
|
5300 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
5301 |
|
5302 status = parse_tls_extension_list( |
|
5303 handshake_data_length, |
|
5304 &data_offset, |
|
5305 tls_handshake_header, |
|
5306 tls_handshake_message); |
|
5307 if (status != eap_status_ok) |
|
5308 { |
|
5309 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5310 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5311 } |
|
5312 |
|
5313 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
5314 |
|
5315 //---------------------------------------------------------- |
|
5316 |
|
5317 if (status == eap_status_ok) |
|
5318 { |
|
5319 // Note the add_handshake_message() frees message in any case. |
|
5320 automatic_tls_handshake_message.do_not_free_variable(); |
|
5321 |
|
5322 status = received_tls_record_message->add_handshake_message(tls_handshake_message, true); |
|
5323 if (status != eap_status_ok) |
|
5324 { |
|
5325 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5326 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5327 } |
|
5328 } |
|
5329 |
|
5330 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5331 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5332 } |
|
5333 |
|
5334 //-------------------------------------------------- |
|
5335 |
|
5336 EAP_FUNC_EXPORT eap_status_e tls_record_c::parse_handshake_type_server_key_exchange( |
|
5337 tls_record_message_c * const received_tls_record_message, |
|
5338 tls_handshake_header_c * const tls_handshake_header, |
|
5339 const u32_t handshake_data_length) |
|
5340 { |
|
5341 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5342 |
|
5343 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
5344 EAP_TRACE_DEBUG( |
|
5345 m_am_tools, |
|
5346 TRACE_FLAGS_DEFAULT, |
|
5347 (EAPL("TLS: %s: parse_function: starts: tls_record_c::parse_handshake_type_server_key_exchange()\n"), |
|
5348 (m_is_client == true ? "client": "server"))); |
|
5349 |
|
5350 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::parse_handshake_type_server_key_exchange()"); |
|
5351 |
|
5352 tls_handshake_message_c *tls_handshake_message = 0; |
|
5353 |
|
5354 eap_automatic_variable_c<tls_handshake_message_c> |
|
5355 automatic_tls_handshake_message(m_am_tools); |
|
5356 |
|
5357 eap_status_e status = allocate_handshake_message_copy( |
|
5358 &tls_handshake_message, |
|
5359 &automatic_tls_handshake_message, |
|
5360 tls_handshake_header); |
|
5361 if (status != eap_status_ok) |
|
5362 { |
|
5363 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5364 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5365 } |
|
5366 |
|
5367 u32_t handshake_length = tls_handshake_header->get_data_length(); |
|
5368 u32_t data_offset = 0ul; |
|
5369 |
|
5370 //---------------------------------------------------------- |
|
5371 |
|
5372 { |
|
5373 if (data_offset+TLS_DHE_PRIME_LENGTH_FIELD_SIZE > handshake_data_length) |
|
5374 { |
|
5375 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5376 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5377 } |
|
5378 |
|
5379 u8_t *p_dhe_prime_length = tls_handshake_header->get_data_offset( |
|
5380 data_offset, |
|
5381 TLS_DHE_PRIME_LENGTH_FIELD_SIZE); |
|
5382 if (p_dhe_prime_length == 0) |
|
5383 { |
|
5384 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5385 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5386 } |
|
5387 data_offset += TLS_DHE_PRIME_LENGTH_FIELD_SIZE; |
|
5388 |
|
5389 u16_t dhe_prime_length |
|
5390 = eap_read_u16_t_network_order(p_dhe_prime_length, TLS_DHE_PRIME_LENGTH_FIELD_SIZE); |
|
5391 |
|
5392 u8_t *p_dhe_prime_value = tls_handshake_header->get_data_offset( |
|
5393 data_offset, |
|
5394 dhe_prime_length); |
|
5395 if (p_dhe_prime_value == 0) |
|
5396 { |
|
5397 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5398 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5399 } |
|
5400 |
|
5401 eap_variable_data_c dhe_prime(m_am_tools); |
|
5402 status = dhe_prime.set_buffer(p_dhe_prime_value, dhe_prime_length, false, false); |
|
5403 if (status != eap_status_ok) |
|
5404 { |
|
5405 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5406 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5407 } |
|
5408 |
|
5409 status = tls_handshake_message->set_dhe_prime(&dhe_prime); |
|
5410 if (status != eap_status_ok) |
|
5411 { |
|
5412 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5413 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5414 } |
|
5415 |
|
5416 data_offset += dhe_prime_length; |
|
5417 } |
|
5418 |
|
5419 //---------------------------------------------------------- |
|
5420 |
|
5421 { |
|
5422 if (data_offset+TLS_DHE_GROUP_GENERATOR_LENGTH_FIELD_SIZE > handshake_data_length) |
|
5423 { |
|
5424 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5425 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5426 } |
|
5427 |
|
5428 u8_t *p_dhe_group_generator_length = tls_handshake_header->get_data_offset( |
|
5429 data_offset, |
|
5430 TLS_DHE_GROUP_GENERATOR_LENGTH_FIELD_SIZE); |
|
5431 if (p_dhe_group_generator_length == 0) |
|
5432 { |
|
5433 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5434 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5435 } |
|
5436 data_offset += TLS_DHE_GROUP_GENERATOR_LENGTH_FIELD_SIZE; |
|
5437 |
|
5438 u16_t dhe_group_generator_length = |
|
5439 eap_read_u16_t_network_order( |
|
5440 p_dhe_group_generator_length, |
|
5441 TLS_DHE_GROUP_GENERATOR_LENGTH_FIELD_SIZE); |
|
5442 |
|
5443 u8_t *p_dhe_group_generator_value = tls_handshake_header->get_data_offset( |
|
5444 data_offset, |
|
5445 dhe_group_generator_length); |
|
5446 if (p_dhe_group_generator_value == 0) |
|
5447 { |
|
5448 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5449 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5450 } |
|
5451 |
|
5452 eap_variable_data_c dhe_group_generator(m_am_tools); |
|
5453 status = dhe_group_generator.set_buffer( |
|
5454 p_dhe_group_generator_value, |
|
5455 dhe_group_generator_length, |
|
5456 false, |
|
5457 false); |
|
5458 if (status != eap_status_ok) |
|
5459 { |
|
5460 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5461 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5462 } |
|
5463 |
|
5464 status = tls_handshake_message->set_dhe_group_generator(&dhe_group_generator); |
|
5465 if (status != eap_status_ok) |
|
5466 { |
|
5467 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5468 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5469 } |
|
5470 |
|
5471 data_offset += dhe_group_generator_length; |
|
5472 } |
|
5473 |
|
5474 //---------------------------------------------------------- |
|
5475 |
|
5476 { |
|
5477 if (data_offset+TLS_PUBLIC_DHE_KEY_LENGTH_FIELD_SIZE > handshake_data_length) |
|
5478 { |
|
5479 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5480 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5481 } |
|
5482 |
|
5483 u8_t *p_public_dhe_key_length = tls_handshake_header->get_data_offset( |
|
5484 data_offset, |
|
5485 TLS_PUBLIC_DHE_KEY_LENGTH_FIELD_SIZE); |
|
5486 if (p_public_dhe_key_length == 0) |
|
5487 { |
|
5488 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5489 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5490 } |
|
5491 data_offset += TLS_PUBLIC_DHE_KEY_LENGTH_FIELD_SIZE; |
|
5492 |
|
5493 u16_t public_dhe_key_length = |
|
5494 eap_read_u16_t_network_order( |
|
5495 p_public_dhe_key_length, |
|
5496 TLS_PUBLIC_DHE_KEY_LENGTH_FIELD_SIZE); |
|
5497 |
|
5498 u8_t *p_public_dhe_key_value = tls_handshake_header->get_data_offset( |
|
5499 data_offset, |
|
5500 public_dhe_key_length); |
|
5501 if (p_public_dhe_key_value == 0) |
|
5502 { |
|
5503 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5504 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5505 } |
|
5506 |
|
5507 eap_variable_data_c public_dhe_key(m_am_tools); |
|
5508 status = public_dhe_key.set_buffer( |
|
5509 p_public_dhe_key_value, |
|
5510 public_dhe_key_length, |
|
5511 false, |
|
5512 false); |
|
5513 if (status != eap_status_ok) |
|
5514 { |
|
5515 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5516 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5517 } |
|
5518 |
|
5519 status = tls_handshake_message->set_public_dhe_key(&public_dhe_key); |
|
5520 if (status != eap_status_ok) |
|
5521 { |
|
5522 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5523 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5524 } |
|
5525 |
|
5526 data_offset += public_dhe_key_length; |
|
5527 } |
|
5528 |
|
5529 //---------------------------------------------------------- |
|
5530 |
|
5531 #if defined(USE_FAST_EAP_TYPE) |
|
5532 if (m_eap_type == eap_type_fast |
|
5533 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true |
|
5534 && data_offset == handshake_data_length) |
|
5535 { |
|
5536 // Here are no signed hash. |
|
5537 EAP_TRACE_DEBUG( |
|
5538 m_am_tools, |
|
5539 TRACE_FLAGS_DEFAULT, |
|
5540 (EAPL("TLS: %s: parse_function: starts: tls_record_c::parse_handshake_type_server_key_exchange(): EAP-FAST server unauthenticated provisioning mode, no signed hash\n"), |
|
5541 (m_is_client == true ? "client": "server"))); |
|
5542 } |
|
5543 else |
|
5544 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
5545 { |
|
5546 if (data_offset >= handshake_data_length) |
|
5547 { |
|
5548 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5549 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5550 } |
|
5551 |
|
5552 u16_t expected_dss_sha1_signature_length |
|
5553 = static_cast<u16_t>(handshake_length - data_offset); |
|
5554 |
|
5555 u8_t *p_dss_sha1_signature_length = tls_handshake_header->get_data_offset( |
|
5556 data_offset, |
|
5557 TLS_DSS_SHA1_SIGNATURE_LENGTH_FIELD_SIZE); |
|
5558 if (p_dss_sha1_signature_length == 0) |
|
5559 { |
|
5560 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5561 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5562 } |
|
5563 |
|
5564 u16_t dss_sha1_signature_length = |
|
5565 eap_read_u16_t_network_order( |
|
5566 p_dss_sha1_signature_length, |
|
5567 TLS_DSS_SHA1_SIGNATURE_LENGTH_FIELD_SIZE); |
|
5568 |
|
5569 if (expected_dss_sha1_signature_length == dss_sha1_signature_length+2ul) |
|
5570 { |
|
5571 // WARNING: Here we have additional length field. OpenSSL does this. |
|
5572 /* |
|
5573 // TLS 1.0 RFC 2246 says the length of sha_hash is explicitly 20 bytes |
|
5574 // (Chapter 7.4.3. Server key exchange message). |
|
5575 // The length of the vector is not included in the encoded stream |
|
5576 // (Chapter 4.3. Vectors). |
|
5577 select (SignatureAlgorithm) |
|
5578 { case anonymous: struct { }; |
|
5579 case rsa: |
|
5580 digitally-signed struct { |
|
5581 opaque md5_hash[16]; |
|
5582 opaque sha_hash[20]; |
|
5583 }; |
|
5584 case dsa: |
|
5585 digitally-signed struct { |
|
5586 opaque sha_hash[20]; |
|
5587 }; |
|
5588 } Signature; |
|
5589 */ |
|
5590 data_offset += TLS_DSS_SHA1_SIGNATURE_LENGTH_FIELD_SIZE; |
|
5591 } |
|
5592 else |
|
5593 { |
|
5594 dss_sha1_signature_length = expected_dss_sha1_signature_length; |
|
5595 } |
|
5596 |
|
5597 u8_t *p_dss_sha1_signature = tls_handshake_header->get_data_offset( |
|
5598 data_offset, |
|
5599 dss_sha1_signature_length); |
|
5600 if (p_dss_sha1_signature == 0) |
|
5601 { |
|
5602 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5603 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5604 } |
|
5605 |
|
5606 eap_variable_data_c dss_sha1_signature(m_am_tools); |
|
5607 status = dss_sha1_signature.set_buffer( |
|
5608 p_dss_sha1_signature, |
|
5609 dss_sha1_signature_length, |
|
5610 false, |
|
5611 false); |
|
5612 if (status != eap_status_ok) |
|
5613 { |
|
5614 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5615 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5616 } |
|
5617 |
|
5618 status = tls_handshake_message->set_signed_message_hash(&dss_sha1_signature); |
|
5619 if (status != eap_status_ok) |
|
5620 { |
|
5621 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5622 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5623 } |
|
5624 |
|
5625 data_offset += dss_sha1_signature_length; |
|
5626 } |
|
5627 |
|
5628 //---------------------------------------------------------- |
|
5629 |
|
5630 if (status == eap_status_ok) |
|
5631 { |
|
5632 // Note the add_handshake_message() frees message in any case. |
|
5633 automatic_tls_handshake_message.do_not_free_variable(); |
|
5634 |
|
5635 status = received_tls_record_message->add_handshake_message(tls_handshake_message, true); |
|
5636 if (status != eap_status_ok) |
|
5637 { |
|
5638 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5639 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5640 } |
|
5641 } |
|
5642 |
|
5643 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5644 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5645 } |
|
5646 |
|
5647 //-------------------------------------------------- |
|
5648 |
|
5649 EAP_FUNC_EXPORT eap_status_e tls_record_c::parse_handshake_type_client_key_exchange( |
|
5650 tls_record_message_c * const received_tls_record_message, |
|
5651 tls_handshake_header_c * const tls_handshake_header, |
|
5652 const u32_t handshake_data_length) |
|
5653 { |
|
5654 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5655 |
|
5656 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
5657 EAP_TRACE_DEBUG( |
|
5658 m_am_tools, |
|
5659 TRACE_FLAGS_DEFAULT, |
|
5660 (EAPL("TLS: %s: parse_function: starts: tls_record_c::parse_handshake_type_client_key_exchange()\n"), |
|
5661 (m_is_client == true ? "client": "server"))); |
|
5662 |
|
5663 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::parse_handshake_type_client_key_exchange()"); |
|
5664 |
|
5665 tls_handshake_message_c *tls_handshake_message = 0; |
|
5666 |
|
5667 eap_automatic_variable_c<tls_handshake_message_c> |
|
5668 automatic_tls_handshake_message(m_am_tools); |
|
5669 |
|
5670 eap_status_e status = allocate_handshake_message_copy( |
|
5671 &tls_handshake_message, |
|
5672 &automatic_tls_handshake_message, |
|
5673 tls_handshake_header); |
|
5674 if (status != eap_status_ok) |
|
5675 { |
|
5676 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5677 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5678 } |
|
5679 |
|
5680 u32_t data_offset = 0ul; |
|
5681 |
|
5682 //---------------------------------------------------------- |
|
5683 |
|
5684 if (cipher_suite_is_TLS_RSA() == true) |
|
5685 { |
|
5686 u32_t encrypted_premaster_secret_length = tls_handshake_header->get_data_length(); |
|
5687 |
|
5688 if (data_offset+encrypted_premaster_secret_length > handshake_data_length) |
|
5689 { |
|
5690 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5691 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5692 } |
|
5693 |
|
5694 u8_t *p_encrypted_premaster_secret_length = tls_handshake_header->get_data_offset( |
|
5695 data_offset, |
|
5696 TLS_ENCRYPTED_PREMASTER_SECRET_LENGTH_FIELD_SIZE); |
|
5697 if (p_encrypted_premaster_secret_length == 0) |
|
5698 { |
|
5699 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5700 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5701 } |
|
5702 data_offset += TLS_ENCRYPTED_PREMASTER_SECRET_LENGTH_FIELD_SIZE; |
|
5703 |
|
5704 u16_t data_encrypted_premaster_secret_length |
|
5705 = eap_read_u16_t_network_order( |
|
5706 p_encrypted_premaster_secret_length, |
|
5707 TLS_ENCRYPTED_PREMASTER_SECRET_LENGTH_FIELD_SIZE); |
|
5708 |
|
5709 if ((data_encrypted_premaster_secret_length + 2ul) != encrypted_premaster_secret_length) |
|
5710 { |
|
5711 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5712 return EAP_STATUS_RETURN(m_am_tools, eap_status_header_corrupted); |
|
5713 } |
|
5714 |
|
5715 u8_t *p_encrypted_premaster_secret_value = tls_handshake_header->get_data_offset( |
|
5716 data_offset, |
|
5717 encrypted_premaster_secret_length-2ul); |
|
5718 if (p_encrypted_premaster_secret_value == 0) |
|
5719 { |
|
5720 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5721 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5722 } |
|
5723 |
|
5724 eap_variable_data_c encrypted_premaster_secret(m_am_tools); |
|
5725 status = encrypted_premaster_secret.set_buffer( |
|
5726 p_encrypted_premaster_secret_value, |
|
5727 encrypted_premaster_secret_length-2ul, |
|
5728 false, |
|
5729 false); |
|
5730 if (status != eap_status_ok) |
|
5731 { |
|
5732 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5733 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5734 } |
|
5735 |
|
5736 EAP_TRACE_DATA_DEBUG( |
|
5737 m_am_tools, |
|
5738 TRACE_FLAGS_DEFAULT, |
|
5739 (EAPL("TLS: parse_handshake_type_client_key_exchange(): encrypted premaster_secret"), |
|
5740 encrypted_premaster_secret.get_data(), |
|
5741 encrypted_premaster_secret.get_data_length())); |
|
5742 |
|
5743 status = tls_handshake_message->set_encrypted_premaster_secret(&encrypted_premaster_secret); |
|
5744 if (status != eap_status_ok) |
|
5745 { |
|
5746 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5747 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5748 } |
|
5749 |
|
5750 data_offset += encrypted_premaster_secret_length; |
|
5751 } |
|
5752 else if (cipher_suite_is_TLS_DHE_DSS() == true |
|
5753 || cipher_suite_is_TLS_DHE_RSA() == true |
|
5754 #if defined(USE_FAST_EAP_TYPE) |
|
5755 || (m_eap_type == eap_type_fast |
|
5756 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true |
|
5757 && cipher_suite_is_TLS_DH_anon() == true) |
|
5758 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
5759 ) |
|
5760 { |
|
5761 if (data_offset+TLS_PUBLIC_DHE_KEY_LENGTH_LENGTH_FIELD_SIZE > handshake_data_length) |
|
5762 { |
|
5763 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5764 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5765 } |
|
5766 |
|
5767 u8_t *p_public_dhe_key_length = tls_handshake_header->get_data_offset( |
|
5768 data_offset, |
|
5769 TLS_PUBLIC_DHE_KEY_LENGTH_LENGTH_FIELD_SIZE); |
|
5770 if (p_public_dhe_key_length == 0) |
|
5771 { |
|
5772 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5773 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5774 } |
|
5775 data_offset += TLS_PUBLIC_DHE_KEY_LENGTH_LENGTH_FIELD_SIZE; |
|
5776 |
|
5777 u16_t public_dhe_key_length |
|
5778 = eap_read_u16_t_network_order( |
|
5779 p_public_dhe_key_length, |
|
5780 TLS_PUBLIC_DHE_KEY_LENGTH_LENGTH_FIELD_SIZE); |
|
5781 |
|
5782 u8_t *p_public_dhe_key_value = tls_handshake_header->get_data_offset( |
|
5783 data_offset, |
|
5784 public_dhe_key_length); |
|
5785 if (p_public_dhe_key_value == 0) |
|
5786 { |
|
5787 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5788 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5789 } |
|
5790 |
|
5791 eap_variable_data_c public_dhe_key(m_am_tools); |
|
5792 status = public_dhe_key.set_buffer( |
|
5793 p_public_dhe_key_value, |
|
5794 public_dhe_key_length, |
|
5795 false, |
|
5796 false); |
|
5797 if (status != eap_status_ok) |
|
5798 { |
|
5799 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5800 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5801 } |
|
5802 |
|
5803 status = tls_handshake_message->set_public_dhe_key(&public_dhe_key); |
|
5804 if (status != eap_status_ok) |
|
5805 { |
|
5806 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5807 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5808 } |
|
5809 |
|
5810 data_offset += public_dhe_key_length; |
|
5811 } |
|
5812 else |
|
5813 { |
|
5814 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5815 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_cipher_suite); |
|
5816 } |
|
5817 |
|
5818 //---------------------------------------------------------- |
|
5819 |
|
5820 if (status == eap_status_ok) |
|
5821 { |
|
5822 // Note the add_handshake_message() frees message in any case. |
|
5823 automatic_tls_handshake_message.do_not_free_variable(); |
|
5824 |
|
5825 status = received_tls_record_message->add_handshake_message(tls_handshake_message, true); |
|
5826 if (status != eap_status_ok) |
|
5827 { |
|
5828 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5829 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5830 } |
|
5831 } |
|
5832 |
|
5833 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5834 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5835 } |
|
5836 |
|
5837 //-------------------------------------------------- |
|
5838 |
|
5839 EAP_FUNC_EXPORT eap_status_e tls_record_c::parse_handshake_type_certificate_verify( |
|
5840 tls_record_message_c * const received_tls_record_message, |
|
5841 tls_handshake_header_c * const tls_handshake_header, |
|
5842 const u32_t handshake_data_length) |
|
5843 { |
|
5844 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5845 |
|
5846 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
5847 EAP_TRACE_DEBUG( |
|
5848 m_am_tools, |
|
5849 TRACE_FLAGS_DEFAULT, |
|
5850 (EAPL("TLS: %s: parse_function: starts: tls_record_c::parse_handshake_type_certificate_verify()\n"), |
|
5851 (m_is_client == true ? "client": "server"))); |
|
5852 |
|
5853 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::parse_handshake_type_certificate_verify()"); |
|
5854 |
|
5855 tls_handshake_message_c *tls_handshake_message = 0; |
|
5856 |
|
5857 eap_automatic_variable_c<tls_handshake_message_c> |
|
5858 automatic_tls_handshake_message(m_am_tools); |
|
5859 |
|
5860 eap_status_e status = allocate_handshake_message_copy( |
|
5861 &tls_handshake_message, |
|
5862 &automatic_tls_handshake_message, |
|
5863 tls_handshake_header); |
|
5864 if (status != eap_status_ok) |
|
5865 { |
|
5866 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5867 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5868 } |
|
5869 |
|
5870 u32_t data_offset = 0ul; |
|
5871 |
|
5872 //---------------------------------------------------------- |
|
5873 |
|
5874 |
|
5875 // Save the message hash. |
|
5876 message_hash_save_certificate_verify(); |
|
5877 |
|
5878 if (cipher_suite_is_TLS_RSA() == true |
|
5879 || cipher_suite_is_TLS_DHE_RSA() == true) |
|
5880 { |
|
5881 eap_variable_data_c signed_hash(m_am_tools); |
|
5882 |
|
5883 if (data_offset >= handshake_data_length) |
|
5884 { |
|
5885 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5886 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5887 } |
|
5888 |
|
5889 u32_t handshake_length = tls_handshake_header->get_data_length(); |
|
5890 u32_t rsa_md5_sha1_signature_length = handshake_length - data_offset; |
|
5891 |
|
5892 u8_t *p_signature_length = tls_handshake_header->get_data_offset( |
|
5893 data_offset, |
|
5894 TLS_SIGNATURE_LENGTH_FIELD_SIZE); |
|
5895 if (p_signature_length == 0) |
|
5896 { |
|
5897 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5898 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5899 } |
|
5900 data_offset += TLS_SIGNATURE_LENGTH_FIELD_SIZE; |
|
5901 |
|
5902 u16_t data_signature_length |
|
5903 = eap_read_u16_t_network_order(p_signature_length, TLS_SIGNATURE_LENGTH_FIELD_SIZE); |
|
5904 |
|
5905 if ((data_signature_length + 2ul) != rsa_md5_sha1_signature_length) |
|
5906 { |
|
5907 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5908 return EAP_STATUS_RETURN(m_am_tools, eap_status_header_corrupted); |
|
5909 } |
|
5910 |
|
5911 u8_t *p_rsa_md5_sha1_signature = tls_handshake_header->get_data_offset( |
|
5912 data_offset, |
|
5913 rsa_md5_sha1_signature_length-2ul); |
|
5914 if (p_rsa_md5_sha1_signature == 0) |
|
5915 { |
|
5916 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5917 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5918 } |
|
5919 |
|
5920 status = signed_hash.set_copy_of_buffer( |
|
5921 p_rsa_md5_sha1_signature, |
|
5922 rsa_md5_sha1_signature_length-2ul); |
|
5923 if (status != eap_status_ok) |
|
5924 { |
|
5925 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5926 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
5927 } |
|
5928 |
|
5929 status = tls_handshake_message->set_signed_message_hash( |
|
5930 &signed_hash); |
|
5931 if (status != eap_status_ok) |
|
5932 { |
|
5933 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5934 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5935 } |
|
5936 |
|
5937 data_offset += rsa_md5_sha1_signature_length; |
|
5938 } |
|
5939 else if (cipher_suite_is_TLS_DHE_DSS() == true) |
|
5940 { |
|
5941 eap_variable_data_c signed_hash(m_am_tools); |
|
5942 |
|
5943 if (data_offset >= handshake_data_length) |
|
5944 { |
|
5945 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5946 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5947 } |
|
5948 |
|
5949 u32_t handshake_length = tls_handshake_header->get_data_length(); |
|
5950 u32_t dss_sha1_signature_length = handshake_length - data_offset; |
|
5951 |
|
5952 u8_t *p_signature_length = tls_handshake_header->get_data_offset( |
|
5953 data_offset, |
|
5954 TLS_SIGNATURE_LENGTH_FIELD_SIZE); |
|
5955 if (p_signature_length == 0) |
|
5956 { |
|
5957 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5958 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5959 } |
|
5960 data_offset += TLS_SIGNATURE_LENGTH_FIELD_SIZE; |
|
5961 |
|
5962 u16_t data_signature_length |
|
5963 = eap_read_u16_t_network_order(p_signature_length, TLS_SIGNATURE_LENGTH_FIELD_SIZE); |
|
5964 |
|
5965 if ((data_signature_length + 2ul) != dss_sha1_signature_length) |
|
5966 { |
|
5967 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5968 return EAP_STATUS_RETURN(m_am_tools, eap_status_header_corrupted); |
|
5969 } |
|
5970 |
|
5971 u8_t *p_dss_sha1_signature = tls_handshake_header->get_data_offset( |
|
5972 data_offset, |
|
5973 dss_sha1_signature_length-2ul); |
|
5974 if (p_dss_sha1_signature == 0) |
|
5975 { |
|
5976 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5977 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
5978 } |
|
5979 |
|
5980 status = signed_hash.set_copy_of_buffer( |
|
5981 p_dss_sha1_signature, |
|
5982 dss_sha1_signature_length-2ul); |
|
5983 if (status != eap_status_ok) |
|
5984 { |
|
5985 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5986 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
5987 } |
|
5988 |
|
5989 status = tls_handshake_message->set_signed_message_hash( |
|
5990 &signed_hash); |
|
5991 if (status != eap_status_ok) |
|
5992 { |
|
5993 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
5994 return EAP_STATUS_RETURN(m_am_tools, status); |
|
5995 } |
|
5996 |
|
5997 data_offset += dss_sha1_signature_length; |
|
5998 } |
|
5999 |
|
6000 //---------------------------------------------------------- |
|
6001 |
|
6002 if (status == eap_status_ok) |
|
6003 { |
|
6004 // Note the add_handshake_message() frees message in any case. |
|
6005 automatic_tls_handshake_message.do_not_free_variable(); |
|
6006 |
|
6007 status = received_tls_record_message->add_handshake_message(tls_handshake_message, true); |
|
6008 if (status != eap_status_ok) |
|
6009 { |
|
6010 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6011 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6012 } |
|
6013 } |
|
6014 |
|
6015 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6016 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6017 } |
|
6018 |
|
6019 //-------------------------------------------------- |
|
6020 |
|
6021 EAP_FUNC_EXPORT eap_status_e tls_record_c::parse_handshake_type_finished( |
|
6022 tls_record_message_c * const received_tls_record_message, |
|
6023 tls_handshake_header_c * const tls_handshake_header, |
|
6024 const u32_t /* handshake_data_length */) |
|
6025 { |
|
6026 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6027 |
|
6028 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
6029 EAP_TRACE_DEBUG( |
|
6030 m_am_tools, |
|
6031 TRACE_FLAGS_DEFAULT, |
|
6032 (EAPL("TLS: %s: parse_function: starts: tls_record_c::parse_handshake_type_finished()\n"), |
|
6033 (m_is_client == true ? "client": "server"))); |
|
6034 |
|
6035 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::parse_handshake_type_finished()"); |
|
6036 |
|
6037 tls_handshake_message_c *tls_handshake_message = 0; |
|
6038 |
|
6039 eap_automatic_variable_c<tls_handshake_message_c> |
|
6040 automatic_tls_handshake_message(m_am_tools); |
|
6041 |
|
6042 eap_status_e status = allocate_handshake_message_copy( |
|
6043 &tls_handshake_message, |
|
6044 &automatic_tls_handshake_message, |
|
6045 tls_handshake_header); |
|
6046 if (status != eap_status_ok) |
|
6047 { |
|
6048 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6049 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6050 } |
|
6051 |
|
6052 u32_t data_offset = 0ul; |
|
6053 |
|
6054 //---------------------------------------------------------- |
|
6055 |
|
6056 bool client_originated = true; |
|
6057 if (m_is_client == true) |
|
6058 { |
|
6059 client_originated = false; |
|
6060 } |
|
6061 // Save the message hash. |
|
6062 message_hash_save_finished(client_originated); |
|
6063 |
|
6064 { |
|
6065 eap_variable_data_c finished_data(m_am_tools); |
|
6066 |
|
6067 u8_t *p_finished_data = tls_handshake_header->get_data_offset( |
|
6068 data_offset, |
|
6069 TLS_FINISHED_DATA_SIZE); |
|
6070 if (p_finished_data == 0) |
|
6071 { |
|
6072 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6073 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
6074 } |
|
6075 |
|
6076 status = finished_data.set_copy_of_buffer(p_finished_data, TLS_FINISHED_DATA_SIZE); |
|
6077 if (status != eap_status_ok) |
|
6078 { |
|
6079 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6080 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
6081 } |
|
6082 |
|
6083 status = tls_handshake_message->set_finished_data( |
|
6084 &finished_data); |
|
6085 if (status != eap_status_ok) |
|
6086 { |
|
6087 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6088 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6089 } |
|
6090 |
|
6091 data_offset += TLS_FINISHED_DATA_SIZE; |
|
6092 } |
|
6093 |
|
6094 //---------------------------------------------------------- |
|
6095 |
|
6096 if (status == eap_status_ok) |
|
6097 { |
|
6098 // Note the add_handshake_message() frees message in any case. |
|
6099 automatic_tls_handshake_message.do_not_free_variable(); |
|
6100 |
|
6101 status = received_tls_record_message->add_handshake_message(tls_handshake_message, true); |
|
6102 if (status != eap_status_ok) |
|
6103 { |
|
6104 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6105 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6106 } |
|
6107 } |
|
6108 |
|
6109 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6110 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6111 } |
|
6112 |
|
6113 //-------------------------------------------------- |
|
6114 |
|
6115 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
6116 |
|
6117 EAP_FUNC_EXPORT eap_status_e tls_record_c::parse_handshake_type_new_session_ticket( |
|
6118 tls_record_message_c * const received_tls_record_message, |
|
6119 tls_handshake_header_c * const tls_handshake_header, |
|
6120 const u32_t handshake_data_length) |
|
6121 { |
|
6122 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6123 |
|
6124 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
6125 EAP_TRACE_DEBUG( |
|
6126 m_am_tools, |
|
6127 TRACE_FLAGS_DEFAULT, |
|
6128 (EAPL("TLS: %s: parse_function: starts: tls_record_c::parse_handshake_type_new_session_ticket()\n"), |
|
6129 (m_is_client == true ? "client": "server"))); |
|
6130 |
|
6131 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::parse_handshake_type_new_session_ticket()"); |
|
6132 |
|
6133 tls_handshake_message_c *tls_handshake_message = 0; |
|
6134 |
|
6135 eap_automatic_variable_c<tls_handshake_message_c> |
|
6136 automatic_tls_handshake_message(m_am_tools); |
|
6137 |
|
6138 eap_status_e status = allocate_handshake_message_copy( |
|
6139 &tls_handshake_message, |
|
6140 &automatic_tls_handshake_message, |
|
6141 tls_handshake_header); |
|
6142 if (status != eap_status_ok) |
|
6143 { |
|
6144 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6145 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6146 } |
|
6147 |
|
6148 u32_t data_offset = 0ul; |
|
6149 |
|
6150 u8_t * handshake_data = tls_handshake_header->get_data_offset( |
|
6151 data_offset, |
|
6152 tls_handshake_header->get_data_length()); |
|
6153 if (handshake_data == 0) |
|
6154 { |
|
6155 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6156 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
6157 } |
|
6158 |
|
6159 //---------------------------------------------------------- |
|
6160 |
|
6161 u32_t session_ticket_lifetime_hint(0ul); |
|
6162 |
|
6163 { |
|
6164 if (data_offset+TLS_SESSION_TICKET_LIFETIME_HINT_FIELD_SIZE > handshake_data_length) |
|
6165 { |
|
6166 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6167 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
6168 } |
|
6169 |
|
6170 u8_t *p_session_ticket_lifetime_hint = handshake_data; |
|
6171 |
|
6172 session_ticket_lifetime_hint = eap_read_u32_t_network_order( |
|
6173 p_session_ticket_lifetime_hint, |
|
6174 TLS_SESSION_TICKET_LIFETIME_HINT_FIELD_SIZE); |
|
6175 |
|
6176 data_offset += TLS_SESSION_TICKET_LIFETIME_HINT_FIELD_SIZE; |
|
6177 } |
|
6178 |
|
6179 //---------------------------------------------------------- |
|
6180 |
|
6181 { |
|
6182 if (data_offset+TLS_EXTENSION_DATA_LENGTH_FIELD_SIZE > handshake_data_length) |
|
6183 { |
|
6184 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6185 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
6186 } |
|
6187 |
|
6188 u8_t *p_opaque_session_ticket_length = tls_handshake_header->get_data_offset( |
|
6189 data_offset, |
|
6190 TLS_EXTENSION_DATA_LENGTH_FIELD_SIZE); |
|
6191 if (p_opaque_session_ticket_length == 0) |
|
6192 { |
|
6193 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6194 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
6195 } |
|
6196 |
|
6197 u16_t opaque_session_ticket_length = eap_read_u16_t_network_order( |
|
6198 p_opaque_session_ticket_length, |
|
6199 TLS_EXTENSION_DATA_LENGTH_FIELD_SIZE); |
|
6200 |
|
6201 data_offset += TLS_EXTENSION_DATA_LENGTH_FIELD_SIZE; |
|
6202 |
|
6203 if (data_offset+opaque_session_ticket_length > handshake_data_length) |
|
6204 { |
|
6205 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6206 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
6207 } |
|
6208 |
|
6209 tls_extension_c opaque_session_ticket(m_am_tools); |
|
6210 |
|
6211 if (opaque_session_ticket.get_is_valid() == false) |
|
6212 { |
|
6213 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6214 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
6215 } |
|
6216 |
|
6217 u8_t *p_opaque_session_ticket = tls_handshake_header->get_data_offset( |
|
6218 data_offset, |
|
6219 opaque_session_ticket_length); |
|
6220 if (p_opaque_session_ticket_length == 0) |
|
6221 { |
|
6222 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6223 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
6224 } |
|
6225 |
|
6226 status = opaque_session_ticket.set_buffer( |
|
6227 p_opaque_session_ticket, |
|
6228 opaque_session_ticket_length, |
|
6229 false, |
|
6230 false); |
|
6231 if (status != eap_status_ok) |
|
6232 { |
|
6233 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6234 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6235 } |
|
6236 |
|
6237 opaque_session_ticket.set_type(tls_extension_type_session_ticket); |
|
6238 |
|
6239 opaque_session_ticket.set_lifetime_hint(session_ticket_lifetime_hint); |
|
6240 |
|
6241 eap_array_c<tls_extension_c> tls_extensions(m_am_tools); |
|
6242 |
|
6243 status = tls_extensions.add_object(&opaque_session_ticket, false); |
|
6244 if (status != eap_status_ok) |
|
6245 { |
|
6246 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6247 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6248 } |
|
6249 |
|
6250 // Save the new session ticket to be included in next NewSessionTicket message. |
|
6251 status = tls_handshake_message->set_tls_extensions( |
|
6252 &tls_extensions); |
|
6253 if (status != eap_status_ok) |
|
6254 { |
|
6255 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6256 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6257 } |
|
6258 |
|
6259 EAP_TRACE_DATA_DEBUG( |
|
6260 m_am_tools, |
|
6261 TRACE_FLAGS_DEFAULT, |
|
6262 (EAPL("TLS: parse_handshake_type_new_session_ticket(): opaque_session_ticket"), |
|
6263 opaque_session_ticket.get_data(opaque_session_ticket.get_data_length()), |
|
6264 opaque_session_ticket.get_data_length())); |
|
6265 |
|
6266 data_offset += opaque_session_ticket_length; |
|
6267 } |
|
6268 |
|
6269 //---------------------------------------------------------- |
|
6270 |
|
6271 if (status == eap_status_ok) |
|
6272 { |
|
6273 // Note the add_handshake_message() frees message in any case. |
|
6274 automatic_tls_handshake_message.do_not_free_variable(); |
|
6275 |
|
6276 status = received_tls_record_message->add_handshake_message(tls_handshake_message, true); |
|
6277 if (status != eap_status_ok) |
|
6278 { |
|
6279 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6280 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6281 } |
|
6282 } |
|
6283 |
|
6284 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6285 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6286 } |
|
6287 |
|
6288 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
6289 |
|
6290 //-------------------------------------------------- |
|
6291 |
|
6292 EAP_FUNC_EXPORT eap_status_e tls_record_c::parse_tls_protocol_change_cipher_spec( |
|
6293 tls_record_message_c * const tls_record_message, |
|
6294 eap_variable_data_c * const tls_protocol_messages_buffer) |
|
6295 { |
|
6296 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6297 |
|
6298 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
6299 EAP_TRACE_DEBUG( |
|
6300 m_am_tools, |
|
6301 TRACE_FLAGS_DEFAULT, |
|
6302 (EAPL("TLS: %s: parse_function: starts: tls_record_c::parse_tls_protocol_change_cipher_spec()\n"), |
|
6303 (m_is_client == true ? "client": "server"))); |
|
6304 |
|
6305 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::parse_tls_protocol_change_cipher_spec()"); |
|
6306 |
|
6307 tls_record_message->set_parsed_record(); |
|
6308 |
|
6309 if (verify_state(tls_peap_state_wait_change_cipher_spec) == false |
|
6310 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
6311 && (m_tls_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_none |
|
6312 && verify_state(tls_peap_state_wait_handshake_type_certificate_verify) == false) |
|
6313 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
6314 ) |
|
6315 { |
|
6316 EAP_TRACE_ERROR( |
|
6317 m_am_tools, |
|
6318 TRACE_FLAGS_DEFAULT, |
|
6319 (EAPL("ERROR: TLS: %s: function: verify_state(): current state %s != %s\n"), |
|
6320 (m_is_client == true ? "client": "server"), |
|
6321 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
6322 eap_tls_trace_string_c::get_state_string(tls_peap_state_wait_change_cipher_spec))); |
|
6323 return EAP_STATUS_RETURN(m_am_tools, eap_status_unexpected_message); |
|
6324 } |
|
6325 |
|
6326 eap_status_e status = eap_status_not_supported; |
|
6327 |
|
6328 const u32_t tls_protocols_length = tls_protocol_messages_buffer->get_data_length(); |
|
6329 |
|
6330 tls_change_cipher_spec_message_c * const tls_change_cipher_spec_message |
|
6331 = new tls_change_cipher_spec_message_c(m_am_tools, this, m_is_client); |
|
6332 |
|
6333 eap_automatic_variable_c<tls_change_cipher_spec_message_c> |
|
6334 automatic_tls_change_cipher_spec_message(m_am_tools, tls_change_cipher_spec_message); |
|
6335 |
|
6336 if (tls_change_cipher_spec_message == 0 |
|
6337 || tls_change_cipher_spec_message->get_is_valid() == false) |
|
6338 { |
|
6339 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6340 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
6341 } |
|
6342 |
|
6343 u32_t data_offset = 0ul; |
|
6344 |
|
6345 //---------------------------------------------------------- |
|
6346 |
|
6347 { |
|
6348 if (data_offset+TLS_CHANGE_CIPHER_SPEC_FIELD_SIZE > tls_protocols_length) |
|
6349 { |
|
6350 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6351 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
6352 } |
|
6353 |
|
6354 u8_t *p_change_cipher_spec_type = tls_protocol_messages_buffer->get_data_offset( |
|
6355 data_offset, |
|
6356 TLS_CHANGE_CIPHER_SPEC_FIELD_SIZE); |
|
6357 if (p_change_cipher_spec_type == 0) |
|
6358 { |
|
6359 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6360 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
6361 } |
|
6362 |
|
6363 status = tls_change_cipher_spec_message->set_change_cipher_spec_type( |
|
6364 static_cast<tls_change_cipher_spec_type_e>(*p_change_cipher_spec_type)); |
|
6365 if (status != eap_status_ok) |
|
6366 { |
|
6367 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6368 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6369 } |
|
6370 |
|
6371 data_offset += TLS_CHANGE_CIPHER_SPEC_FIELD_SIZE; |
|
6372 } |
|
6373 |
|
6374 //---------------------------------------------------------- |
|
6375 |
|
6376 if (tls_protocols_length != data_offset) |
|
6377 { |
|
6378 // Parsed record length does not match with received record length. |
|
6379 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6380 return EAP_STATUS_RETURN(m_am_tools, eap_status_header_corrupted); |
|
6381 } |
|
6382 |
|
6383 if (status == eap_status_ok) |
|
6384 { |
|
6385 // Note add_change_cipher_spec_message() frees message on any case. |
|
6386 automatic_tls_change_cipher_spec_message.do_not_free_variable(); |
|
6387 |
|
6388 status = tls_record_message->add_change_cipher_spec_message( |
|
6389 tls_change_cipher_spec_message, |
|
6390 true); |
|
6391 if (status != eap_status_ok) |
|
6392 { |
|
6393 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6394 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6395 } |
|
6396 } |
|
6397 |
|
6398 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6399 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6400 } |
|
6401 |
|
6402 //-------------------------------------------------- |
|
6403 |
|
6404 EAP_FUNC_EXPORT eap_status_e tls_record_c::parse_tls_protocol_alert( |
|
6405 tls_record_message_c * const tls_record_message, |
|
6406 eap_variable_data_c * const tls_protocol_messages_buffer) |
|
6407 { |
|
6408 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6409 |
|
6410 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
6411 EAP_TRACE_DEBUG( |
|
6412 m_am_tools, |
|
6413 TRACE_FLAGS_DEFAULT, |
|
6414 (EAPL("TLS: %s: parse_function: starts: tls_record_c::parse_tls_protocol_alert()\n"), |
|
6415 (m_is_client == true ? "client": "server"))); |
|
6416 |
|
6417 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::parse_tls_protocol_alert()"); |
|
6418 |
|
6419 tls_record_message->set_parsed_record(); |
|
6420 |
|
6421 eap_status_e status = eap_status_not_supported; |
|
6422 |
|
6423 // Because we received alert message, we do not send alert messages anymore. |
|
6424 m_could_send_fatal_alert_message = false; |
|
6425 m_could_send_warning_alert_message = false; |
|
6426 |
|
6427 const u32_t tls_protocol_messages_length = tls_protocol_messages_buffer->get_data_length(); |
|
6428 u32_t data_start_offset = 0ul; |
|
6429 |
|
6430 while (data_start_offset < tls_protocol_messages_length) |
|
6431 { |
|
6432 tls_alert_message_c * const tls_alert_message |
|
6433 = new tls_alert_message_c(m_am_tools, m_is_client); |
|
6434 |
|
6435 eap_automatic_variable_c<tls_alert_message_c> |
|
6436 automatic_tls_alert_message(m_am_tools, tls_alert_message); |
|
6437 |
|
6438 if (tls_alert_message == 0 |
|
6439 || tls_alert_message->get_is_valid() == false) |
|
6440 { |
|
6441 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6442 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
6443 } |
|
6444 |
|
6445 u32_t data_offset = 0ul; |
|
6446 |
|
6447 //---------------------------------------------------------- |
|
6448 |
|
6449 { |
|
6450 if (data_start_offset+data_offset+TLS_ALERT_LEVEL_FIELD_SIZE |
|
6451 > tls_protocol_messages_length) |
|
6452 { |
|
6453 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6454 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
6455 } |
|
6456 |
|
6457 u8_t *p_alert_level = tls_protocol_messages_buffer->get_data_offset( |
|
6458 data_start_offset+data_offset, |
|
6459 TLS_ALERT_LEVEL_FIELD_SIZE); |
|
6460 if (p_alert_level == 0) |
|
6461 { |
|
6462 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6463 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
6464 } |
|
6465 |
|
6466 status = tls_alert_message->set_alert_level( |
|
6467 static_cast<tls_alert_level_e>(*p_alert_level)); |
|
6468 if (status != eap_status_ok) |
|
6469 { |
|
6470 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6471 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6472 } |
|
6473 |
|
6474 data_offset += TLS_ALERT_LEVEL_FIELD_SIZE; |
|
6475 } |
|
6476 |
|
6477 //---------------------------------------------------------- |
|
6478 |
|
6479 { |
|
6480 if (data_start_offset+data_offset+TLS_ALERT_DESCRIPTION_FIELD_SIZE |
|
6481 > tls_protocol_messages_length) |
|
6482 { |
|
6483 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6484 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
6485 } |
|
6486 |
|
6487 u8_t *p_alert_description = tls_protocol_messages_buffer->get_data_offset( |
|
6488 data_start_offset+data_offset, |
|
6489 TLS_ALERT_DESCRIPTION_FIELD_SIZE); |
|
6490 if (p_alert_description == 0) |
|
6491 { |
|
6492 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6493 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
6494 } |
|
6495 |
|
6496 status = tls_alert_message->set_alert_description( |
|
6497 static_cast<tls_alert_description_e>(*p_alert_description)); |
|
6498 if (status != eap_status_ok) |
|
6499 { |
|
6500 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6501 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6502 } |
|
6503 |
|
6504 data_offset += TLS_ALERT_DESCRIPTION_FIELD_SIZE; |
|
6505 } |
|
6506 |
|
6507 if (status == eap_status_ok) |
|
6508 { |
|
6509 // Note add_alert_message() frees message on any case. |
|
6510 automatic_tls_alert_message.do_not_free_variable(); |
|
6511 |
|
6512 status = tls_record_message->add_alert_message(tls_alert_message, true); |
|
6513 if (status != eap_status_ok) |
|
6514 { |
|
6515 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6516 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6517 } |
|
6518 } |
|
6519 |
|
6520 data_start_offset += data_offset; |
|
6521 } // while() |
|
6522 |
|
6523 //---------------------------------------------------------- |
|
6524 |
|
6525 if (tls_protocol_messages_length != data_start_offset) |
|
6526 { |
|
6527 // Parsed record length does not match with received record length. |
|
6528 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6529 return EAP_STATUS_RETURN(m_am_tools, eap_status_header_corrupted); |
|
6530 } |
|
6531 |
|
6532 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6533 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6534 } |
|
6535 |
|
6536 //-------------------------------------------------- |
|
6537 |
|
6538 EAP_FUNC_EXPORT eap_status_e tls_record_c::parse_tls_protocol_handshake( |
|
6539 tls_record_message_c * const tls_record_message, |
|
6540 eap_variable_data_c * const tls_protocol_messages_buffer) |
|
6541 { |
|
6542 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6543 |
|
6544 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
6545 EAP_TRACE_DEBUG( |
|
6546 m_am_tools, |
|
6547 TRACE_FLAGS_DEFAULT, |
|
6548 (EAPL("TLS: %s: parse_function: starts: tls_record_c::parse_tls_protocol_handshake()\n"), |
|
6549 (m_is_client == true ? "client": "server"))); |
|
6550 |
|
6551 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::parse_tls_protocol_handshake()"); |
|
6552 |
|
6553 tls_record_message->set_parsed_record(); |
|
6554 |
|
6555 const u32_t tls_protocol_messages_length = tls_protocol_messages_buffer->get_data_length(); |
|
6556 |
|
6557 u32_t data_start_offset = 0ul; |
|
6558 |
|
6559 tls_handshake_header_c tls_handshake_header( |
|
6560 m_am_tools, |
|
6561 tls_protocol_messages_buffer->get_data_offset( |
|
6562 data_start_offset, |
|
6563 tls_protocol_messages_buffer->get_data_length()-data_start_offset), |
|
6564 tls_protocol_messages_buffer->get_data_length()-data_start_offset); |
|
6565 if (tls_handshake_header.get_is_valid() == false) |
|
6566 { |
|
6567 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6568 return EAP_STATUS_RETURN(m_am_tools, eap_status_header_corrupted); |
|
6569 } |
|
6570 |
|
6571 if (tls_handshake_header.get_header_length()+tls_handshake_header.get_data_length() > tls_handshake_header.get_header_buffer_length() |
|
6572 || tls_handshake_header.get_header_buffer( |
|
6573 tls_handshake_header.get_header_length()+tls_handshake_header.get_data_length()) == 0) |
|
6574 { |
|
6575 // Not enough data. |
|
6576 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6577 return EAP_STATUS_RETURN(m_am_tools, eap_status_header_corrupted); |
|
6578 } |
|
6579 |
|
6580 EAP_TRACE_DATA_DEBUG( |
|
6581 m_am_tools, |
|
6582 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
6583 (EAPL("TLS-handshake tls_handshake_header"), |
|
6584 tls_handshake_header.get_header_buffer( |
|
6585 tls_handshake_header.get_header_length()+tls_handshake_header.get_data_length()), |
|
6586 (tls_handshake_header.get_header_length()+tls_handshake_header.get_data_length()))); |
|
6587 |
|
6588 eap_status_e status = eap_status_ok; |
|
6589 |
|
6590 u32_t counter = 0ul; |
|
6591 |
|
6592 |
|
6593 while (tls_handshake_header.get_is_valid() == true |
|
6594 && data_start_offset < tls_protocol_messages_length) |
|
6595 { |
|
6596 const u32_t handshake_data_length = tls_handshake_header.get_data_length(); |
|
6597 if (handshake_data_length+data_start_offset > tls_protocol_messages_length) |
|
6598 { |
|
6599 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6600 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
6601 } |
|
6602 |
|
6603 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
6604 EAP_TRACE_DEBUG( |
|
6605 m_am_tools, |
|
6606 TRACE_FLAGS_DEFAULT, |
|
6607 (EAPL("TLS: %s: parse_function: parse_tls_protocol_handshake(): ") |
|
6608 EAPL("counter[%u] type = 0x%08x=%s.\n"), |
|
6609 (m_is_client == true ? "client": "server"), |
|
6610 counter, |
|
6611 tls_handshake_header.get_handshake_type(), |
|
6612 tls_handshake_header.get_tls_handshake_string())); |
|
6613 |
|
6614 status = tls_handshake_header.check_header( |
|
6615 tls_handshake_header.get_handshake_type(), |
|
6616 m_is_client); |
|
6617 if (status != eap_status_ok) |
|
6618 { |
|
6619 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6620 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6621 } |
|
6622 |
|
6623 if (tls_handshake_header.get_header_length()+tls_handshake_header.get_data_length() |
|
6624 > tls_handshake_header.get_header_buffer_length() |
|
6625 || tls_handshake_header.get_header_buffer( |
|
6626 tls_handshake_header.get_header_length()+tls_handshake_header.get_data_length()) == 0) |
|
6627 { |
|
6628 // Not enough data. |
|
6629 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6630 return EAP_STATUS_RETURN(m_am_tools, eap_status_header_corrupted); |
|
6631 } |
|
6632 |
|
6633 bool add_to_message_hash = false; |
|
6634 |
|
6635 switch (tls_handshake_header.get_handshake_type()) |
|
6636 { |
|
6637 case tls_handshake_type_hello_request: |
|
6638 status = parse_handshake_type_hello_request( |
|
6639 tls_record_message, |
|
6640 &tls_handshake_header, |
|
6641 handshake_data_length); |
|
6642 add_to_message_hash = false; |
|
6643 break; |
|
6644 case tls_handshake_type_client_hello: |
|
6645 status = parse_handshake_type_client_hello( |
|
6646 tls_record_message, |
|
6647 &tls_handshake_header, |
|
6648 handshake_data_length); |
|
6649 add_to_message_hash = true; |
|
6650 break; |
|
6651 case tls_handshake_type_server_hello: |
|
6652 status = parse_handshake_type_server_hello( |
|
6653 tls_record_message, |
|
6654 &tls_handshake_header, |
|
6655 handshake_data_length); |
|
6656 add_to_message_hash = true; |
|
6657 break; |
|
6658 case tls_handshake_type_certificate: |
|
6659 status = parse_handshake_type_certificate( |
|
6660 tls_record_message, |
|
6661 &tls_handshake_header, |
|
6662 handshake_data_length); |
|
6663 add_to_message_hash = true; |
|
6664 break; |
|
6665 case tls_handshake_type_server_key_exchange: |
|
6666 status = parse_handshake_type_server_key_exchange( |
|
6667 tls_record_message, |
|
6668 &tls_handshake_header, |
|
6669 handshake_data_length); |
|
6670 add_to_message_hash = true; |
|
6671 break; |
|
6672 case tls_handshake_type_certificate_request: |
|
6673 status = parse_handshake_type_certificate_request( |
|
6674 tls_record_message, |
|
6675 &tls_handshake_header, |
|
6676 handshake_data_length); |
|
6677 add_to_message_hash = true; |
|
6678 break; |
|
6679 case tls_handshake_type_server_hello_done: |
|
6680 status = parse_handshake_type_server_hello_done( |
|
6681 tls_record_message, |
|
6682 &tls_handshake_header, |
|
6683 handshake_data_length); |
|
6684 add_to_message_hash = true; |
|
6685 break; |
|
6686 case tls_handshake_type_certificate_verify: |
|
6687 status = parse_handshake_type_certificate_verify( |
|
6688 tls_record_message, |
|
6689 &tls_handshake_header, |
|
6690 handshake_data_length); |
|
6691 add_to_message_hash = true; |
|
6692 break; |
|
6693 case tls_handshake_type_client_key_exchange: |
|
6694 status = parse_handshake_type_client_key_exchange( |
|
6695 tls_record_message, |
|
6696 &tls_handshake_header, |
|
6697 handshake_data_length); |
|
6698 add_to_message_hash = true; |
|
6699 break; |
|
6700 case tls_handshake_type_finished: |
|
6701 status = parse_handshake_type_finished( |
|
6702 tls_record_message, |
|
6703 &tls_handshake_header, |
|
6704 handshake_data_length); |
|
6705 add_to_message_hash = true; |
|
6706 break; |
|
6707 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
6708 case tls_handshake_type_new_session_ticket: |
|
6709 status = parse_handshake_type_new_session_ticket( |
|
6710 tls_record_message, |
|
6711 &tls_handshake_header, |
|
6712 handshake_data_length); |
|
6713 add_to_message_hash = true; |
|
6714 break; |
|
6715 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
6716 default: |
|
6717 return EAP_STATUS_RETURN(m_am_tools, eap_status_unexpected_message); |
|
6718 } // switch() |
|
6719 |
|
6720 |
|
6721 if (status != eap_status_ok) |
|
6722 { |
|
6723 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6724 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6725 } |
|
6726 |
|
6727 |
|
6728 if (add_to_message_hash == true) |
|
6729 { |
|
6730 status = message_hash_update( |
|
6731 true, |
|
6732 tls_handshake_header.get_handshake_type(), |
|
6733 tls_handshake_header.get_header_buffer( |
|
6734 tls_handshake_header.get_header_length() |
|
6735 +tls_handshake_header.get_data_length()), |
|
6736 tls_handshake_header.get_header_length() |
|
6737 +tls_handshake_header.get_data_length()); |
|
6738 if (status != eap_status_ok) |
|
6739 { |
|
6740 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6741 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6742 } |
|
6743 } |
|
6744 |
|
6745 data_start_offset += (tls_handshake_header.get_header_length() |
|
6746 +tls_handshake_header.get_data_length()); |
|
6747 |
|
6748 if (data_start_offset > tls_protocol_messages_buffer->get_data_length()) |
|
6749 { |
|
6750 // Parsed record length does not match with received record length. |
|
6751 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6752 return EAP_STATUS_RETURN(m_am_tools, eap_status_header_corrupted); |
|
6753 } |
|
6754 |
|
6755 tls_handshake_header.set_header_buffer( |
|
6756 tls_protocol_messages_buffer->get_data_offset( |
|
6757 data_start_offset, |
|
6758 tls_protocol_messages_buffer->get_data_length()-data_start_offset), |
|
6759 tls_protocol_messages_buffer->get_data_length()-data_start_offset); |
|
6760 // NOTE tls_handshake_header is checked in the begin of the loop. |
|
6761 |
|
6762 ++counter; |
|
6763 |
|
6764 } // while() |
|
6765 |
|
6766 if (tls_protocol_messages_length != data_start_offset) |
|
6767 { |
|
6768 // Parsed record length does not match with received record length. |
|
6769 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6770 return EAP_STATUS_RETURN(m_am_tools, eap_status_header_corrupted); |
|
6771 } |
|
6772 |
|
6773 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6774 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6775 } |
|
6776 |
|
6777 //-------------------------------------------------- |
|
6778 |
|
6779 EAP_FUNC_EXPORT eap_status_e tls_record_c::parse_tls_protocol_application_data( |
|
6780 tls_record_message_c * const tls_record_message, |
|
6781 eap_variable_data_c * const tls_protocol_messages_buffer) |
|
6782 { |
|
6783 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6784 |
|
6785 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
6786 EAP_TRACE_DEBUG( |
|
6787 m_am_tools, |
|
6788 TRACE_FLAGS_DEFAULT, |
|
6789 (EAPL("TLS: %s: parse_function: starts: tls_record_c::parse_tls_protocol_application_data()\n"), |
|
6790 (m_is_client == true ? "client": "server"))); |
|
6791 |
|
6792 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::parse_tls_protocol_application_data()"); |
|
6793 |
|
6794 tls_record_message->set_parsed_record(); |
|
6795 |
|
6796 eap_status_e status = eap_status_not_supported; |
|
6797 |
|
6798 const u32_t tls_protocol_messages_length = tls_protocol_messages_buffer->get_data_length(); |
|
6799 |
|
6800 EAP_TRACE_DATA_DEBUG( |
|
6801 m_am_tools, |
|
6802 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
6803 (EAPL("TLS-application data"), |
|
6804 tls_protocol_messages_buffer->get_data(tls_protocol_messages_length), |
|
6805 tls_protocol_messages_length)); |
|
6806 |
|
6807 tls_application_data_message_c * const tls_application_data_message |
|
6808 = new tls_application_data_message_c(m_am_tools, m_is_client); |
|
6809 |
|
6810 eap_automatic_variable_c<tls_application_data_message_c> |
|
6811 automatic_tls_application_data_message(m_am_tools, tls_application_data_message); |
|
6812 |
|
6813 if (tls_application_data_message == 0 |
|
6814 || tls_application_data_message->get_is_valid() == false) |
|
6815 { |
|
6816 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6817 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
6818 } |
|
6819 |
|
6820 u32_t data_offset = 0ul; |
|
6821 |
|
6822 //---------------------------------------------------------- |
|
6823 |
|
6824 { |
|
6825 u8_t *p_application_data = tls_protocol_messages_buffer->get_data( |
|
6826 tls_protocol_messages_length); |
|
6827 if (p_application_data == 0) |
|
6828 { |
|
6829 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6830 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
6831 } |
|
6832 |
|
6833 status = tls_application_data_message->set_application_data( |
|
6834 p_application_data, |
|
6835 tls_protocol_messages_length); |
|
6836 if (status != eap_status_ok) |
|
6837 { |
|
6838 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6839 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6840 } |
|
6841 |
|
6842 data_offset += tls_protocol_messages_length; |
|
6843 } |
|
6844 |
|
6845 //---------------------------------------------------------- |
|
6846 |
|
6847 if (tls_protocol_messages_length != data_offset) |
|
6848 { |
|
6849 // Parsed record length does not match with received record length. |
|
6850 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6851 return EAP_STATUS_RETURN(m_am_tools, eap_status_header_corrupted); |
|
6852 } |
|
6853 |
|
6854 if (status == eap_status_ok) |
|
6855 { |
|
6856 // Note add_application_data_message() frees message on any case. |
|
6857 automatic_tls_application_data_message.do_not_free_variable(); |
|
6858 |
|
6859 status = tls_record_message->add_application_data_message( |
|
6860 tls_application_data_message, true); |
|
6861 if (status != eap_status_ok) |
|
6862 { |
|
6863 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6864 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6865 } |
|
6866 } |
|
6867 |
|
6868 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6869 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6870 } |
|
6871 |
|
6872 //-------------------------------------------------- |
|
6873 |
|
6874 EAP_FUNC_EXPORT eap_status_e tls_record_c::reassemble_tls_records( |
|
6875 tls_record_message_c * const tls_record_message, |
|
6876 tls_record_header_c * const next_tls_record_header) |
|
6877 { |
|
6878 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6879 |
|
6880 EAP_TRACE_DEBUG( |
|
6881 m_am_tools, |
|
6882 TRACE_FLAGS_DEFAULT, |
|
6883 (EAPL("TLS: this = 0x%08x, %s: starts: tls_record_c::reassemble_tls_records()\n"), |
|
6884 this, |
|
6885 (m_is_client == true ? "client": "server"))); |
|
6886 |
|
6887 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::reassemble_tls_records()"); |
|
6888 |
|
6889 eap_status_e status = tls_record_message->get_record_message_data()->add_data( |
|
6890 next_tls_record_header->get_data(next_tls_record_header->get_data_length()), |
|
6891 next_tls_record_header->get_data_length()); |
|
6892 if (status != eap_status_ok) |
|
6893 { |
|
6894 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6895 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6896 } |
|
6897 |
|
6898 status = tls_record_message->add_data_length(next_tls_record_header->get_data_length()); |
|
6899 |
|
6900 EAP_TRACE_DEBUG( |
|
6901 m_am_tools, |
|
6902 TRACE_FLAGS_DEFAULT, |
|
6903 (EAPL("TLS: this = 0x%08x, %s: tls_record_c::reassemble_tls_records(): fragment %d bytes, ") |
|
6904 EAPL("message %d bytes.\n"), |
|
6905 this, |
|
6906 (m_is_client == true ? "client": "server"), |
|
6907 next_tls_record_header->get_data_length(), |
|
6908 tls_record_message->get_data_length())); |
|
6909 |
|
6910 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6911 return EAP_STATUS_RETURN(m_am_tools, status); |
|
6912 } |
|
6913 |
|
6914 //-------------------------------------------------- |
|
6915 |
|
6916 EAP_FUNC_EXPORT eap_status_e tls_record_c::process_tls_records() |
|
6917 { |
|
6918 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6919 |
|
6920 EAP_TRACE_DEBUG( |
|
6921 m_am_tools, |
|
6922 TRACE_FLAGS_DEFAULT, |
|
6923 (EAPL("\n"))); |
|
6924 EAP_TRACE_DEBUG( |
|
6925 m_am_tools, |
|
6926 TRACE_FLAGS_DEFAULT, |
|
6927 (EAPL("TLS: %s: parse_function: starts: tls_record_c::process_tls_records(): index = %d, record count = %d\n"), |
|
6928 (m_is_client == true ? "client": "server"), |
|
6929 m_received_tls_message.get_analyse_index(), |
|
6930 m_received_tls_message.get_record_message_count())); |
|
6931 |
|
6932 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::process_tls_records()"); |
|
6933 |
|
6934 if (m_already_in_process_tls_records == true) |
|
6935 { |
|
6936 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
6937 // This is recursive call of process_tls_records(). |
|
6938 // This MUST return eap_status_ok. Other return values will skip |
|
6939 // further prosessing of TLS message. |
|
6940 EAP_TRACE_DEBUG( |
|
6941 m_am_tools, TRACE_FLAGS_DEFAULT, |
|
6942 (EAPL("TLS: %s: send_function: process_tls_records(): skip recursion\n"), |
|
6943 (m_is_client == true ? "client": "server"))); |
|
6944 return EAP_STATUS_RETURN(m_am_tools, eap_status_end_recursion); |
|
6945 } |
|
6946 m_already_in_process_tls_records = true; |
|
6947 |
|
6948 eap_automatic_simple_value_c<bool> restore_already_in_process_tls_records( |
|
6949 m_am_tools, |
|
6950 &m_already_in_process_tls_records, |
|
6951 false); |
|
6952 |
|
6953 // One TLS-message could include many records. Each of records could |
|
6954 // include many protocol messages. |
|
6955 // +=================================================+ |
|
6956 // +=================================================+ |
|
6957 // | 1. tls_record_header_c | |
|
6958 // | protocol tls_record_protocol_handshake | |
|
6959 // +-------------------------------------------------+ |
|
6960 // | 1a. tls_handshake_header_c | |
|
6961 // +- - - - - - - - - - - - - - - - - - - - - - - - -+ |
|
6962 // | 1a. data of handshake | |
|
6963 // +-------------------------------------------------+ |
|
6964 // | 1b. tls_handshake_header_c | |
|
6965 // +- - - - - - - - - - - - - - - - - - - - - - - - -+ |
|
6966 // | 1b. data of handshake | |
|
6967 // +=================================================+ |
|
6968 // +=================================================+ |
|
6969 // | 2. tls_record_header_c | |
|
6970 // | protocol tls_record_protocol_change_cipher_spec | |
|
6971 // +-------------------------------------------------+ |
|
6972 // | 2a. data of change_cipher_spec | |
|
6973 // +=================================================+ |
|
6974 // +=================================================+ |
|
6975 // | 3. tls_record_header_c | |
|
6976 // | protocol tls_record_protocol_handshake | |
|
6977 // +-------------------------------------------------+ |
|
6978 // | 3a. tls_handshake_header_c | |
|
6979 // +- - - - - - - - - - - - - - - - - - - - - - - - -+ |
|
6980 // | 3a. data of handshake | |
|
6981 // +=================================================+ |
|
6982 // +=================================================+ |
|
6983 |
|
6984 // One protocol message could be fragmented to many records. |
|
6985 // +=================================================+ |
|
6986 // +=================================================+ |
|
6987 // | 1. tls_record_header_c | |
|
6988 // | protocol tls_record_protocol_handshake | |
|
6989 // +-------------------------------------------------+ |
|
6990 // | 1a. tls_handshake_header_c | |
|
6991 // +- - - - - - - - - - - - - - - - - - - - - - - - -+ |
|
6992 // | 1a. data of handshake (1/2) | |
|
6993 // +=================================================+ |
|
6994 // +=================================================+ |
|
6995 // | 2. tls_record_header_c | |
|
6996 // | protocol tls_record_protocol_change_cipher_spec | |
|
6997 // +-------------------------------------------------+ |
|
6998 // | 2a. data of handshake (2/2) | |
|
6999 // +=================================================+ |
|
7000 // +=================================================+ |
|
7001 |
|
7002 eap_status_e status = eap_status_ok; |
|
7003 u32_t index = 0ul; |
|
7004 bool analyse_messages = true; |
|
7005 |
|
7006 for (index = m_received_tls_message.get_analyse_index() |
|
7007 ; analyse_messages == true |
|
7008 && index < m_received_tls_message.get_record_message_count() |
|
7009 ; index++) |
|
7010 { |
|
7011 // This is used in EAP-FAST to see the next TLS message type. |
|
7012 m_received_tls_message.save_analyse_index(index); |
|
7013 |
|
7014 tls_record_message_c * const tls_record_message |
|
7015 = m_received_tls_message.get_record_message(index); |
|
7016 if (tls_record_message == 0) |
|
7017 { |
|
7018 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7019 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
7020 m_am_tools, |
|
7021 eap_status_too_short_message); |
|
7022 } |
|
7023 |
|
7024 u32_t tls_record_length = tls_record_message->get_record_message_data()->get_data_length(); |
|
7025 |
|
7026 tls_record_header_c tls_record_header( |
|
7027 m_am_tools, |
|
7028 tls_record_message->get_record_message_data()->get_data( |
|
7029 tls_record_header_c::get_header_length()), |
|
7030 tls_record_length); |
|
7031 |
|
7032 if (tls_record_header.get_is_valid() == false |
|
7033 || tls_record_length < tls_record_header.get_data_length()) |
|
7034 { |
|
7035 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7036 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
7037 m_am_tools, |
|
7038 eap_status_too_short_message); |
|
7039 } |
|
7040 |
|
7041 EAP_TRACE_DATA_DEBUG( |
|
7042 m_am_tools, |
|
7043 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
7044 (EAPL("process TLS-record message"), |
|
7045 tls_record_header.get_header_buffer(tls_record_header.get_header_length() |
|
7046 + tls_record_header.get_data_length()), |
|
7047 tls_record_header.get_header_length() |
|
7048 + tls_record_header.get_data_length())); |
|
7049 |
|
7050 if ((tls_record_length) |
|
7051 < (tls_record_header.get_header_length() + tls_record_header.get_data_length())) |
|
7052 { |
|
7053 // Record header indicates more data than the received buffer includes. |
|
7054 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7055 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
7056 m_am_tools, |
|
7057 eap_status_process_illegal_packet_error); |
|
7058 } |
|
7059 |
|
7060 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
7061 EAP_TRACE_DEBUG( |
|
7062 m_am_tools, |
|
7063 TRACE_FLAGS_DEFAULT, |
|
7064 (EAPL("TLS: %s: parse_function: process_tls_records(): ") |
|
7065 EAPL("index[%u] protocol = 0x%08x=%s.\n"), |
|
7066 (m_is_client == true ? "client": "server"), |
|
7067 index, |
|
7068 tls_record_header.get_protocol(), |
|
7069 tls_record_header.get_tls_protocol_string())); |
|
7070 |
|
7071 |
|
7072 if (tls_record_message->get_cipher_suite_applied() == false) |
|
7073 { |
|
7074 status = apply_receive_cipher_suite(tls_record_message->get_record_message_data()); |
|
7075 if (status != eap_status_ok) |
|
7076 { |
|
7077 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7078 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
7079 } |
|
7080 |
|
7081 tls_record_message->set_cipher_suite_applied(); |
|
7082 |
|
7083 tls_record_length = tls_record_message->get_record_message_data()->get_data_length(); |
|
7084 |
|
7085 // We must query tls_record_header again, |
|
7086 // memory buffer may be changed during apply_receive_cipher_suite() call. |
|
7087 tls_record_header.set_header_buffer( |
|
7088 tls_record_message->get_record_message_data()->get_data( |
|
7089 tls_record_header_c::get_header_length()), |
|
7090 tls_record_length); |
|
7091 |
|
7092 if (tls_record_header.get_is_valid() == false |
|
7093 || tls_record_length < tls_record_header.get_data_length() |
|
7094 || tls_record_length |
|
7095 < tls_record_header.get_header_length() |
|
7096 + tls_record_header.get_data_length()) |
|
7097 { |
|
7098 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7099 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
7100 m_am_tools, |
|
7101 eap_status_too_short_message); |
|
7102 } |
|
7103 } |
|
7104 |
|
7105 |
|
7106 while (index+1ul < m_received_tls_message.get_record_message_count()) |
|
7107 { |
|
7108 tls_record_message_c * const next_tls_record_message |
|
7109 = m_received_tls_message.get_record_message(index+1ul); |
|
7110 if (next_tls_record_message != 0) |
|
7111 { |
|
7112 u32_t next_tls_record_length |
|
7113 = next_tls_record_message->get_record_message_data()->get_data_length(); |
|
7114 |
|
7115 tls_record_header_c next_tls_record_header( |
|
7116 m_am_tools, |
|
7117 next_tls_record_message->get_record_message_data()->get_data( |
|
7118 tls_record_header_c::get_header_length()), |
|
7119 next_tls_record_length); |
|
7120 |
|
7121 if (next_tls_record_header.get_is_valid() == false |
|
7122 || next_tls_record_length < next_tls_record_header.get_data_length()) |
|
7123 { |
|
7124 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7125 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
7126 m_am_tools, |
|
7127 eap_status_too_short_message); |
|
7128 } |
|
7129 |
|
7130 if (tls_record_header.get_protocol() == next_tls_record_header.get_protocol()) |
|
7131 { |
|
7132 // Reassembly checks this and the next TLS-records whether they are fragments |
|
7133 // and it reassembles fragments to one TLS-record. |
|
7134 // The easiest check does need only the TLS-protocol fields. |
|
7135 // If TLS-protocol fields are the same those records could be reassembled. |
|
7136 |
|
7137 if (next_tls_record_message->get_cipher_suite_applied() == false) |
|
7138 { |
|
7139 status = apply_receive_cipher_suite( |
|
7140 next_tls_record_message->get_record_message_data()); |
|
7141 if (status != eap_status_ok) |
|
7142 { |
|
7143 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7144 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
7145 m_am_tools, |
|
7146 status); |
|
7147 } |
|
7148 |
|
7149 next_tls_record_message->set_cipher_suite_applied(); |
|
7150 } |
|
7151 |
|
7152 next_tls_record_length |
|
7153 = next_tls_record_message->get_record_message_data()->get_data_length(); |
|
7154 |
|
7155 next_tls_record_header.set_header_buffer( |
|
7156 next_tls_record_message->get_record_message_data()->get_data( |
|
7157 tls_record_header_c::get_header_length()), |
|
7158 next_tls_record_length); |
|
7159 |
|
7160 if (next_tls_record_header.get_is_valid() == false |
|
7161 || next_tls_record_length < next_tls_record_header.get_data_length()) |
|
7162 { |
|
7163 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7164 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
7165 m_am_tools, |
|
7166 eap_status_too_short_message); |
|
7167 } |
|
7168 |
|
7169 status = reassemble_tls_records(tls_record_message, &next_tls_record_header); |
|
7170 if (status != eap_status_ok) |
|
7171 { |
|
7172 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7173 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
7174 } |
|
7175 |
|
7176 // If TLS-record is complete then it could be parsed and analysed. |
|
7177 // TLS-record is complete when the next TLS-record is other type of protocol. |
|
7178 // If TLS-record is NOT complete the next TLS-record must processed. |
|
7179 // In a case the TLS-record cannot be reassemled the whole |
|
7180 // TLS-message must be dropped. |
|
7181 |
|
7182 // Remove the next_tls_record_message. |
|
7183 status = m_received_tls_message.remove_record_message(index+1ul); |
|
7184 if (status != eap_status_ok) |
|
7185 { |
|
7186 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7187 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
7188 } |
|
7189 } |
|
7190 else |
|
7191 { |
|
7192 break; |
|
7193 } |
|
7194 } |
|
7195 else |
|
7196 { |
|
7197 break; |
|
7198 } |
|
7199 } // while() |
|
7200 |
|
7201 // NOTE at this point the length may be longer than 2^14 bytes. |
|
7202 tls_record_length = tls_record_message->get_record_message_data()->get_data_length(); |
|
7203 |
|
7204 // We must query tls_record_header again, |
|
7205 // memory buffer may be changed during reassembly. |
|
7206 tls_record_header.set_header_buffer( |
|
7207 tls_record_message->get_record_message_data()->get_data( |
|
7208 tls_record_length), |
|
7209 tls_record_length); |
|
7210 |
|
7211 if (tls_record_header.get_is_valid() == false |
|
7212 || tls_record_length < tls_record_header.get_data_length() |
|
7213 || tls_record_length |
|
7214 < tls_record_header.get_header_length() |
|
7215 + tls_record_header.get_data_length()) |
|
7216 { |
|
7217 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7218 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
7219 m_am_tools, |
|
7220 eap_status_too_short_message); |
|
7221 } |
|
7222 |
|
7223 |
|
7224 |
|
7225 // Here we extract the protocol messages from the buffer. |
|
7226 // Note the tls_record_header includes only the first protocol message, |
|
7227 // that causes the use of tls_record_message->get_record_message_data(). |
|
7228 u32_t protocol_messages_length = tls_record_length - tls_record_header.get_header_length(); |
|
7229 eap_variable_data_c protocol_messages(m_am_tools); |
|
7230 |
|
7231 status = protocol_messages.set_buffer( |
|
7232 tls_record_message->get_record_message_data()->get_data_offset( |
|
7233 tls_record_header.get_header_length(), |
|
7234 protocol_messages_length), |
|
7235 protocol_messages_length, |
|
7236 false, |
|
7237 true); |
|
7238 if (status != eap_status_ok) |
|
7239 { |
|
7240 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7241 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
7242 } |
|
7243 |
|
7244 EAP_TRACE_DATA_DEBUG( |
|
7245 m_am_tools, |
|
7246 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
7247 (EAPL("reassembled TLS-protocol messages"), |
|
7248 protocol_messages.get_data( |
|
7249 protocol_messages.get_data_length()), |
|
7250 protocol_messages.get_data_length())); |
|
7251 |
|
7252 switch(tls_record_header.get_protocol()) |
|
7253 { |
|
7254 case tls_record_protocol_change_cipher_spec: |
|
7255 { |
|
7256 if (tls_record_message->get_parsed_record() == false) |
|
7257 { |
|
7258 status = parse_tls_protocol_change_cipher_spec( |
|
7259 tls_record_message, |
|
7260 &protocol_messages); |
|
7261 if (status != eap_status_ok) |
|
7262 { |
|
7263 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7264 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
7265 } |
|
7266 } |
|
7267 |
|
7268 status = analyse_tls_protocol_change_cipher_spec( |
|
7269 tls_record_message); |
|
7270 break; |
|
7271 } |
|
7272 case tls_record_protocol_alert: |
|
7273 { |
|
7274 if (tls_record_message->get_parsed_record() == false) |
|
7275 { |
|
7276 status = parse_tls_protocol_alert( |
|
7277 tls_record_message, |
|
7278 &protocol_messages); |
|
7279 if (status != eap_status_ok) |
|
7280 { |
|
7281 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7282 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
7283 } |
|
7284 } |
|
7285 |
|
7286 status = analyse_tls_protocol_alert( |
|
7287 tls_record_message); |
|
7288 break; |
|
7289 } |
|
7290 case tls_record_protocol_handshake: |
|
7291 { |
|
7292 if (tls_record_message->get_parsed_record() == false) |
|
7293 { |
|
7294 status = parse_tls_protocol_handshake( |
|
7295 tls_record_message, |
|
7296 &protocol_messages); |
|
7297 if (status != eap_status_ok) |
|
7298 { |
|
7299 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7300 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
7301 } |
|
7302 } |
|
7303 |
|
7304 status = analyse_tls_protocol_handshake( |
|
7305 tls_record_message, |
|
7306 m_received_tls_message.get_received_eap_identifier()); |
|
7307 break; |
|
7308 } |
|
7309 case tls_record_protocol_application_data: |
|
7310 { |
|
7311 if (tls_record_message->get_parsed_record() == false) |
|
7312 { |
|
7313 status = parse_tls_protocol_application_data( |
|
7314 tls_record_message, |
|
7315 &protocol_messages); |
|
7316 if (status != eap_status_ok) |
|
7317 { |
|
7318 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7319 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
7320 } |
|
7321 } |
|
7322 |
|
7323 status = analyse_tls_protocol_application_data( |
|
7324 tls_record_message, |
|
7325 m_received_tls_message.get_received_eap_identifier()); |
|
7326 break; |
|
7327 } |
|
7328 default: |
|
7329 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7330 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
7331 m_am_tools, |
|
7332 eap_status_wrong_protocol); |
|
7333 } // switch() |
|
7334 |
|
7335 |
|
7336 // Save the analysed state. We will continue from the following record |
|
7337 // after the pending request is completed. |
|
7338 m_received_tls_message.save_analyse_index(index+1ul); |
|
7339 |
|
7340 EAP_TRACE_DEBUG( |
|
7341 m_am_tools, |
|
7342 TRACE_FLAGS_DEFAULT, |
|
7343 (EAPL("TLS: %s: parse_function: process_tls_records(): saves index+1 = %u.\n"), |
|
7344 (m_is_client == true ? "client": "server"), |
|
7345 index+1ul)); |
|
7346 |
|
7347 |
|
7348 if (status == eap_status_pending_request) |
|
7349 { |
|
7350 // Save analyse state. We will continue from the current record |
|
7351 // after the pending request is completed. |
|
7352 m_received_tls_message.save_analyse_index(index); |
|
7353 |
|
7354 EAP_TRACE_DEBUG( |
|
7355 m_am_tools, |
|
7356 TRACE_FLAGS_DEFAULT, |
|
7357 (EAPL("TLS: %s: parse_function: process_tls_records(): pending request, saves index = %u.\n"), |
|
7358 (m_is_client == true ? "client": "server"), |
|
7359 index)); |
|
7360 |
|
7361 analyse_messages = false; |
|
7362 |
|
7363 eap_status_e compl_status = completion_action_add( |
|
7364 tls_completion_action_process_tls_records); |
|
7365 if (compl_status != eap_status_ok) |
|
7366 { |
|
7367 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7368 return EAP_STATUS_RETURN(m_am_tools, status); |
|
7369 } |
|
7370 } |
|
7371 else if (status != eap_status_ok) |
|
7372 { |
|
7373 analyse_messages = false; |
|
7374 } |
|
7375 |
|
7376 if ((get_is_tunneled_tls() == false |
|
7377 && m_tls_peap_state == tls_peap_state_tls_success) |
|
7378 || (get_is_tunneled_tls() == true |
|
7379 && m_tls_peap_state == tls_peap_state_peap_tunnel_ready)) |
|
7380 { |
|
7381 // Authentication OK. |
|
7382 |
|
7383 if (m_eap_type == eap_type_peap |
|
7384 && m_peap_version == peap_version_2 |
|
7385 && m_tls_peap_state == tls_peap_state_peap_tunnel_ready) |
|
7386 { |
|
7387 // PEAPv2 sends EAP-Request/Identity message |
|
7388 // within the application data within the same message |
|
7389 // with TLS hello finished. |
|
7390 EAP_TRACE_DEBUG( |
|
7391 m_am_tools, |
|
7392 TRACE_FLAGS_DEFAULT, |
|
7393 (EAPL("TLS: PEAPv2 tunnel ready, application data may follow.\n"))); |
|
7394 } |
|
7395 else |
|
7396 { |
|
7397 analyse_messages = false; |
|
7398 if ((index+1ul) != m_received_tls_message.get_record_message_count()) |
|
7399 { |
|
7400 EAP_TRACE_DEBUG( |
|
7401 m_am_tools, |
|
7402 TRACE_FLAGS_DEFAULT, |
|
7403 (EAPL("ERROR: TLS: %s: parse_function: starts: tls_record_c::process_tls_records(): (index+1 = %d) != (record count = %d)\n"), |
|
7404 (m_is_client == true ? "client": "server"), |
|
7405 index+1, |
|
7406 m_received_tls_message.get_record_message_count())); |
|
7407 // Authentication was successfull, but there are unused TLS-records to process. |
|
7408 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7409 return EAP_STATUS_RETURN(m_am_tools, eap_status_unexpected_message); |
|
7410 } |
|
7411 EAP_TRACE_DEBUG( |
|
7412 m_am_tools, |
|
7413 TRACE_FLAGS_DEFAULT, |
|
7414 (EAPL("TLS: tls_record_c::process_tls_records(): m_received_tls_message.reset().\n"))); |
|
7415 m_received_tls_message.reset(); |
|
7416 } |
|
7417 } |
|
7418 } // for() |
|
7419 |
|
7420 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7421 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
7422 } |
|
7423 |
|
7424 //-------------------------------------------------- |
|
7425 |
|
7426 EAP_FUNC_EXPORT eap_status_e tls_record_c::process_tls_message() |
|
7427 { |
|
7428 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7429 |
|
7430 EAP_TRACE_DEBUG( |
|
7431 m_am_tools, |
|
7432 TRACE_FLAGS_DEFAULT, |
|
7433 (EAPL("\n"))); |
|
7434 EAP_TRACE_DEBUG( |
|
7435 m_am_tools, |
|
7436 TRACE_FLAGS_DEFAULT, |
|
7437 (EAPL("TLS: %s: parse_function: starts: tls_record_c::process_tls_message()\n"), |
|
7438 (m_is_client == true ? "client": "server"))); |
|
7439 |
|
7440 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::process_tls_message()"); |
|
7441 |
|
7442 EAP_TRACE_DATA_DEBUG( |
|
7443 m_am_tools, |
|
7444 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
7445 (EAPL("TLS-message"), |
|
7446 m_received_tls_message.get_tls_message_data()->get_data( |
|
7447 m_received_tls_message.get_tls_message_data()->get_data_length()), |
|
7448 m_received_tls_message.get_tls_message_data()->get_data_length())); |
|
7449 |
|
7450 u32_t next_start_offset = 0ul; |
|
7451 u32_t tls_packet_length = m_received_tls_message.get_tls_message_data()->get_data_length(); |
|
7452 |
|
7453 if (tls_packet_length < tls_record_header_c::get_header_length()) |
|
7454 { |
|
7455 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7456 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
7457 m_am_tools, |
|
7458 eap_status_too_short_message); |
|
7459 } |
|
7460 |
|
7461 tls_record_header_c tls_record_header( |
|
7462 m_am_tools, |
|
7463 m_received_tls_message.get_tls_message_data()->get_data_offset( |
|
7464 next_start_offset, |
|
7465 tls_record_header_c::get_header_length()), |
|
7466 tls_packet_length); |
|
7467 |
|
7468 if (tls_record_header.get_is_valid() == false |
|
7469 || tls_packet_length < tls_record_header.get_data_length()) |
|
7470 { |
|
7471 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7472 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
7473 m_am_tools, |
|
7474 eap_status_too_short_message); |
|
7475 } |
|
7476 |
|
7477 eap_status_e status = eap_status_ok; |
|
7478 u32_t counter = 0ul; |
|
7479 |
|
7480 // One TLS-message could include many records. Each of records |
|
7481 // could include many protocol messages. |
|
7482 // +=================================================+ |
|
7483 // +=================================================+ |
|
7484 // | 1. tls_record_header_c | |
|
7485 // | protocol tls_record_protocol_handshake | |
|
7486 // +-------------------------------------------------+ |
|
7487 // | 1a. tls_handshake_header_c | |
|
7488 // +- - - - - - - - - - - - - - - - - - - - - - - - -+ |
|
7489 // | 1a. data of handshake | |
|
7490 // +-------------------------------------------------+ |
|
7491 // | 1b. tls_handshake_header_c | |
|
7492 // +- - - - - - - - - - - - - - - - - - - - - - - - -+ |
|
7493 // | 1b. data of handshake | |
|
7494 // +=================================================+ |
|
7495 // +=================================================+ |
|
7496 // | 2. tls_record_header_c | |
|
7497 // | protocol tls_record_protocol_change_cipher_spec | |
|
7498 // +-------------------------------------------------+ |
|
7499 // | 2a. data of change_cipher_spec | |
|
7500 // +=================================================+ |
|
7501 // +=================================================+ |
|
7502 // | 3. tls_record_header_c | |
|
7503 // | protocol tls_record_protocol_handshake | |
|
7504 // +-------------------------------------------------+ |
|
7505 // | 3a. tls_handshake_header_c | |
|
7506 // +- - - - - - - - - - - - - - - - - - - - - - - - -+ |
|
7507 // | 3a. data of handshake | |
|
7508 // +=================================================+ |
|
7509 // +=================================================+ |
|
7510 |
|
7511 // One protocol message could be fragmented to many records. |
|
7512 // +=================================================+ |
|
7513 // +=================================================+ |
|
7514 // | 1. tls_record_header_c | |
|
7515 // | protocol tls_record_protocol_handshake | |
|
7516 // +-------------------------------------------------+ |
|
7517 // | 1a. tls_handshake_header_c | |
|
7518 // +- - - - - - - - - - - - - - - - - - - - - - - - -+ |
|
7519 // | 1a. data of handshake (1/2) | |
|
7520 // +=================================================+ |
|
7521 // +=================================================+ |
|
7522 // | 2. tls_record_header_c | |
|
7523 // | protocol tls_record_protocol_change_cipher_spec | |
|
7524 // +-------------------------------------------------+ |
|
7525 // | 2a. data of handshake (2/2) | |
|
7526 // +=================================================+ |
|
7527 // +=================================================+ |
|
7528 |
|
7529 while(status == eap_status_ok |
|
7530 && next_start_offset < tls_packet_length |
|
7531 && tls_record_header.get_is_valid() == true) |
|
7532 { |
|
7533 if ((tls_packet_length-next_start_offset) |
|
7534 < (tls_record_header.get_header_length() + tls_record_header.get_data_length())) |
|
7535 { |
|
7536 // Record header indicates more data than the received buffer includes. |
|
7537 EAP_TRACE_ERROR( |
|
7538 m_am_tools, |
|
7539 TRACE_FLAGS_DEFAULT, |
|
7540 (EAPL("ERROR: Record header indicates more data %u ") |
|
7541 EAPL("than the received buffer includes %u.\n"), |
|
7542 (tls_record_header.get_header_length() + tls_record_header.get_data_length()), |
|
7543 (tls_packet_length-next_start_offset))); |
|
7544 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7545 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
7546 m_am_tools, |
|
7547 eap_status_process_illegal_packet_error); |
|
7548 } |
|
7549 |
|
7550 EAP_TRACE_DATA_DEBUG( |
|
7551 m_am_tools, |
|
7552 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
7553 (EAPL("process TLS-record"), |
|
7554 tls_record_header.get_header_buffer( |
|
7555 tls_record_header.get_header_length() |
|
7556 + tls_record_header.get_data_length()), |
|
7557 tls_record_header.get_header_length() |
|
7558 + tls_record_header.get_data_length())); |
|
7559 |
|
7560 u32_t tls_record_length = tls_record_header.get_header_length() |
|
7561 + tls_record_header.get_data_length(); |
|
7562 |
|
7563 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
7564 EAP_TRACE_DEBUG( |
|
7565 m_am_tools, |
|
7566 TRACE_FLAGS_DEFAULT, |
|
7567 (EAPL("TLS: %s: parse_function: process_tls_message(): ") |
|
7568 EAPL("counter[%u] protocol = 0x%08x=%s.\n"), |
|
7569 (m_is_client == true ? "client": "server"), |
|
7570 counter, |
|
7571 tls_record_header.get_protocol(), |
|
7572 tls_record_header.get_tls_protocol_string())); |
|
7573 |
|
7574 tls_record_message_c * const tls_record_message |
|
7575 = new tls_record_message_c(m_am_tools, this, m_is_client); |
|
7576 |
|
7577 eap_automatic_variable_c<tls_record_message_c> |
|
7578 automatic_tls_record_message(m_am_tools, tls_record_message); |
|
7579 |
|
7580 if (tls_record_message == 0 |
|
7581 || tls_record_message->get_is_valid() == false) |
|
7582 { |
|
7583 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7584 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
7585 m_am_tools, |
|
7586 eap_status_allocation_error); |
|
7587 } |
|
7588 |
|
7589 tls_record_message->set_tls_record_header_is_included(true); |
|
7590 |
|
7591 status = tls_record_message->set_record_header_copy(&tls_record_header); |
|
7592 if (status != eap_status_ok) |
|
7593 { |
|
7594 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7595 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
7596 } |
|
7597 |
|
7598 tls_record_message->set_record_message_data( |
|
7599 tls_record_header.get_header_buffer(tls_record_header.get_header_length() |
|
7600 + tls_record_header.get_data_length()), |
|
7601 tls_record_header.get_header_length() |
|
7602 + tls_record_header.get_data_length()); |
|
7603 |
|
7604 // Note m_received_tls_message frees message on any case. |
|
7605 automatic_tls_record_message.do_not_free_variable(); |
|
7606 |
|
7607 status = m_received_tls_message.add_record_message( |
|
7608 tls_record_message, |
|
7609 true, |
|
7610 false // Here the TLS-Hello messages are not marked. |
|
7611 ); |
|
7612 if (status != eap_status_ok) |
|
7613 { |
|
7614 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7615 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
7616 } |
|
7617 |
|
7618 |
|
7619 next_start_offset += tls_record_length; |
|
7620 |
|
7621 if (next_start_offset < tls_packet_length) |
|
7622 { |
|
7623 u32_t remain_data_length = tls_packet_length - next_start_offset; |
|
7624 if (remain_data_length < tls_record_header_c::get_header_length()) |
|
7625 { |
|
7626 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7627 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
7628 m_am_tools, |
|
7629 eap_status_too_short_message); |
|
7630 } |
|
7631 |
|
7632 tls_record_header.set_header_buffer( |
|
7633 m_received_tls_message.get_tls_message_data()->get_data_offset( |
|
7634 next_start_offset, |
|
7635 tls_record_header_c::get_header_length()), |
|
7636 remain_data_length); |
|
7637 |
|
7638 if (tls_record_header.get_is_valid() == false |
|
7639 || remain_data_length < tls_record_header.get_data_length()) |
|
7640 { |
|
7641 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7642 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
7643 m_am_tools, |
|
7644 eap_status_too_short_message); |
|
7645 } |
|
7646 } |
|
7647 |
|
7648 ++counter; |
|
7649 |
|
7650 } // while() |
|
7651 |
|
7652 if (next_start_offset != tls_packet_length) |
|
7653 { |
|
7654 // Parsed packet length does not match with received packet length. |
|
7655 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7656 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT( |
|
7657 m_am_tools, |
|
7658 eap_status_process_illegal_packet_error); |
|
7659 } |
|
7660 |
|
7661 status = process_tls_records(); |
|
7662 |
|
7663 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7664 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
7665 } |
|
7666 |
|
7667 //-------------------------------------------------- |
|
7668 |
|
7669 EAP_FUNC_EXPORT eap_status_e tls_record_c::check_selected_cipher_suite( |
|
7670 const tls_cipher_suites_e selected_cipher_suite) |
|
7671 { |
|
7672 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7673 |
|
7674 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
7675 EAP_TRACE_DEBUG( |
|
7676 m_am_tools, |
|
7677 TRACE_FLAGS_DEFAULT, |
|
7678 (EAPL("TLS: %s: suite_function: starts: tls_record_c::check_selected_cipher_suite(): selected_cipher_suite=%d=%s\n"), |
|
7679 (m_is_client == true ? "client": "server"), |
|
7680 selected_cipher_suite, |
|
7681 eap_tls_trace_string_c::get_cipher_suite_string(selected_cipher_suite))); |
|
7682 |
|
7683 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::check_selected_cipher_suite()"); |
|
7684 |
|
7685 u16_t tmp_selected_cipher_suite = static_cast<u16_t>(selected_cipher_suite); |
|
7686 |
|
7687 i32_t index = find_simple<u16_t>( |
|
7688 &m_proposed_cipher_suites, |
|
7689 &tmp_selected_cipher_suite, |
|
7690 m_am_tools); |
|
7691 if (index == -1) |
|
7692 { |
|
7693 for (u32_t ind = 0ul; ind < m_proposed_cipher_suites.get_object_count(); ++ind) |
|
7694 { |
|
7695 u16_t * proposed_cipher_suite = m_proposed_cipher_suites.get_object(ind); |
|
7696 if (proposed_cipher_suite != 0) |
|
7697 { |
|
7698 EAP_TRACE_DEBUG( |
|
7699 m_am_tools, |
|
7700 TRACE_FLAGS_DEFAULT, |
|
7701 (EAPL("TLS: %s: suite_function: check_selected_cipher_suite(): proposed cipher suite=%d=%s\n"), |
|
7702 (m_is_client == true ? "client": "server"), |
|
7703 *proposed_cipher_suite, |
|
7704 eap_tls_trace_string_c::get_cipher_suite_string(static_cast<tls_cipher_suites_e>(*proposed_cipher_suite)))); |
|
7705 } |
|
7706 } |
|
7707 |
|
7708 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7709 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_cipher_suite); |
|
7710 } |
|
7711 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7712 return EAP_STATUS_RETURN(m_am_tools, eap_status_ok); |
|
7713 } |
|
7714 |
|
7715 //-------------------------------------------------- |
|
7716 |
|
7717 EAP_FUNC_EXPORT eap_status_e tls_record_c::check_selected_compression_method( |
|
7718 const tls_compression_method_e selected_compression_method) |
|
7719 { |
|
7720 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7721 |
|
7722 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
7723 EAP_TRACE_DEBUG( |
|
7724 m_am_tools, |
|
7725 TRACE_FLAGS_DEFAULT, |
|
7726 (EAPL("TLS: %s: suite_function: starts: tls_record_c::check_selected_compression_method(): %s\n"), |
|
7727 (m_is_client == true ? "client": "server"), |
|
7728 eap_tls_trace_string_c::get_compression_method_string(selected_compression_method))); |
|
7729 |
|
7730 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::check_selected_compression_method()"); |
|
7731 |
|
7732 if (selected_compression_method == tls_compression_method_null) |
|
7733 { |
|
7734 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7735 return EAP_STATUS_RETURN(m_am_tools, eap_status_ok); |
|
7736 } |
|
7737 |
|
7738 u8_t tmp_selected_compression_method = static_cast<u8_t>(selected_compression_method); |
|
7739 |
|
7740 i32_t index = find_simple<u8_t>( |
|
7741 &m_proposed_compression_methods, |
|
7742 &tmp_selected_compression_method, m_am_tools); |
|
7743 if (index == -1) |
|
7744 { |
|
7745 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7746 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_cipher_suite); |
|
7747 } |
|
7748 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7749 return EAP_STATUS_RETURN(m_am_tools, eap_status_ok); |
|
7750 } |
|
7751 |
|
7752 //-------------------------------------------------- |
|
7753 |
|
7754 EAP_FUNC_EXPORT eap_status_e tls_record_c::u16_t_to_host_order( |
|
7755 u16_t * const value, |
|
7756 abs_eap_am_tools_c * const m_am_tools) |
|
7757 { |
|
7758 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7759 EAP_UNREFERENCED_PARAMETER(m_am_tools); |
|
7760 |
|
7761 *value = eap_ntohs(*value); |
|
7762 |
|
7763 return EAP_STATUS_RETURN(m_am_tools, eap_status_ok); |
|
7764 } |
|
7765 |
|
7766 //-------------------------------------------------- |
|
7767 |
|
7768 EAP_FUNC_EXPORT eap_status_e tls_record_c::u16_t_to_network_order( |
|
7769 u16_t * const value, |
|
7770 abs_eap_am_tools_c * const m_am_tools) |
|
7771 { |
|
7772 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7773 EAP_UNREFERENCED_PARAMETER(m_am_tools); |
|
7774 |
|
7775 *value = eap_htons(*value); |
|
7776 |
|
7777 return EAP_STATUS_RETURN(m_am_tools, eap_status_ok); |
|
7778 } |
|
7779 |
|
7780 |
|
7781 //-------------------------------------------------- |
|
7782 |
|
7783 EAP_FUNC_EXPORT eap_status_e tls_record_c::analyse_handshake_type_hello_request( |
|
7784 EAP_TEMPLATE_CONST tls_handshake_message_c * const /* handshake_message */) |
|
7785 { |
|
7786 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7787 |
|
7788 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
7789 EAP_TRACE_DEBUG( |
|
7790 m_am_tools, |
|
7791 TRACE_FLAGS_DEFAULT, |
|
7792 (EAPL("TLS: %s: message_function: starts: tls_record_c::analyse_handshake_type_hello_request()\n"), |
|
7793 (m_is_client == true ? "client": "server"))); |
|
7794 |
|
7795 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::analyse_handshake_type_hello_request()"); |
|
7796 |
|
7797 EAP_ASSERT(m_is_client == true); |
|
7798 |
|
7799 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
7800 set_tls_identity_privacy_handshake_state(tls_identity_privacy_handshake_state_runs); |
|
7801 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
7802 |
|
7803 set_state(tls_peap_state_wait_handshake_type_server_hello); |
|
7804 |
|
7805 eap_status_e status = completion_action_add(tls_completion_action_create_handshake_type_client_hello); |
|
7806 if (status != eap_status_ok) |
|
7807 { |
|
7808 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7809 return EAP_STATUS_RETURN(m_am_tools, status); |
|
7810 } |
|
7811 |
|
7812 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7813 return EAP_STATUS_RETURN(m_am_tools, status); |
|
7814 } |
|
7815 |
|
7816 //-------------------------------------------------- |
|
7817 |
|
7818 EAP_FUNC_EXPORT eap_status_e tls_record_c::analyse_handshake_type_client_hello( |
|
7819 EAP_TEMPLATE_CONST tls_handshake_message_c * const handshake_message) |
|
7820 { |
|
7821 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7822 |
|
7823 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
7824 |
|
7825 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
7826 EAP_TRACE_DEBUG( |
|
7827 m_am_tools, |
|
7828 TRACE_FLAGS_DEFAULT, |
|
7829 (EAPL("TLS: %s: message_function: starts: tls_record_c::analyse_handshake_type_client_hello(): privacy_handshake_state=%d=%s, session_type=%s\n"), |
|
7830 (m_is_client == true ? "client": "server"), |
|
7831 m_tls_identity_privacy_handshake_state, |
|
7832 eap_tls_trace_string_c::get_tls_identity_privacy_handshake_state_string(m_tls_identity_privacy_handshake_state), |
|
7833 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type) |
|
7834 )); |
|
7835 #else |
|
7836 EAP_TRACE_DEBUG( |
|
7837 m_am_tools, |
|
7838 TRACE_FLAGS_DEFAULT, |
|
7839 (EAPL("TLS: %s: message_function: starts: tls_record_c::analyse_handshake_type_client_hello(): privacy_handshake_state=%d=%s\n"), |
|
7840 (m_is_client == true ? "client": "server"), |
|
7841 0, |
|
7842 "" |
|
7843 )); |
|
7844 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
7845 |
|
7846 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::analyse_handshake_type_client_hello()"); |
|
7847 |
|
7848 EAP_ASSERT(m_is_client == false); |
|
7849 |
|
7850 // 0 1 2 3 |
|
7851 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
7852 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
7853 // | Version: 3 | Version: 1 | | |
|
7854 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
7855 // | | |
|
7856 // + + |
|
7857 // | | |
|
7858 // + + |
|
7859 // | ClientRandomValue | |
|
7860 // + (32 bytes) +-+-+-+-+-+-+-+-+ |
|
7861 // | | ID length | |
|
7862 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
7863 // | | |
|
7864 // + + |
|
7865 // | Session ID | |
|
7866 // + (maximum 32 bytes) + |
|
7867 // | | |
|
7868 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
7869 // | CipherSuite length | CipherSuite 1 | |
|
7870 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
7871 // | CipherSuite 2 | CipherSuite 3 | |
|
7872 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
7873 // | CipherSuite 4 | Cmp length | Cmp 1 | |
|
7874 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
7875 // | Cmp 2 | Cmp 3 | extensions ... | |
|
7876 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
7877 |
|
7878 eap_status_e status = eap_status_not_supported; |
|
7879 |
|
7880 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
7881 |
|
7882 if (handshake_message->get_random_value() == 0 |
|
7883 || handshake_message->get_random_value()->get_data_length() |
|
7884 != TLS_HANDSHAKE_RANDOM_VALUE_SIZE) |
|
7885 { |
|
7886 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7887 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
7888 } |
|
7889 |
|
7890 |
|
7891 status = m_client_handshake_random_value.set_copy_of_buffer( |
|
7892 handshake_message->get_random_value()); |
|
7893 if (status != eap_status_ok |
|
7894 || m_client_handshake_random_value.get_data_length() != TLS_HANDSHAKE_RANDOM_VALUE_SIZE) |
|
7895 { |
|
7896 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7897 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
7898 } |
|
7899 |
|
7900 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
7901 |
|
7902 if (handshake_message->get_session_id() == 0 |
|
7903 || (handshake_message->get_session_id()->get_is_valid_data() == true |
|
7904 && handshake_message->get_session_id()->get_data_length() > TLS_SESSION_ID_SIZE)) |
|
7905 { |
|
7906 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7907 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
7908 } |
|
7909 |
|
7910 if (handshake_message->get_session_id()->get_is_valid_data() == true |
|
7911 && handshake_message->get_session_id()->get_data_length() > 0ul) |
|
7912 { |
|
7913 status = m_session_id.set_copy_of_buffer(handshake_message->get_session_id()); |
|
7914 if (status != eap_status_ok |
|
7915 || m_session_id.get_data_length() > TLS_SESSION_ID_SIZE) |
|
7916 { |
|
7917 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7918 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
7919 } |
|
7920 } |
|
7921 |
|
7922 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
7923 |
|
7924 { |
|
7925 EAP_TEMPLATE_CONST eap_array_c<u16_t> * const cipher_suites |
|
7926 = handshake_message->get_cipher_suites(); |
|
7927 |
|
7928 if (cipher_suites->get_object_count() == 0ul) |
|
7929 { |
|
7930 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7931 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
7932 } |
|
7933 |
|
7934 m_proposed_cipher_suites.reset(); |
|
7935 |
|
7936 status = copy_simple<u16_t>( |
|
7937 cipher_suites, |
|
7938 &m_proposed_cipher_suites, |
|
7939 m_am_tools, |
|
7940 false); |
|
7941 if (status != eap_status_ok |
|
7942 || m_proposed_cipher_suites.get_object_count() == 0ul) |
|
7943 { |
|
7944 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7945 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
7946 } |
|
7947 } |
|
7948 |
|
7949 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
7950 |
|
7951 { |
|
7952 EAP_TEMPLATE_CONST eap_array_c<u8_t> * const compression_methods |
|
7953 = handshake_message->get_compression_methods(); |
|
7954 |
|
7955 status = copy_simple<u8_t>( |
|
7956 compression_methods, |
|
7957 &m_proposed_compression_methods, |
|
7958 m_am_tools, |
|
7959 false); |
|
7960 if (status != eap_status_ok) |
|
7961 { |
|
7962 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7963 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
7964 } |
|
7965 } |
|
7966 |
|
7967 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
7968 |
|
7969 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
7970 |
|
7971 { |
|
7972 EAP_TEMPLATE_CONST eap_array_c<tls_extension_c> * const tls_extensions |
|
7973 = handshake_message->get_tls_extensions(); |
|
7974 |
|
7975 status = copy<tls_extension_c>( |
|
7976 tls_extensions, |
|
7977 &m_received_tls_extensions, |
|
7978 m_am_tools, |
|
7979 false); |
|
7980 if (status != eap_status_ok) |
|
7981 { |
|
7982 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
7983 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
7984 } |
|
7985 } |
|
7986 |
|
7987 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
7988 |
|
7989 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
7990 |
|
7991 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
7992 if (m_tls_session_type == tls_session_type_full_authentication |
|
7993 && m_tls_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_negotiates) |
|
7994 { |
|
7995 set_tls_identity_privacy_handshake_state(tls_identity_privacy_handshake_state_runs); |
|
7996 } |
|
7997 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
7998 |
|
7999 status = completion_action_add(tls_completion_action_create_handshake_type_server_hello); |
|
8000 if (status != eap_status_ok) |
|
8001 { |
|
8002 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8003 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8004 } |
|
8005 |
|
8006 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
8007 if (m_tls_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_none) |
|
8008 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
8009 { |
|
8010 status = m_am_tls_services->select_cipher_suite_and_check_session_id( |
|
8011 &m_proposed_cipher_suites, |
|
8012 &m_session_id |
|
8013 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
8014 , tls_extension_c::get_tls_extension( |
|
8015 tls_extension_type_session_ticket, |
|
8016 &m_received_tls_extensions, |
|
8017 m_am_tools) |
|
8018 #endif //#if defined(USE_EAP_TLS_SESSION_TICKET) |
|
8019 ); |
|
8020 if (status == eap_status_pending_request) |
|
8021 { |
|
8022 // This is pending query, that will be completed by |
|
8023 // complete_select_cipher_suite_and_check_session_id() call. |
|
8024 m_pending_select_cipher_suite_and_check_session_id = true; |
|
8025 } |
|
8026 else if (status == eap_status_completed_request) |
|
8027 { |
|
8028 // This is already completed by complete_select_cipher_suite_and_check_session_id() call. |
|
8029 } |
|
8030 else if (status == eap_status_ok) |
|
8031 { |
|
8032 // This is also an error case, because this call is always completed on success. |
|
8033 status = eap_status_process_general_error; |
|
8034 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8035 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8036 } |
|
8037 else // All other status values means error, because this call is always completed on success. |
|
8038 { |
|
8039 // This is an error case. |
|
8040 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8041 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
8042 } |
|
8043 } |
|
8044 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
8045 else if (m_tls_session_type == tls_session_type_full_authentication |
|
8046 && m_tls_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_runs) |
|
8047 { |
|
8048 if (m_tls_peap_server_authenticates_client_config_server == true) |
|
8049 { |
|
8050 set_state(tls_peap_state_wait_handshake_type_certificate); |
|
8051 } |
|
8052 else |
|
8053 { |
|
8054 set_state(tls_peap_state_wait_handshake_type_client_key_exchange); |
|
8055 } |
|
8056 |
|
8057 status = completion_action_add(tls_completion_action_create_handshake_type_certificate); |
|
8058 if (status != eap_status_ok) |
|
8059 { |
|
8060 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8061 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8062 } |
|
8063 |
|
8064 if (cipher_suite_is_TLS_DHE_DSS() == true |
|
8065 || cipher_suite_is_TLS_DHE_RSA() == true) |
|
8066 { |
|
8067 // Ephemeral DH key exchange causes creation of server_key_exchange message. |
|
8068 // Server sends DH public key and related parameters to client. |
|
8069 |
|
8070 status = completion_action_add(tls_completion_action_query_dh_parameters); |
|
8071 if (status != eap_status_ok) |
|
8072 { |
|
8073 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8074 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8075 } |
|
8076 |
|
8077 status = completion_action_add( |
|
8078 tls_completion_action_create_handshake_type_server_key_exchange); |
|
8079 if (status != eap_status_ok) |
|
8080 { |
|
8081 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8082 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8083 } |
|
8084 |
|
8085 // This will complete creation of handshake_type_server_key_exchange message. |
|
8086 status = completion_action_add( |
|
8087 tls_completion_action_complete_create_handshake_type_server_key_exchange); |
|
8088 if (status != eap_status_ok) |
|
8089 { |
|
8090 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8091 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8092 } |
|
8093 |
|
8094 // Also the other pending messages will be processed after this action is completed. |
|
8095 eap_status_e compl_status = completion_action_add( |
|
8096 tls_completion_action_process_tls_records); |
|
8097 if (compl_status != eap_status_ok) |
|
8098 { |
|
8099 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8100 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8101 } |
|
8102 } |
|
8103 |
|
8104 if (m_tls_peap_server_authenticates_client_config_server == true) |
|
8105 { |
|
8106 // Server initiates client authentication. |
|
8107 status = completion_action_add( |
|
8108 tls_completion_action_create_handshake_type_certificate_request); |
|
8109 if (status != eap_status_ok) |
|
8110 { |
|
8111 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8112 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8113 } |
|
8114 } |
|
8115 |
|
8116 status = completion_action_add( |
|
8117 tls_completion_action_create_handshake_type_server_hello_done); |
|
8118 if (status != eap_status_ok) |
|
8119 { |
|
8120 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8121 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8122 } |
|
8123 } |
|
8124 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
8125 |
|
8126 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
8127 |
|
8128 if (/* status == eap_status_pending_request |
|
8129 || */ status == eap_status_completed_request) |
|
8130 { |
|
8131 status = eap_status_ok; |
|
8132 } |
|
8133 |
|
8134 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8135 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8136 } |
|
8137 |
|
8138 //-------------------------------------------------- |
|
8139 |
|
8140 EAP_FUNC_EXPORT eap_status_e tls_record_c::analyse_handshake_type_server_hello( |
|
8141 EAP_TEMPLATE_CONST tls_handshake_message_c * const handshake_message) |
|
8142 { |
|
8143 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8144 |
|
8145 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
8146 EAP_TRACE_DEBUG( |
|
8147 m_am_tools, |
|
8148 TRACE_FLAGS_DEFAULT, |
|
8149 (EAPL("TLS: %s: message_function: starts: tls_record_c::analyse_handshake_type_server_hello()\n"), |
|
8150 (m_is_client == true ? "client": "server"))); |
|
8151 |
|
8152 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::analyse_handshake_type_server_hello()"); |
|
8153 |
|
8154 // 0 1 2 3 |
|
8155 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
8156 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
8157 // | Version: 3 | Version: 1 | | |
|
8158 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
8159 // | | |
|
8160 // + + |
|
8161 // | | |
|
8162 // + + |
|
8163 // | ServerRandomValue | |
|
8164 // + (32 bytes) +-+-+-+-+-+-+-+-+ |
|
8165 // | | ID length | |
|
8166 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
8167 // | | |
|
8168 // + + |
|
8169 // | Session ID | |
|
8170 // + (maximum 32 bytes) + |
|
8171 // | | |
|
8172 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
8173 // | CipherSuite | Cmp | extensions ...| |
|
8174 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
8175 |
|
8176 eap_status_e status = eap_status_not_supported; |
|
8177 |
|
8178 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
8179 |
|
8180 if (handshake_message->get_random_value() == 0 |
|
8181 || handshake_message->get_random_value()->get_data_length() |
|
8182 != TLS_HANDSHAKE_RANDOM_VALUE_SIZE) |
|
8183 { |
|
8184 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8185 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
8186 } |
|
8187 |
|
8188 status = m_server_handshake_random_value.set_copy_of_buffer( |
|
8189 handshake_message->get_random_value()); |
|
8190 if (status != eap_status_ok |
|
8191 || m_server_handshake_random_value.get_data_length() != TLS_HANDSHAKE_RANDOM_VALUE_SIZE) |
|
8192 { |
|
8193 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8194 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
8195 } |
|
8196 |
|
8197 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
8198 |
|
8199 set_selected_cipher_suite(handshake_message->get_selected_cipher_suite()); |
|
8200 |
|
8201 status = check_selected_cipher_suite(m_selected_cipher_suite); |
|
8202 if (status != eap_status_ok) |
|
8203 { |
|
8204 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8205 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8206 } |
|
8207 |
|
8208 { |
|
8209 EAP_TRACE_DEBUG( |
|
8210 m_am_tools, |
|
8211 TRACE_FLAGS_DEFAULT, |
|
8212 (EAPL("%s: TLS/PEAP selected cipher_suite %s\n"), |
|
8213 (m_is_client == true ? "client": "server"), |
|
8214 eap_tls_trace_string_c::get_cipher_suite_string(m_selected_cipher_suite))); |
|
8215 } |
|
8216 |
|
8217 |
|
8218 m_selected_compression_method = handshake_message->get_selected_compression_method(); |
|
8219 |
|
8220 status = check_selected_compression_method(m_selected_compression_method); |
|
8221 if (status != eap_status_ok) |
|
8222 { |
|
8223 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8224 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8225 } |
|
8226 |
|
8227 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
8228 |
|
8229 if (handshake_message->get_session_id() == 0 |
|
8230 || (handshake_message->get_session_id()->get_is_valid_data() == true |
|
8231 && handshake_message->get_session_id()->get_data_length() > TLS_SESSION_ID_SIZE)) |
|
8232 { |
|
8233 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8234 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
8235 } |
|
8236 |
|
8237 |
|
8238 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
8239 m_will_receive_new_session_ticket = false; |
|
8240 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
8241 |
|
8242 |
|
8243 #if defined(USE_FAST_EAP_TYPE) |
|
8244 if (m_eap_type == eap_type_fast |
|
8245 && m_tls_session_type == tls_session_type_eap_fast_server_unauthenticated_provisioning_mode_ADHP |
|
8246 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true) |
|
8247 { |
|
8248 EAP_TRACE_DEBUG( |
|
8249 m_am_tools, |
|
8250 TRACE_FLAGS_DEFAULT, |
|
8251 (EAPL("TLS: %s: message_function: analyse_handshake_type_server_hello(): ") |
|
8252 EAPL("EAP-FAST server unauthenticated provisioning mode\n"), |
|
8253 (m_is_client == true ? "client": "server"))); |
|
8254 } |
|
8255 else |
|
8256 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
8257 if (handshake_message->get_session_id()->get_is_valid_data() == true |
|
8258 && handshake_message->get_session_id()->get_data_length() > 0ul |
|
8259 #if defined(USE_FAST_EAP_TYPE) |
|
8260 // EAP-FAST specification says to watch the next message to see whether the session is resumed or not. |
|
8261 // Original TLS is specified to correctly so the client know what happens when it receives ServerHello message. |
|
8262 && (m_eap_type != eap_type_fast |
|
8263 || (m_tls_session_type == tls_session_type_original_session_resumption |
|
8264 || m_tls_session_type == tls_session_type_full_authentication)) |
|
8265 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
8266 ) |
|
8267 { |
|
8268 |
|
8269 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
8270 |
|
8271 if (m_tls_session_type == tls_session_type_stateless_session_resumption) |
|
8272 { |
|
8273 m_received_tls_extensions.reset(); |
|
8274 |
|
8275 const tls_extension_c * const supported_session_ticket_extension = tls_extension_c::get_tls_extension( |
|
8276 tls_extension_type_session_ticket, |
|
8277 &m_supported_tls_extensions, |
|
8278 m_am_tools); |
|
8279 |
|
8280 if (supported_session_ticket_extension != 0) |
|
8281 { |
|
8282 EAP_TEMPLATE_CONST eap_array_c<tls_extension_c> * const tls_extensions |
|
8283 = handshake_message->get_tls_extensions(); |
|
8284 |
|
8285 const tls_extension_c * const received_session_ticket_extension = tls_extension_c::get_tls_extension( |
|
8286 tls_extension_type_session_ticket, |
|
8287 tls_extensions, |
|
8288 m_am_tools); |
|
8289 |
|
8290 if (received_session_ticket_extension != 0) |
|
8291 { |
|
8292 EAP_TRACE_DEBUG( |
|
8293 m_am_tools, |
|
8294 TRACE_FLAGS_DEFAULT, |
|
8295 (EAPL("TLS: %s: message_function: analyse_handshake_type_server_hello(): ") |
|
8296 EAPL("SST: receives stateless session ticket: length = %d\n"), |
|
8297 (m_is_client == true ? "client": "server"), |
|
8298 received_session_ticket_extension->get_data_length())); |
|
8299 |
|
8300 eap_array_c<tls_extension_c> tmp_extensions(m_am_tools); |
|
8301 |
|
8302 tls_extension_c * const received_session_ticket_extension_copy = received_session_ticket_extension->copy(); |
|
8303 |
|
8304 if (received_session_ticket_extension_copy != 0) |
|
8305 { |
|
8306 status = tmp_extensions.add_object(received_session_ticket_extension_copy, true); |
|
8307 |
|
8308 status = copy<tls_extension_c>( |
|
8309 &tmp_extensions, |
|
8310 &m_received_tls_extensions, |
|
8311 m_am_tools, |
|
8312 false); |
|
8313 if (status != eap_status_ok) |
|
8314 { |
|
8315 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8316 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
8317 } |
|
8318 |
|
8319 m_will_receive_new_session_ticket = true; |
|
8320 } |
|
8321 } |
|
8322 } |
|
8323 } |
|
8324 |
|
8325 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
8326 |
|
8327 |
|
8328 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
8329 if (m_tls_session_type == tls_session_type_stateless_session_resumption) |
|
8330 { |
|
8331 EAP_TRACE_DEBUG( |
|
8332 m_am_tools, |
|
8333 TRACE_FLAGS_DEFAULT, |
|
8334 (EAPL("TLS: %s: message_function: analyse_handshake_type_server_hello(): ") |
|
8335 EAPL("restores stateless session\n"), |
|
8336 (m_is_client == true ? "client": "server"))); |
|
8337 |
|
8338 status = m_session_id.set_copy_of_buffer(handshake_message->get_session_id()); |
|
8339 if (status != eap_status_ok |
|
8340 || m_session_id.get_data_length() > TLS_SESSION_ID_SIZE) |
|
8341 { |
|
8342 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8343 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
8344 } |
|
8345 |
|
8346 status = indicate_state_to_lower_layer( |
|
8347 tls_peap_state_stateless_session_resumption); |
|
8348 if (status != eap_status_ok) |
|
8349 { |
|
8350 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8351 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8352 } |
|
8353 } |
|
8354 else |
|
8355 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
8356 /** @{ PEAPv2 does not support session resumption yet. } */ |
|
8357 if (((m_eap_type == eap_type_peap |
|
8358 && m_peap_version != peap_version_2) |
|
8359 || m_eap_type == eap_type_tls |
|
8360 || m_eap_type == eap_type_ttls |
|
8361 #if defined(USE_FAST_EAP_TYPE) |
|
8362 || m_eap_type == eap_type_fast |
|
8363 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
8364 ) |
|
8365 && m_tls_session_type == tls_session_type_original_session_resumption |
|
8366 && m_resumed_cipher_suite == m_selected_cipher_suite |
|
8367 && handshake_message->get_session_id()->compare(&m_session_id) == 0) |
|
8368 { |
|
8369 // OK, previous session will be restored. |
|
8370 |
|
8371 EAP_TRACE_DEBUG( |
|
8372 m_am_tools, |
|
8373 TRACE_FLAGS_DEFAULT, |
|
8374 (EAPL("TLS: %s: message_function: analyse_handshake_type_server_hello(): ") |
|
8375 EAPL("restores session\n"), |
|
8376 (m_is_client == true ? "client": "server"))); |
|
8377 |
|
8378 |
|
8379 eap_status_e notification_status = indicate_state_to_lower_layer( |
|
8380 tls_peap_state_original_session_resumption); |
|
8381 if (notification_status != eap_status_ok) |
|
8382 { |
|
8383 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8384 return EAP_STATUS_RETURN(m_am_tools, notification_status); |
|
8385 } |
|
8386 } |
|
8387 else |
|
8388 { |
|
8389 |
|
8390 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
8391 if (m_is_client == true |
|
8392 && m_tls_use_identity_privacy == true |
|
8393 && m_tls_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_none) |
|
8394 { |
|
8395 set_tls_identity_privacy_handshake_state(tls_identity_privacy_handshake_state_negotiates); |
|
8396 } |
|
8397 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
8398 |
|
8399 set_tls_session_type(tls_session_type_full_authentication); |
|
8400 |
|
8401 EAP_TRACE_DEBUG( |
|
8402 m_am_tools, |
|
8403 TRACE_FLAGS_DEFAULT, |
|
8404 (EAPL("TLS: %s: message_function: analyse_handshake_type_server_hello(): ") |
|
8405 EAPL("creates new session\n"), |
|
8406 (m_is_client == true ? "client": "server"))); |
|
8407 |
|
8408 status = m_session_id.set_copy_of_buffer(handshake_message->get_session_id()); |
|
8409 if (status != eap_status_ok |
|
8410 || m_session_id.get_data_length() > TLS_SESSION_ID_SIZE) |
|
8411 { |
|
8412 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8413 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
8414 } |
|
8415 |
|
8416 status = indicate_state_to_lower_layer( |
|
8417 tls_peap_state_full_authentication); |
|
8418 if (status != eap_status_ok) |
|
8419 { |
|
8420 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8421 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8422 } |
|
8423 } |
|
8424 } |
|
8425 else |
|
8426 { |
|
8427 // No session identifier. |
|
8428 #if defined(USE_FAST_EAP_TYPE) |
|
8429 if (m_tls_session_type == tls_session_type_eap_fast_pac_session_resumption |
|
8430 && get_next_tls_handshake_message_type() == tls_handshake_type_none |
|
8431 && get_next_tls_record_message_protocol() == tls_record_protocol_change_cipher_spec) |
|
8432 { |
|
8433 EAP_TRACE_DEBUG( |
|
8434 m_am_tools, |
|
8435 TRACE_FLAGS_DEFAULT, |
|
8436 (EAPL("TLS: %s: message_function: analyse_handshake_type_server_hello(): ") |
|
8437 EAPL("EAP-FAST PAC session resumtion.\n"), |
|
8438 (m_is_client == true ? "client": "server"))); |
|
8439 |
|
8440 // Generates master secret from PAC-Key. |
|
8441 status = generate_eap_fast_master_secret_from_pac_key( |
|
8442 &m_eap_fast_pac_key); |
|
8443 |
|
8444 m_eap_fast_pac_key.reset(); |
|
8445 |
|
8446 if (status != eap_status_ok) |
|
8447 { |
|
8448 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8449 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8450 } |
|
8451 } |
|
8452 else |
|
8453 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
8454 { |
|
8455 EAP_TRACE_DEBUG( |
|
8456 m_am_tools, |
|
8457 TRACE_FLAGS_DEFAULT, |
|
8458 (EAPL("TLS: %s: message_function: analyse_handshake_type_server_hello(): ") |
|
8459 EAPL("creates new session, no session identifier\n"), |
|
8460 (m_is_client == true ? "client": "server"))); |
|
8461 |
|
8462 #if defined(USE_FAST_EAP_TYPE) |
|
8463 if (m_tls_session_type == tls_session_type_eap_fast_pac_session_resumption) |
|
8464 { |
|
8465 // Server does not accept the Tunnel PAC. |
|
8466 // We will remove the Tunnel PAC if server authenticates OK. |
|
8467 m_remove_tunnel_pac = true; |
|
8468 } |
|
8469 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
8470 |
|
8471 set_tls_session_type(tls_session_type_full_authentication); |
|
8472 } |
|
8473 |
|
8474 } |
|
8475 |
|
8476 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
8477 |
|
8478 if (m_tls_session_type == tls_session_type_original_session_resumption |
|
8479 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
8480 || m_tls_session_type == tls_session_type_stateless_session_resumption |
|
8481 #if defined(USE_FAST_EAP_TYPE) |
|
8482 || m_tls_session_type == tls_session_type_eap_fast_pac_session_resumption |
|
8483 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
8484 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
8485 ) |
|
8486 { |
|
8487 if (m_tls_session_type == tls_session_type_original_session_resumption |
|
8488 #if defined(USE_FAST_EAP_TYPE) |
|
8489 || m_tls_session_type == tls_session_type_eap_fast_pac_session_resumption |
|
8490 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
8491 ) |
|
8492 { |
|
8493 // We must generate the key material. |
|
8494 status = generate_key_material(); |
|
8495 if (status != eap_status_ok) |
|
8496 { |
|
8497 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8498 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8499 } |
|
8500 } |
|
8501 |
|
8502 set_state(tls_peap_state_wait_change_cipher_spec); |
|
8503 } |
|
8504 #if defined(USE_FAST_EAP_TYPE) |
|
8505 else if (m_eap_type == eap_type_fast |
|
8506 && m_tls_session_type == tls_session_type_eap_fast_server_unauthenticated_provisioning_mode_ADHP |
|
8507 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true) |
|
8508 { |
|
8509 set_state(tls_peap_state_wait_handshake_type_server_key_exchange); |
|
8510 } |
|
8511 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
8512 else |
|
8513 { |
|
8514 set_state(tls_peap_state_wait_handshake_type_certificate); |
|
8515 } |
|
8516 |
|
8517 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
8518 |
|
8519 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8520 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8521 } |
|
8522 |
|
8523 //-------------------------------------------------- |
|
8524 |
|
8525 EAP_FUNC_EXPORT eap_status_e tls_record_c::analyse_handshake_type_certificate( |
|
8526 EAP_TEMPLATE_CONST tls_handshake_message_c * const handshake_message) |
|
8527 { |
|
8528 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8529 |
|
8530 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
8531 EAP_TRACE_DEBUG( |
|
8532 m_am_tools, |
|
8533 TRACE_FLAGS_DEFAULT, |
|
8534 (EAPL("TLS: %s: message_function: starts: tls_record_c::analyse_handshake_type_certificate()\n"), |
|
8535 (m_is_client == true ? "client": "server"))); |
|
8536 |
|
8537 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::analyse_handshake_type_certificate()"); |
|
8538 |
|
8539 // 0 1 2 3 |
|
8540 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
8541 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
8542 // | Certificate Chain Length | |
|
8543 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
8544 // | Certificate 1 Length | | |
|
8545 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
8546 // | | |
|
8547 // + + |
|
8548 // | Certificate 1 | |
|
8549 // + + |
|
8550 // | | |
|
8551 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
8552 // . ... . |
|
8553 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
8554 // | Certificate n Length | | |
|
8555 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
8556 // | | |
|
8557 // + + |
|
8558 // | Certificate n | |
|
8559 // + + |
|
8560 // | | |
|
8561 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
8562 |
|
8563 eap_status_e status = eap_status_not_supported; |
|
8564 |
|
8565 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
8566 |
|
8567 EAP_TEMPLATE_CONST eap_array_c<eap_variable_data_c> * const certificate_chain |
|
8568 = handshake_message->get_certificate_chain(); |
|
8569 |
|
8570 if (m_is_client == false |
|
8571 && certificate_chain->get_object_count() == 0ul |
|
8572 && m_tls_peap_server_authenticates_client_policy_flag == false) |
|
8573 { |
|
8574 // Server allows server only authentication, client is anonymous. |
|
8575 |
|
8576 EAP_TRACE_DEBUG( |
|
8577 m_am_tools, |
|
8578 TRACE_FLAGS_DEFAULT, |
|
8579 (EAPL("TLS: %s: pki_function: analyse_handshake_type_certificate(): ") |
|
8580 EAPL("Server allows anonymous client.\n"), |
|
8581 (m_is_client == true ? "client": "server"))); |
|
8582 |
|
8583 m_tls_peap_server_authenticates_client_action = false; |
|
8584 } |
|
8585 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
8586 else if (m_is_client == false |
|
8587 && m_tls_use_identity_privacy == true |
|
8588 && m_tls_session_type == tls_session_type_full_authentication |
|
8589 && m_tls_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_none |
|
8590 && certificate_chain->get_object_count() == 0ul) |
|
8591 { |
|
8592 // Server allows TLS identity privacy, at this point client is anonymous. |
|
8593 |
|
8594 EAP_TRACE_DEBUG( |
|
8595 m_am_tools, |
|
8596 TRACE_FLAGS_DEFAULT, |
|
8597 (EAPL("TLS: %s: pki_function: analyse_handshake_type_certificate(): ") |
|
8598 EAPL("Server allows TLS identity privacy.\n"), |
|
8599 (m_is_client == true ? "client": "server"))); |
|
8600 |
|
8601 set_tls_identity_privacy_handshake_state(tls_identity_privacy_handshake_state_negotiates); |
|
8602 } |
|
8603 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
8604 else if (certificate_chain->get_object_count() == 0ul) |
|
8605 { |
|
8606 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
8607 #if defined(USE_FAST_EAP_TYPE) |
|
8608 if (m_is_client == false |
|
8609 && m_tls_use_identity_privacy == false |
|
8610 && m_eap_type == eap_type_fast |
|
8611 && m_tls_session_type == tls_session_type_full_authentication) |
|
8612 { |
|
8613 EAP_TRACE_DEBUG( |
|
8614 m_am_tools, |
|
8615 TRACE_FLAGS_DEFAULT, |
|
8616 (EAPL("TLS: %s: pki_function: analyse_handshake_type_certificate(): ") |
|
8617 EAPL("EAP-FAST %s allows anonymous client.\n"), |
|
8618 (m_is_client == true ? "client": "server"), |
|
8619 (m_is_client == true ? "client": "server"))); |
|
8620 |
|
8621 m_tls_peap_server_authenticates_client_action = false; |
|
8622 m_tls_identity_privacy_handshake_state = tls_identity_privacy_handshake_state_none; |
|
8623 } |
|
8624 else |
|
8625 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
8626 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
8627 { |
|
8628 EAP_TRACE_ERROR( |
|
8629 m_am_tools, |
|
8630 TRACE_FLAGS_DEFAULT, |
|
8631 (EAPL("TLS: %s: pki_function: analyse_handshake_type_certificate(): ") |
|
8632 EAPL("TLS %s does NOT allow anonymous %s.\n"), |
|
8633 (m_is_client == true ? "client": "server"), |
|
8634 (m_is_client == true ? "client": "server"), |
|
8635 (m_is_client == false ? "client": "server"))); |
|
8636 |
|
8637 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8638 return EAP_STATUS_RETURN(m_am_tools, eap_status_insufficient_security); |
|
8639 } |
|
8640 } |
|
8641 else |
|
8642 { |
|
8643 status = copy<eap_variable_data_c>( |
|
8644 certificate_chain, |
|
8645 &m_peer_certificate_chain, |
|
8646 m_am_tools, |
|
8647 false); |
|
8648 if (status != eap_status_ok |
|
8649 || m_peer_certificate_chain.get_object_count() == 0ul) |
|
8650 { |
|
8651 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8652 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
8653 } |
|
8654 } |
|
8655 |
|
8656 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
8657 |
|
8658 if (m_is_client == true) |
|
8659 { |
|
8660 status = completion_action_add(tls_completion_action_verify_certificate_chain); |
|
8661 if (status != eap_status_ok) |
|
8662 { |
|
8663 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8664 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8665 } |
|
8666 |
|
8667 EAP_TRACE_DEBUG( |
|
8668 m_am_tools, |
|
8669 TRACE_FLAGS_DEFAULT, |
|
8670 (EAPL("TLS: %s: pki_function: query_certificate_chain()\n"), |
|
8671 (m_is_client == true ? "client": "server"))); |
|
8672 |
|
8673 status = m_am_tls_services->query_certificate_chain( |
|
8674 &m_peer_certificate_authorities, |
|
8675 &m_peer_certificate_types, |
|
8676 m_selected_cipher_suite); |
|
8677 if (status == eap_status_pending_request) |
|
8678 { |
|
8679 // This is pending query, that will be completed by |
|
8680 // complete_query_certificate_chain() call. |
|
8681 m_pending_query_certificate_chain = true; |
|
8682 } |
|
8683 else if (status == eap_status_completed_request) |
|
8684 { |
|
8685 // This is already completed by complete_query_certificate_chain() call. |
|
8686 } |
|
8687 else if (status == eap_status_ok) |
|
8688 { |
|
8689 // This is also an error case, because this call is always completed on success. |
|
8690 status = eap_status_process_general_error; |
|
8691 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8692 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8693 } |
|
8694 else // All other status values means error, because this |
|
8695 // call is always completed on success. |
|
8696 { |
|
8697 // This is an error case. |
|
8698 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8699 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
8700 } |
|
8701 } |
|
8702 else if (m_is_client == false |
|
8703 && m_tls_peap_server_authenticates_client_action == true) |
|
8704 { |
|
8705 // This is server. |
|
8706 |
|
8707 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
8708 if (m_tls_session_type == tls_session_type_full_authentication |
|
8709 && m_tls_use_identity_privacy == true |
|
8710 && certificate_chain->get_object_count() == 0ul) |
|
8711 { |
|
8712 EAP_TRACE_DEBUG( |
|
8713 m_am_tools, |
|
8714 TRACE_FLAGS_DEFAULT, |
|
8715 (EAPL("TLS: %s: pki_function: TLS identity privacy does not verify client certificate yet.\n"), |
|
8716 (m_is_client == true ? "client": "server"))); |
|
8717 status = eap_status_ok; |
|
8718 } |
|
8719 else |
|
8720 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
8721 { |
|
8722 EAP_TRACE_DEBUG( |
|
8723 m_am_tools, |
|
8724 TRACE_FLAGS_DEFAULT, |
|
8725 (EAPL("TLS: %s: pki_function: verify_certificate_chain()\n"), |
|
8726 (m_is_client == true ? "client": "server"))); |
|
8727 |
|
8728 status = m_am_tls_services->verify_certificate_chain( |
|
8729 &m_peer_certificate_chain, |
|
8730 m_selected_cipher_suite); |
|
8731 if (status == eap_status_pending_request) |
|
8732 { |
|
8733 // This is pending query, that will be completed by |
|
8734 // complete_verify_certificate_chain() call. |
|
8735 m_pending_verify_certificate_chain = true; |
|
8736 } |
|
8737 else if (status == eap_status_completed_request) |
|
8738 { |
|
8739 // This is already completed by complete_verify_certificate_chain() call. |
|
8740 } |
|
8741 else if (status == eap_status_ok) |
|
8742 { |
|
8743 // This is also an error case, because this call is always completed on success. |
|
8744 status = eap_status_process_general_error; |
|
8745 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8746 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8747 } |
|
8748 else // All other status values means error, because this |
|
8749 // call is always completed on success. |
|
8750 { |
|
8751 // This is an error case. |
|
8752 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8753 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
8754 } |
|
8755 } |
|
8756 } |
|
8757 else if (m_is_client == false |
|
8758 && m_tls_peap_server_authenticates_client_action == false) |
|
8759 { |
|
8760 // This is server. Server allows anonymous client. |
|
8761 status = eap_status_ok; |
|
8762 } |
|
8763 |
|
8764 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
8765 |
|
8766 if (status == eap_status_completed_request) |
|
8767 { |
|
8768 status = eap_status_ok; |
|
8769 } |
|
8770 |
|
8771 if (m_is_client == true) |
|
8772 { |
|
8773 if (cipher_suite_is_TLS_DHE_DSS() == true |
|
8774 || cipher_suite_is_TLS_DHE_RSA() == true) |
|
8775 { |
|
8776 set_state(tls_peap_state_wait_handshake_type_server_key_exchange); |
|
8777 } |
|
8778 else if (cipher_suite_is_TLS_RSA() == true) |
|
8779 { |
|
8780 set_state(tls_peap_state_wait_handshake_type_certificate_request_or_server_hello_done); |
|
8781 } |
|
8782 else |
|
8783 { |
|
8784 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8785 return EAP_STATUS_RETURN(m_am_tools, eap_status_not_supported); |
|
8786 } |
|
8787 } |
|
8788 else |
|
8789 { |
|
8790 // Server. |
|
8791 set_state(tls_peap_state_wait_handshake_type_client_key_exchange); |
|
8792 } |
|
8793 |
|
8794 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8795 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8796 } |
|
8797 |
|
8798 //-------------------------------------------------- |
|
8799 |
|
8800 EAP_FUNC_EXPORT eap_status_e tls_record_c::analyse_handshake_type_certificate_request( |
|
8801 EAP_TEMPLATE_CONST tls_handshake_message_c * const handshake_message) |
|
8802 { |
|
8803 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8804 |
|
8805 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
8806 EAP_TRACE_DEBUG( |
|
8807 m_am_tools, |
|
8808 TRACE_FLAGS_DEFAULT, |
|
8809 (EAPL("TLS: %s: message_function: starts: tls_record_c::analyse_handshake_type_certificate_request()\n"), |
|
8810 (m_is_client == true ? "client": "server"))); |
|
8811 |
|
8812 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::analyse_handshake_type_certificate_request()"); |
|
8813 |
|
8814 EAP_ASSERT_ALWAYS(m_is_client == true); |
|
8815 |
|
8816 // 0 1 2 3 |
|
8817 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
8818 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
8819 // | CT length | CT 1 | CT 2 | |
|
8820 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
8821 // | CT 3 | CT 4 | CAs length | |
|
8822 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
8823 // | CA 1 length | | |
|
8824 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
8825 // | | |
|
8826 // + + |
|
8827 // | Distinguished name of Certificate Authority 1 | |
|
8828 // + + |
|
8829 // | | |
|
8830 // + +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
8831 // | | CA 2 length | |
|
8832 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
8833 // | | |
|
8834 // + + |
|
8835 // | Distinguished name of Certificate Authority 2 | |
|
8836 // + + |
|
8837 // | | |
|
8838 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
8839 |
|
8840 eap_status_e status = eap_status_not_supported; |
|
8841 |
|
8842 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
8843 |
|
8844 { |
|
8845 EAP_TEMPLATE_CONST eap_array_c<u8_t> * const certificate_types |
|
8846 = handshake_message->get_certificate_types(); |
|
8847 |
|
8848 if (certificate_types->get_object_count() == 0ul) |
|
8849 { |
|
8850 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8851 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
8852 } |
|
8853 |
|
8854 status = copy_simple<u8_t>( |
|
8855 certificate_types, |
|
8856 &m_peer_certificate_types, |
|
8857 m_am_tools, |
|
8858 false); |
|
8859 if (status != eap_status_ok) |
|
8860 { |
|
8861 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8862 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
8863 } |
|
8864 } |
|
8865 |
|
8866 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
8867 |
|
8868 { |
|
8869 EAP_TEMPLATE_CONST eap_array_c<eap_variable_data_c> * const certificate_authorities |
|
8870 = handshake_message->get_certificate_authorities(); |
|
8871 |
|
8872 if (certificate_authorities->get_object_count() == 0ul |
|
8873 && m_client_allows_empty_certificate_authorities_list == false) |
|
8874 { |
|
8875 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8876 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
8877 } |
|
8878 |
|
8879 status = copy<eap_variable_data_c>( |
|
8880 certificate_authorities, |
|
8881 &m_peer_certificate_authorities, |
|
8882 m_am_tools, |
|
8883 false); |
|
8884 if (status != eap_status_ok) |
|
8885 { |
|
8886 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8887 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
8888 } |
|
8889 } |
|
8890 |
|
8891 m_tls_peap_server_requested_client_certificate = true; |
|
8892 |
|
8893 |
|
8894 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
8895 |
|
8896 set_state(tls_peap_state_wait_handshake_type_server_hello_done); |
|
8897 |
|
8898 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8899 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8900 } |
|
8901 |
|
8902 //-------------------------------------------------- |
|
8903 |
|
8904 EAP_FUNC_EXPORT eap_status_e tls_record_c::analyse_handshake_type_server_hello_done( |
|
8905 EAP_TEMPLATE_CONST tls_handshake_message_c * const /*handshake_message*/) |
|
8906 { |
|
8907 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8908 |
|
8909 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
8910 EAP_TRACE_DEBUG( |
|
8911 m_am_tools, |
|
8912 TRACE_FLAGS_DEFAULT, |
|
8913 (EAPL("TLS: %s: message_function: starts: tls_record_c::analyse_handshake_type_server_hello_done()\n"), |
|
8914 (m_is_client == true ? "client": "server"))); |
|
8915 |
|
8916 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::analyse_handshake_type_server_hello_done()"); |
|
8917 |
|
8918 EAP_ASSERT(m_is_client == true); |
|
8919 |
|
8920 eap_status_e status = eap_status_process_general_error; |
|
8921 |
|
8922 // 0 1 2 3 |
|
8923 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
8924 // |
|
8925 // ServerHelloDone message does not include payload. |
|
8926 |
|
8927 if (cipher_suite_is_TLS_DHE_DSS() == true |
|
8928 || cipher_suite_is_TLS_RSA() == true |
|
8929 || cipher_suite_is_TLS_DHE_RSA() == true |
|
8930 #if defined(USE_FAST_EAP_TYPE) |
|
8931 || (m_eap_type == eap_type_fast |
|
8932 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true |
|
8933 && cipher_suite_is_TLS_DH_anon() == true) |
|
8934 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
8935 ) |
|
8936 { |
|
8937 if (m_tls_peap_server_requested_client_certificate == true) |
|
8938 { |
|
8939 status = completion_action_add(tls_completion_action_create_handshake_type_certificate); |
|
8940 if (status != eap_status_ok) |
|
8941 { |
|
8942 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8943 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8944 } |
|
8945 } |
|
8946 |
|
8947 status = completion_action_add( |
|
8948 tls_completion_action_create_handshake_type_client_key_exchange); |
|
8949 if (status != eap_status_ok) |
|
8950 { |
|
8951 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8952 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8953 } |
|
8954 |
|
8955 status = completion_action_add( |
|
8956 tls_completion_action_complete_create_handshake_type_client_key_exchange); |
|
8957 if (status != eap_status_ok) |
|
8958 { |
|
8959 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8960 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8961 } |
|
8962 |
|
8963 if (m_tls_peap_server_authenticates_client_action == true |
|
8964 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
8965 && ( |
|
8966 m_tls_use_identity_privacy == false |
|
8967 || (m_tls_session_type == tls_session_type_full_authentication |
|
8968 && m_tls_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_runs)) |
|
8969 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
8970 ) |
|
8971 { |
|
8972 status = completion_action_add( |
|
8973 tls_completion_action_create_handshake_type_certificate_verify); |
|
8974 if (status != eap_status_ok) |
|
8975 { |
|
8976 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8977 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8978 } |
|
8979 |
|
8980 // This will complete creation of handshake_type_certificate_verify message. |
|
8981 status = completion_action_add( |
|
8982 tls_completion_action_complete_create_handshake_type_certificate_verify); |
|
8983 if (status != eap_status_ok) |
|
8984 { |
|
8985 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8986 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8987 } |
|
8988 |
|
8989 // Also the other pending messages will be processed after this action is completed. |
|
8990 eap_status_e compl_status = completion_action_add( |
|
8991 tls_completion_action_process_tls_records); |
|
8992 if (compl_status != eap_status_ok) |
|
8993 { |
|
8994 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
8995 return EAP_STATUS_RETURN(m_am_tools, status); |
|
8996 } |
|
8997 } |
|
8998 |
|
8999 status = completion_action_add( |
|
9000 tls_completion_action_create_change_cipher_spec_type_change_cipher_spec); |
|
9001 if (status != eap_status_ok) |
|
9002 { |
|
9003 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9004 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9005 } |
|
9006 |
|
9007 status = completion_action_add(tls_completion_action_create_handshake_type_finished); |
|
9008 if (status != eap_status_ok) |
|
9009 { |
|
9010 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9011 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9012 } |
|
9013 } |
|
9014 else |
|
9015 { |
|
9016 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9017 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_cipher_suite); |
|
9018 } |
|
9019 |
|
9020 |
|
9021 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
9022 |
|
9023 set_state(tls_peap_state_wait_change_cipher_spec); |
|
9024 |
|
9025 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9026 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9027 } |
|
9028 |
|
9029 //-------------------------------------------------- |
|
9030 |
|
9031 EAP_FUNC_EXPORT eap_status_e tls_record_c::analyse_handshake_type_server_key_exchange( |
|
9032 EAP_TEMPLATE_CONST tls_handshake_message_c * const handshake_message) |
|
9033 { |
|
9034 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9035 |
|
9036 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
9037 EAP_TRACE_DEBUG( |
|
9038 m_am_tools, |
|
9039 TRACE_FLAGS_DEFAULT, |
|
9040 (EAPL("TLS: %s: message_function: starts: tls_record_c::analyse_handshake_type_server_key_exchange()\n"), |
|
9041 (m_is_client == true ? "client": "server"))); |
|
9042 |
|
9043 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::analyse_handshake_type_server_key_exchange()"); |
|
9044 |
|
9045 eap_status_e status = eap_status_not_supported; |
|
9046 |
|
9047 #if EAP_TLS_UNSUPPORTED_CIPHER_SUITE |
|
9048 #error This one needs more code. RSA key exchange with different parameters is NOT supported. |
|
9049 if (cipher_suite_is_TLS_RSA() == true) |
|
9050 { |
|
9051 // RSA modulus and exponent are included when selected cipher suite |
|
9052 // is using RSA key exchange |
|
9053 // and parameters are different than included in the certificate. |
|
9054 // 0 1 2 3 |
|
9055 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
9056 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9057 // | rsa_modulus length | | |
|
9058 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
9059 // | | |
|
9060 // + + |
|
9061 // | rsa_modulus | |
|
9062 // + + |
|
9063 // | | |
|
9064 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9065 // | rsa_exponent length | | |
|
9066 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
9067 // | | |
|
9068 // + rsa_exponent + |
|
9069 // | | |
|
9070 // + + |
|
9071 // | | |
|
9072 // + + |
|
9073 // | | |
|
9074 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9075 // | | |
|
9076 // + + |
|
9077 // | digitally-signed MD5 hash 16 bytes | |
|
9078 // + (ClientHello.random + ServerHello.random + ServerParams) + |
|
9079 // | | |
|
9080 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9081 // | | |
|
9082 // + + |
|
9083 // | digitally-signed SHA-1 hash 20 bytes | |
|
9084 // + (ClientHello.random + ServerHello.random + ServerParams) + |
|
9085 // | | |
|
9086 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9087 |
|
9088 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9089 return EAP_STATUS_RETURN(m_am_tools, eap_status_not_supported); |
|
9090 } |
|
9091 else |
|
9092 #endif |
|
9093 if (cipher_suite_is_TLS_DHE_DSS() == true |
|
9094 || cipher_suite_is_TLS_DHE_RSA() == true) |
|
9095 { |
|
9096 // Diffie-Hellman prime modulus, generator and server's |
|
9097 // Diffie-Hellman public value (g^X mod p) |
|
9098 // are included when selected cipher suite is ephemeral Diffie-Hellman key exchange. |
|
9099 // 0 1 2 3 |
|
9100 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
9101 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9102 // | DH p length | | |
|
9103 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
9104 // | | |
|
9105 // + + |
|
9106 // | DH p value (prime modulus) | |
|
9107 // + + |
|
9108 // | | |
|
9109 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9110 // | DH g length | | |
|
9111 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
9112 // | | |
|
9113 // + + |
|
9114 // | DH g value (generator) | |
|
9115 // + + |
|
9116 // | | |
|
9117 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9118 // | DH Ys length | | |
|
9119 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
9120 // | | |
|
9121 // + + |
|
9122 // | DH Ys value | |
|
9123 // + (server's Diffie-Hellman public value) + |
|
9124 // | | |
|
9125 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9126 // | | |
|
9127 // + + |
|
9128 // | digitally-signed SHA-1 hash 47 bytes | |
|
9129 // + (ClientHello.random + ServerHello.random + ServerParams) + |
|
9130 // | | |
|
9131 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9132 |
|
9133 if (handshake_message->get_dhe_prime() == 0 |
|
9134 || handshake_message->get_dhe_prime()->get_is_valid_data() == false |
|
9135 || handshake_message->get_dhe_prime()->get_data_length() == 0) |
|
9136 { |
|
9137 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9138 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9139 } |
|
9140 |
|
9141 if (handshake_message->get_dhe_group_generator() == 0 |
|
9142 || handshake_message->get_dhe_group_generator()->get_is_valid_data() == false |
|
9143 || handshake_message->get_dhe_group_generator()->get_data_length() == 0) |
|
9144 { |
|
9145 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9146 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9147 } |
|
9148 |
|
9149 if (handshake_message->get_public_dhe_key() == 0 |
|
9150 || handshake_message->get_public_dhe_key()->get_is_valid_data() == false |
|
9151 || handshake_message->get_public_dhe_key()->get_data_length() == 0) |
|
9152 { |
|
9153 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9154 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9155 } |
|
9156 |
|
9157 if (handshake_message->get_signed_message_hash() == 0 |
|
9158 || handshake_message->get_signed_message_hash()->get_is_valid_data() == false |
|
9159 || handshake_message->get_signed_message_hash()->get_data_length() == 0) |
|
9160 { |
|
9161 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9162 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9163 } |
|
9164 |
|
9165 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
9166 |
|
9167 status = m_dhe_prime.set_copy_of_buffer(handshake_message->get_dhe_prime()); |
|
9168 if (status != eap_status_ok |
|
9169 || m_dhe_prime.get_is_valid_data() == false |
|
9170 || m_dhe_prime.get_data_length() == 0) |
|
9171 { |
|
9172 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9173 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9174 } |
|
9175 |
|
9176 status = m_dhe_group_generator.set_copy_of_buffer( |
|
9177 handshake_message->get_dhe_group_generator()); |
|
9178 if (status != eap_status_ok |
|
9179 || m_dhe_group_generator.get_is_valid_data() == false |
|
9180 || m_dhe_group_generator.get_data_length() == 0) |
|
9181 { |
|
9182 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9183 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9184 } |
|
9185 |
|
9186 status = m_peer_public_dhe_key.set_copy_of_buffer(handshake_message->get_public_dhe_key()); |
|
9187 if (status != eap_status_ok |
|
9188 || m_peer_public_dhe_key.get_is_valid_data() == false |
|
9189 || m_peer_public_dhe_key.get_data_length() == 0) |
|
9190 { |
|
9191 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9192 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9193 } |
|
9194 |
|
9195 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
9196 |
|
9197 if (cipher_suite_is_TLS_DHE_DSS() == true |
|
9198 || cipher_suite_is_TLS_DHE_RSA() == true) |
|
9199 { |
|
9200 // We must verify the signature of ServerKeyExchange. |
|
9201 status = verify_signature_of_server_key_exchange( |
|
9202 handshake_message->get_signed_message_hash()); |
|
9203 if (status == eap_status_pending_request) |
|
9204 { |
|
9205 // This is pending query, that will be completed by |
|
9206 // complete_query_certificate_chain() call. |
|
9207 m_pending_verify_with_public_key = true; |
|
9208 } |
|
9209 else if (status == eap_status_completed_request) |
|
9210 { |
|
9211 // This is already completed by complete_query_certificate_chain() call. |
|
9212 } |
|
9213 else if (status == eap_status_ok) |
|
9214 { |
|
9215 // This is also an error case, because this call is always completed on success. |
|
9216 status = eap_status_process_general_error; |
|
9217 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9218 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9219 } |
|
9220 else // All other status values means error, because this call |
|
9221 // is always completed on success. |
|
9222 { |
|
9223 // This is an error case. |
|
9224 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9225 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9226 } |
|
9227 } |
|
9228 else |
|
9229 { |
|
9230 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9231 return EAP_STATUS_RETURN(m_am_tools, eap_status_not_supported); |
|
9232 } |
|
9233 } |
|
9234 #if defined(USE_FAST_EAP_TYPE) |
|
9235 else if (m_eap_type == eap_type_fast |
|
9236 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true |
|
9237 && cipher_suite_is_TLS_DH_anon() == true) |
|
9238 { |
|
9239 // Diffie-Hellman prime modulus, generator and server's |
|
9240 // Diffie-Hellman public value (g^X mod p) |
|
9241 // are included when selected cipher suite is ephemeral Diffie-Hellman key exchange. |
|
9242 // NOTE: Here are no signed hash. This is not authenticated at all and vulnerable to |
|
9243 // man-in-the-middle attacks. |
|
9244 // 0 1 2 3 |
|
9245 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
9246 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9247 // | DH p length | | |
|
9248 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
9249 // | | |
|
9250 // + + |
|
9251 // | DH p value (prime modulus) | |
|
9252 // + + |
|
9253 // | | |
|
9254 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9255 // | DH g length | | |
|
9256 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
9257 // | | |
|
9258 // + + |
|
9259 // | DH g value (generator) | |
|
9260 // + + |
|
9261 // | | |
|
9262 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9263 // | DH Ys length | | |
|
9264 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
9265 // | | |
|
9266 // + + |
|
9267 // | DH Ys value | |
|
9268 // + (server's Diffie-Hellman public value) + |
|
9269 // | | |
|
9270 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9271 |
|
9272 EAP_TRACE_DEBUG( |
|
9273 m_am_tools, |
|
9274 TRACE_FLAGS_DEFAULT, |
|
9275 (EAPL("TLS: analyse_handshake_type_server_key_exchange() no m_signed_message_hash\n"))); |
|
9276 |
|
9277 if (handshake_message->get_dhe_prime() == 0 |
|
9278 || handshake_message->get_dhe_prime()->get_is_valid_data() == false |
|
9279 || handshake_message->get_dhe_prime()->get_data_length() == 0) |
|
9280 { |
|
9281 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9282 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9283 } |
|
9284 |
|
9285 if (handshake_message->get_dhe_group_generator() == 0 |
|
9286 || handshake_message->get_dhe_group_generator()->get_is_valid_data() == false |
|
9287 || handshake_message->get_dhe_group_generator()->get_data_length() == 0) |
|
9288 { |
|
9289 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9290 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9291 } |
|
9292 |
|
9293 if (handshake_message->get_public_dhe_key() == 0 |
|
9294 || handshake_message->get_public_dhe_key()->get_is_valid_data() == false |
|
9295 || handshake_message->get_public_dhe_key()->get_data_length() == 0) |
|
9296 { |
|
9297 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9298 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9299 } |
|
9300 |
|
9301 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
9302 |
|
9303 status = m_dhe_prime.set_copy_of_buffer(handshake_message->get_dhe_prime()); |
|
9304 if (status != eap_status_ok |
|
9305 || m_dhe_prime.get_is_valid_data() == false |
|
9306 || m_dhe_prime.get_data_length() == 0) |
|
9307 { |
|
9308 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9309 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9310 } |
|
9311 |
|
9312 status = m_dhe_group_generator.set_copy_of_buffer( |
|
9313 handshake_message->get_dhe_group_generator()); |
|
9314 if (status != eap_status_ok |
|
9315 || m_dhe_group_generator.get_is_valid_data() == false |
|
9316 || m_dhe_group_generator.get_data_length() == 0) |
|
9317 { |
|
9318 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9319 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9320 } |
|
9321 |
|
9322 status = m_peer_public_dhe_key.set_copy_of_buffer(handshake_message->get_public_dhe_key()); |
|
9323 if (status != eap_status_ok |
|
9324 || m_peer_public_dhe_key.get_is_valid_data() == false |
|
9325 || m_peer_public_dhe_key.get_data_length() == 0) |
|
9326 { |
|
9327 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9328 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9329 } |
|
9330 } |
|
9331 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
9332 |
|
9333 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
9334 |
|
9335 if (/* status == eap_status_pending_request |
|
9336 ||*/ status == eap_status_completed_request) |
|
9337 { |
|
9338 status = eap_status_ok; |
|
9339 } |
|
9340 |
|
9341 // Next we wait certificate_request or server_hello_done |
|
9342 // If next message is certificate_request, server requires client authentication. |
|
9343 // If next message is server_hello_done, server does NOT require client authentication. |
|
9344 set_state(tls_peap_state_wait_handshake_type_certificate_request_or_server_hello_done); |
|
9345 |
|
9346 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9347 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9348 } |
|
9349 |
|
9350 //-------------------------------------------------- |
|
9351 |
|
9352 EAP_FUNC_EXPORT eap_status_e tls_record_c::analyse_handshake_type_client_key_exchange( |
|
9353 EAP_TEMPLATE_CONST tls_handshake_message_c * const handshake_message) |
|
9354 { |
|
9355 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9356 |
|
9357 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
9358 EAP_TRACE_DEBUG( |
|
9359 m_am_tools, |
|
9360 TRACE_FLAGS_DEFAULT, |
|
9361 (EAPL("TLS: %s: message_function: starts: tls_record_c::analyse_handshake_type_client_key_exchange()\n"), |
|
9362 (m_is_client == true ? "client": "server"))); |
|
9363 |
|
9364 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::analyse_handshake_type_client_key_exchange()"); |
|
9365 |
|
9366 eap_status_e status = eap_status_not_supported; |
|
9367 |
|
9368 |
|
9369 if (cipher_suite_is_TLS_RSA() == true) |
|
9370 { |
|
9371 // Encrypted premaster secret is included when selected cipher suite |
|
9372 // is using RSA key exchange. |
|
9373 // First two bytes are version of TLS. |
|
9374 // 0 1 2 3 |
|
9375 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
9376 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9377 // | | |
|
9378 // +-+-+-+-+-+-+-+-+ + |
|
9379 // | | |
|
9380 // + + |
|
9381 // | Encrypted Premaster Secret (48 bytes) | |
|
9382 // + + |
|
9383 // | | |
|
9384 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9385 |
|
9386 if (handshake_message->get_encrypted_premaster_secret() == 0 |
|
9387 || handshake_message->get_encrypted_premaster_secret()->get_is_valid_data() == false |
|
9388 || handshake_message->get_encrypted_premaster_secret()->get_data_length() == 0) |
|
9389 { |
|
9390 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9391 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9392 } |
|
9393 |
|
9394 EAP_TRACE_DEBUG( |
|
9395 m_am_tools, |
|
9396 TRACE_FLAGS_DEFAULT, |
|
9397 (EAPL("TLS: %s: pki_function: rsa_decrypt_with_private_key()\n"), |
|
9398 (m_is_client == true ? "client": "server"))); |
|
9399 |
|
9400 EAP_TRACE_DATA_DEBUG( |
|
9401 m_am_tools, |
|
9402 TRACE_FLAGS_DEFAULT, |
|
9403 (EAPL("TLS: analyse_handshake_type_client_key_exchange(): encrypted premaster_secret"), |
|
9404 handshake_message->get_encrypted_premaster_secret()->get_data(), |
|
9405 handshake_message->get_encrypted_premaster_secret()->get_data_length())); |
|
9406 |
|
9407 status = m_am_tls_services->rsa_decrypt_with_private_key( |
|
9408 handshake_message->get_encrypted_premaster_secret()); |
|
9409 if (status == eap_status_pending_request) |
|
9410 { |
|
9411 // This is pending query, that will be completed by |
|
9412 // complete_rsa_decrypt_with_private_key() call. |
|
9413 m_pending_rsa_decrypt_with_private_key = true; |
|
9414 } |
|
9415 else if (status == eap_status_completed_request) |
|
9416 { |
|
9417 // This is already completed by complete_rsa_decrypt_with_private_key() call. |
|
9418 } |
|
9419 else if (status == eap_status_ok) |
|
9420 { |
|
9421 // This is also an error case, because this call is always completed on success. |
|
9422 status = eap_status_process_general_error; |
|
9423 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9424 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9425 } |
|
9426 else // All other status values means error, because this call |
|
9427 // is always completed on success. |
|
9428 { |
|
9429 // This is an error case. |
|
9430 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9431 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
9432 } |
|
9433 } |
|
9434 else if (cipher_suite_is_TLS_DHE_DSS() == true |
|
9435 || cipher_suite_is_TLS_DHE_RSA() == true |
|
9436 #if defined(USE_FAST_EAP_TYPE) |
|
9437 || (m_eap_type == eap_type_fast |
|
9438 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true |
|
9439 && cipher_suite_is_TLS_DH_anon() == true) |
|
9440 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
9441 ) |
|
9442 { |
|
9443 // Diffie-Hellman prime modulus, generator and server's |
|
9444 // Diffie-Hellman public value (g^X mod p) |
|
9445 // are included when selected cipher suite is ephemeral Diffie-Hellman key exchange. |
|
9446 // 0 1 2 3 |
|
9447 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
9448 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9449 // | DH p length | | |
|
9450 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
9451 // | | |
|
9452 // + + |
|
9453 // | DH p value (prime modulus) | |
|
9454 // + + |
|
9455 // | | |
|
9456 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9457 // | DH g length | | |
|
9458 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
9459 // | | |
|
9460 // + + |
|
9461 // | DH g value (generator) | |
|
9462 // + + |
|
9463 // | | |
|
9464 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9465 // | DH Ys length | | |
|
9466 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
9467 // | | |
|
9468 // + + |
|
9469 // | DH Ys value | |
|
9470 // + (server's Diffie-Hellman public value) + |
|
9471 // | | |
|
9472 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9473 |
|
9474 if (handshake_message->get_public_dhe_key() == 0 |
|
9475 || handshake_message->get_public_dhe_key()->get_is_valid_data() == false |
|
9476 || handshake_message->get_public_dhe_key()->get_data_length() == 0) |
|
9477 { |
|
9478 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9479 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9480 } |
|
9481 |
|
9482 status = m_peer_public_dhe_key.set_copy_of_buffer(handshake_message->get_public_dhe_key()); |
|
9483 if (status != eap_status_ok |
|
9484 || m_peer_public_dhe_key.get_is_valid_data() == false |
|
9485 || m_peer_public_dhe_key.get_data_length() == 0) |
|
9486 { |
|
9487 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9488 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9489 } |
|
9490 |
|
9491 |
|
9492 // We must generate premaster secret. |
|
9493 status = generate_premaster_secret(); |
|
9494 if (status != eap_status_ok) |
|
9495 { |
|
9496 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9497 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9498 } |
|
9499 |
|
9500 // We must generate master secret. |
|
9501 status = generate_master_secret(); |
|
9502 if (status != eap_status_ok) |
|
9503 { |
|
9504 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9505 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9506 } |
|
9507 |
|
9508 // We must generate the key material. |
|
9509 status = generate_key_material(); |
|
9510 if (status != eap_status_ok) |
|
9511 { |
|
9512 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9513 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9514 } |
|
9515 } |
|
9516 |
|
9517 |
|
9518 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
9519 |
|
9520 if (/*status == eap_status_pending_request |
|
9521 ||*/ status == eap_status_completed_request) |
|
9522 { |
|
9523 status = eap_status_ok; |
|
9524 } |
|
9525 |
|
9526 if (m_tls_peap_server_authenticates_client_action == true) |
|
9527 { |
|
9528 set_state(tls_peap_state_wait_handshake_type_certificate_verify); |
|
9529 } |
|
9530 else |
|
9531 { |
|
9532 set_state(tls_peap_state_wait_change_cipher_spec); |
|
9533 } |
|
9534 |
|
9535 |
|
9536 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9537 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9538 } |
|
9539 |
|
9540 //-------------------------------------------------- |
|
9541 |
|
9542 EAP_FUNC_EXPORT eap_status_e tls_record_c::analyse_handshake_type_certificate_verify( |
|
9543 EAP_TEMPLATE_CONST tls_handshake_message_c * const handshake_message) |
|
9544 { |
|
9545 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9546 |
|
9547 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
9548 EAP_TRACE_DEBUG( |
|
9549 m_am_tools, |
|
9550 TRACE_FLAGS_DEFAULT, |
|
9551 (EAPL("TLS: %s: message_function: starts: tls_record_c::analyse_handshake_type_certificate_verify()\n"), |
|
9552 (m_is_client == true ? "client": "server"))); |
|
9553 |
|
9554 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::analyse_handshake_type_certificate_verify()"); |
|
9555 |
|
9556 eap_status_e status = eap_status_not_supported; |
|
9557 |
|
9558 if (cipher_suite_is_TLS_RSA() == true |
|
9559 || cipher_suite_is_TLS_DHE_RSA() == true |
|
9560 || cipher_suite_is_TLS_DHE_DSS() == true) |
|
9561 { |
|
9562 // Signatures when RSA is used: |
|
9563 // 0 1 2 3 |
|
9564 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
9565 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9566 // | | |
|
9567 // +-+-+-+-+-+-+-+-+ + |
|
9568 // | | |
|
9569 // + Signed MD5 hash + |
|
9570 // | (16 bytes) | |
|
9571 // + + |
|
9572 // | | |
|
9573 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9574 // | | |
|
9575 // + Signed SHA hash + |
|
9576 // | (20 bytes) | |
|
9577 // + + |
|
9578 // | | |
|
9579 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9580 |
|
9581 // Signature when DSA is used: |
|
9582 // 0 1 2 3 |
|
9583 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
9584 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9585 // | | |
|
9586 // +-+-+-+-+-+-+-+-+ + |
|
9587 // | | |
|
9588 // + Signed SHA hash + |
|
9589 // | (48 bytes) | |
|
9590 // + + |
|
9591 // | | |
|
9592 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
9593 |
|
9594 eap_variable_data_c signed_certificate_verify_hash(m_am_tools); |
|
9595 |
|
9596 status = signed_certificate_verify_hash.set_copy_of_buffer( |
|
9597 handshake_message->get_signed_message_hash()); |
|
9598 if (status != eap_status_ok) |
|
9599 { |
|
9600 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9601 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9602 } |
|
9603 |
|
9604 if (signed_certificate_verify_hash.get_is_valid_data() == false) |
|
9605 { |
|
9606 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9607 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_parameter); |
|
9608 } |
|
9609 |
|
9610 eap_variable_data_c message_hash(m_am_tools); |
|
9611 |
|
9612 status = message_hash_create( |
|
9613 true, |
|
9614 tls_handshake_type_certificate_verify, |
|
9615 &message_hash, |
|
9616 true); |
|
9617 if (status != eap_status_ok) |
|
9618 { |
|
9619 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9620 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9621 } |
|
9622 |
|
9623 EAP_TRACE_DEBUG( |
|
9624 m_am_tools, |
|
9625 TRACE_FLAGS_DEFAULT, |
|
9626 (EAPL("TLS: %s: pki_function: analyse_handshake_type_certificate_verify()\n"), |
|
9627 (m_is_client == true ? "client": "server"))); |
|
9628 |
|
9629 EAP_TRACE_DATA_DEBUG( |
|
9630 m_am_tools, |
|
9631 TRACE_FLAGS_DEFAULT, |
|
9632 (EAPL("TLS: analyse_handshake_type_certificate_verify(): message_hash"), |
|
9633 message_hash.get_data(message_hash.get_data_length()), |
|
9634 message_hash.get_data_length())); |
|
9635 |
|
9636 EAP_TRACE_DATA_DEBUG( |
|
9637 m_am_tools, |
|
9638 TRACE_FLAGS_DEFAULT, |
|
9639 (EAPL("TLS: analyse_handshake_type_certificate_verify(): signed_certificate_verify_hash"), |
|
9640 signed_certificate_verify_hash.get_data( |
|
9641 signed_certificate_verify_hash.get_data_length()), |
|
9642 signed_certificate_verify_hash.get_data_length())); |
|
9643 |
|
9644 status = m_am_tls_services->verify_with_public_key( |
|
9645 &message_hash, |
|
9646 &signed_certificate_verify_hash); |
|
9647 if (status == eap_status_pending_request) |
|
9648 { |
|
9649 // This is pending query, that will be completed by |
|
9650 // complete_query_certificate_chain() call. |
|
9651 m_pending_verify_with_public_key = true; |
|
9652 } |
|
9653 else if (status == eap_status_completed_request) |
|
9654 { |
|
9655 // This is already completed by complete_query_certificate_chain() call. |
|
9656 status = eap_status_ok; |
|
9657 } |
|
9658 else if (status == eap_status_ok) |
|
9659 { |
|
9660 // This is also an error case, because this call is always completed on success. |
|
9661 status = eap_status_process_general_error; |
|
9662 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9663 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9664 } |
|
9665 else // All other status values means error, because this call |
|
9666 // is always completed on success. |
|
9667 { |
|
9668 // This is an error case. |
|
9669 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9670 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
9671 } |
|
9672 } |
|
9673 else |
|
9674 { |
|
9675 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9676 return EAP_STATUS_RETURN(m_am_tools, eap_status_not_supported); |
|
9677 } |
|
9678 |
|
9679 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
9680 |
|
9681 set_state(tls_peap_state_wait_change_cipher_spec); |
|
9682 |
|
9683 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9684 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9685 } |
|
9686 |
|
9687 //-------------------------------------------------- |
|
9688 |
|
9689 EAP_FUNC_EXPORT eap_status_e tls_record_c::analyse_handshake_type_finished( |
|
9690 EAP_TEMPLATE_CONST tls_handshake_message_c * const handshake_message, |
|
9691 const u8_t received_eap_identifier) |
|
9692 { |
|
9693 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9694 |
|
9695 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
9696 EAP_TRACE_DEBUG( |
|
9697 m_am_tools, |
|
9698 TRACE_FLAGS_DEFAULT, |
|
9699 (EAPL("TLS: %s: message_function: starts: tls_record_c::analyse_handshake_type_finished()\n"), |
|
9700 (m_is_client == true ? "client": "server"))); |
|
9701 |
|
9702 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::analyse_handshake_type_finished()"); |
|
9703 |
|
9704 eap_status_e status = eap_status_not_supported; |
|
9705 |
|
9706 |
|
9707 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
9708 |
|
9709 if (handshake_message->get_finished_data() == 0 |
|
9710 || handshake_message->get_finished_data()->get_is_valid_data() == false) |
|
9711 { |
|
9712 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9713 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9714 } |
|
9715 |
|
9716 eap_variable_data_c message_hash(m_am_tools); |
|
9717 |
|
9718 bool client_originated_message = true; |
|
9719 if (m_is_client == true) |
|
9720 { |
|
9721 client_originated_message = false; |
|
9722 } |
|
9723 |
|
9724 status = message_hash_create_finished(client_originated_message, &message_hash); |
|
9725 if (status != eap_status_ok) |
|
9726 { |
|
9727 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9728 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9729 } |
|
9730 |
|
9731 if (message_hash.compare(handshake_message->get_finished_data()) != 0) |
|
9732 { |
|
9733 EAP_TRACE_ERROR( |
|
9734 m_am_tools, |
|
9735 TRACE_FLAGS_DEFAULT, |
|
9736 (EAPL("ERROR: TLS: %s: analyse_handshake_type_finished(): ") |
|
9737 EAPL("verify check finished data failed, m_tls_session_type=%d=%s.\n"), |
|
9738 (m_is_client == true ? "client": "server"), |
|
9739 m_tls_session_type, |
|
9740 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type) |
|
9741 )); |
|
9742 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9743 return EAP_STATUS_RETURN(m_am_tools, eap_status_authentication_failure); |
|
9744 } |
|
9745 else |
|
9746 { |
|
9747 EAP_TRACE_ALWAYS( |
|
9748 m_am_tools, |
|
9749 TRACE_FLAGS_DEFAULT, |
|
9750 (EAPL("TLS: %s: message_function: analyse_handshake_type_finished(): ") |
|
9751 EAPL("verify check finished data OK, m_tls_session_type=%d=%s.\n"), |
|
9752 (m_is_client == true ? "client": "server"), |
|
9753 m_tls_session_type, |
|
9754 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type))); |
|
9755 } |
|
9756 |
|
9757 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
9758 |
|
9759 if ((m_is_client == false |
|
9760 && m_tls_session_type == tls_session_type_full_authentication) |
|
9761 || (m_is_client == true |
|
9762 && (m_tls_session_type == tls_session_type_original_session_resumption |
|
9763 || m_tls_session_type == tls_session_type_stateless_session_resumption |
|
9764 #if defined(USE_FAST_EAP_TYPE) |
|
9765 || m_tls_session_type == tls_session_type_eap_fast_pac_session_resumption |
|
9766 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
9767 ) |
|
9768 ) |
|
9769 ) |
|
9770 { |
|
9771 // We need to send ChangeCipherSpec and Handshake/Finished. |
|
9772 |
|
9773 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
9774 if ( |
|
9775 m_is_client == false |
|
9776 #if defined(USE_FAST_EAP_TYPE) |
|
9777 && m_eap_type != eap_type_fast |
|
9778 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
9779 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
9780 && (m_tls_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_none |
|
9781 || m_tls_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_runs) |
|
9782 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
9783 && m_tls_session_type == tls_session_type_full_authentication |
|
9784 && tls_extension_c::get_tls_extension( |
|
9785 tls_extension_type_session_ticket, |
|
9786 &m_supported_tls_extensions, |
|
9787 m_am_tools) != 0) |
|
9788 { |
|
9789 { |
|
9790 const tls_extension_c * const supported_session_ticket_extension = tls_extension_c::get_tls_extension( |
|
9791 tls_extension_type_session_ticket, |
|
9792 &m_supported_tls_extensions, |
|
9793 m_am_tools); |
|
9794 EAP_UNREFERENCED_PARAMETER(supported_session_ticket_extension); |
|
9795 |
|
9796 EAP_TRACE_DEBUG( |
|
9797 m_am_tools, |
|
9798 TRACE_FLAGS_DEFAULT, |
|
9799 (EAPL("TLS: %s: message_function: analyse_handshake_type_finished(): ") |
|
9800 EAPL("SST: Server will send a new session ticket to client, length = %d.\n"), |
|
9801 (m_is_client == true ? "client": "server"), |
|
9802 supported_session_ticket_extension->get_data_length())); |
|
9803 } |
|
9804 |
|
9805 // Server will send a new session ticket to client. |
|
9806 status = completion_action_add( |
|
9807 tls_completion_action_create_handshake_type_new_session_ticket); |
|
9808 if (status != eap_status_ok) |
|
9809 { |
|
9810 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9811 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9812 } |
|
9813 } |
|
9814 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
9815 |
|
9816 status = completion_action_add( |
|
9817 tls_completion_action_create_change_cipher_spec_type_change_cipher_spec); |
|
9818 if (status != eap_status_ok) |
|
9819 { |
|
9820 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9821 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9822 } |
|
9823 |
|
9824 status = completion_action_add(tls_completion_action_create_handshake_type_finished); |
|
9825 if (status != eap_status_ok) |
|
9826 { |
|
9827 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9828 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9829 } |
|
9830 |
|
9831 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
9832 if (m_is_client == false |
|
9833 && m_tls_session_type == tls_session_type_full_authentication |
|
9834 && m_tls_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_negotiates) |
|
9835 { |
|
9836 status = completion_action_add(tls_completion_action_create_handshake_type_hello_request); |
|
9837 if (status != eap_status_ok) |
|
9838 { |
|
9839 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9840 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9841 } |
|
9842 } |
|
9843 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
9844 |
|
9845 status = completion_action_add(tls_completion_action_check_sent_tls_message); |
|
9846 if (status != eap_status_ok) |
|
9847 { |
|
9848 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9849 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9850 } |
|
9851 } |
|
9852 #if defined(USE_FAST_EAP_TYPE) |
|
9853 else if (m_is_client == false |
|
9854 && m_eap_type == eap_type_fast |
|
9855 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true |
|
9856 && cipher_suite_is_TLS_DH_anon() == true) |
|
9857 { |
|
9858 status = completion_action_add( |
|
9859 tls_completion_action_create_change_cipher_spec_type_change_cipher_spec); |
|
9860 if (status != eap_status_ok) |
|
9861 { |
|
9862 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9863 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9864 } |
|
9865 |
|
9866 status = completion_action_add(tls_completion_action_create_handshake_type_finished); |
|
9867 if (status != eap_status_ok) |
|
9868 { |
|
9869 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9870 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9871 } |
|
9872 |
|
9873 status = completion_action_add(tls_completion_action_check_sent_tls_message); |
|
9874 if (status != eap_status_ok) |
|
9875 { |
|
9876 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9877 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9878 } |
|
9879 } |
|
9880 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
9881 |
|
9882 |
|
9883 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
9884 if (m_tls_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_none |
|
9885 || m_tls_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_runs |
|
9886 || m_tls_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_negotiates |
|
9887 ) |
|
9888 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
9889 { |
|
9890 // Authentication OK. |
|
9891 status = completion_action_add(tls_completion_action_finish_handshake); |
|
9892 if (status != eap_status_ok) |
|
9893 { |
|
9894 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9895 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9896 } |
|
9897 |
|
9898 status = completion_action_add(tls_completion_action_process_tls_records); |
|
9899 if (status != eap_status_ok) |
|
9900 { |
|
9901 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9902 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9903 } |
|
9904 |
|
9905 #if defined(USE_FAST_EAP_TYPE) |
|
9906 if (m_is_client == false |
|
9907 && m_eap_type == eap_type_fast |
|
9908 && m_tls_session_type == tls_session_type_eap_fast_pac_session_resumption) |
|
9909 { |
|
9910 status = completion_action_add(tls_completion_action_check_tunnel_authentication_runs); |
|
9911 if (status != eap_status_ok) |
|
9912 { |
|
9913 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9914 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9915 } |
|
9916 } |
|
9917 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
9918 } |
|
9919 |
|
9920 m_received_eap_identifier = received_eap_identifier; |
|
9921 |
|
9922 |
|
9923 set_state(tls_peap_state_process_pending_tls_completions); |
|
9924 |
|
9925 if (status == eap_status_ok) |
|
9926 { |
|
9927 status = check_sent_tls_message(); |
|
9928 if (status != eap_status_ok) |
|
9929 { |
|
9930 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9931 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9932 } |
|
9933 } |
|
9934 |
|
9935 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
9936 |
|
9937 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9938 return EAP_STATUS_RETURN(m_am_tools, status); |
|
9939 } |
|
9940 |
|
9941 //-------------------------------------------------- |
|
9942 |
|
9943 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
9944 |
|
9945 EAP_FUNC_EXPORT eap_status_e tls_record_c::analyse_handshake_type_new_session_ticket( |
|
9946 EAP_TEMPLATE_CONST tls_handshake_message_c * const handshake_message, |
|
9947 const u8_t /* received_eap_identifier */) |
|
9948 { |
|
9949 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9950 |
|
9951 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
9952 EAP_TRACE_DEBUG( |
|
9953 m_am_tools, |
|
9954 TRACE_FLAGS_DEFAULT, |
|
9955 (EAPL("TLS: %s: message_function: starts: tls_record_c::analyse_handshake_type_new_session_ticket()\n"), |
|
9956 (m_is_client == true ? "client": "server"))); |
|
9957 |
|
9958 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::analyse_handshake_type_new_session_ticket()"); |
|
9959 |
|
9960 eap_status_e status = eap_status_not_supported; |
|
9961 |
|
9962 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
9963 |
|
9964 EAP_TEMPLATE_CONST eap_array_c<tls_extension_c> * const tls_extensions |
|
9965 = handshake_message->get_tls_extensions(); |
|
9966 |
|
9967 if (tls_extensions == 0) |
|
9968 { |
|
9969 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9970 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9971 } |
|
9972 |
|
9973 const tls_extension_c * const session_ticket = tls_extension_c::get_tls_extension( |
|
9974 tls_extension_type_session_ticket, |
|
9975 tls_extensions, |
|
9976 m_am_tools); |
|
9977 |
|
9978 if (session_ticket == 0) |
|
9979 { |
|
9980 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9981 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
9982 } |
|
9983 |
|
9984 m_received_tls_extensions.reset(); |
|
9985 |
|
9986 EAP_TRACE_DEBUG( |
|
9987 m_am_tools, |
|
9988 TRACE_FLAGS_DEFAULT, |
|
9989 (EAPL("TLS: %s: message_function: analyse_handshake_type_new_session_ticket(): ") |
|
9990 EAPL("SST: session ticket received, length = %d.\n"), |
|
9991 (m_is_client == true ? "client": "server"), |
|
9992 session_ticket->get_data_length())); |
|
9993 |
|
9994 tls_extension_c * const copy_of_session_ticket = session_ticket->copy(); |
|
9995 |
|
9996 if (copy_of_session_ticket == 0) |
|
9997 { |
|
9998 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
9999 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
10000 } |
|
10001 |
|
10002 status = m_received_tls_extensions.add_object(copy_of_session_ticket, true); |
|
10003 |
|
10004 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10005 return EAP_STATUS_RETURN(m_am_tools, status); |
|
10006 } |
|
10007 |
|
10008 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
10009 |
|
10010 //-------------------------------------------------- |
|
10011 |
|
10012 EAP_FUNC_EXPORT eap_status_e tls_record_c::analyse_tls_protocol_change_cipher_spec( |
|
10013 const tls_record_message_c * const record) |
|
10014 { |
|
10015 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10016 |
|
10017 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
10018 EAP_TRACE_DEBUG( |
|
10019 m_am_tools, |
|
10020 TRACE_FLAGS_DEFAULT, |
|
10021 (EAPL("TLS: %s: message_function: starts: tls_record_c::analyse_tls_protocol_change_cipher_spec()\n"), |
|
10022 (m_is_client == true ? "client": "server"))); |
|
10023 |
|
10024 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::analyse_tls_protocol_change_cipher_spec()"); |
|
10025 |
|
10026 eap_status_e status = eap_status_not_supported; |
|
10027 |
|
10028 u32_t ind_change_cipher_spec = 0ul; |
|
10029 |
|
10030 for (ind_change_cipher_spec = 0ul |
|
10031 ; ind_change_cipher_spec < record->get_change_cipher_spec_count() |
|
10032 ; ind_change_cipher_spec++) |
|
10033 { |
|
10034 const tls_change_cipher_spec_message_c * const change_cipher_spec_message |
|
10035 = record->get_change_cipher_spec(ind_change_cipher_spec); |
|
10036 |
|
10037 switch (change_cipher_spec_message->get_change_cipher_spec_type()) |
|
10038 { |
|
10039 case tls_change_cipher_spec_type_change_cipher_spec: |
|
10040 |
|
10041 if (m_tls_session_type == tls_session_type_stateless_session_resumption |
|
10042 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
10043 || (m_tls_session_type == tls_session_type_full_authentication |
|
10044 && m_tls_use_identity_privacy == true |
|
10045 && m_tls_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_runs) |
|
10046 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
10047 ) |
|
10048 { |
|
10049 // We must generate the key material. |
|
10050 status = generate_key_material(); |
|
10051 if (status != eap_status_ok) |
|
10052 { |
|
10053 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10054 return EAP_STATUS_RETURN(m_am_tools, status); |
|
10055 } |
|
10056 } |
|
10057 |
|
10058 // We change the receive cipher suite. |
|
10059 status = change_cipher_spec(false); |
|
10060 if (status != eap_status_ok) |
|
10061 { |
|
10062 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10063 return EAP_STATUS_RETURN(m_am_tools, status); |
|
10064 } |
|
10065 else |
|
10066 { |
|
10067 set_state(tls_peap_state_wait_handshake_type_finished); |
|
10068 } |
|
10069 |
|
10070 break; |
|
10071 |
|
10072 default: |
|
10073 |
|
10074 set_state(tls_peap_state_failure); |
|
10075 return EAP_STATUS_RETURN(m_am_tools, eap_status_not_supported); |
|
10076 } // switch() |
|
10077 |
|
10078 } // for() |
|
10079 |
|
10080 |
|
10081 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10082 return EAP_STATUS_RETURN(m_am_tools, status); |
|
10083 } |
|
10084 |
|
10085 //-------------------------------------------------- |
|
10086 |
|
10087 EAP_FUNC_EXPORT eap_status_e tls_record_c::analyse_tls_protocol_alert( |
|
10088 const tls_record_message_c * const record) |
|
10089 { |
|
10090 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10091 |
|
10092 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
10093 EAP_TRACE_DEBUG( |
|
10094 m_am_tools, |
|
10095 TRACE_FLAGS_DEFAULT, |
|
10096 (EAPL("TLS: %s: message_function: starts: tls_record_c::analyse_tls_protocol_alert()\n"), |
|
10097 (m_is_client == true ? "client": "server"))); |
|
10098 |
|
10099 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::analyse_tls_protocol_alert()"); |
|
10100 |
|
10101 eap_status_e status = eap_status_authentication_failure; |
|
10102 |
|
10103 u32_t ind_alert = 0ul; |
|
10104 |
|
10105 m_new_tls_message.reset(); |
|
10106 |
|
10107 |
|
10108 for (ind_alert = 0ul |
|
10109 ; ind_alert < record->get_alert_count() |
|
10110 ; ind_alert++) |
|
10111 { |
|
10112 const tls_alert_message_c * const alert_message |
|
10113 = record->get_alert(ind_alert); |
|
10114 |
|
10115 EAP_TRACE_ERROR( |
|
10116 m_am_tools, |
|
10117 TRACE_FLAGS_DEFAULT, |
|
10118 (EAPL("ERROR: %s: EAP_type_TLS_PEAP: Alert message %s:%s\n"), |
|
10119 (m_is_client == true) ? "client": "server", |
|
10120 eap_tls_trace_string_c::get_alert_level_string(alert_message->get_alert_level()), |
|
10121 eap_tls_trace_string_c::get_alert_description_string(alert_message->get_alert_description()))); |
|
10122 |
|
10123 if (m_application != 0) |
|
10124 { |
|
10125 // Indication to TLS-application. |
|
10126 (void) m_application->alert_received( |
|
10127 alert_message->get_alert_level(), |
|
10128 alert_message->get_alert_description()); |
|
10129 } |
|
10130 |
|
10131 // indication to TLS AM. |
|
10132 m_am_tls_services->alert_received( |
|
10133 alert_message->get_alert_level(), |
|
10134 alert_message->get_alert_description()); |
|
10135 |
|
10136 switch (alert_message->get_alert_description()) |
|
10137 { |
|
10138 case tls_alert_description_close_notify: |
|
10139 break; |
|
10140 case tls_alert_description_unexpected_message: |
|
10141 // This message is always fatal. |
|
10142 break; |
|
10143 case tls_alert_description_bad_record_mac: |
|
10144 // This message is always fatal. |
|
10145 break; |
|
10146 case tls_alert_description_decryption_failed: |
|
10147 // This message is always fatal. |
|
10148 break; |
|
10149 case tls_alert_description_record_overflow: |
|
10150 // This message is always fatal. |
|
10151 break; |
|
10152 case tls_alert_description_decompression_failure: |
|
10153 // This message is always fatal. |
|
10154 break; |
|
10155 case tls_alert_description_handshake_failure: |
|
10156 // This message is always fatal. |
|
10157 break; |
|
10158 case tls_alert_description_bad_certificate: |
|
10159 break; |
|
10160 case tls_alert_description_unsupported_certificate: |
|
10161 break; |
|
10162 case tls_alert_description_certificate_revoked: |
|
10163 break; |
|
10164 case tls_alert_description_certificate_expired: |
|
10165 break; |
|
10166 case tls_alert_description_certificate_unknown: |
|
10167 break; |
|
10168 case tls_alert_description_illegal_parameter: |
|
10169 // This message is always fatal. |
|
10170 break; |
|
10171 case tls_alert_description_unknown_ca: |
|
10172 // This message is always fatal. |
|
10173 break; |
|
10174 case tls_alert_description_access_denied: |
|
10175 // This message is always fatal. |
|
10176 break; |
|
10177 case tls_alert_description_decode_error: |
|
10178 // This message is always fatal. |
|
10179 break; |
|
10180 case tls_alert_description_decrypt_error: |
|
10181 break; |
|
10182 case tls_alert_description_export_restriction: |
|
10183 // This message is always fatal. |
|
10184 break; |
|
10185 case tls_alert_description_protocol_version: |
|
10186 // This message is always fatal. |
|
10187 break; |
|
10188 case tls_alert_description_insufficient_security: |
|
10189 // This message is always fatal. |
|
10190 break; |
|
10191 case tls_alert_description_internal_error: |
|
10192 // This message is always fatal. |
|
10193 break; |
|
10194 case tls_alert_description_user_canceled: |
|
10195 break; |
|
10196 case tls_alert_description_no_renegotiation: |
|
10197 // This message is always a warning. |
|
10198 break; |
|
10199 case tls_alert_description_none: |
|
10200 break; |
|
10201 default: |
|
10202 break; |
|
10203 } // switch() |
|
10204 |
|
10205 } // for() |
|
10206 |
|
10207 |
|
10208 set_state(tls_peap_state_failure); |
|
10209 |
|
10210 // This will cause the session terminate immediately. |
|
10211 status = get_type_partner()->set_session_timeout(0ul); |
|
10212 if (status != eap_status_ok) |
|
10213 { |
|
10214 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10215 return EAP_STATUS_RETURN(m_am_tools, status); |
|
10216 } |
|
10217 |
|
10218 |
|
10219 { |
|
10220 eap_state_notification_c notification( |
|
10221 m_am_tools, |
|
10222 &m_send_network_id, |
|
10223 m_is_client, |
|
10224 eap_state_notification_generic, |
|
10225 eap_protocol_layer_internal_type, |
|
10226 0, |
|
10227 tls_peap_state_none, |
|
10228 eap_state_authentication_terminated_unsuccessfully, |
|
10229 0, |
|
10230 false); |
|
10231 |
|
10232 notification.set_authentication_error(eap_status_authentication_failure); |
|
10233 |
|
10234 get_type_partner()->state_notification(¬ification); |
|
10235 } |
|
10236 |
|
10237 |
|
10238 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10239 return EAP_STATUS_RETURN(m_am_tools, status); |
|
10240 } |
|
10241 |
|
10242 //-------------------------------------------------- |
|
10243 |
|
10244 EAP_FUNC_EXPORT tls_record_protocol_e tls_record_c::get_next_tls_record_message_protocol() |
|
10245 { |
|
10246 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10247 |
|
10248 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
10249 EAP_TRACE_DEBUG( |
|
10250 m_am_tools, |
|
10251 TRACE_FLAGS_DEFAULT, |
|
10252 (EAPL("TLS: %s: message_function: starts: tls_record_c::get_next_tls_record_message_protocol()\n"), |
|
10253 (m_is_client == true ? "client": "server"))); |
|
10254 |
|
10255 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::get_next_tls_record_message_protocol()"); |
|
10256 |
|
10257 tls_record_protocol_e record_protocol(tls_record_protocol_none); |
|
10258 |
|
10259 if (m_received_tls_message.get_record_message_count() <= m_received_tls_message.get_analyse_index()+1ul) |
|
10260 { |
|
10261 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10262 return record_protocol; |
|
10263 } |
|
10264 |
|
10265 tls_record_message_c * const tls_record_message |
|
10266 = m_received_tls_message.get_record_message(m_received_tls_message.get_analyse_index()+1ul); |
|
10267 if (tls_record_message == 0 |
|
10268 || tls_record_message->get_is_valid() == false) |
|
10269 { |
|
10270 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10271 return record_protocol; |
|
10272 } |
|
10273 |
|
10274 const u32_t tls_record_length = tls_record_message->get_record_message_data()->get_data_length(); |
|
10275 |
|
10276 if (tls_record_message->get_record_message_data()->get_data_length() < tls_record_header_c::get_header_length()) |
|
10277 { |
|
10278 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10279 return record_protocol; |
|
10280 } |
|
10281 |
|
10282 tls_record_header_c tls_record_header( |
|
10283 m_am_tools, |
|
10284 tls_record_message->get_record_message_data()->get_data( |
|
10285 tls_record_header_c::get_header_length()), |
|
10286 tls_record_length); |
|
10287 |
|
10288 if (tls_record_header.get_is_valid() == false |
|
10289 || tls_record_length < tls_record_header.get_data_length() |
|
10290 || tls_record_length |
|
10291 < tls_record_header.get_header_length() |
|
10292 + tls_record_header.get_data_length()) |
|
10293 { |
|
10294 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10295 return record_protocol; |
|
10296 } |
|
10297 |
|
10298 record_protocol = tls_record_header.get_protocol(); |
|
10299 |
|
10300 EAP_TRACE_DEBUG( |
|
10301 m_am_tools, |
|
10302 TRACE_FLAGS_DEFAULT, |
|
10303 (EAPL("TLS: %s: message_function: ends: tls_record_c::get_next_tls_record_message_protocol(): %d=%s\n"), |
|
10304 (m_is_client == true ? "client": "server"), |
|
10305 record_protocol, |
|
10306 tls_record_header_c::get_tls_protocol_string(record_protocol))); |
|
10307 |
|
10308 |
|
10309 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10310 return record_protocol; |
|
10311 } |
|
10312 |
|
10313 //-------------------------------------------------- |
|
10314 |
|
10315 EAP_FUNC_EXPORT tls_handshake_type_e tls_record_c::get_next_tls_handshake_message_type() |
|
10316 { |
|
10317 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10318 |
|
10319 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
10320 EAP_TRACE_DEBUG( |
|
10321 m_am_tools, |
|
10322 TRACE_FLAGS_DEFAULT, |
|
10323 (EAPL("TLS: %s: message_function: starts: tls_record_c::get_next_tls_handshake_message_type()\n"), |
|
10324 (m_is_client == true ? "client": "server"))); |
|
10325 |
|
10326 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::get_next_tls_handshake_message_type()"); |
|
10327 |
|
10328 tls_handshake_type_e handshake_type(tls_handshake_type_none); |
|
10329 |
|
10330 if (m_received_tls_message.get_record_message_count() <= m_received_tls_message.get_analyse_index()) |
|
10331 { |
|
10332 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10333 return handshake_type; |
|
10334 } |
|
10335 |
|
10336 tls_record_message_c * const tls_record_message |
|
10337 = m_received_tls_message.get_record_message(m_received_tls_message.get_analyse_index()); |
|
10338 if (tls_record_message == 0 |
|
10339 || tls_record_message->get_is_valid() == false) |
|
10340 { |
|
10341 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10342 return handshake_type; |
|
10343 } |
|
10344 |
|
10345 const u32_t tls_record_length = tls_record_message->get_record_message_data()->get_data_length(); |
|
10346 |
|
10347 if (tls_record_message->get_record_message_data()->get_data_length() < tls_record_header_c::get_header_length()) |
|
10348 { |
|
10349 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10350 return handshake_type; |
|
10351 } |
|
10352 |
|
10353 tls_record_header_c tls_record_header( |
|
10354 m_am_tools, |
|
10355 tls_record_message->get_record_message_data()->get_data( |
|
10356 tls_record_header_c::get_header_length()), |
|
10357 tls_record_length); |
|
10358 |
|
10359 if (tls_record_header.get_is_valid() == false |
|
10360 || tls_record_length < tls_record_header.get_data_length() |
|
10361 || tls_record_length |
|
10362 < tls_record_header.get_header_length() |
|
10363 + tls_record_header.get_data_length()) |
|
10364 { |
|
10365 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10366 return handshake_type; |
|
10367 } |
|
10368 |
|
10369 tls_record_protocol_e tls_protocol(tls_record_header.get_protocol()); |
|
10370 |
|
10371 if (tls_protocol == tls_record_protocol_handshake) |
|
10372 { |
|
10373 if (tls_record_message->get_handshake_count() <= tls_record_message->get_analyse_index()+1ul) |
|
10374 { |
|
10375 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10376 return handshake_type; |
|
10377 } |
|
10378 |
|
10379 tls_handshake_message_c * const handshake_message = tls_record_message->get_handshake(tls_record_message->get_analyse_index()+1ul); |
|
10380 |
|
10381 if (handshake_message == 0 |
|
10382 || handshake_message->get_is_valid() == false) |
|
10383 { |
|
10384 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10385 return handshake_type; |
|
10386 } |
|
10387 |
|
10388 handshake_type = handshake_message->get_handshake_type(); |
|
10389 |
|
10390 EAP_TRACE_DEBUG( |
|
10391 m_am_tools, |
|
10392 TRACE_FLAGS_DEFAULT, |
|
10393 (EAPL("TLS: %s: message_function: ends: tls_record_c::get_next_tls_handshake_message_type(): %d=%s\n"), |
|
10394 (m_is_client == true ? "client": "server"), |
|
10395 handshake_type, |
|
10396 tls_handshake_header_c::get_tls_handshake_string(handshake_type))); |
|
10397 } |
|
10398 |
|
10399 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10400 return handshake_type; |
|
10401 } |
|
10402 |
|
10403 //-------------------------------------------------- |
|
10404 |
|
10405 EAP_FUNC_EXPORT eap_status_e tls_record_c::analyse_tls_protocol_handshake( |
|
10406 tls_record_message_c * const record, |
|
10407 const u8_t received_eap_identifier) |
|
10408 { |
|
10409 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10410 |
|
10411 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
10412 EAP_TRACE_DEBUG( |
|
10413 m_am_tools, |
|
10414 TRACE_FLAGS_DEFAULT, |
|
10415 (EAPL("TLS: %s: message_function: starts: tls_record_c::analyse_tls_protocol_handshake()\n"), |
|
10416 (m_is_client == true ? "client": "server"))); |
|
10417 |
|
10418 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::analyse_tls_protocol_handshake()"); |
|
10419 |
|
10420 eap_status_e status = eap_status_ok; |
|
10421 |
|
10422 u32_t ind_handshake = 0ul; |
|
10423 |
|
10424 for (ind_handshake = record->get_analyse_index() |
|
10425 ; ind_handshake < record->get_handshake_count() |
|
10426 ; ind_handshake++) |
|
10427 { |
|
10428 // This is used in EAP-FAST to see the next TLS-handshake message type. |
|
10429 record->save_analyse_index(ind_handshake); |
|
10430 |
|
10431 tls_handshake_message_c * const handshake_message = record->get_handshake(ind_handshake); |
|
10432 |
|
10433 if (handshake_message->get_is_valid() == false) |
|
10434 { |
|
10435 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10436 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
10437 } |
|
10438 |
|
10439 EAP_TRACE_DEBUG( |
|
10440 m_am_tools, |
|
10441 TRACE_FLAGS_DEFAULT, |
|
10442 (EAPL("TLS: %s: message_function: analyse_tls_protocol_handshake(): ") |
|
10443 EAPL("handshake type %d, analysed %d\n"), |
|
10444 (m_is_client == true ? "client": "server"), |
|
10445 handshake_message->get_handshake_type(), |
|
10446 handshake_message->get_is_analysed())); |
|
10447 |
|
10448 if (handshake_message->get_is_analysed() == false) |
|
10449 { |
|
10450 handshake_message->set_is_analysed(); |
|
10451 |
|
10452 switch (handshake_message->get_handshake_type()) |
|
10453 { |
|
10454 case tls_handshake_type_hello_request: |
|
10455 status = analyse_handshake_type_hello_request( |
|
10456 handshake_message); |
|
10457 break; |
|
10458 case tls_handshake_type_client_hello: |
|
10459 if (m_tls_peap_test_version == true |
|
10460 && verify_state(tls_peap_state_tls_success) == true) |
|
10461 { |
|
10462 // OK, this is test version. |
|
10463 } |
|
10464 else if (verify_state(tls_peap_state_wait_handshake_type_client_hello) == false) |
|
10465 { |
|
10466 EAP_TRACE_ERROR( |
|
10467 m_am_tools, |
|
10468 TRACE_FLAGS_DEFAULT, |
|
10469 (EAPL("ERROR: TLS: %s: function: verify_state(): current state %s != %s\n"), |
|
10470 (m_is_client == true ? "client": "server"), |
|
10471 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
10472 eap_tls_trace_string_c::get_state_string( |
|
10473 tls_peap_state_wait_handshake_type_client_hello))); |
|
10474 return EAP_STATUS_RETURN(m_am_tools, eap_status_unexpected_message); |
|
10475 } |
|
10476 |
|
10477 status = analyse_handshake_type_client_hello( |
|
10478 handshake_message); |
|
10479 break; |
|
10480 case tls_handshake_type_server_hello: |
|
10481 if (verify_state(tls_peap_state_wait_handshake_type_server_hello) == false) |
|
10482 { |
|
10483 EAP_TRACE_ERROR( |
|
10484 m_am_tools, |
|
10485 TRACE_FLAGS_DEFAULT, |
|
10486 (EAPL("ERROR: TLS: %s: function: verify_state(): current state %s != %s\n"), |
|
10487 (m_is_client == true ? "client": "server"), |
|
10488 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
10489 eap_tls_trace_string_c::get_state_string( |
|
10490 tls_peap_state_wait_handshake_type_server_hello))); |
|
10491 return EAP_STATUS_RETURN(m_am_tools, eap_status_unexpected_message); |
|
10492 } |
|
10493 |
|
10494 status = analyse_handshake_type_server_hello( |
|
10495 handshake_message); |
|
10496 break; |
|
10497 case tls_handshake_type_certificate: |
|
10498 if (m_tls_session_type == tls_session_type_stateless_session_resumption |
|
10499 && verify_state(tls_peap_state_wait_change_cipher_spec) == true) |
|
10500 { |
|
10501 // Server wish to initiate a full handshake. |
|
10502 m_tls_session_type = tls_session_type_full_authentication; |
|
10503 set_state(tls_peap_state_wait_handshake_type_certificate); |
|
10504 } |
|
10505 else if (verify_state(tls_peap_state_wait_handshake_type_certificate) == false) |
|
10506 { |
|
10507 EAP_TRACE_ERROR( |
|
10508 m_am_tools, |
|
10509 TRACE_FLAGS_DEFAULT, |
|
10510 (EAPL("ERROR: TLS: %s: function: verify_state(): current state %s != %s\n"), |
|
10511 (m_is_client == true ? "client": "server"), |
|
10512 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
10513 eap_tls_trace_string_c::get_state_string( |
|
10514 tls_peap_state_wait_handshake_type_certificate))); |
|
10515 return EAP_STATUS_RETURN(m_am_tools, eap_status_unexpected_message); |
|
10516 } |
|
10517 |
|
10518 status = analyse_handshake_type_certificate( |
|
10519 handshake_message); |
|
10520 break; |
|
10521 case tls_handshake_type_server_key_exchange: |
|
10522 if (verify_state(tls_peap_state_wait_handshake_type_server_key_exchange) == false) |
|
10523 { |
|
10524 EAP_TRACE_ERROR( |
|
10525 m_am_tools, |
|
10526 TRACE_FLAGS_DEFAULT, |
|
10527 (EAPL("ERROR: TLS: %s: function: verify_state(): current state %s != %s\n"), |
|
10528 (m_is_client == true ? "client": "server"), |
|
10529 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
10530 eap_tls_trace_string_c::get_state_string( |
|
10531 tls_peap_state_wait_handshake_type_server_key_exchange))); |
|
10532 return EAP_STATUS_RETURN(m_am_tools, eap_status_unexpected_message); |
|
10533 } |
|
10534 |
|
10535 status = analyse_handshake_type_server_key_exchange( |
|
10536 handshake_message); |
|
10537 break; |
|
10538 case tls_handshake_type_certificate_request: |
|
10539 if (verify_state( |
|
10540 tls_peap_state_wait_handshake_type_certificate_request_or_server_hello_done) |
|
10541 == false) |
|
10542 { |
|
10543 EAP_TRACE_ERROR( |
|
10544 m_am_tools, |
|
10545 TRACE_FLAGS_DEFAULT, |
|
10546 (EAPL("ERROR: TLS: %s: function: verify_state(): current state %s != %s\n"), |
|
10547 (m_is_client == true ? "client": "server"), |
|
10548 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
10549 eap_tls_trace_string_c::get_state_string( |
|
10550 tls_peap_state_wait_handshake_type_certificate_request_or_server_hello_done))); |
|
10551 return EAP_STATUS_RETURN(m_am_tools, eap_status_unexpected_message); |
|
10552 } |
|
10553 |
|
10554 status = analyse_handshake_type_certificate_request( |
|
10555 handshake_message); |
|
10556 break; |
|
10557 case tls_handshake_type_server_hello_done: |
|
10558 |
|
10559 EAP_TRACE_DEBUG( |
|
10560 m_am_tools, |
|
10561 TRACE_FLAGS_DEFAULT, |
|
10562 (EAPL("TLS: %s: message_function: analyse_tls_protocol_handshake(): m_tls_peap_server_authenticates_client_policy_flag=%d\n"), |
|
10563 (m_is_client == true ? "client": "server"), |
|
10564 m_tls_peap_server_authenticates_client_policy_flag)); |
|
10565 |
|
10566 if (verify_state( |
|
10567 tls_peap_state_wait_handshake_type_certificate_request_or_server_hello_done) |
|
10568 == true) |
|
10569 { |
|
10570 if (m_tls_peap_server_authenticates_client_policy_flag == false) |
|
10571 { |
|
10572 // Client accepts server only authentication. |
|
10573 m_tls_peap_server_authenticates_client_action = false; |
|
10574 } |
|
10575 else |
|
10576 { |
|
10577 // ERROR: Client does NOT accept server only authentication. |
|
10578 EAP_TRACE_ERROR( |
|
10579 m_am_tools, |
|
10580 TRACE_FLAGS_DEFAULT, |
|
10581 (EAPL("ERROR: TLS: %s: function: current state %s: ") |
|
10582 EAPL("Client does NOT accept server only authentication.\n"), |
|
10583 (m_is_client == true ? "client": "server"), |
|
10584 eap_tls_trace_string_c::get_state_string(m_tls_peap_state))); |
|
10585 return EAP_STATUS_RETURN(m_am_tools, eap_status_insufficient_security); |
|
10586 } |
|
10587 } |
|
10588 else if (verify_state(tls_peap_state_wait_handshake_type_server_hello_done) |
|
10589 == false) |
|
10590 { |
|
10591 EAP_TRACE_ERROR( |
|
10592 m_am_tools, |
|
10593 TRACE_FLAGS_DEFAULT, |
|
10594 (EAPL("ERROR: TLS: %s: function: verify_state(): current state %s != %s\n"), |
|
10595 (m_is_client == true ? "client": "server"), |
|
10596 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
10597 eap_tls_trace_string_c::get_state_string( |
|
10598 tls_peap_state_wait_handshake_type_server_hello_done))); |
|
10599 return EAP_STATUS_RETURN(m_am_tools, eap_status_unexpected_message); |
|
10600 } |
|
10601 |
|
10602 status = analyse_handshake_type_server_hello_done( |
|
10603 handshake_message); |
|
10604 break; |
|
10605 case tls_handshake_type_certificate_verify: |
|
10606 if (verify_state(tls_peap_state_wait_handshake_type_certificate_verify) == false) |
|
10607 { |
|
10608 EAP_TRACE_ERROR( |
|
10609 m_am_tools, |
|
10610 TRACE_FLAGS_DEFAULT, |
|
10611 (EAPL("ERROR: TLS: %s: function: verify_state(): current state %s != %s\n"), |
|
10612 (m_is_client == true ? "client": "server"), |
|
10613 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
10614 eap_tls_trace_string_c::get_state_string( |
|
10615 tls_peap_state_wait_handshake_type_certificate_verify))); |
|
10616 return EAP_STATUS_RETURN(m_am_tools, eap_status_unexpected_message); |
|
10617 } |
|
10618 |
|
10619 status = analyse_handshake_type_certificate_verify( |
|
10620 handshake_message); |
|
10621 break; |
|
10622 case tls_handshake_type_client_key_exchange: |
|
10623 if (verify_state(tls_peap_state_wait_handshake_type_client_key_exchange) == false) |
|
10624 { |
|
10625 EAP_TRACE_ERROR( |
|
10626 m_am_tools, |
|
10627 TRACE_FLAGS_DEFAULT, |
|
10628 (EAPL("ERROR: TLS: %s: function: verify_state(): current state %s != %s\n"), |
|
10629 (m_is_client == true ? "client": "server"), |
|
10630 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
10631 eap_tls_trace_string_c::get_state_string( |
|
10632 tls_peap_state_wait_handshake_type_client_key_exchange))); |
|
10633 return EAP_STATUS_RETURN(m_am_tools, eap_status_unexpected_message); |
|
10634 } |
|
10635 |
|
10636 status = analyse_handshake_type_client_key_exchange( |
|
10637 handshake_message); |
|
10638 break; |
|
10639 case tls_handshake_type_finished: |
|
10640 if (verify_state(tls_peap_state_wait_handshake_type_finished) == false) |
|
10641 { |
|
10642 EAP_TRACE_ERROR( |
|
10643 m_am_tools, |
|
10644 TRACE_FLAGS_DEFAULT, |
|
10645 (EAPL("ERROR: TLS: %s: function: verify_state(): current state %s != %s\n"), |
|
10646 (m_is_client == true ? "client": "server"), |
|
10647 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
10648 eap_tls_trace_string_c::get_state_string( |
|
10649 tls_peap_state_wait_handshake_type_finished))); |
|
10650 return EAP_STATUS_RETURN(m_am_tools, eap_status_unexpected_message); |
|
10651 } |
|
10652 |
|
10653 status = analyse_handshake_type_finished( |
|
10654 handshake_message, |
|
10655 received_eap_identifier); |
|
10656 break; |
|
10657 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
10658 case tls_handshake_type_new_session_ticket: |
|
10659 { |
|
10660 // Note This is optional Handshake message. |
|
10661 |
|
10662 const tls_extension_c * const supported_session_ticket_extension = tls_extension_c::get_tls_extension( |
|
10663 tls_extension_type_session_ticket, |
|
10664 &m_supported_tls_extensions, |
|
10665 m_am_tools); |
|
10666 |
|
10667 if (supported_session_ticket_extension != 0 |
|
10668 && (verify_state(tls_peap_state_wait_change_cipher_spec) == true |
|
10669 || verify_state(tls_peap_state_wait_handshake_type_new_session_ticket) == true)) |
|
10670 { |
|
10671 // OK new Session ticket handshake allowed. |
|
10672 EAP_TRACE_DEBUG( |
|
10673 m_am_tools, |
|
10674 TRACE_FLAGS_DEFAULT, |
|
10675 (EAPL("TLS: %s: function: verify_state(): SST: current state %s == %s: Session Ticket Handshake allowed, length = %d.\n"), |
|
10676 (m_is_client == true ? "client": "server"), |
|
10677 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
10678 eap_tls_trace_string_c::get_state_string( |
|
10679 tls_peap_state_wait_handshake_type_new_session_ticket), |
|
10680 supported_session_ticket_extension->get_data_length())); |
|
10681 } |
|
10682 else if (verify_state(tls_peap_state_wait_handshake_type_new_session_ticket) == false) |
|
10683 { |
|
10684 EAP_TRACE_ERROR( |
|
10685 m_am_tools, |
|
10686 TRACE_FLAGS_DEFAULT, |
|
10687 (EAPL("ERROR: TLS: %s: function: verify_state(): SST: current state %s != %s\n"), |
|
10688 (m_is_client == true ? "client": "server"), |
|
10689 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
10690 eap_tls_trace_string_c::get_state_string( |
|
10691 tls_peap_state_wait_handshake_type_new_session_ticket))); |
|
10692 return EAP_STATUS_RETURN(m_am_tools, eap_status_unexpected_message); |
|
10693 } |
|
10694 |
|
10695 status = analyse_handshake_type_new_session_ticket( |
|
10696 handshake_message, |
|
10697 received_eap_identifier); |
|
10698 break; |
|
10699 } |
|
10700 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
10701 default: |
|
10702 return EAP_STATUS_RETURN(m_am_tools, eap_status_not_supported); |
|
10703 } // switch() |
|
10704 } |
|
10705 |
|
10706 if (status == eap_status_pending_request) |
|
10707 { |
|
10708 // Save pending state. |
|
10709 record->save_analyse_index(ind_handshake); |
|
10710 |
|
10711 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10712 return EAP_STATUS_RETURN(m_am_tools, status); |
|
10713 } |
|
10714 else if (status != eap_status_ok) |
|
10715 { |
|
10716 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10717 return EAP_STATUS_RETURN(m_am_tools, status); |
|
10718 } |
|
10719 |
|
10720 if ((get_is_tunneled_tls() == false |
|
10721 && m_tls_peap_state == tls_peap_state_tls_success) |
|
10722 || (get_is_tunneled_tls() == true |
|
10723 && m_tls_peap_state == tls_peap_state_peap_tunnel_ready)) |
|
10724 { |
|
10725 // Stop processing TLS-records. |
|
10726 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10727 return EAP_STATUS_RETURN(m_am_tools, status); |
|
10728 } |
|
10729 } // for() |
|
10730 |
|
10731 |
|
10732 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10733 return EAP_STATUS_RETURN(m_am_tools, status); |
|
10734 } |
|
10735 |
|
10736 //-------------------------------------------------- |
|
10737 |
|
10738 EAP_FUNC_EXPORT eap_status_e tls_record_c::analyse_tls_protocol_application_data( |
|
10739 const tls_record_message_c * const record, |
|
10740 const u8_t received_eap_identifier) |
|
10741 { |
|
10742 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10743 |
|
10744 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
10745 EAP_TRACE_DEBUG( |
|
10746 m_am_tools, |
|
10747 TRACE_FLAGS_DEFAULT, |
|
10748 (EAPL("TLS: %s: message_function: starts: tls_record_c::analyse_tls_protocol_application_data()\n"), |
|
10749 (m_is_client == true ? "client": "server"))); |
|
10750 |
|
10751 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::analyse_tls_protocol_application_data()"); |
|
10752 |
|
10753 eap_status_e status = eap_status_ok; |
|
10754 |
|
10755 u32_t ind; |
|
10756 for (ind = 0ul |
|
10757 ; ind < record->get_application_data_count() |
|
10758 ; ind++) |
|
10759 { |
|
10760 tls_application_data_message_c * const application_data_message |
|
10761 = record->get_application_data(ind); |
|
10762 if (application_data_message == 0 |
|
10763 || application_data_message->get_is_valid() == false) |
|
10764 { |
|
10765 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10766 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
10767 } |
|
10768 |
|
10769 if (application_data_message->get_is_analysed() == false) |
|
10770 { |
|
10771 application_data_message->set_is_analysed(); |
|
10772 |
|
10773 if (m_application == 0) |
|
10774 { |
|
10775 // ERROR: No application. |
|
10776 EAP_TRACE_DEBUG( |
|
10777 m_am_tools, |
|
10778 TRACE_FLAGS_DEFAULT, |
|
10779 (EAPL("ERROR: TLS: %s: message_function: starts: tls_record_c::analyse_tls_protocol_application_data(): no application.\n"), |
|
10780 (m_is_client == true ? "client": "server"))); |
|
10781 status = eap_status_illegal_data_payload; |
|
10782 } |
|
10783 else |
|
10784 { |
|
10785 status = m_application->packet_process( |
|
10786 application_data_message->get_application_data(), |
|
10787 received_eap_identifier); |
|
10788 } |
|
10789 |
|
10790 if (status != eap_status_ok) |
|
10791 { |
|
10792 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10793 return EAP_STATUS_RETURN(m_am_tools, status); |
|
10794 } |
|
10795 } |
|
10796 else |
|
10797 { |
|
10798 EAP_TRACE_DEBUG( |
|
10799 m_am_tools, |
|
10800 TRACE_FLAGS_DEFAULT, |
|
10801 (EAPL("TLS: %s: message_function: starts: tls_record_c::analyse_tls_protocol_application_data(): already analysed.\n"), |
|
10802 (m_is_client == true ? "client": "server"))); |
|
10803 } |
|
10804 } |
|
10805 |
|
10806 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10807 return EAP_STATUS_RETURN(m_am_tools, status); |
|
10808 } |
|
10809 |
|
10810 //-------------------------------------------------- |
|
10811 |
|
10812 EAP_FUNC_EXPORT eap_status_e tls_record_c::are_pending_queries_completed() |
|
10813 { |
|
10814 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10815 |
|
10816 eap_status_e status = eap_status_pending_request; |
|
10817 |
|
10818 eap_status_string_c status_string; |
|
10819 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
10820 EAP_TRACE_DEBUG( |
|
10821 m_am_tools, |
|
10822 TRACE_FLAGS_DEFAULT, |
|
10823 (EAPL("TLS: %s: pending_function: starts: tls_record_c::are_pending_queries_completed(): %s\n"), |
|
10824 (m_is_client == true ? "client": "server"), |
|
10825 status_string.get_status_string(status))); |
|
10826 |
|
10827 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::are_pending_queries_completed()"); |
|
10828 |
|
10829 if (m_pending_query_certificate_authorities_and_types == false |
|
10830 && m_pending_query_certificate_chain == false |
|
10831 && m_pending_query_cipher_suites_and_previous_session == false |
|
10832 && m_pending_query_dh_parameters == false |
|
10833 && m_pending_query_realm == false |
|
10834 && m_pending_select_cipher_suite_and_check_session_id == false |
|
10835 && m_pending_verify_certificate_chain == false |
|
10836 && m_pending_rsa_decrypt_with_private_key == false |
|
10837 && m_pending_rsa_encrypt_with_public_key == false |
|
10838 && m_pending_sign_with_private_key == false |
|
10839 && m_pending_verify_with_public_key == false |
|
10840 && m_pending_query_tunnel_PAC == false) |
|
10841 { |
|
10842 status = eap_status_ok; |
|
10843 } |
|
10844 |
|
10845 EAP_TRACE_DEBUG( |
|
10846 m_am_tools, |
|
10847 TRACE_FLAGS_DEFAULT, |
|
10848 (EAPL("TLS: %s: pending_function: are_pending_queries_completed(): %s\n"), |
|
10849 (m_is_client == true ? "client": "server"), |
|
10850 status_string.get_status_string(status))); |
|
10851 |
|
10852 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10853 return EAP_STATUS_RETURN(m_am_tools, status); |
|
10854 } |
|
10855 |
|
10856 //-------------------------------------------------- |
|
10857 |
|
10858 EAP_FUNC_EXPORT eap_status_e tls_record_c::indicate_state_to_lower_layer( |
|
10859 const tls_peap_state_e indicated_state) |
|
10860 { |
|
10861 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10862 |
|
10863 // Notify lower layer the state of TLS. |
|
10864 |
|
10865 EAP_TRACE_DEBUG( |
|
10866 m_am_tools, |
|
10867 TRACE_FLAGS_DEFAULT, |
|
10868 (EAPL("TLS: %s: state_function: starts: tls_record_c::indicate_state_to_lower_layer(): m_tls_session_type=%d=%s, state=%d=%s\n"), |
|
10869 (m_is_client == true ? "client": "server"), |
|
10870 m_tls_session_type, |
|
10871 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type), |
|
10872 indicated_state, |
|
10873 eap_tls_trace_string_c::get_state_string(indicated_state))); |
|
10874 |
|
10875 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::indicate_state_to_lower_layer()"); |
|
10876 |
|
10877 |
|
10878 #if defined(USE_EAP_TRACE_ALWAYS) |
|
10879 |
|
10880 if (m_tls_peap_state == tls_peap_state_tls_success) |
|
10881 { |
|
10882 |
|
10883 tls_identity_privacy_handshake_state_e tmp_identity_privacy_handshake_state = |
|
10884 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
10885 m_tls_identity_privacy_handshake_state; |
|
10886 #else |
|
10887 tls_identity_privacy_handshake_state_none; |
|
10888 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
10889 |
|
10890 EAP_TRACE_ALWAYS( |
|
10891 m_am_tools, |
|
10892 TRACE_FLAGS_DEFAULT, |
|
10893 (EAPL("%s: indicate_state_to_lower_layer(): TLS/PEAP authentication ") |
|
10894 EAPL("SUCCESS: %s, %s, tunnel %d, tunneling type %s, tunneling version %s, cipher_suite %s, %s\n"), |
|
10895 (m_is_client == true ? "client": "server"), |
|
10896 (m_tls_peap_server_authenticates_client_action == true |
|
10897 ? "mutual": "anonymous client"), |
|
10898 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type), |
|
10899 get_is_tunneled_tls(), |
|
10900 eap_header_string_c::get_eap_type_string(m_eap_type), |
|
10901 eap_tls_trace_string_c::get_peap_version_string(m_peap_version), |
|
10902 eap_tls_trace_string_c::get_cipher_suite_string(m_selected_cipher_suite), |
|
10903 eap_tls_trace_string_c::get_tls_identity_privacy_handshake_state_string(tmp_identity_privacy_handshake_state))); |
|
10904 } |
|
10905 else if (m_tls_peap_state == tls_peap_state_peap_tunnel_ready |
|
10906 || m_tls_peap_state == tls_peap_state_wait_application_data) |
|
10907 { |
|
10908 EAP_TRACE_ALWAYS( |
|
10909 m_am_tools, |
|
10910 TRACE_FLAGS_DEFAULT, |
|
10911 (EAPL("%s: indicate_state_to_lower_layer(): TLS/PEAP authentication ") |
|
10912 EAPL("tunnel ready: %s, %s, tunnel %d, tunneling type %s, tunneling version %s, cipher_suite %s\n"), |
|
10913 (m_is_client == true ? "client": "server"), |
|
10914 (m_tls_peap_server_authenticates_client_action == true |
|
10915 ? "mutual": "anonymous client"), |
|
10916 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type), |
|
10917 get_is_tunneled_tls(), |
|
10918 eap_header_string_c::get_eap_type_string(m_eap_type), |
|
10919 eap_tls_trace_string_c::get_peap_version_string(m_peap_version), |
|
10920 eap_tls_trace_string_c::get_cipher_suite_string(m_selected_cipher_suite))); |
|
10921 |
|
10922 } |
|
10923 else if (m_tls_peap_state == tls_peap_state_failure) |
|
10924 { |
|
10925 EAP_TRACE_ERROR( |
|
10926 m_am_tools, |
|
10927 TRACE_FLAGS_DEFAULT, |
|
10928 (EAPL("%s: indicate_state_to_lower_layer(): TLS/PEAP authentication ") |
|
10929 EAPL("FAILED: %s, %s, tunnel %d, tunneling type %s, tunneling version %s, cipher_suite %s\n"), |
|
10930 (m_is_client == true ? "client": "server"), |
|
10931 (m_tls_peap_server_authenticates_client_action == true ? "mutual": "anonymous client"), |
|
10932 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type), |
|
10933 get_is_tunneled_tls(), |
|
10934 eap_header_string_c::get_eap_type_string(m_eap_type), |
|
10935 eap_tls_trace_string_c::get_peap_version_string(m_peap_version), |
|
10936 eap_tls_trace_string_c::get_cipher_suite_string(m_selected_cipher_suite))); |
|
10937 } |
|
10938 |
|
10939 #endif //#if !defined(USE_EAP_TRACE_ALWAYS) |
|
10940 |
|
10941 |
|
10942 eap_state_notification_c notification( |
|
10943 m_am_tools, |
|
10944 &m_send_network_id, |
|
10945 m_is_client, |
|
10946 eap_state_notification_generic, |
|
10947 eap_protocol_layer_internal_type, |
|
10948 0, |
|
10949 tls_peap_state_none, |
|
10950 indicated_state, |
|
10951 0, |
|
10952 false); |
|
10953 get_type_partner()->state_notification(¬ification); |
|
10954 |
|
10955 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10956 return EAP_STATUS_RETURN(m_am_tools, eap_status_ok); |
|
10957 } |
|
10958 |
|
10959 //-------------------------------------------------- |
|
10960 |
|
10961 EAP_FUNC_EXPORT eap_status_e tls_record_c::indicate_messages_processed() |
|
10962 { |
|
10963 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10964 |
|
10965 // Notify lower layer that TLS-messages are processed. |
|
10966 |
|
10967 EAP_TRACE_DEBUG( |
|
10968 m_am_tools, |
|
10969 TRACE_FLAGS_DEFAULT, |
|
10970 (EAPL("TLS: %s: state_function: starts: tls_record_c::indicate_messages_processed(): %s\n"), |
|
10971 (m_is_client == true ? "client": "server"), |
|
10972 eap_tls_trace_string_c::get_state_string(m_tls_peap_state))); |
|
10973 |
|
10974 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::indicate_messages_processed()"); |
|
10975 |
|
10976 eap_state_notification_c notification( |
|
10977 m_am_tools, |
|
10978 &m_send_network_id, |
|
10979 m_is_client, |
|
10980 eap_state_notification_generic, |
|
10981 eap_protocol_layer_internal_type, |
|
10982 0, |
|
10983 tls_peap_state_none, |
|
10984 tls_peap_state_pending_tls_messages_processed, |
|
10985 0, |
|
10986 false); |
|
10987 get_type_partner()->state_notification(¬ification); |
|
10988 |
|
10989 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10990 return EAP_STATUS_RETURN(m_am_tools, eap_status_ok); |
|
10991 } |
|
10992 |
|
10993 //-------------------------------------------------- |
|
10994 |
|
10995 EAP_FUNC_EXPORT eap_status_e tls_record_c::send_tls_message() |
|
10996 { |
|
10997 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
10998 |
|
10999 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
11000 EAP_TRACE_DEBUG( |
|
11001 m_am_tools, |
|
11002 TRACE_FLAGS_DEFAULT, |
|
11003 (EAPL("TLS: %s: send_function: starts: tls_record_c::send_tls_message()\n"), |
|
11004 (m_is_client == true ? "client": "server"))); |
|
11005 |
|
11006 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::send_tls_message()"); |
|
11007 |
|
11008 eap_variable_data_c tls_message_buffer(m_am_tools); |
|
11009 |
|
11010 bool includes_tls_handshake_message = false; |
|
11011 |
|
11012 eap_status_e status = m_new_tls_message.add_message_data( |
|
11013 &tls_message_buffer, |
|
11014 &includes_tls_handshake_message); |
|
11015 if (status != eap_status_ok) |
|
11016 { |
|
11017 m_new_tls_message.reset(); |
|
11018 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11019 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11020 } |
|
11021 |
|
11022 // -------------------------------------------------------------------- |
|
11023 |
|
11024 eap_buf_chain_wr_c sent_packet( |
|
11025 eap_write_buffer, |
|
11026 m_am_tools, |
|
11027 tls_message_buffer.get_data(tls_message_buffer.get_data_length()), |
|
11028 tls_message_buffer.get_data_length(), |
|
11029 false, |
|
11030 false, |
|
11031 0ul); |
|
11032 if (sent_packet.get_is_valid() == false) |
|
11033 { |
|
11034 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
11035 } |
|
11036 |
|
11037 EAP_TRACE_DATA_DEBUG( |
|
11038 m_am_tools, |
|
11039 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
11040 (EAPL("send TLS-message"), |
|
11041 sent_packet.get_data(sent_packet.get_data_length()), |
|
11042 sent_packet.get_data_length())); |
|
11043 |
|
11044 status = get_type_partner()->tls_peap_packet_send( |
|
11045 &sent_packet, |
|
11046 0ul, |
|
11047 sent_packet.get_data_length(), |
|
11048 sent_packet.get_data_length(), |
|
11049 includes_tls_handshake_message |
|
11050 ); |
|
11051 |
|
11052 m_new_tls_message.reset(); |
|
11053 |
|
11054 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11055 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11056 } |
|
11057 |
|
11058 //-------------------------------------------------- |
|
11059 |
|
11060 EAP_FUNC_EXPORT eap_status_e tls_record_c::check_sent_tls_message() |
|
11061 { |
|
11062 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11063 |
|
11064 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
11065 EAP_TRACE_DEBUG( |
|
11066 m_am_tools, |
|
11067 TRACE_FLAGS_DEFAULT, |
|
11068 (EAPL("TLS: %s: send_function: starts: tls_record_c::check_sent_tls_message()\n"), |
|
11069 (m_is_client == true ? "client": "server"))); |
|
11070 |
|
11071 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::check_sent_tls_message()"); |
|
11072 |
|
11073 eap_status_e msg_status = eap_status_authentication_failure; |
|
11074 |
|
11075 if (m_already_in_completion_action_check == true) |
|
11076 { |
|
11077 // This is recursive call. Do not process yet. |
|
11078 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11079 return EAP_STATUS_RETURN(m_am_tools, eap_status_ok); |
|
11080 } |
|
11081 |
|
11082 if (m_force_tls_message_send == true) |
|
11083 { |
|
11084 // There may be an alert message pending. |
|
11085 msg_status = send_tls_message(); |
|
11086 } |
|
11087 else |
|
11088 { |
|
11089 msg_status = are_pending_queries_completed(); |
|
11090 if (msg_status == eap_status_ok) |
|
11091 { |
|
11092 eap_status_e compl_status = completion_action_check(); |
|
11093 |
|
11094 if (compl_status == eap_status_pending_request) |
|
11095 { |
|
11096 // Some asyncronous query is still pending. |
|
11097 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11098 return EAP_STATUS_RETURN(m_am_tools, compl_status); |
|
11099 } |
|
11100 else if (compl_status != eap_status_ok) |
|
11101 { |
|
11102 // There may be Alert message to be sent. |
|
11103 msg_status = compl_status; |
|
11104 } |
|
11105 |
|
11106 |
|
11107 if (m_allow_message_send == true) |
|
11108 { |
|
11109 if (msg_status == eap_status_ok |
|
11110 && m_new_tls_message.get_record_message_count() > 0ul) |
|
11111 { |
|
11112 // We could send the pending TLS-messages. |
|
11113 msg_status = send_tls_message(); |
|
11114 } |
|
11115 else if (m_force_tls_message_send == true // There may be Alert message to be sent. |
|
11116 && m_new_tls_message.get_record_message_count() > 0ul) |
|
11117 { |
|
11118 // We could send the pending TLS-messages. |
|
11119 send_tls_message(); |
|
11120 } |
|
11121 else |
|
11122 { |
|
11123 // No message to sent. |
|
11124 EAP_TRACE_DEBUG( |
|
11125 m_am_tools, |
|
11126 TRACE_FLAGS_DEFAULT, |
|
11127 (EAPL("TLS: %s: send_function: check_sent_tls_message(), ") |
|
11128 EAPL("No message to sent.\n"), |
|
11129 (m_is_client == true ? "client": "server"))); |
|
11130 } |
|
11131 } |
|
11132 |
|
11133 if (msg_status == eap_status_ok |
|
11134 && m_allow_message_send == true) |
|
11135 { |
|
11136 eap_status_e indication_status = indicate_messages_processed(); |
|
11137 if (indication_status != eap_status_ok) |
|
11138 { |
|
11139 // This is an error case. |
|
11140 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11141 return EAP_STATUS_RETURN(m_am_tools, indication_status); |
|
11142 } |
|
11143 } |
|
11144 } |
|
11145 } |
|
11146 |
|
11147 |
|
11148 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11149 return EAP_STATUS_RETURN(m_am_tools, msg_status); |
|
11150 } |
|
11151 |
|
11152 //-------------------------------------------------- |
|
11153 |
|
11154 EAP_FUNC_EXPORT eap_status_e tls_record_c::message_hash_init() |
|
11155 { |
|
11156 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11157 |
|
11158 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
11159 EAP_TRACE_DEBUG( |
|
11160 m_am_tools, |
|
11161 TRACE_FLAGS_DEFAULT, |
|
11162 (EAPL("TLS: %s: hash_function: starts: tls_record_c::message_hash_init()\n"), |
|
11163 (m_is_client == true ? "client": "server"))); |
|
11164 |
|
11165 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::message_hash_init()"); |
|
11166 |
|
11167 eap_status_e status = eap_status_not_supported; |
|
11168 |
|
11169 status = m_message_hash_md5.hash_init(); |
|
11170 if (status != eap_status_ok) |
|
11171 { |
|
11172 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11173 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11174 } |
|
11175 |
|
11176 status = m_message_hash_sha1.hash_init(); |
|
11177 if (status != eap_status_ok) |
|
11178 { |
|
11179 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11180 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11181 } |
|
11182 |
|
11183 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11184 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11185 } |
|
11186 |
|
11187 //-------------------------------------------------- |
|
11188 |
|
11189 EAP_FUNC_EXPORT eap_status_e tls_record_c::message_hash_update( |
|
11190 const bool true_when_parse_message, |
|
11191 const tls_handshake_type_e type, |
|
11192 u8_t * const tls_packet, |
|
11193 const u32_t tls_packet_length) |
|
11194 { |
|
11195 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11196 |
|
11197 #if !defined(USE_EAP_DEBUG_TRACE) |
|
11198 EAP_UNREFERENCED_PARAMETER(true_when_parse_message); |
|
11199 EAP_UNREFERENCED_PARAMETER(type); |
|
11200 #endif |
|
11201 |
|
11202 eap_status_e status = eap_status_not_supported; |
|
11203 |
|
11204 EAP_TRACE_DEBUG( |
|
11205 m_am_tools, |
|
11206 TRACE_FLAGS_DEFAULT, |
|
11207 (EAPL("\n"))); |
|
11208 EAP_TRACE_DEBUG( |
|
11209 m_am_tools, |
|
11210 TRACE_FLAGS_DEFAULT, |
|
11211 (EAPL("TLS: %s: hash_function: starts: tls_record_c::message_hash_update(): handshake type %s, %s\n"), |
|
11212 (m_is_client == true ? "client": "server"), |
|
11213 tls_handshake_header_c::get_tls_handshake_string(type), |
|
11214 (true_when_parse_message == true ? "parse": "create"))); |
|
11215 |
|
11216 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::message_hash_update()"); |
|
11217 |
|
11218 EAP_TRACE_DATA_DEBUG( |
|
11219 m_am_tools, |
|
11220 EAP_TRACE_FLAGS_MESSAGE_DATA, |
|
11221 (EAPL("TLS: message_hash_update()"), |
|
11222 tls_packet, |
|
11223 tls_packet_length)); |
|
11224 |
|
11225 if (tls_packet == 0 |
|
11226 || tls_packet_length == 0ul) |
|
11227 { |
|
11228 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11229 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
11230 } |
|
11231 |
|
11232 status = m_message_hash_md5.hash_update(tls_packet, tls_packet_length); |
|
11233 if (status != eap_status_ok) |
|
11234 { |
|
11235 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11236 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11237 } |
|
11238 |
|
11239 status = m_message_hash_sha1.hash_update(tls_packet, tls_packet_length); |
|
11240 if (status != eap_status_ok) |
|
11241 { |
|
11242 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11243 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11244 } |
|
11245 |
|
11246 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11247 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11248 } |
|
11249 |
|
11250 //-------------------------------------------------- |
|
11251 |
|
11252 EAP_FUNC_EXPORT eap_status_e tls_record_c::message_hash_create( |
|
11253 const bool true_when_parse_message, |
|
11254 const tls_handshake_type_e type, |
|
11255 eap_variable_data_c * const message_hash, |
|
11256 const bool client_originated) |
|
11257 { |
|
11258 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11259 |
|
11260 #if !defined(USE_EAP_DEBUG_TRACE) |
|
11261 EAP_UNREFERENCED_PARAMETER(true_when_parse_message); |
|
11262 #endif |
|
11263 |
|
11264 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
11265 EAP_TRACE_DEBUG( |
|
11266 m_am_tools, |
|
11267 TRACE_FLAGS_DEFAULT, |
|
11268 (EAPL("TLS: %s: hash_function: starts: tls_record_c::message_hash_create(): handshake type %s, %s\n"), |
|
11269 (m_is_client == true ? "client": "server"), |
|
11270 tls_handshake_header_c::get_tls_handshake_string(type), |
|
11271 (true_when_parse_message == true ? "parse": "create"))); |
|
11272 |
|
11273 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::message_hash_create()"); |
|
11274 |
|
11275 eap_status_e status = eap_status_not_supported; |
|
11276 |
|
11277 eap_variable_data_c * message_hash_md5 = 0; |
|
11278 eap_variable_data_c * message_hash_sha1 = 0; |
|
11279 |
|
11280 if (type == tls_handshake_type_certificate_verify) |
|
11281 { |
|
11282 message_hash_md5 = &m_message_hash_md5_certificate_verify; |
|
11283 message_hash_sha1 = &m_message_hash_sha1_certificate_verify; |
|
11284 } |
|
11285 else if (type == tls_handshake_type_finished) |
|
11286 { |
|
11287 if (client_originated == true) |
|
11288 { |
|
11289 message_hash_md5 = &m_client_message_hash_md5_finished; |
|
11290 message_hash_sha1 = &m_client_message_hash_sha1_finished; |
|
11291 } |
|
11292 else |
|
11293 { |
|
11294 message_hash_md5 = &m_server_message_hash_md5_finished; |
|
11295 message_hash_sha1 = &m_server_message_hash_sha1_finished; |
|
11296 } |
|
11297 } |
|
11298 else |
|
11299 { |
|
11300 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11301 return EAP_STATUS_RETURN(m_am_tools, eap_status_wrong_type); |
|
11302 } |
|
11303 |
|
11304 u32_t md5_digest_length = message_hash_md5->get_data_length(); |
|
11305 |
|
11306 u32_t sha1_digest_length = message_hash_sha1->get_data_length(); |
|
11307 |
|
11308 if (cipher_suite_is_TLS_DHE_DSS() == true) |
|
11309 { |
|
11310 md5_digest_length = 0ul; |
|
11311 } |
|
11312 |
|
11313 status = message_hash->set_buffer_length(md5_digest_length+sha1_digest_length); |
|
11314 if (status != eap_status_ok) |
|
11315 { |
|
11316 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11317 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11318 } |
|
11319 message_hash->set_data_length(0ul); |
|
11320 |
|
11321 |
|
11322 |
|
11323 if (type == tls_handshake_type_certificate_verify) |
|
11324 { |
|
11325 if (cipher_suite_is_TLS_RSA() == true |
|
11326 || cipher_suite_is_TLS_DHE_RSA() == true) |
|
11327 { |
|
11328 status = message_hash->add_data(message_hash_md5); |
|
11329 if (status != eap_status_ok) |
|
11330 { |
|
11331 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11332 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11333 } |
|
11334 } |
|
11335 |
|
11336 if (cipher_suite_is_TLS_RSA() == true |
|
11337 || cipher_suite_is_TLS_DHE_DSS() == true |
|
11338 || cipher_suite_is_TLS_DHE_RSA() == true) |
|
11339 { |
|
11340 status = message_hash->add_data(message_hash_sha1); |
|
11341 if (status != eap_status_ok) |
|
11342 { |
|
11343 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11344 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11345 } |
|
11346 } |
|
11347 } |
|
11348 else if (type == tls_handshake_type_finished) |
|
11349 { |
|
11350 status = message_hash->add_data(message_hash_md5); |
|
11351 if (status != eap_status_ok) |
|
11352 { |
|
11353 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11354 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11355 } |
|
11356 |
|
11357 status = message_hash->add_data(message_hash_sha1); |
|
11358 if (status != eap_status_ok) |
|
11359 { |
|
11360 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11361 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11362 } |
|
11363 } |
|
11364 |
|
11365 EAP_TRACE_DATA_DEBUG( |
|
11366 m_am_tools, |
|
11367 TRACE_FLAGS_DEFAULT, |
|
11368 (EAPL("TLS: message_hash_create(): message_hash"), |
|
11369 message_hash->get_data(message_hash->get_data_length()), |
|
11370 message_hash->get_data_length())); |
|
11371 |
|
11372 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11373 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11374 } |
|
11375 |
|
11376 //-------------------------------------------------- |
|
11377 |
|
11378 EAP_FUNC_EXPORT eap_status_e tls_record_c::message_hash_final( |
|
11379 eap_variable_data_c * const md5_digest, |
|
11380 eap_variable_data_c * const sha1_digest) |
|
11381 { |
|
11382 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11383 |
|
11384 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
11385 EAP_TRACE_DEBUG( |
|
11386 m_am_tools, |
|
11387 TRACE_FLAGS_DEFAULT, |
|
11388 (EAPL("TLS: %s: hash_function: starts: tls_record_c::message_hash_final()\n"), |
|
11389 (m_is_client == true ? "client": "server"))); |
|
11390 |
|
11391 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::message_hash_final()"); |
|
11392 |
|
11393 eap_status_e status = eap_status_process_general_error; |
|
11394 |
|
11395 if (md5_digest == 0 |
|
11396 || sha1_digest == 0) |
|
11397 { |
|
11398 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11399 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_parameter); |
|
11400 } |
|
11401 |
|
11402 |
|
11403 { |
|
11404 // The copy of hash context saves original hash context for later use. |
|
11405 // This way we do need store only one SHA1 and MD5 context for all handshake message hashes. |
|
11406 abs_crypto_hash_algorithm_c * const copy_message_hash_md5 = m_message_hash_md5.copy(); |
|
11407 |
|
11408 eap_automatic_variable_c<abs_crypto_hash_algorithm_c> |
|
11409 deletes_copy_message_hash_md5(m_am_tools, copy_message_hash_md5); |
|
11410 |
|
11411 if (copy_message_hash_md5 == 0 |
|
11412 || copy_message_hash_md5->get_is_valid() == false) |
|
11413 { |
|
11414 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11415 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
11416 } |
|
11417 |
|
11418 status = md5_digest->set_buffer_length(copy_message_hash_md5->get_digest_length()); |
|
11419 if (status != eap_status_ok) |
|
11420 { |
|
11421 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11422 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11423 } |
|
11424 md5_digest->set_data_length(copy_message_hash_md5->get_digest_length()); |
|
11425 |
|
11426 u32_t digest_length = md5_digest->get_data_length(); |
|
11427 |
|
11428 status = copy_message_hash_md5->hash_final( |
|
11429 md5_digest->get_data(md5_digest->get_data_length()), |
|
11430 &digest_length); |
|
11431 if (digest_length != copy_message_hash_md5->get_digest_length()) |
|
11432 { |
|
11433 status = eap_status_process_general_error; |
|
11434 } |
|
11435 if (status != eap_status_ok) |
|
11436 { |
|
11437 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11438 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11439 } |
|
11440 } |
|
11441 |
|
11442 |
|
11443 { |
|
11444 // The copy of hash context saves original hash context for later use. |
|
11445 // This way we do need store only one SHA1 and MD5 context for all handshake message hashes. |
|
11446 abs_crypto_hash_algorithm_c * const copy_message_hash_sha1 = m_message_hash_sha1.copy(); |
|
11447 |
|
11448 eap_automatic_variable_c<abs_crypto_hash_algorithm_c> |
|
11449 deletes_copy_message_hash_sha1(m_am_tools, copy_message_hash_sha1); |
|
11450 |
|
11451 if (copy_message_hash_sha1 == 0 |
|
11452 || copy_message_hash_sha1->get_is_valid() == false) |
|
11453 { |
|
11454 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11455 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
11456 } |
|
11457 |
|
11458 status = sha1_digest->set_buffer_length(copy_message_hash_sha1->get_digest_length()); |
|
11459 if (status != eap_status_ok) |
|
11460 { |
|
11461 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11462 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11463 } |
|
11464 sha1_digest->set_data_length(copy_message_hash_sha1->get_digest_length()); |
|
11465 |
|
11466 u32_t digest_length = sha1_digest->get_data_length(); |
|
11467 |
|
11468 status = copy_message_hash_sha1->hash_final( |
|
11469 sha1_digest->get_data(sha1_digest->get_data_length()), |
|
11470 &digest_length); |
|
11471 if (digest_length != copy_message_hash_sha1->get_digest_length()) |
|
11472 { |
|
11473 status = eap_status_process_general_error; |
|
11474 } |
|
11475 if (status != eap_status_ok) |
|
11476 { |
|
11477 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11478 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11479 } |
|
11480 } |
|
11481 |
|
11482 |
|
11483 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11484 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11485 } |
|
11486 |
|
11487 //-------------------------------------------------- |
|
11488 |
|
11489 EAP_FUNC_EXPORT eap_status_e tls_record_c::message_hash_save_certificate_verify() |
|
11490 { |
|
11491 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11492 |
|
11493 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
11494 EAP_TRACE_DEBUG( |
|
11495 m_am_tools, |
|
11496 TRACE_FLAGS_DEFAULT, |
|
11497 (EAPL("TLS: %s: hash_function: starts: tls_record_c::message_hash_save_certificate_verify()\n"), |
|
11498 (m_is_client == true ? "client": "server"))); |
|
11499 |
|
11500 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::message_hash_save_certificate_verify()"); |
|
11501 |
|
11502 eap_status_e status = eap_status_process_general_error; |
|
11503 |
|
11504 status = message_hash_final( |
|
11505 &m_message_hash_md5_certificate_verify, |
|
11506 &m_message_hash_sha1_certificate_verify); |
|
11507 |
|
11508 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11509 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11510 } |
|
11511 |
|
11512 //-------------------------------------------------- |
|
11513 |
|
11514 EAP_FUNC_EXPORT eap_status_e tls_record_c::message_hash_save_finished( |
|
11515 const bool client_originated) |
|
11516 { |
|
11517 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11518 |
|
11519 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
11520 EAP_TRACE_DEBUG( |
|
11521 m_am_tools, |
|
11522 TRACE_FLAGS_DEFAULT, |
|
11523 (EAPL("TLS: %s: hash_function: starts: tls_record_c::message_hash_save_finished()\n"), |
|
11524 (m_is_client == true ? "client": "server"))); |
|
11525 |
|
11526 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::message_hash_save_finished()"); |
|
11527 |
|
11528 eap_variable_data_c *message_hash_md5_finished = &m_client_message_hash_md5_finished; |
|
11529 eap_variable_data_c *message_hash_sha1_finished = &m_client_message_hash_sha1_finished; |
|
11530 |
|
11531 eap_status_e status = eap_status_process_general_error; |
|
11532 |
|
11533 |
|
11534 if (client_originated == false) |
|
11535 { |
|
11536 message_hash_md5_finished = &m_server_message_hash_md5_finished; |
|
11537 message_hash_sha1_finished = &m_server_message_hash_sha1_finished; |
|
11538 } |
|
11539 |
|
11540 status = message_hash_final( |
|
11541 message_hash_md5_finished, |
|
11542 message_hash_sha1_finished); |
|
11543 |
|
11544 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11545 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11546 } |
|
11547 |
|
11548 //-------------------------------------------------- |
|
11549 |
|
11550 EAP_FUNC_EXPORT eap_status_e tls_record_c::message_hash_create_finished( |
|
11551 const bool client_originated_message, |
|
11552 eap_variable_data_c * const message_hash) |
|
11553 { |
|
11554 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11555 |
|
11556 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
11557 EAP_TRACE_DEBUG( |
|
11558 m_am_tools, |
|
11559 TRACE_FLAGS_DEFAULT, |
|
11560 (EAPL("TLS: %s: hash_function: starts: tls_record_c::message_hash_create_finished()\n"), |
|
11561 (m_is_client == true ? "client": "server"))); |
|
11562 |
|
11563 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::message_hash_create_finished()"); |
|
11564 |
|
11565 eap_status_e status = eap_status_not_supported; |
|
11566 |
|
11567 eap_variable_data_c label_finished(m_am_tools); |
|
11568 if (label_finished.get_is_valid() == false) |
|
11569 { |
|
11570 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
11571 } |
|
11572 |
|
11573 if (client_originated_message == true) |
|
11574 { |
|
11575 status = label_finished.add_data( |
|
11576 TLS_CLIENT_FINISHED_LABEL, |
|
11577 TLS_CLIENT_FINISHED_LABEL_LENGTH); |
|
11578 } |
|
11579 else |
|
11580 { |
|
11581 status = label_finished.add_data( |
|
11582 TLS_SERVER_FINISHED_LABEL, |
|
11583 TLS_SERVER_FINISHED_LABEL_LENGTH); |
|
11584 } |
|
11585 |
|
11586 if (status != eap_status_ok) |
|
11587 { |
|
11588 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11589 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11590 } |
|
11591 |
|
11592 eap_variable_data_c hash(m_am_tools); |
|
11593 if (hash.get_is_valid() == false) |
|
11594 { |
|
11595 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
11596 } |
|
11597 |
|
11598 status = message_hash_create( |
|
11599 false, |
|
11600 tls_handshake_type_finished, |
|
11601 &hash, |
|
11602 client_originated_message); |
|
11603 if (status != eap_status_ok) |
|
11604 { |
|
11605 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11606 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11607 } |
|
11608 |
|
11609 |
|
11610 EAP_TRACE_DATA_DEBUG( |
|
11611 m_am_tools, |
|
11612 TRACE_FLAGS_DEFAULT, |
|
11613 (EAPL("TLS: message_hash_create_finished(): m_master_secret"), |
|
11614 m_master_secret.get_data(), |
|
11615 m_master_secret.get_data_length())); |
|
11616 |
|
11617 EAP_TRACE_DATA_DEBUG( |
|
11618 m_am_tools, |
|
11619 TRACE_FLAGS_DEFAULT, |
|
11620 (EAPL("TLS: message_hash_create_finished(): label_finished"), |
|
11621 label_finished.get_data(), |
|
11622 label_finished.get_data_length())); |
|
11623 |
|
11624 EAP_TRACE_DATA_DEBUG( |
|
11625 m_am_tools, |
|
11626 TRACE_FLAGS_DEFAULT, |
|
11627 (EAPL("TLS: message_hash_create_finished(): hash"), |
|
11628 hash.get_data(), |
|
11629 hash.get_data_length())); |
|
11630 |
|
11631 |
|
11632 EAP_TRACE_DEBUG( |
|
11633 m_am_tools, |
|
11634 TRACE_FLAGS_DEFAULT, |
|
11635 (EAPL("TLS: %s: prf_function: tls_prf.tls_prf_output()\n"), |
|
11636 (m_is_client == true ? "client": "server"))); |
|
11637 |
|
11638 crypto_tls_prf_c tls_prf(m_am_tools); |
|
11639 |
|
11640 status = tls_prf.tls_prf_init( |
|
11641 &m_master_secret, |
|
11642 &label_finished, |
|
11643 &hash); |
|
11644 if (status != eap_status_ok) |
|
11645 { |
|
11646 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11647 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11648 } |
|
11649 |
|
11650 status = message_hash->set_buffer_length(TLS_FINISHED_DATA_SIZE); |
|
11651 if (status != eap_status_ok) |
|
11652 { |
|
11653 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11654 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11655 } |
|
11656 message_hash->set_data_length(TLS_FINISHED_DATA_SIZE); |
|
11657 |
|
11658 status = tls_prf.tls_prf_output( |
|
11659 message_hash->get_data(message_hash->get_data_length()), |
|
11660 message_hash->get_data_length()); |
|
11661 if (status != eap_status_ok) |
|
11662 { |
|
11663 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11664 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11665 } |
|
11666 |
|
11667 EAP_TRACE_DATA_DEBUG( |
|
11668 m_am_tools, |
|
11669 TRACE_FLAGS_DEFAULT, |
|
11670 (EAPL("TLS: message_hash_create_finished(): message hash"), |
|
11671 message_hash->get_data(), |
|
11672 message_hash->get_data_length())); |
|
11673 |
|
11674 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11675 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11676 } |
|
11677 |
|
11678 //-------------------------------------------------- |
|
11679 |
|
11680 EAP_FUNC_EXPORT eap_status_e tls_record_c::packet_process( |
|
11681 eap_variable_data_c * const tls_packet, |
|
11682 const u8_t received_eap_identifier) |
|
11683 { |
|
11684 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11685 |
|
11686 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
11687 |
|
11688 tls_identity_privacy_handshake_state_e tmp_identity_privacy_handshake_state = |
|
11689 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
11690 m_tls_identity_privacy_handshake_state; |
|
11691 #else |
|
11692 tls_identity_privacy_handshake_state_none; |
|
11693 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
11694 EAP_UNREFERENCED_PARAMETER(tmp_identity_privacy_handshake_state); |
|
11695 |
|
11696 EAP_TRACE_DEBUG( |
|
11697 m_am_tools, |
|
11698 TRACE_FLAGS_DEFAULT, |
|
11699 (EAPL("TLS: %s: message_function: starts: tls_record_c::packet_process(): state %s, privacy_handshake_state=%d=%s, session_type=%s\n"), |
|
11700 (m_is_client == true ? "client": "server"), |
|
11701 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
11702 tmp_identity_privacy_handshake_state, |
|
11703 eap_tls_trace_string_c::get_tls_identity_privacy_handshake_state_string(tmp_identity_privacy_handshake_state), |
|
11704 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type))); |
|
11705 |
|
11706 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::packet_process()"); |
|
11707 |
|
11708 m_received_tls_message.reset(); |
|
11709 |
|
11710 eap_status_e status = m_received_tls_message.set_tls_message_data( |
|
11711 tls_packet, |
|
11712 received_eap_identifier); |
|
11713 if (status != eap_status_ok) |
|
11714 { |
|
11715 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11716 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11717 } |
|
11718 |
|
11719 eap_automatic_simple_value_c<bool> restore_allow_message_send( |
|
11720 m_am_tools, |
|
11721 &m_allow_message_send, |
|
11722 true); |
|
11723 |
|
11724 // Packet send is delayed until after the process_tls_message() function returns. |
|
11725 m_allow_message_send = false; |
|
11726 |
|
11727 status = process_tls_message(); |
|
11728 |
|
11729 m_allow_message_send = true; |
|
11730 |
|
11731 |
|
11732 if (status != eap_status_pending_request) |
|
11733 { |
|
11734 // Note this call will return eap_status_pending_request if any asyncronous call is pending. |
|
11735 eap_status_e send_status = check_sent_tls_message(); |
|
11736 if (send_status != eap_status_ok) |
|
11737 { |
|
11738 status = send_status; |
|
11739 } |
|
11740 } |
|
11741 |
|
11742 if (status == eap_status_success |
|
11743 && m_tls_peap_state != tls_peap_state_tls_success) |
|
11744 { |
|
11745 status = eap_status_ok; |
|
11746 } |
|
11747 |
|
11748 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11749 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11750 } |
|
11751 |
|
11752 //-------------------------------------------------- |
|
11753 |
|
11754 EAP_FUNC_EXPORT eap_status_e tls_record_c::plain_eap_success_failure_packet_received( |
|
11755 const eap_am_network_id_c * const receive_network_id, |
|
11756 const eap_code_value_e received_eap_code, |
|
11757 const u8_t received_eap_identifier) |
|
11758 { |
|
11759 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11760 |
|
11761 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
11762 EAP_TRACE_DEBUG( |
|
11763 m_am_tools, |
|
11764 TRACE_FLAGS_DEFAULT, |
|
11765 (EAPL("TLS: %s: message_function: starts: tls_record_c::plain_eap_success_failure_packet_received(): state %s, m_tls_session_type=%s\n"), |
|
11766 (m_is_client == true ? "client": "server"), |
|
11767 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
11768 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type))); |
|
11769 |
|
11770 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::plain_eap_success_failure_packet_received()"); |
|
11771 |
|
11772 eap_status_e status(eap_status_ok); |
|
11773 |
|
11774 if (received_eap_code == eap_code_success |
|
11775 && m_eap_type == eap_type_peap |
|
11776 && m_peap_version == peap_version_1 |
|
11777 && m_use_tppd_tls_peap == true) |
|
11778 { |
|
11779 status = m_am_tls_services->save_tls_session( |
|
11780 &m_session_id, |
|
11781 &m_master_secret, |
|
11782 m_selected_cipher_suite |
|
11783 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
11784 , tls_extension_c::get_tls_extension( |
|
11785 tls_extension_type_session_ticket, |
|
11786 &m_received_tls_extensions, |
|
11787 m_am_tools) |
|
11788 #endif //#if defined(USE_EAP_TLS_SESSION_TICKET) |
|
11789 ); |
|
11790 if (status != eap_status_ok) |
|
11791 { |
|
11792 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11793 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11794 } |
|
11795 } |
|
11796 #if defined(USE_FAST_EAP_TYPE) |
|
11797 else if (m_eap_type == eap_type_fast) |
|
11798 { |
|
11799 if (received_eap_code == eap_code_success |
|
11800 && m_tls_peap_state == tls_peap_state_tls_success |
|
11801 && (m_tls_session_type == tls_session_type_original_session_resumption |
|
11802 || m_tls_session_type == tls_session_type_stateless_session_resumption)) |
|
11803 { |
|
11804 eap_state_variable_e current_state(eap_state_authentication_finished_successfully); |
|
11805 |
|
11806 // Here we swap the addresses. |
|
11807 eap_am_network_id_c send_network_id(m_am_tools, |
|
11808 receive_network_id->get_destination_id(), |
|
11809 receive_network_id->get_source_id(), |
|
11810 receive_network_id->get_type()); |
|
11811 |
|
11812 eap_state_notification_c notification( |
|
11813 m_am_tools, |
|
11814 &send_network_id, |
|
11815 m_is_client, |
|
11816 eap_state_notification_eap, |
|
11817 eap_protocol_layer_eap, |
|
11818 m_eap_type, |
|
11819 eap_state_none, |
|
11820 current_state, |
|
11821 m_received_eap_identifier, |
|
11822 false); |
|
11823 |
|
11824 state_notification(¬ification); |
|
11825 } |
|
11826 else |
|
11827 { |
|
11828 status = m_application->plain_eap_success_failure_packet_received( |
|
11829 receive_network_id, |
|
11830 received_eap_code, |
|
11831 received_eap_identifier); |
|
11832 } |
|
11833 } |
|
11834 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
11835 else if (m_eap_type == eap_type_peap |
|
11836 || m_eap_type == eap_type_ttls |
|
11837 ) |
|
11838 { |
|
11839 status = m_application->plain_eap_success_failure_packet_received( |
|
11840 receive_network_id, |
|
11841 received_eap_code, |
|
11842 received_eap_identifier); |
|
11843 } |
|
11844 |
|
11845 if (status != eap_status_pending_request) |
|
11846 { |
|
11847 // Note this call will return eap_status_pending_request if any asyncronous call is pending. |
|
11848 eap_status_e send_status = check_sent_tls_message(); |
|
11849 if (send_status != eap_status_ok) |
|
11850 { |
|
11851 status = send_status; |
|
11852 } |
|
11853 } |
|
11854 |
|
11855 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11856 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11857 } |
|
11858 |
|
11859 //-------------------------------------------------- |
|
11860 |
|
11861 EAP_FUNC_EXPORT eap_status_e tls_record_c::empty_ack_packet_received( |
|
11862 const eap_am_network_id_c * const receive_network_id, |
|
11863 const u8_t received_eap_identifier) |
|
11864 { |
|
11865 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11866 |
|
11867 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
11868 EAP_TRACE_DEBUG( |
|
11869 m_am_tools, |
|
11870 TRACE_FLAGS_DEFAULT, |
|
11871 (EAPL("TLS: %s: message_function: starts: tls_record_c::empty_ack_packet_received(): state %s\n"), |
|
11872 (m_is_client == true ? "client": "server"), |
|
11873 eap_tls_trace_string_c::get_state_string(m_tls_peap_state))); |
|
11874 |
|
11875 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::empty_ack_packet_received()"); |
|
11876 |
|
11877 eap_status_e status(eap_status_not_supported); |
|
11878 |
|
11879 if (m_eap_type == eap_type_ttls) |
|
11880 { |
|
11881 status = m_application->empty_ack_packet_received( |
|
11882 receive_network_id, |
|
11883 received_eap_identifier); |
|
11884 |
|
11885 if (status != eap_status_pending_request) |
|
11886 { |
|
11887 // Note this call will return eap_status_pending_request if any asyncronous call is pending. |
|
11888 eap_status_e send_status = check_sent_tls_message(); |
|
11889 if (send_status != eap_status_ok) |
|
11890 { |
|
11891 status = send_status; |
|
11892 } |
|
11893 } |
|
11894 } |
|
11895 |
|
11896 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11897 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11898 } |
|
11899 |
|
11900 //-------------------------------------------------- |
|
11901 |
|
11902 EAP_FUNC_EXPORT bool tls_record_c::get_is_valid() |
|
11903 { |
|
11904 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11905 |
|
11906 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11907 return m_is_valid; |
|
11908 } |
|
11909 |
|
11910 //-------------------------------------------------- |
|
11911 |
|
11912 EAP_FUNC_EXPORT eap_status_e tls_record_c::reset() |
|
11913 { |
|
11914 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11915 |
|
11916 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
11917 EAP_TRACE_DEBUG( |
|
11918 m_am_tools, |
|
11919 TRACE_FLAGS_DEFAULT, |
|
11920 (EAPL("TLS: this = 0x%08x, %s: function: starts: tls_record_c::reset()\n"), |
|
11921 this, |
|
11922 (m_is_client == true ? "client": "server"))); |
|
11923 |
|
11924 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::reset()"); |
|
11925 |
|
11926 completion_action_clenup(); |
|
11927 |
|
11928 { |
|
11929 m_received_tls_message.reset(); |
|
11930 m_new_tls_message.reset(); |
|
11931 m_message_hash_md5.hash_cleanup(); |
|
11932 m_message_hash_sha1.hash_cleanup(); |
|
11933 m_message_hash_md5_certificate_verify.reset(); |
|
11934 m_message_hash_sha1_certificate_verify.reset(); |
|
11935 m_client_message_hash_md5_finished.reset(); |
|
11936 m_client_message_hash_sha1_finished.reset(); |
|
11937 m_server_message_hash_md5_finished.reset(); |
|
11938 m_server_message_hash_sha1_finished.reset(); |
|
11939 m_client_handshake_random_value.reset(); |
|
11940 m_server_handshake_random_value.reset(); |
|
11941 m_session_id.reset(); |
|
11942 m_master_secret.reset(); |
|
11943 m_eap_master_session_key.reset(); |
|
11944 m_send_mac_key.reset(); |
|
11945 m_receive_mac_key.reset(); |
|
11946 m_send_encryption_key.reset(); |
|
11947 m_receive_encryption_key.reset(); |
|
11948 m_send_iv.reset(); |
|
11949 m_receive_iv.reset(); |
|
11950 m_own_private_dhe_key.reset(); |
|
11951 m_own_public_dhe_key.reset(); |
|
11952 m_peer_public_dhe_key.reset(); |
|
11953 m_shared_dh_key.reset(); |
|
11954 m_dhe_prime.reset(); |
|
11955 m_dhe_group_generator.reset(); |
|
11956 m_signed_message_hash.reset(); |
|
11957 m_premaster_secret.reset(); |
|
11958 #if defined(USE_FAST_EAP_TYPE) |
|
11959 m_eap_fast_pac_key.reset(); |
|
11960 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
11961 m_own_encrypted_premaster_secret.reset(); |
|
11962 m_proposed_cipher_suites.reset(); |
|
11963 m_proposed_compression_methods.reset(); |
|
11964 m_NAI_realm.reset(); |
|
11965 m_own_certificate_chain.reset(); |
|
11966 m_own_certificate_types.reset(); |
|
11967 m_own_certificate_authorities.reset(); |
|
11968 m_peer_certificate_chain.reset(); |
|
11969 m_peer_certificate_chain_result = eap_status_illegal_certificate; |
|
11970 m_verify_signature = eap_status_authentication_failure; |
|
11971 m_peer_certificate_types.reset(); |
|
11972 m_peer_certificate_authorities.reset(); |
|
11973 } |
|
11974 |
|
11975 eap_status_e status = message_hash_init(); |
|
11976 if (status != eap_status_ok) |
|
11977 { |
|
11978 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11979 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11980 } |
|
11981 |
|
11982 set_selected_cipher_suite(tls_cipher_suites_none); |
|
11983 m_selected_compression_method = tls_compression_method_none; |
|
11984 |
|
11985 status = set_receive_cipher_suite(tls_cipher_suites_TLS_NULL_WITH_NULL_NULL); |
|
11986 if (status != eap_status_ok) |
|
11987 { |
|
11988 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11989 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11990 } |
|
11991 m_receive_compression_method = tls_compression_method_null; |
|
11992 |
|
11993 status = set_send_cipher_suite(tls_cipher_suites_TLS_NULL_WITH_NULL_NULL); |
|
11994 if (status != eap_status_ok) |
|
11995 { |
|
11996 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
11997 return EAP_STATUS_RETURN(m_am_tools, status); |
|
11998 } |
|
11999 m_send_compression_method = tls_compression_method_null; |
|
12000 |
|
12001 m_completion_queue.reset(); |
|
12002 |
|
12003 m_send_record_sequence_number = 0ul; |
|
12004 m_receive_record_sequence_number = 0ul; |
|
12005 |
|
12006 m_key_material_generated = false; |
|
12007 |
|
12008 m_force_tls_message_send = false; |
|
12009 |
|
12010 if (m_is_client == false) |
|
12011 { |
|
12012 // Server |
|
12013 // NOTE: set_state() function cannot reset state. |
|
12014 m_tls_peap_state = tls_peap_state_wait_handshake_type_client_hello; |
|
12015 } |
|
12016 else |
|
12017 { |
|
12018 // Client |
|
12019 // NOTE: set_state() function cannot reset state. |
|
12020 m_tls_peap_state = tls_peap_state_wait_tls_start; |
|
12021 } |
|
12022 |
|
12023 m_tunneled_eap_type_authentication_state = eap_state_none; |
|
12024 |
|
12025 m_tls_peap_server_authenticates_client_action = true; |
|
12026 if (m_is_client == false |
|
12027 && m_tls_peap_server_authenticates_client_config_server == false) |
|
12028 { |
|
12029 m_tls_peap_server_authenticates_client_action = false; |
|
12030 } |
|
12031 |
|
12032 m_tls_peap_server_requested_client_certificate = false; |
|
12033 |
|
12034 m_could_send_fatal_alert_message = true; |
|
12035 m_could_send_warning_alert_message = true; |
|
12036 |
|
12037 if (m_application != 0) |
|
12038 { |
|
12039 m_application->reset(); |
|
12040 } |
|
12041 |
|
12042 reset_block_ciphers(true); |
|
12043 reset_block_ciphers(false); |
|
12044 |
|
12045 reset_stream_ciphers(true); |
|
12046 reset_stream_ciphers(false); |
|
12047 |
|
12048 reset_hmac_algorithms(true); |
|
12049 reset_hmac_algorithms(false); |
|
12050 |
|
12051 m_use_tppd_tls_peap = false; |
|
12052 m_use_tppd_peapv1_acknowledge_hack = false; |
|
12053 |
|
12054 m_will_receive_new_session_ticket = false; |
|
12055 |
|
12056 #if defined(USE_FAST_EAP_TYPE) |
|
12057 m_remove_tunnel_pac = false; |
|
12058 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
12059 |
|
12060 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
12061 set_tls_identity_privacy_handshake_state(tls_identity_privacy_handshake_state_none); |
|
12062 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
12063 |
|
12064 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12065 return EAP_STATUS_RETURN(m_am_tools, eap_status_ok); |
|
12066 } |
|
12067 |
|
12068 |
|
12069 //-------------------------------------------------- |
|
12070 |
|
12071 EAP_FUNC_EXPORT u32_t tls_record_c::get_key_expansion_size( |
|
12072 u32_t * const mac_key_length, |
|
12073 u32_t * const encryption_key_length, |
|
12074 u32_t * const iv_length, |
|
12075 u32_t * const session_key_seed_length, |
|
12076 u32_t * const mschapv2_challenges_length |
|
12077 ) |
|
12078 { |
|
12079 u32_t length = 0ul; |
|
12080 |
|
12081 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
12082 EAP_TRACE_DEBUG( |
|
12083 m_am_tools, |
|
12084 TRACE_FLAGS_DEFAULT, |
|
12085 (EAPL("TLS: %s: key_function: starts: tls_record_c::get_key_expansion_size()\n"), |
|
12086 (m_is_client == true ? "client": "server"))); |
|
12087 |
|
12088 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::get_key_expansion_size()"); |
|
12089 |
|
12090 *mac_key_length = 0ul; |
|
12091 *encryption_key_length = 0ul; |
|
12092 *iv_length = 0ul; |
|
12093 *session_key_seed_length = 0ul; |
|
12094 *mschapv2_challenges_length = 0ul; |
|
12095 |
|
12096 if (cipher_suite_is_3DES_EDE_CBC_SHA(m_selected_cipher_suite) == true) |
|
12097 { |
|
12098 crypto_3des_ede_c ede_3des(m_am_tools); |
|
12099 |
|
12100 crypto_sha1_c sha1(m_am_tools); |
|
12101 crypto_hmac_c hmac_sha1(m_am_tools, &sha1, false); |
|
12102 |
|
12103 if (hmac_sha1.get_is_valid() == false) |
|
12104 { |
|
12105 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12106 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12107 } |
|
12108 |
|
12109 |
|
12110 eap_variable_data_c tmp_key(m_am_tools); |
|
12111 if (tmp_key.get_is_valid() == false) |
|
12112 { |
|
12113 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12114 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12115 } |
|
12116 |
|
12117 eap_status_e status = tmp_key.add_data("", 0ul); |
|
12118 if (status != eap_status_ok) |
|
12119 { |
|
12120 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12121 return 0; |
|
12122 } |
|
12123 |
|
12124 status = hmac_sha1.hmac_set_key(&tmp_key); |
|
12125 if (status != eap_status_ok) |
|
12126 { |
|
12127 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12128 return 0; |
|
12129 } |
|
12130 |
|
12131 length = 2ul * hmac_sha1.get_digest_length() |
|
12132 + 2ul * ede_3des.get_key_length() |
|
12133 + 2ul * ede_3des.get_block_size(); |
|
12134 |
|
12135 *mac_key_length = hmac_sha1.get_digest_length(); |
|
12136 *encryption_key_length = ede_3des.get_key_length(); |
|
12137 *iv_length = ede_3des.get_block_size(); |
|
12138 } |
|
12139 else if (cipher_suite_is_AES_128_CBC_SHA(m_selected_cipher_suite) == true) |
|
12140 { |
|
12141 crypto_aes_c aes(m_am_tools); |
|
12142 |
|
12143 crypto_sha1_c sha1(m_am_tools); |
|
12144 crypto_hmac_c hmac_sha1(m_am_tools, &sha1, false); |
|
12145 |
|
12146 if (hmac_sha1.get_is_valid() == false) |
|
12147 { |
|
12148 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12149 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12150 } |
|
12151 |
|
12152 eap_variable_data_c tmp_key(m_am_tools); |
|
12153 if (tmp_key.get_is_valid() == false) |
|
12154 { |
|
12155 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12156 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12157 } |
|
12158 |
|
12159 eap_status_e status = tmp_key.add_data("", 0ul); |
|
12160 if (status != eap_status_ok) |
|
12161 { |
|
12162 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12163 return 0; |
|
12164 } |
|
12165 |
|
12166 status = hmac_sha1.hmac_set_key(&tmp_key); |
|
12167 if (status != eap_status_ok) |
|
12168 { |
|
12169 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12170 return 0; |
|
12171 } |
|
12172 |
|
12173 length = 2ul * hmac_sha1.get_digest_length() |
|
12174 + 2ul * aes.get_key_length() |
|
12175 + 2ul * aes.get_block_size(); |
|
12176 |
|
12177 *mac_key_length = hmac_sha1.get_digest_length(); |
|
12178 *encryption_key_length = aes.get_key_length(); |
|
12179 *iv_length = aes.get_block_size(); |
|
12180 } |
|
12181 else if (cipher_suite_is_RC4_128_MD5(m_selected_cipher_suite) == true) |
|
12182 { |
|
12183 crypto_md5_c md5(m_am_tools); |
|
12184 crypto_hmac_c hmac_md5(m_am_tools, &md5, false); |
|
12185 |
|
12186 if (hmac_md5.get_is_valid() == false) |
|
12187 { |
|
12188 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12189 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12190 } |
|
12191 |
|
12192 eap_variable_data_c tmp_key(m_am_tools); |
|
12193 if (tmp_key.get_is_valid() == false) |
|
12194 { |
|
12195 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12196 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12197 } |
|
12198 |
|
12199 eap_status_e status = tmp_key.add_data("", 0ul); |
|
12200 if (status != eap_status_ok) |
|
12201 { |
|
12202 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12203 return 0; |
|
12204 } |
|
12205 |
|
12206 status = hmac_md5.hmac_set_key(&tmp_key); |
|
12207 if (status != eap_status_ok) |
|
12208 { |
|
12209 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12210 return 0; |
|
12211 } |
|
12212 |
|
12213 length = 2ul * hmac_md5.get_digest_length() |
|
12214 + 2ul * TLS_RC4_128_KEY_LENGTH |
|
12215 + 2ul * TLS_RC4_128_IV_LENGTH; |
|
12216 |
|
12217 *mac_key_length = hmac_md5.get_digest_length(); |
|
12218 *encryption_key_length = TLS_RC4_128_KEY_LENGTH; |
|
12219 *iv_length = TLS_RC4_128_IV_LENGTH; |
|
12220 } |
|
12221 else if (cipher_suite_is_RC4_128_SHA(m_selected_cipher_suite) == true) |
|
12222 { |
|
12223 crypto_sha1_c sha1(m_am_tools); |
|
12224 crypto_hmac_c hmac_sha1(m_am_tools, &sha1, false); |
|
12225 |
|
12226 if (hmac_sha1.get_is_valid() == false) |
|
12227 { |
|
12228 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12229 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12230 } |
|
12231 |
|
12232 eap_variable_data_c tmp_key(m_am_tools); |
|
12233 if (tmp_key.get_is_valid() == false) |
|
12234 { |
|
12235 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12236 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12237 } |
|
12238 |
|
12239 eap_status_e status = tmp_key.add_data("", 0ul); |
|
12240 if (status != eap_status_ok) |
|
12241 { |
|
12242 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12243 return 0; |
|
12244 } |
|
12245 |
|
12246 status = hmac_sha1.hmac_set_key(&tmp_key); |
|
12247 if (status != eap_status_ok) |
|
12248 { |
|
12249 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12250 return 0; |
|
12251 } |
|
12252 |
|
12253 length = 2ul * hmac_sha1.get_digest_length() |
|
12254 + 2ul * TLS_RC4_128_KEY_LENGTH |
|
12255 + 2ul * TLS_RC4_128_IV_LENGTH; |
|
12256 |
|
12257 *mac_key_length = hmac_sha1.get_digest_length(); |
|
12258 *encryption_key_length = TLS_RC4_128_KEY_LENGTH; |
|
12259 *iv_length = TLS_RC4_128_IV_LENGTH; |
|
12260 } |
|
12261 |
|
12262 #if defined(USE_FAST_EAP_TYPE) |
|
12263 if (m_eap_type == eap_type_fast) |
|
12264 { |
|
12265 *session_key_seed_length = EAP_FAST_SESSION_KEY_SEED_LENGTH; |
|
12266 length += EAP_FAST_SESSION_KEY_SEED_LENGTH; |
|
12267 |
|
12268 if (m_tls_session_type == tls_session_type_eap_fast_server_unauthenticated_provisioning_mode_ADHP |
|
12269 && m_selected_cipher_suite == tls_cipher_suites_TLS_DH_anon_WITH_AES_128_CBC_SHA) |
|
12270 { |
|
12271 *mschapv2_challenges_length = 2ul * EAP_FAST_MSCHAPV2_CHALLENGE_LENGTH; |
|
12272 length += 2ul * EAP_FAST_MSCHAPV2_CHALLENGE_LENGTH; |
|
12273 } |
|
12274 } |
|
12275 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
12276 |
|
12277 return length; |
|
12278 } |
|
12279 |
|
12280 //-------------------------------------------------- |
|
12281 |
|
12282 EAP_FUNC_EXPORT eap_status_e tls_record_c::cipher_suite_initialization_cbc( |
|
12283 abs_crypto_cbc_block_algorithm_c ** const member_cbc_crypto_block_algorithm, |
|
12284 abs_crypto_block_algorithm_c * const crypto_block_algorithm, |
|
12285 const eap_variable_data_c * const member_iv, |
|
12286 const eap_variable_data_c * const member_key, |
|
12287 const bool true_when_encrypt) |
|
12288 { |
|
12289 EAP_TRACE_DEBUG( |
|
12290 m_am_tools, |
|
12291 TRACE_FLAGS_DEFAULT, |
|
12292 (EAPL("TLS: %s: key_function: starts: tls_record_c::cipher_suite_initialization_cbc()\n"), |
|
12293 (m_is_client == true ? "client": "server"))); |
|
12294 |
|
12295 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::cipher_suite_initialization_cbc()"); |
|
12296 |
|
12297 eap_automatic_variable_c<abs_crypto_block_algorithm_c> |
|
12298 block_algorithm_remove(m_am_tools, crypto_block_algorithm); |
|
12299 |
|
12300 if (crypto_block_algorithm == 0) |
|
12301 { |
|
12302 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12303 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12304 } |
|
12305 |
|
12306 if (crypto_block_algorithm->get_is_valid() == false) |
|
12307 { |
|
12308 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12309 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12310 } |
|
12311 |
|
12312 if (member_cbc_crypto_block_algorithm == 0) |
|
12313 { |
|
12314 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12315 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12316 } |
|
12317 |
|
12318 *member_cbc_crypto_block_algorithm = new crypto_cbc_c( |
|
12319 m_am_tools, |
|
12320 crypto_block_algorithm, |
|
12321 true); |
|
12322 |
|
12323 if (*member_cbc_crypto_block_algorithm == 0 |
|
12324 || (*member_cbc_crypto_block_algorithm)->get_is_valid() == false) |
|
12325 { |
|
12326 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12327 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12328 } |
|
12329 |
|
12330 // After this point *member_cbc_crypto_block_algorithm will delete crypto_block_algorithm. |
|
12331 block_algorithm_remove.do_not_free_variable(); |
|
12332 |
|
12333 if ((*member_cbc_crypto_block_algorithm)->get_is_valid() == false) |
|
12334 { |
|
12335 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12336 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12337 } |
|
12338 |
|
12339 eap_status_e status = eap_status_process_general_error; |
|
12340 |
|
12341 |
|
12342 EAP_TRACE_DATA_DEBUG( |
|
12343 m_am_tools, |
|
12344 TRACE_FLAGS_DEFAULT, |
|
12345 (EAPL("CBC member_iv"), |
|
12346 member_iv->get_data(member_iv->get_data_length()), |
|
12347 member_iv->get_data_length())); |
|
12348 |
|
12349 EAP_TRACE_DATA_DEBUG( |
|
12350 m_am_tools, |
|
12351 TRACE_FLAGS_DEFAULT, |
|
12352 (EAPL("CBC member_key"), |
|
12353 member_key->get_data(member_key->get_data_length()), |
|
12354 member_key->get_data_length())); |
|
12355 |
|
12356 |
|
12357 if (true_when_encrypt == true) |
|
12358 { |
|
12359 status = (*member_cbc_crypto_block_algorithm)->set_encryption_key( |
|
12360 member_iv->get_data(member_iv->get_data_length()), |
|
12361 member_iv->get_data_length(), |
|
12362 member_key->get_data(member_key->get_data_length()), |
|
12363 member_key->get_data_length()); |
|
12364 } |
|
12365 else |
|
12366 { |
|
12367 status = (*member_cbc_crypto_block_algorithm)->set_decryption_key( |
|
12368 member_iv->get_data(member_iv->get_data_length()), |
|
12369 member_iv->get_data_length(), |
|
12370 member_key->get_data(member_key->get_data_length()), |
|
12371 member_key->get_data_length()); |
|
12372 } |
|
12373 |
|
12374 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12375 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12376 } |
|
12377 |
|
12378 //-------------------------------------------------- |
|
12379 |
|
12380 EAP_FUNC_EXPORT eap_status_e tls_record_c::cipher_suite_initialization_hmac( |
|
12381 abs_crypto_hmac_algorithm_c * const member_hmac_algorithm, |
|
12382 const eap_variable_data_c * const member_key) |
|
12383 { |
|
12384 EAP_TRACE_DEBUG( |
|
12385 m_am_tools, |
|
12386 TRACE_FLAGS_DEFAULT, |
|
12387 (EAPL("TLS: %s: key_function: starts: tls_record_c::cipher_suite_initialization_hmac()\n"), |
|
12388 (m_is_client == true ? "client": "server"))); |
|
12389 |
|
12390 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::cipher_suite_initialization_hmac()"); |
|
12391 |
|
12392 if (member_hmac_algorithm == 0) |
|
12393 { |
|
12394 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12395 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12396 } |
|
12397 |
|
12398 if (member_hmac_algorithm->get_is_valid() == false) |
|
12399 { |
|
12400 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12401 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12402 } |
|
12403 |
|
12404 eap_status_e status = eap_status_process_general_error; |
|
12405 |
|
12406 EAP_TRACE_DATA_DEBUG( |
|
12407 m_am_tools, |
|
12408 TRACE_FLAGS_DEFAULT, |
|
12409 (EAPL("HMAC member_key"), |
|
12410 member_key->get_data(member_key->get_data_length()), |
|
12411 member_key->get_data_length())); |
|
12412 |
|
12413 status = member_hmac_algorithm->hmac_set_key( |
|
12414 member_key); |
|
12415 |
|
12416 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12417 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12418 } |
|
12419 |
|
12420 //-------------------------------------------------- |
|
12421 |
|
12422 EAP_FUNC_EXPORT eap_status_e tls_record_c::cipher_suite_initialization_stream( |
|
12423 abs_crypto_stream_algorithm_c * const member_crypto_stream_algorithm, |
|
12424 const eap_variable_data_c * const member_key, |
|
12425 const bool /* true_when_encrypt */) |
|
12426 { |
|
12427 EAP_TRACE_DEBUG( |
|
12428 m_am_tools, |
|
12429 TRACE_FLAGS_DEFAULT, |
|
12430 (EAPL("TLS: %s: key_function: starts: tls_record_c::cipher_suite_initialization_stream()\n"), |
|
12431 (m_is_client == true ? "client": "server"))); |
|
12432 |
|
12433 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::cipher_suite_initialization_stream()"); |
|
12434 |
|
12435 if (member_crypto_stream_algorithm == 0) |
|
12436 { |
|
12437 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12438 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12439 } |
|
12440 |
|
12441 if (member_crypto_stream_algorithm->get_is_valid() == false) |
|
12442 { |
|
12443 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12444 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12445 } |
|
12446 |
|
12447 EAP_TRACE_DATA_DEBUG( |
|
12448 m_am_tools, |
|
12449 TRACE_FLAGS_DEFAULT, |
|
12450 (EAPL("STREAM member_key"), |
|
12451 member_key->get_data(member_key->get_data_length()), |
|
12452 member_key->get_data_length())); |
|
12453 |
|
12454 eap_status_e status = member_crypto_stream_algorithm->set_key(member_key); |
|
12455 if (status != eap_status_ok) |
|
12456 { |
|
12457 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12458 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12459 } |
|
12460 |
|
12461 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12462 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12463 } |
|
12464 |
|
12465 //-------------------------------------------------- |
|
12466 |
|
12467 EAP_FUNC_EXPORT eap_status_e tls_record_c::cipher_suite_initialization_hmac_sha1(const bool send_when_true) |
|
12468 { |
|
12469 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
12470 EAP_TRACE_DEBUG( |
|
12471 m_am_tools, |
|
12472 TRACE_FLAGS_DEFAULT, |
|
12473 (EAPL("TLS: %s: key_function: starts: tls_record_c::cipher_suite_initialization_hmac_sha1()\n"), |
|
12474 (m_is_client == true ? "client": "server"))); |
|
12475 |
|
12476 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::cipher_suite_initialization_hmac_sha1()"); |
|
12477 |
|
12478 reset_hmac_algorithms(send_when_true); |
|
12479 |
|
12480 eap_status_e status = eap_status_ok; |
|
12481 |
|
12482 if (send_when_true == true) |
|
12483 { |
|
12484 crypto_sha1_c * const sha1 = new crypto_sha1_c(m_am_tools); |
|
12485 if (sha1 == 0) |
|
12486 { |
|
12487 delete sha1; |
|
12488 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12489 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12490 } |
|
12491 |
|
12492 m_send_hmac_algorithm = new crypto_hmac_c(m_am_tools, sha1, true); |
|
12493 |
|
12494 status = cipher_suite_initialization_hmac( |
|
12495 m_send_hmac_algorithm, |
|
12496 &m_send_mac_key); |
|
12497 if (status != eap_status_ok) |
|
12498 { |
|
12499 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12500 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12501 } |
|
12502 } |
|
12503 else |
|
12504 { |
|
12505 crypto_sha1_c * const sha1 = new crypto_sha1_c(m_am_tools); |
|
12506 if (sha1 == 0) |
|
12507 { |
|
12508 delete sha1; |
|
12509 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12510 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12511 } |
|
12512 |
|
12513 m_receive_hmac_algorithm = new crypto_hmac_c(m_am_tools, sha1, true); |
|
12514 |
|
12515 status = cipher_suite_initialization_hmac( |
|
12516 m_receive_hmac_algorithm, |
|
12517 &m_receive_mac_key); |
|
12518 if (status != eap_status_ok) |
|
12519 { |
|
12520 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12521 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12522 } |
|
12523 } |
|
12524 |
|
12525 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12526 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12527 } |
|
12528 |
|
12529 //-------------------------------------------------- |
|
12530 |
|
12531 EAP_FUNC_EXPORT eap_status_e tls_record_c::cipher_suite_initialization_hmac_md5(const bool send_when_true) |
|
12532 { |
|
12533 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
12534 EAP_TRACE_DEBUG( |
|
12535 m_am_tools, |
|
12536 TRACE_FLAGS_DEFAULT, |
|
12537 (EAPL("TLS: %s: key_function: starts: cipher_suite_initialization_hmac_md5()\n"), |
|
12538 (m_is_client == true ? "client": "server"))); |
|
12539 |
|
12540 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::cipher_suite_initialization_hmac_md5()"); |
|
12541 |
|
12542 reset_hmac_algorithms(send_when_true); |
|
12543 |
|
12544 eap_status_e status = eap_status_ok; |
|
12545 |
|
12546 if (send_when_true == true) |
|
12547 { |
|
12548 crypto_md5_c * const md5 = new crypto_md5_c(m_am_tools); |
|
12549 if (md5 == 0) |
|
12550 { |
|
12551 delete md5; |
|
12552 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12553 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12554 } |
|
12555 |
|
12556 m_send_hmac_algorithm = new crypto_hmac_c(m_am_tools, md5, true); |
|
12557 |
|
12558 status = cipher_suite_initialization_hmac( |
|
12559 m_send_hmac_algorithm, |
|
12560 &m_send_mac_key); |
|
12561 if (status != eap_status_ok) |
|
12562 { |
|
12563 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12564 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12565 } |
|
12566 } |
|
12567 else |
|
12568 { |
|
12569 crypto_md5_c * const md5 = new crypto_md5_c(m_am_tools); |
|
12570 if (md5 == 0) |
|
12571 { |
|
12572 delete md5; |
|
12573 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12574 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12575 } |
|
12576 |
|
12577 m_receive_hmac_algorithm = new crypto_hmac_c(m_am_tools, md5, true); |
|
12578 |
|
12579 status = cipher_suite_initialization_hmac( |
|
12580 m_receive_hmac_algorithm, |
|
12581 &m_receive_mac_key); |
|
12582 if (status != eap_status_ok) |
|
12583 { |
|
12584 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12585 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12586 } |
|
12587 } |
|
12588 |
|
12589 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12590 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12591 } |
|
12592 |
|
12593 //-------------------------------------------------- |
|
12594 |
|
12595 EAP_FUNC_EXPORT eap_status_e tls_record_c::cipher_suite_initialization( |
|
12596 const bool send_when_true) |
|
12597 { |
|
12598 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
12599 |
|
12600 EAP_TRACE_DEBUG( |
|
12601 m_am_tools, |
|
12602 TRACE_FLAGS_DEFAULT, |
|
12603 (EAPL("TLS: %s: key_function: starts: tls_record_c::cipher_suite_initialization(), cipher suite %s: %s\n"), |
|
12604 (m_is_client == true ? "client": "server"), |
|
12605 eap_tls_trace_string_c::get_cipher_suite_string(m_selected_cipher_suite), |
|
12606 (send_when_true == true ? "send": "receive"))); |
|
12607 |
|
12608 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::cipher_suite_initialization()"); |
|
12609 |
|
12610 reset_block_ciphers(send_when_true); |
|
12611 |
|
12612 reset_stream_ciphers(send_when_true); |
|
12613 |
|
12614 |
|
12615 EAP_TRACE_DATA_DEBUG( |
|
12616 m_am_tools, |
|
12617 TRACE_FLAGS_DEFAULT, |
|
12618 (EAPL("m_send_encryption_key"), |
|
12619 m_send_encryption_key.get_data(), |
|
12620 m_send_encryption_key.get_data_length())); |
|
12621 |
|
12622 EAP_TRACE_DATA_DEBUG( |
|
12623 m_am_tools, |
|
12624 TRACE_FLAGS_DEFAULT, |
|
12625 (EAPL("m_receive_encryption_key"), |
|
12626 m_receive_encryption_key.get_data(), |
|
12627 m_receive_encryption_key.get_data_length())); |
|
12628 |
|
12629 |
|
12630 EAP_TRACE_DATA_DEBUG( |
|
12631 m_am_tools, |
|
12632 TRACE_FLAGS_DEFAULT, |
|
12633 (EAPL("m_send_mac_key"), |
|
12634 m_send_mac_key.get_data(), |
|
12635 m_send_mac_key.get_data_length())); |
|
12636 |
|
12637 EAP_TRACE_DATA_DEBUG( |
|
12638 m_am_tools, |
|
12639 TRACE_FLAGS_DEFAULT, |
|
12640 (EAPL("m_receive_mac_key"), |
|
12641 m_receive_mac_key.get_data(), |
|
12642 m_receive_mac_key.get_data_length())); |
|
12643 |
|
12644 EAP_TRACE_DATA_DEBUG( |
|
12645 m_am_tools, |
|
12646 TRACE_FLAGS_DEFAULT, |
|
12647 (EAPL("m_send_iv"), |
|
12648 m_send_iv.get_data(), |
|
12649 m_send_iv.get_data_length())); |
|
12650 |
|
12651 EAP_TRACE_DATA_DEBUG( |
|
12652 m_am_tools, |
|
12653 TRACE_FLAGS_DEFAULT, |
|
12654 (EAPL("m_receive_iv"), |
|
12655 m_receive_iv.get_data(), |
|
12656 m_receive_iv.get_data_length())); |
|
12657 |
|
12658 |
|
12659 eap_status_e status = eap_status_ok; |
|
12660 |
|
12661 if (cipher_suite_is_3DES_EDE_CBC_SHA(m_selected_cipher_suite) == true) |
|
12662 { |
|
12663 if (send_when_true == true) |
|
12664 { |
|
12665 crypto_3des_ede_c * des3 = new crypto_3des_ede_c(m_am_tools); |
|
12666 |
|
12667 status = cipher_suite_initialization_cbc( |
|
12668 &m_send_block_cipher, |
|
12669 des3, |
|
12670 &m_send_iv, |
|
12671 &m_send_encryption_key, |
|
12672 true); |
|
12673 if (status != eap_status_ok) |
|
12674 { |
|
12675 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12676 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12677 } |
|
12678 } |
|
12679 else |
|
12680 { |
|
12681 crypto_3des_ede_c * des3 = new crypto_3des_ede_c(m_am_tools); |
|
12682 |
|
12683 status = cipher_suite_initialization_cbc( |
|
12684 &m_receive_block_cipher, |
|
12685 des3, |
|
12686 &m_receive_iv, |
|
12687 &m_receive_encryption_key, |
|
12688 false); |
|
12689 if (status != eap_status_ok) |
|
12690 { |
|
12691 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12692 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12693 } |
|
12694 } |
|
12695 |
|
12696 status = cipher_suite_initialization_hmac_sha1(send_when_true); |
|
12697 if (status != eap_status_ok) |
|
12698 { |
|
12699 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12700 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12701 } |
|
12702 } |
|
12703 else if (cipher_suite_is_AES_128_CBC_SHA(m_selected_cipher_suite) == true) |
|
12704 { |
|
12705 if (send_when_true == true) |
|
12706 { |
|
12707 crypto_aes_c * aes = new crypto_aes_c(m_am_tools); |
|
12708 |
|
12709 status = cipher_suite_initialization_cbc( |
|
12710 &m_send_block_cipher, |
|
12711 aes, |
|
12712 &m_send_iv, |
|
12713 &m_send_encryption_key, |
|
12714 true); |
|
12715 if (status != eap_status_ok) |
|
12716 { |
|
12717 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12718 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12719 } |
|
12720 } |
|
12721 else |
|
12722 { |
|
12723 crypto_aes_c * aes = new crypto_aes_c(m_am_tools); |
|
12724 |
|
12725 status = cipher_suite_initialization_cbc( |
|
12726 &m_receive_block_cipher, |
|
12727 aes, |
|
12728 &m_receive_iv, |
|
12729 &m_receive_encryption_key, |
|
12730 false); |
|
12731 if (status != eap_status_ok) |
|
12732 { |
|
12733 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12734 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12735 } |
|
12736 } |
|
12737 |
|
12738 status = cipher_suite_initialization_hmac_sha1(send_when_true); |
|
12739 if (status != eap_status_ok) |
|
12740 { |
|
12741 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12742 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12743 } |
|
12744 } |
|
12745 else if (cipher_suite_is_RC4_128_MD5(m_selected_cipher_suite) == true) |
|
12746 { |
|
12747 if (send_when_true == true) |
|
12748 { |
|
12749 m_send_stream_cipher = new crypto_rc4_c(m_am_tools); |
|
12750 |
|
12751 status = cipher_suite_initialization_stream( |
|
12752 m_send_stream_cipher, |
|
12753 &m_send_encryption_key, |
|
12754 true); |
|
12755 if (status != eap_status_ok) |
|
12756 { |
|
12757 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12758 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12759 } |
|
12760 } |
|
12761 else |
|
12762 { |
|
12763 m_receive_stream_cipher = new crypto_rc4_c(m_am_tools); |
|
12764 |
|
12765 status = cipher_suite_initialization_stream( |
|
12766 m_receive_stream_cipher, |
|
12767 &m_receive_encryption_key, |
|
12768 false); |
|
12769 if (status != eap_status_ok) |
|
12770 { |
|
12771 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12772 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12773 } |
|
12774 } |
|
12775 |
|
12776 status = cipher_suite_initialization_hmac_md5(send_when_true); |
|
12777 if (status != eap_status_ok) |
|
12778 { |
|
12779 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12780 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12781 } |
|
12782 } |
|
12783 else if (cipher_suite_is_RC4_128_SHA(m_selected_cipher_suite) == true) |
|
12784 { |
|
12785 if (send_when_true == true) |
|
12786 { |
|
12787 m_send_stream_cipher = new crypto_rc4_c(m_am_tools); |
|
12788 |
|
12789 status = cipher_suite_initialization_stream( |
|
12790 m_send_stream_cipher, |
|
12791 &m_send_encryption_key, |
|
12792 true); |
|
12793 if (status != eap_status_ok) |
|
12794 { |
|
12795 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12796 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12797 } |
|
12798 } |
|
12799 else |
|
12800 { |
|
12801 m_receive_stream_cipher = new crypto_rc4_c(m_am_tools); |
|
12802 |
|
12803 status = cipher_suite_initialization_stream( |
|
12804 m_receive_stream_cipher, |
|
12805 &m_receive_encryption_key, |
|
12806 false); |
|
12807 if (status != eap_status_ok) |
|
12808 { |
|
12809 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12810 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12811 } |
|
12812 } |
|
12813 |
|
12814 status = cipher_suite_initialization_hmac_sha1(send_when_true); |
|
12815 if (status != eap_status_ok) |
|
12816 { |
|
12817 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12818 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12819 } |
|
12820 } |
|
12821 else |
|
12822 { |
|
12823 status = eap_status_illegal_cipher_suite; |
|
12824 } |
|
12825 |
|
12826 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12827 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12828 } |
|
12829 |
|
12830 //-------------------------------------------------- |
|
12831 |
|
12832 EAP_FUNC_EXPORT eap_status_e tls_record_c::generate_key_material() |
|
12833 { |
|
12834 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12835 |
|
12836 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
12837 EAP_TRACE_DEBUG( |
|
12838 m_am_tools, |
|
12839 TRACE_FLAGS_DEFAULT, |
|
12840 (EAPL("TLS: %s: tls_record_c::generate_key_material()\n"), |
|
12841 (m_is_client == true) ? "client": "server")); |
|
12842 |
|
12843 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::generate_key_material()"); |
|
12844 |
|
12845 eap_status_e status = eap_status_illegal_cipher_suite; |
|
12846 |
|
12847 if (m_key_material_generated == true) |
|
12848 { |
|
12849 // Already generated. |
|
12850 status = eap_status_ok; |
|
12851 } |
|
12852 else |
|
12853 { |
|
12854 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
12855 EAP_TRACE_DEBUG( |
|
12856 m_am_tools, |
|
12857 TRACE_FLAGS_DEFAULT, |
|
12858 (EAPL("TLS: %s: key_function: starts: tls_record_c::generate_key_material()\n"), |
|
12859 (m_is_client == true) ? "client": "server")); |
|
12860 |
|
12861 if (m_master_secret.get_is_valid_data() == false |
|
12862 || m_client_handshake_random_value.get_is_valid_data() == false |
|
12863 || m_server_handshake_random_value.get_is_valid_data() == false) |
|
12864 { |
|
12865 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12866 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_parameter); |
|
12867 } |
|
12868 |
|
12869 u32_t mac_key_length = 0ul; |
|
12870 u32_t encryption_key_length = 0ul; |
|
12871 u32_t iv_length = 0ul; |
|
12872 u32_t session_key_seed_length = 0ul; |
|
12873 u32_t mschapv2_challenges_length = 0ul; |
|
12874 |
|
12875 u32_t key_expansion_size = get_key_expansion_size( |
|
12876 &mac_key_length, |
|
12877 &encryption_key_length, |
|
12878 &iv_length, |
|
12879 &session_key_seed_length, |
|
12880 &mschapv2_challenges_length); |
|
12881 |
|
12882 if (key_expansion_size == 0ul) |
|
12883 { |
|
12884 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12885 return EAP_STATUS_RETURN(m_am_tools, eap_status_key_error); |
|
12886 } |
|
12887 |
|
12888 eap_variable_data_c label(m_am_tools); |
|
12889 if (label.get_is_valid() == false) |
|
12890 { |
|
12891 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12892 } |
|
12893 |
|
12894 status = label.add_data( |
|
12895 TLS_PEAP_KEY_EXPANSION_LABEL, |
|
12896 TLS_PEAP_KEY_EXPANSION_LABEL_LENGTH); |
|
12897 if (status != eap_status_ok) |
|
12898 { |
|
12899 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12900 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12901 } |
|
12902 |
|
12903 eap_variable_data_c seed(m_am_tools); |
|
12904 if (seed.get_is_valid() == false) |
|
12905 { |
|
12906 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
12907 } |
|
12908 status = seed.set_copy_of_buffer(&m_server_handshake_random_value); |
|
12909 if (status != eap_status_ok) |
|
12910 { |
|
12911 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12912 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12913 } |
|
12914 |
|
12915 status = seed.add_data(&m_client_handshake_random_value); |
|
12916 if (status != eap_status_ok) |
|
12917 { |
|
12918 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12919 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12920 } |
|
12921 |
|
12922 EAP_TRACE_DEBUG( |
|
12923 m_am_tools, |
|
12924 TRACE_FLAGS_DEFAULT, |
|
12925 (EAPL("TLS: %s: prf_function: tls_prf.tls_prf_output()\n"), |
|
12926 (m_is_client == true ? "client": "server"))); |
|
12927 |
|
12928 crypto_tls_prf_c tls_prf(m_am_tools); |
|
12929 |
|
12930 status = tls_prf.tls_prf_init( |
|
12931 &m_master_secret, |
|
12932 &label, |
|
12933 &seed); |
|
12934 if (status != eap_status_ok) |
|
12935 { |
|
12936 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12937 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12938 } |
|
12939 |
|
12940 eap_variable_data_c key_expansion(m_am_tools); |
|
12941 |
|
12942 status = key_expansion.set_buffer_length(key_expansion_size); |
|
12943 if (status != eap_status_ok) |
|
12944 { |
|
12945 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12946 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12947 } |
|
12948 key_expansion.set_data_length(key_expansion_size); |
|
12949 |
|
12950 status = tls_prf.tls_prf_output( |
|
12951 key_expansion.get_data(key_expansion.get_data_length()), |
|
12952 key_expansion.get_data_length()); |
|
12953 if (status != eap_status_ok) |
|
12954 { |
|
12955 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12956 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12957 } |
|
12958 |
|
12959 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
12960 |
|
12961 u32_t key_offset = 0ul; |
|
12962 |
|
12963 eap_variable_data_c *send_mac_key = &m_new_send_mac_key; |
|
12964 eap_variable_data_c *receive_mac_key = &m_new_receive_mac_key; |
|
12965 eap_variable_data_c *send_encryption_key = &m_new_send_encryption_key; |
|
12966 eap_variable_data_c *receive_encryption_key = &m_new_receive_encryption_key; |
|
12967 eap_variable_data_c *send_iv = &m_new_send_iv; |
|
12968 eap_variable_data_c *receive_iv = &m_new_receive_iv; |
|
12969 |
|
12970 if (m_is_client == false) |
|
12971 { |
|
12972 send_mac_key = &m_new_receive_mac_key; |
|
12973 receive_mac_key = &m_new_send_mac_key; |
|
12974 send_encryption_key = &m_new_receive_encryption_key; |
|
12975 receive_encryption_key = &m_new_send_encryption_key; |
|
12976 send_iv = &m_new_receive_iv; |
|
12977 receive_iv = &m_new_send_iv; |
|
12978 } |
|
12979 |
|
12980 status = send_mac_key->set_copy_of_buffer( |
|
12981 key_expansion.get_data_offset(key_offset, mac_key_length), |
|
12982 mac_key_length); |
|
12983 if (status != eap_status_ok) |
|
12984 { |
|
12985 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12986 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12987 } |
|
12988 key_offset += mac_key_length; |
|
12989 |
|
12990 status = receive_mac_key->set_copy_of_buffer( |
|
12991 key_expansion.get_data_offset(key_offset, mac_key_length), |
|
12992 mac_key_length); |
|
12993 if (status != eap_status_ok) |
|
12994 { |
|
12995 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
12996 return EAP_STATUS_RETURN(m_am_tools, status); |
|
12997 } |
|
12998 key_offset += mac_key_length; |
|
12999 |
|
13000 status = send_encryption_key->set_copy_of_buffer( |
|
13001 key_expansion.get_data_offset(key_offset, encryption_key_length), |
|
13002 encryption_key_length); |
|
13003 if (status != eap_status_ok) |
|
13004 { |
|
13005 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13006 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13007 } |
|
13008 key_offset += encryption_key_length; |
|
13009 |
|
13010 status = receive_encryption_key->set_copy_of_buffer( |
|
13011 key_expansion.get_data_offset(key_offset, encryption_key_length), |
|
13012 encryption_key_length); |
|
13013 if (status != eap_status_ok) |
|
13014 { |
|
13015 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13016 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13017 } |
|
13018 key_offset += encryption_key_length; |
|
13019 |
|
13020 if (iv_length > 0ul) |
|
13021 { |
|
13022 status = send_iv->set_copy_of_buffer( |
|
13023 key_expansion.get_data_offset(key_offset, iv_length), |
|
13024 iv_length); |
|
13025 if (status != eap_status_ok) |
|
13026 { |
|
13027 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13028 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13029 } |
|
13030 key_offset += iv_length; |
|
13031 } |
|
13032 else |
|
13033 { |
|
13034 status = send_iv->init(0ul); |
|
13035 if (status != eap_status_ok) |
|
13036 { |
|
13037 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13038 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13039 } |
|
13040 send_iv->set_is_valid(); |
|
13041 } |
|
13042 |
|
13043 if (iv_length > 0ul) |
|
13044 { |
|
13045 status = receive_iv->set_copy_of_buffer( |
|
13046 key_expansion.get_data_offset(key_offset, iv_length), |
|
13047 iv_length); |
|
13048 if (status != eap_status_ok) |
|
13049 { |
|
13050 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13051 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13052 } |
|
13053 key_offset += iv_length; |
|
13054 } |
|
13055 else |
|
13056 { |
|
13057 status = receive_iv->init(0ul); |
|
13058 if (status != eap_status_ok) |
|
13059 { |
|
13060 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13061 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13062 } |
|
13063 receive_iv->set_is_valid(); |
|
13064 } |
|
13065 |
|
13066 #if defined(USE_FAST_EAP_TYPE) |
|
13067 if (session_key_seed_length > 0ul) |
|
13068 { |
|
13069 status = m_session_key_seed.set_copy_of_buffer( |
|
13070 key_expansion.get_data_offset(key_offset, session_key_seed_length), |
|
13071 session_key_seed_length); |
|
13072 if (status != eap_status_ok) |
|
13073 { |
|
13074 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13075 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13076 } |
|
13077 key_offset += session_key_seed_length; |
|
13078 } |
|
13079 |
|
13080 if (mschapv2_challenges_length > 0ul) |
|
13081 { |
|
13082 status = m_mschapv2_challenges.set_copy_of_buffer( |
|
13083 key_expansion.get_data_offset(key_offset, mschapv2_challenges_length), |
|
13084 mschapv2_challenges_length); |
|
13085 if (status != eap_status_ok) |
|
13086 { |
|
13087 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13088 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13089 } |
|
13090 key_offset += mschapv2_challenges_length; |
|
13091 } |
|
13092 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
13093 |
|
13094 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
13095 |
|
13096 EAP_TRACE_DATA_DEBUG( |
|
13097 m_am_tools, |
|
13098 TRACE_FLAGS_DEFAULT, |
|
13099 (EAPL("TLS: generate_key_material(): m_master_secret"), |
|
13100 m_master_secret.get_data(), |
|
13101 m_master_secret.get_data_length())); |
|
13102 |
|
13103 EAP_TRACE_DATA_DEBUG( |
|
13104 m_am_tools, |
|
13105 TRACE_FLAGS_DEFAULT, |
|
13106 (EAPL("TLS: generate_key_material(): m_client_handshake_random_value"), |
|
13107 m_client_handshake_random_value.get_data(), |
|
13108 m_client_handshake_random_value.get_data_length())); |
|
13109 |
|
13110 EAP_TRACE_DATA_DEBUG( |
|
13111 m_am_tools, |
|
13112 TRACE_FLAGS_DEFAULT, |
|
13113 (EAPL("TLS: generate_key_material(): m_server_handshake_random_value"), |
|
13114 m_server_handshake_random_value.get_data(), |
|
13115 m_server_handshake_random_value.get_data_length())); |
|
13116 |
|
13117 EAP_TRACE_DATA_DEBUG( |
|
13118 m_am_tools, |
|
13119 TRACE_FLAGS_DEFAULT, |
|
13120 (EAPL("TLS: generate_key_material(): key_expansion"), |
|
13121 key_expansion.get_data(), |
|
13122 key_expansion.get_data_length())); |
|
13123 |
|
13124 |
|
13125 |
|
13126 EAP_TRACE_DATA_DEBUG( |
|
13127 m_am_tools, |
|
13128 TRACE_FLAGS_DEFAULT, |
|
13129 (EAPL("TLS: generate_key_material(): m_new_send_mac_key"), |
|
13130 m_new_send_mac_key.get_data(), |
|
13131 m_new_send_mac_key.get_data_length())); |
|
13132 |
|
13133 EAP_TRACE_DATA_DEBUG( |
|
13134 m_am_tools, |
|
13135 TRACE_FLAGS_DEFAULT, |
|
13136 (EAPL("TLS: generate_key_material(): m_new_receive_mac_key"), |
|
13137 m_new_receive_mac_key.get_data(), |
|
13138 m_new_receive_mac_key.get_data_length())); |
|
13139 |
|
13140 EAP_TRACE_DATA_DEBUG( |
|
13141 m_am_tools, |
|
13142 TRACE_FLAGS_DEFAULT, |
|
13143 (EAPL("TLS: generate_key_material(): m_new_send_encryption_key"), |
|
13144 m_new_send_encryption_key.get_data(), |
|
13145 m_new_send_encryption_key.get_data_length())); |
|
13146 |
|
13147 EAP_TRACE_DATA_DEBUG( |
|
13148 m_am_tools, |
|
13149 TRACE_FLAGS_DEFAULT, |
|
13150 (EAPL("TLS: generate_key_material(): m_new_receive_encryption_key"), |
|
13151 m_new_receive_encryption_key.get_data(), |
|
13152 m_new_receive_encryption_key.get_data_length())); |
|
13153 |
|
13154 EAP_TRACE_DATA_DEBUG( |
|
13155 m_am_tools, |
|
13156 TRACE_FLAGS_DEFAULT, |
|
13157 (EAPL("TLS: generate_key_material(): m_new_send_iv"), |
|
13158 m_new_send_iv.get_data(), |
|
13159 m_new_send_iv.get_data_length())); |
|
13160 |
|
13161 EAP_TRACE_DATA_DEBUG( |
|
13162 m_am_tools, |
|
13163 TRACE_FLAGS_DEFAULT, |
|
13164 (EAPL("TLS: generate_key_material(): m_new_receive_iv"), |
|
13165 m_new_receive_iv.get_data(), |
|
13166 m_new_receive_iv.get_data_length())); |
|
13167 |
|
13168 if (m_session_key_seed.get_is_valid_data() == true) |
|
13169 { |
|
13170 EAP_TRACE_DATA_DEBUG( |
|
13171 m_am_tools, |
|
13172 TRACE_FLAGS_DEFAULT, |
|
13173 (EAPL("TLS: generate_key_material(): m_session_key_seed"), |
|
13174 m_session_key_seed.get_data(), |
|
13175 m_session_key_seed.get_data_length())); |
|
13176 } |
|
13177 |
|
13178 #if defined(USE_FAST_EAP_TYPE) |
|
13179 if (m_mschapv2_challenges.get_is_valid_data() == true) |
|
13180 { |
|
13181 EAP_TRACE_DATA_DEBUG( |
|
13182 m_am_tools, |
|
13183 TRACE_FLAGS_DEFAULT, |
|
13184 (EAPL("TLS: generate_key_material(): server_mschapv2_challenge"), |
|
13185 m_mschapv2_challenges.get_data(), |
|
13186 EAP_FAST_MSCHAPV2_CHALLENGE_LENGTH)); |
|
13187 |
|
13188 EAP_TRACE_DATA_DEBUG( |
|
13189 m_am_tools, |
|
13190 TRACE_FLAGS_DEFAULT, |
|
13191 (EAPL("TLS: generate_key_material(): client_mschapv2_challenge"), |
|
13192 m_mschapv2_challenges.get_data_offset(EAP_FAST_MSCHAPV2_CHALLENGE_LENGTH, EAP_FAST_MSCHAPV2_CHALLENGE_LENGTH), |
|
13193 EAP_FAST_MSCHAPV2_CHALLENGE_LENGTH)); |
|
13194 } |
|
13195 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
13196 |
|
13197 m_key_material_generated = true; |
|
13198 |
|
13199 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
13200 } |
|
13201 |
|
13202 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13203 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13204 } |
|
13205 |
|
13206 //-------------------------------------------------- |
|
13207 |
|
13208 // |
|
13209 EAP_FUNC_EXPORT eap_status_e tls_record_c::set_tls_master_secret( |
|
13210 const eap_variable_data_c * const master_secret, |
|
13211 const eap_variable_data_c * const client_random, |
|
13212 const eap_variable_data_c * const server_random) |
|
13213 { |
|
13214 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13215 |
|
13216 EAP_TRACE_DEBUG( |
|
13217 m_am_tools, |
|
13218 TRACE_FLAGS_DEFAULT, |
|
13219 (EAPL("TLS: this = 0x%08x, %s: key_function: starts: tls_record_c::set_tls_master_secret()\n"), |
|
13220 this, |
|
13221 (m_is_client == true) ? "client": "server")); |
|
13222 |
|
13223 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::set_tls_master_secret()"); |
|
13224 |
|
13225 eap_variable_data_c label(m_am_tools); |
|
13226 if (label.get_is_valid() == false) |
|
13227 { |
|
13228 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
13229 } |
|
13230 |
|
13231 eap_status_e status = eap_status_process_general_error; |
|
13232 |
|
13233 if (m_eap_type == eap_type_ttls) |
|
13234 { |
|
13235 status = label.add_data( |
|
13236 EAP_TTLS_KEY_EXPANSION_LABEL, |
|
13237 EAP_TTLS_KEY_EXPANSION_LABEL_LENGTH); |
|
13238 } |
|
13239 else if (m_eap_type == eap_type_peap |
|
13240 && m_peap_version == peap_version_1 |
|
13241 && m_use_tppd_tls_peap == false) |
|
13242 { |
|
13243 status = label.add_data( |
|
13244 EAP_TLS_PEAP_CLIENT_ENCRYPTION_LABEL_V1_DRAFT_5, |
|
13245 EAP_TLS_PEAP_CLIENT_ENCRYPTION_LABEL_V1_DRAFT_5_LENGTH); |
|
13246 } |
|
13247 else |
|
13248 { |
|
13249 status = label.add_data( |
|
13250 EAP_TLS_PEAP_CLIENT_ENCRYPTION_LABEL, |
|
13251 EAP_TLS_PEAP_CLIENT_ENCRYPTION_LABEL_LENGTH); |
|
13252 } |
|
13253 |
|
13254 if (status != eap_status_ok) |
|
13255 { |
|
13256 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13257 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13258 } |
|
13259 |
|
13260 |
|
13261 status = get_tls_prf_data( |
|
13262 master_secret, |
|
13263 client_random, |
|
13264 server_random, |
|
13265 &label, |
|
13266 &m_eap_master_session_key, |
|
13267 EAP_TLS_PEAP_MASTER_SESSION_KEY_SIZE); |
|
13268 if (status != eap_status_ok) |
|
13269 { |
|
13270 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13271 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13272 } |
|
13273 |
|
13274 EAP_TRACE_DATA_DEBUG( |
|
13275 m_am_tools, |
|
13276 TRACE_FLAGS_DEFAULT, |
|
13277 (EAPL("tls_record_c::set_tls_master_secret(): TLS_MSK"), |
|
13278 m_eap_master_session_key.get_data(EAP_TLS_PEAP_MSK_SIZE), |
|
13279 EAP_TLS_PEAP_MSK_SIZE)); |
|
13280 |
|
13281 EAP_TRACE_DATA_DEBUG( |
|
13282 m_am_tools, |
|
13283 TRACE_FLAGS_DEFAULT, |
|
13284 (EAPL("tls_record_c::set_tls_master_secret(): TLS_EMSK"), |
|
13285 m_eap_master_session_key.get_data_offset(EAP_TLS_PEAP_MSK_SIZE, EAP_TLS_PEAP_EMSK_SIZE), |
|
13286 EAP_TLS_PEAP_EMSK_SIZE)); |
|
13287 |
|
13288 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13289 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13290 } |
|
13291 |
|
13292 //-------------------------------------------------- |
|
13293 |
|
13294 // |
|
13295 EAP_FUNC_EXPORT eap_status_e tls_record_c::get_ttls_implicit_challenge( |
|
13296 eap_variable_data_c * const ttls_implicit_challenge, |
|
13297 const u32_t required_ttls_implicit_challenge_length) |
|
13298 { |
|
13299 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13300 |
|
13301 EAP_TRACE_DEBUG( |
|
13302 m_am_tools, |
|
13303 TRACE_FLAGS_DEFAULT, |
|
13304 (EAPL("TLS: this = 0x%08x, %s: key_function: starts: tls_record_c::get_ttls_implicit_challenge()\n"), |
|
13305 this, |
|
13306 (m_is_client == true) ? "client": "server")); |
|
13307 |
|
13308 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::get_ttls_implicit_challenge()"); |
|
13309 |
|
13310 eap_variable_data_c label(m_am_tools); |
|
13311 if (label.get_is_valid() == false) |
|
13312 { |
|
13313 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
13314 } |
|
13315 |
|
13316 |
|
13317 eap_status_e status = eap_status_process_general_error; |
|
13318 |
|
13319 status = label.add_data( |
|
13320 EAP_TTLS_IMPLICIT_CHALLENGE_LABEL, |
|
13321 EAP_TTLS_IMPLICIT_CHALLENGE_LABEL_LENGTH); |
|
13322 if (status != eap_status_ok) |
|
13323 { |
|
13324 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13325 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13326 } |
|
13327 |
|
13328 status = get_tls_prf_data( |
|
13329 &m_master_secret, |
|
13330 &m_client_handshake_random_value, |
|
13331 &m_server_handshake_random_value, |
|
13332 &label, |
|
13333 ttls_implicit_challenge, |
|
13334 required_ttls_implicit_challenge_length); |
|
13335 if (status != eap_status_ok) |
|
13336 { |
|
13337 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13338 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13339 } |
|
13340 |
|
13341 EAP_TRACE_DATA_DEBUG( |
|
13342 m_am_tools, |
|
13343 TRACE_FLAGS_DEFAULT, |
|
13344 (EAPL("tls_record_c::get_ttls_implicit_challenge(): ttls_implicit_challenge"), |
|
13345 ttls_implicit_challenge->get_data(), |
|
13346 ttls_implicit_challenge->get_data_length())); |
|
13347 |
|
13348 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13349 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13350 } |
|
13351 |
|
13352 //-------------------------------------------------- |
|
13353 |
|
13354 // |
|
13355 EAP_FUNC_EXPORT eap_status_e tls_record_c::get_tls_prf_data( |
|
13356 const eap_variable_data_c * const master_secret, |
|
13357 const eap_variable_data_c * const client_random, |
|
13358 const eap_variable_data_c * const server_random, |
|
13359 const eap_variable_data_c * const label, |
|
13360 eap_variable_data_c * const prf_data, |
|
13361 const u32_t required_prf_data_length) |
|
13362 { |
|
13363 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13364 |
|
13365 EAP_TRACE_DEBUG( |
|
13366 m_am_tools, |
|
13367 TRACE_FLAGS_DEFAULT, |
|
13368 (EAPL("TLS: this = 0x%08x, %s: key_function: starts: tls_record_c::get_tls_prf_data()\n"), |
|
13369 this, |
|
13370 (m_is_client == true) ? "client": "server")); |
|
13371 |
|
13372 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::get_tls_prf_data()"); |
|
13373 |
|
13374 eap_status_e status = eap_status_process_general_error; |
|
13375 |
|
13376 eap_variable_data_c seed(m_am_tools); |
|
13377 if (seed.get_is_valid() == false) |
|
13378 { |
|
13379 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
13380 } |
|
13381 |
|
13382 status = seed.set_copy_of_buffer(client_random); |
|
13383 if (status != eap_status_ok) |
|
13384 { |
|
13385 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13386 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13387 } |
|
13388 |
|
13389 status = seed.add_data(server_random); |
|
13390 if (status != eap_status_ok) |
|
13391 { |
|
13392 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13393 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13394 } |
|
13395 |
|
13396 crypto_tls_prf_c tls_prf(m_am_tools); |
|
13397 |
|
13398 status = tls_prf.tls_prf_init( |
|
13399 master_secret, |
|
13400 label, |
|
13401 &seed); |
|
13402 if (status != eap_status_ok) |
|
13403 { |
|
13404 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13405 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13406 } |
|
13407 |
|
13408 status = prf_data->set_buffer_length( |
|
13409 required_prf_data_length); |
|
13410 if (status != eap_status_ok) |
|
13411 { |
|
13412 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13413 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13414 } |
|
13415 prf_data->set_data_length(required_prf_data_length); |
|
13416 |
|
13417 status = tls_prf.tls_prf_output( |
|
13418 prf_data->get_data(), |
|
13419 prf_data->get_data_length()); |
|
13420 if (status != eap_status_ok) |
|
13421 { |
|
13422 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13423 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13424 } |
|
13425 |
|
13426 EAP_TRACE_DATA_DEBUG( |
|
13427 m_am_tools, |
|
13428 TRACE_FLAGS_DEFAULT, |
|
13429 (EAPL("tls_record_c::get_tls_prf_data(): prf_data"), |
|
13430 prf_data->get_data(), |
|
13431 prf_data->get_data_length())); |
|
13432 |
|
13433 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13434 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13435 } |
|
13436 |
|
13437 //-------------------------------------------------- |
|
13438 |
|
13439 EAP_FUNC_EXPORT eap_status_e tls_record_c::change_cipher_spec( |
|
13440 const bool send_when_true) |
|
13441 { |
|
13442 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13443 |
|
13444 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
13445 EAP_TRACE_DEBUG( |
|
13446 m_am_tools, |
|
13447 TRACE_FLAGS_DEFAULT, |
|
13448 (EAPL("TLS: this = 0x%08x, %s: suite_function: starts: tls_record_c::change_cipher_spec(%s)\n"), |
|
13449 this, |
|
13450 (m_is_client == true) ? "client": "server", |
|
13451 (send_when_true == true) ? "send": "receive")); |
|
13452 |
|
13453 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::change_cipher_spec()"); |
|
13454 |
|
13455 eap_status_e status = eap_status_illegal_cipher_suite; |
|
13456 |
|
13457 if (m_selected_cipher_suite != tls_cipher_suites_none) |
|
13458 { |
|
13459 status = eap_status_ok; |
|
13460 |
|
13461 if (send_when_true == true) |
|
13462 { |
|
13463 status = set_send_cipher_suite(m_selected_cipher_suite); |
|
13464 if (status != eap_status_ok) |
|
13465 { |
|
13466 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13467 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13468 } |
|
13469 |
|
13470 EAP_TRACE_DEBUG(m_am_tools, |
|
13471 TRACE_FLAGS_DEFAULT, |
|
13472 (EAPL("TLS: change_cipher_spec(): send to %s\n"), |
|
13473 eap_tls_trace_string_c::get_cipher_suite_string(m_send_cipher_suite))); |
|
13474 |
|
13475 } |
|
13476 else |
|
13477 { |
|
13478 status = set_receive_cipher_suite(m_selected_cipher_suite); |
|
13479 if (status != eap_status_ok) |
|
13480 { |
|
13481 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13482 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13483 } |
|
13484 |
|
13485 EAP_TRACE_DEBUG(m_am_tools, |
|
13486 TRACE_FLAGS_DEFAULT, |
|
13487 (EAPL("TLS: change_cipher_spec(): receive to %s\n"), |
|
13488 eap_tls_trace_string_c::get_cipher_suite_string(m_receive_cipher_suite))); |
|
13489 } |
|
13490 |
|
13491 // This will initialize encryption, decryption and MAC algorithms. |
|
13492 status = cipher_suite_initialization(send_when_true); |
|
13493 if (status != eap_status_ok) |
|
13494 { |
|
13495 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13496 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13497 } |
|
13498 } |
|
13499 |
|
13500 if (status == eap_status_ok) |
|
13501 { |
|
13502 if (send_when_true == true) |
|
13503 { |
|
13504 m_send_compression_method = m_selected_compression_method; |
|
13505 |
|
13506 EAP_TRACE_DEBUG(m_am_tools, |
|
13507 TRACE_FLAGS_DEFAULT, |
|
13508 (EAPL("TLS: change_cipher_spec() send to %s\n"), |
|
13509 eap_tls_trace_string_c::get_compression_method_string( |
|
13510 m_send_compression_method))); |
|
13511 } |
|
13512 else |
|
13513 { |
|
13514 m_receive_compression_method = m_selected_compression_method; |
|
13515 |
|
13516 EAP_TRACE_DEBUG(m_am_tools, |
|
13517 TRACE_FLAGS_DEFAULT, |
|
13518 (EAPL("TLS: change_cipher_spec() receive to %s\n"), |
|
13519 eap_tls_trace_string_c::get_compression_method_string( |
|
13520 m_receive_compression_method))); |
|
13521 } |
|
13522 } |
|
13523 |
|
13524 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13525 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13526 } |
|
13527 |
|
13528 //-------------------------------------------------- |
|
13529 |
|
13530 EAP_FUNC_EXPORT eap_status_e tls_record_c::new_record_message( |
|
13531 tls_record_message_c ** const tls_record_message, |
|
13532 const tls_record_protocol_e protocol) |
|
13533 { |
|
13534 EAP_TRACE_DEBUG( |
|
13535 m_am_tools, |
|
13536 TRACE_FLAGS_DEFAULT, |
|
13537 (EAPL("TLS: %s: receive_function: starts: tls_record_c::new_record_message()\n"), |
|
13538 (m_is_client == true ? "client": "server"))); |
|
13539 |
|
13540 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::new_record_message()"); |
|
13541 |
|
13542 bool add_new_record = false; |
|
13543 |
|
13544 eap_automatic_variable_c<tls_record_message_c> automatic_tls_record_message( |
|
13545 m_am_tools, |
|
13546 0); |
|
13547 |
|
13548 eap_status_e status = eap_status_process_general_error; |
|
13549 |
|
13550 |
|
13551 *tls_record_message = m_new_tls_message.get_last_record_message(); |
|
13552 if (*tls_record_message != 0 |
|
13553 && (*tls_record_message)->get_protocol() != protocol) |
|
13554 { |
|
13555 // We need a new different protocol. |
|
13556 *tls_record_message = 0; |
|
13557 } |
|
13558 |
|
13559 if (m_use_separate_tls_record == true) |
|
13560 { |
|
13561 // Every message is in separate TLS-record. |
|
13562 *tls_record_message = 0; |
|
13563 } |
|
13564 |
|
13565 if (*tls_record_message == 0) |
|
13566 { |
|
13567 *tls_record_message = new tls_record_message_c(m_am_tools, this, m_is_client); |
|
13568 |
|
13569 automatic_tls_record_message.set_variable(*tls_record_message); |
|
13570 |
|
13571 if (*tls_record_message == 0 |
|
13572 || (*tls_record_message)->get_is_valid() == false) |
|
13573 { |
|
13574 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13575 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
13576 } |
|
13577 |
|
13578 status = (*tls_record_message)->set_protocol(protocol); |
|
13579 if (status != eap_status_ok) |
|
13580 { |
|
13581 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13582 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13583 } |
|
13584 |
|
13585 status = (*tls_record_message)->set_version(tls_version_3_1); |
|
13586 if (status != eap_status_ok) |
|
13587 { |
|
13588 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13589 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13590 } |
|
13591 |
|
13592 add_new_record = true; |
|
13593 } |
|
13594 |
|
13595 if (add_new_record == true) |
|
13596 { |
|
13597 // Note m_new_tls_message free message on any case. |
|
13598 automatic_tls_record_message.do_not_free_variable(); |
|
13599 |
|
13600 bool includes_tls_handshake_message = false; |
|
13601 |
|
13602 if (protocol == tls_record_protocol_handshake) |
|
13603 { |
|
13604 includes_tls_handshake_message = true; |
|
13605 } |
|
13606 |
|
13607 status = m_new_tls_message.add_record_message( |
|
13608 (*tls_record_message), |
|
13609 true, |
|
13610 includes_tls_handshake_message); |
|
13611 if (status != eap_status_ok) |
|
13612 { |
|
13613 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13614 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13615 } |
|
13616 } |
|
13617 else |
|
13618 { |
|
13619 status = eap_status_ok; |
|
13620 } |
|
13621 |
|
13622 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13623 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13624 } |
|
13625 |
|
13626 //-------------------------------------------------- |
|
13627 |
|
13628 EAP_FUNC_EXPORT eap_status_e tls_record_c::add_record_message( |
|
13629 tls_handshake_message_c * const tls_handshake_message) |
|
13630 { |
|
13631 EAP_TRACE_DEBUG( |
|
13632 m_am_tools, |
|
13633 TRACE_FLAGS_DEFAULT, |
|
13634 (EAPL("TLS: %s: receive_function: starts: tls_record_c::add_record_message()\n"), |
|
13635 (m_is_client == true ? "client": "server"))); |
|
13636 |
|
13637 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::add_record_message()"); |
|
13638 |
|
13639 tls_record_message_c *tls_record_message = 0; |
|
13640 |
|
13641 eap_status_e status = new_record_message( |
|
13642 &tls_record_message, |
|
13643 tls_record_protocol_handshake); |
|
13644 if (status != eap_status_ok |
|
13645 || tls_record_message == 0) |
|
13646 { |
|
13647 delete tls_handshake_message; |
|
13648 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13649 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13650 } |
|
13651 |
|
13652 status = tls_record_message->add_handshake_message( |
|
13653 tls_handshake_message, |
|
13654 true); |
|
13655 if (status != eap_status_ok) |
|
13656 { |
|
13657 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13658 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13659 } |
|
13660 |
|
13661 status = tls_handshake_message->create_message_data(); |
|
13662 if (status != eap_status_ok) |
|
13663 { |
|
13664 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13665 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13666 } |
|
13667 |
|
13668 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13669 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13670 } |
|
13671 |
|
13672 //-------------------------------------------------- |
|
13673 |
|
13674 EAP_FUNC_EXPORT eap_status_e tls_record_c::add_record_message( |
|
13675 tls_change_cipher_spec_message_c * const change_cipher_spec_message) |
|
13676 { |
|
13677 EAP_TRACE_DEBUG( |
|
13678 m_am_tools, |
|
13679 TRACE_FLAGS_DEFAULT, |
|
13680 (EAPL("TLS: %s: receive_function: starts: tls_record_c::add_record_message()\n"), |
|
13681 (m_is_client == true ? "client": "server"))); |
|
13682 |
|
13683 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::add_record_message()"); |
|
13684 |
|
13685 tls_record_message_c *tls_record_message = 0; |
|
13686 |
|
13687 eap_status_e status = new_record_message( |
|
13688 &tls_record_message, |
|
13689 tls_record_protocol_change_cipher_spec); |
|
13690 if (status != eap_status_ok |
|
13691 || tls_record_message == 0) |
|
13692 { |
|
13693 delete change_cipher_spec_message; |
|
13694 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13695 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13696 } |
|
13697 |
|
13698 status = tls_record_message->add_change_cipher_spec_message( |
|
13699 change_cipher_spec_message, |
|
13700 true); |
|
13701 if (status != eap_status_ok) |
|
13702 { |
|
13703 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13704 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13705 } |
|
13706 |
|
13707 status = change_cipher_spec_message->create_message_data(); |
|
13708 if (status != eap_status_ok) |
|
13709 { |
|
13710 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13711 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13712 } |
|
13713 |
|
13714 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13715 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13716 } |
|
13717 |
|
13718 //-------------------------------------------------- |
|
13719 |
|
13720 EAP_FUNC_EXPORT eap_status_e tls_record_c::add_record_message( |
|
13721 tls_alert_message_c * const alert_message) |
|
13722 { |
|
13723 EAP_TRACE_DEBUG( |
|
13724 m_am_tools, |
|
13725 TRACE_FLAGS_DEFAULT, |
|
13726 (EAPL("TLS: %s: receive_function: starts: tls_record_c::add_record_message()\n"), |
|
13727 (m_is_client == true ? "client": "server"))); |
|
13728 |
|
13729 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::add_record_message()"); |
|
13730 |
|
13731 tls_record_message_c *tls_record_message = 0; |
|
13732 |
|
13733 eap_status_e status = new_record_message( |
|
13734 &tls_record_message, |
|
13735 tls_record_protocol_alert); |
|
13736 if (status != eap_status_ok |
|
13737 || tls_record_message == 0) |
|
13738 { |
|
13739 delete alert_message; |
|
13740 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13741 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13742 } |
|
13743 |
|
13744 status = tls_record_message->add_alert_message( |
|
13745 alert_message, |
|
13746 true); |
|
13747 if (status != eap_status_ok) |
|
13748 { |
|
13749 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13750 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13751 } |
|
13752 |
|
13753 status = alert_message->create_message_data(); |
|
13754 if (status != eap_status_ok) |
|
13755 { |
|
13756 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13757 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13758 } |
|
13759 |
|
13760 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13761 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13762 } |
|
13763 |
|
13764 //-------------------------------------------------- |
|
13765 |
|
13766 EAP_FUNC_EXPORT eap_status_e tls_record_c::add_record_message( |
|
13767 tls_application_data_message_c * const application_data_message) |
|
13768 { |
|
13769 EAP_TRACE_DEBUG( |
|
13770 m_am_tools, |
|
13771 TRACE_FLAGS_DEFAULT, |
|
13772 (EAPL("TLS: %s: receive_function: starts: tls_record_c::add_record_message()\n"), |
|
13773 (m_is_client == true ? "client": "server"))); |
|
13774 |
|
13775 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::add_record_message()"); |
|
13776 |
|
13777 tls_record_message_c *tls_record_message = 0; |
|
13778 |
|
13779 eap_status_e status = new_record_message( |
|
13780 &tls_record_message, |
|
13781 tls_record_protocol_application_data); |
|
13782 if (status != eap_status_ok |
|
13783 || tls_record_message == 0) |
|
13784 { |
|
13785 delete application_data_message; |
|
13786 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13787 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13788 } |
|
13789 |
|
13790 status = tls_record_message->add_application_data_message( |
|
13791 application_data_message, |
|
13792 true); |
|
13793 if (status != eap_status_ok) |
|
13794 { |
|
13795 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13796 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13797 } |
|
13798 |
|
13799 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13800 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13801 } |
|
13802 |
|
13803 //-------------------------------------------------- |
|
13804 |
|
13805 EAP_FUNC_EXPORT eap_status_e tls_record_c::allocate_handshake_message( |
|
13806 tls_handshake_message_c ** const tls_handshake_message, |
|
13807 eap_automatic_variable_c<tls_handshake_message_c> * const automatic_tls_handshake_message, |
|
13808 const tls_handshake_type_e handshake_type) |
|
13809 { |
|
13810 EAP_TRACE_DEBUG( |
|
13811 m_am_tools, |
|
13812 TRACE_FLAGS_DEFAULT, |
|
13813 (EAPL("TLS: %s: receive_function: starts: tls_record_c::allocate_handshake_message()\n"), |
|
13814 (m_is_client == true ? "client": "server"))); |
|
13815 |
|
13816 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::allocate_handshake_message()"); |
|
13817 |
|
13818 *tls_handshake_message |
|
13819 = new tls_handshake_message_c(m_am_tools, this, m_is_client); |
|
13820 |
|
13821 automatic_tls_handshake_message->set_variable(*tls_handshake_message); |
|
13822 |
|
13823 if (*tls_handshake_message == 0 |
|
13824 || (*tls_handshake_message)->get_is_valid() == false) |
|
13825 { |
|
13826 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13827 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
13828 } |
|
13829 |
|
13830 eap_status_e status = (*tls_handshake_message)->set_handshake_type( |
|
13831 handshake_type); |
|
13832 |
|
13833 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13834 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13835 } |
|
13836 |
|
13837 //-------------------------------------------------- |
|
13838 |
|
13839 EAP_FUNC_EXPORT eap_status_e tls_record_c::create_handshake_type_hello_request() |
|
13840 { |
|
13841 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13842 |
|
13843 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
13844 EAP_TRACE_DEBUG( |
|
13845 m_am_tools, |
|
13846 TRACE_FLAGS_DEFAULT, |
|
13847 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::create_handshake_type_hello_request()\n"), |
|
13848 this, |
|
13849 (m_is_client == true ? "client": "server"))); |
|
13850 |
|
13851 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::create_handshake_type_hello_request()"); |
|
13852 |
|
13853 // This is an empty message. |
|
13854 |
|
13855 tls_handshake_message_c *tls_handshake_message = 0; |
|
13856 |
|
13857 eap_automatic_variable_c<tls_handshake_message_c> |
|
13858 automatic_tls_handshake_message(m_am_tools); |
|
13859 |
|
13860 eap_status_e status = allocate_handshake_message( |
|
13861 &tls_handshake_message, |
|
13862 &automatic_tls_handshake_message, |
|
13863 tls_handshake_type_hello_request); |
|
13864 |
|
13865 // Note add_record_message() frees message on any case. |
|
13866 automatic_tls_handshake_message.do_not_free_variable(); |
|
13867 |
|
13868 status = add_record_message(tls_handshake_message); |
|
13869 if (status != eap_status_ok) |
|
13870 { |
|
13871 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13872 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13873 } |
|
13874 |
|
13875 set_state(tls_peap_state_wait_handshake_type_client_hello); |
|
13876 |
|
13877 // -------------------------------------------------------------------- |
|
13878 |
|
13879 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13880 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13881 } |
|
13882 |
|
13883 //-------------------------------------------------- |
|
13884 |
|
13885 EAP_FUNC_EXPORT eap_status_e tls_record_c::create_handshake_type_client_hello() |
|
13886 { |
|
13887 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13888 |
|
13889 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
13890 |
|
13891 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
13892 EAP_TRACE_DEBUG( |
|
13893 m_am_tools, |
|
13894 TRACE_FLAGS_DEFAULT, |
|
13895 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::create_handshake_type_client_hello(): privacy_handshake_state=%d=%s, session_type=%s\n"), |
|
13896 this, |
|
13897 (m_is_client == true ? "client": "server"), |
|
13898 m_tls_identity_privacy_handshake_state, |
|
13899 eap_tls_trace_string_c::get_tls_identity_privacy_handshake_state_string(m_tls_identity_privacy_handshake_state), |
|
13900 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type))); |
|
13901 #else |
|
13902 EAP_TRACE_DEBUG( |
|
13903 m_am_tools, |
|
13904 TRACE_FLAGS_DEFAULT, |
|
13905 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::create_handshake_type_client_hello(): privacy_handshake_state=%d=%s\n"), |
|
13906 this, |
|
13907 (m_is_client == true ? "client": "server"), |
|
13908 0, |
|
13909 "")); |
|
13910 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
13911 |
|
13912 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::create_handshake_type_client_hello()"); |
|
13913 |
|
13914 // 0 1 2 3 |
|
13915 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
13916 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
13917 // | Version: 3 | Version: 1 | | |
|
13918 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
13919 // | | |
|
13920 // + + |
|
13921 // | | |
|
13922 // + + |
|
13923 // | ClientRandomValue | |
|
13924 // + (32 bytes) +-+-+-+-+-+-+-+-+ |
|
13925 // | | ID length | |
|
13926 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
13927 // | | |
|
13928 // + + |
|
13929 // | Session ID | |
|
13930 // + (maximum 32 bytes) + |
|
13931 // | | |
|
13932 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
13933 // | CipherSuite length | CipherSuite 1 | |
|
13934 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
13935 // | CipherSuite 2 | CipherSuite 3 | |
|
13936 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
13937 // | CipherSuite 4 | Cmp length | Cmp 1 | |
|
13938 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
13939 // | Cmp 2 | Cmp 3 | extensions ... | |
|
13940 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
13941 |
|
13942 eap_status_e status(eap_status_ok); |
|
13943 |
|
13944 status = message_hash_init(); |
|
13945 if (status != eap_status_ok) |
|
13946 { |
|
13947 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13948 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13949 } |
|
13950 |
|
13951 tls_handshake_message_c *tls_handshake_message = 0; |
|
13952 |
|
13953 eap_automatic_variable_c<tls_handshake_message_c> |
|
13954 automatic_tls_handshake_message(m_am_tools); |
|
13955 |
|
13956 status = allocate_handshake_message( |
|
13957 &tls_handshake_message, |
|
13958 &automatic_tls_handshake_message, |
|
13959 tls_handshake_type_client_hello); |
|
13960 if (status != eap_status_ok) |
|
13961 { |
|
13962 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13963 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13964 } |
|
13965 |
|
13966 u32_t tmp_gmt_unix_time_network_order = eap_htonl(m_am_tools->get_gmt_unix_time()); |
|
13967 eap_variable_data_c tmp_client_random(m_am_tools); |
|
13968 |
|
13969 status = tmp_client_random.set_buffer_length(TLS_HANDSHAKE_RANDOM_VALUE_SIZE); |
|
13970 if (status != eap_status_ok) |
|
13971 { |
|
13972 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13973 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13974 } |
|
13975 tmp_client_random.set_data_length(TLS_HANDSHAKE_RANDOM_VALUE_SIZE); |
|
13976 |
|
13977 crypto_random_c rand(m_am_tools); |
|
13978 |
|
13979 status = rand.get_rand_bytes( |
|
13980 tmp_client_random.get_data(tmp_client_random.get_data_length()), |
|
13981 tmp_client_random.get_data_length()); |
|
13982 if (status != eap_status_ok) |
|
13983 { |
|
13984 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13985 return EAP_STATUS_RETURN(m_am_tools, status); |
|
13986 } |
|
13987 |
|
13988 // Sets the first bytes to GMT unix time. |
|
13989 u8_t *p_gmt_unix_time = reinterpret_cast<u8_t *>(tmp_client_random.get_data(sizeof(u32_t))); |
|
13990 if (p_gmt_unix_time == 0) |
|
13991 { |
|
13992 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
13993 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
13994 } |
|
13995 m_am_tools->memmove(p_gmt_unix_time, &tmp_gmt_unix_time_network_order, sizeof(tmp_gmt_unix_time_network_order)); |
|
13996 |
|
13997 |
|
13998 status = m_client_handshake_random_value.set_copy_of_buffer( |
|
13999 &tmp_client_random); |
|
14000 if (status != eap_status_ok) |
|
14001 { |
|
14002 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14003 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14004 } |
|
14005 |
|
14006 |
|
14007 status = tls_handshake_message->set_random_value( |
|
14008 &tmp_client_random); |
|
14009 if (status != eap_status_ok) |
|
14010 { |
|
14011 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14012 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14013 } |
|
14014 |
|
14015 if (m_tls_session_type == tls_session_type_original_session_resumption |
|
14016 && m_session_id.get_is_valid_data() == true) |
|
14017 { |
|
14018 status = tls_handshake_message->set_session_id( |
|
14019 &m_session_id); |
|
14020 if (status != eap_status_ok) |
|
14021 { |
|
14022 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14023 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14024 } |
|
14025 } |
|
14026 |
|
14027 // -------------------------------------------------------------------- |
|
14028 |
|
14029 // This copies proposed cipher suites to tls_handshake_message. |
|
14030 status = tls_handshake_message->set_cipher_suites(&m_proposed_cipher_suites); |
|
14031 if (status != eap_status_ok) |
|
14032 { |
|
14033 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14034 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14035 } |
|
14036 |
|
14037 // -------------------------------------------------------------------- |
|
14038 |
|
14039 status = tls_handshake_message->set_compression_methods(&m_proposed_compression_methods); |
|
14040 if (status != eap_status_ok) |
|
14041 { |
|
14042 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14043 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14044 } |
|
14045 |
|
14046 // -------------------------------------------------------------------- |
|
14047 |
|
14048 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
14049 |
|
14050 { |
|
14051 status = tls_handshake_message->set_tls_extensions(&m_supported_tls_extensions); |
|
14052 if (status != eap_status_ok) |
|
14053 { |
|
14054 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14055 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14056 } |
|
14057 |
|
14058 } |
|
14059 |
|
14060 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
14061 |
|
14062 // -------------------------------------------------------------------- |
|
14063 |
|
14064 // Note add_record_message() frees message on any case. |
|
14065 automatic_tls_handshake_message.do_not_free_variable(); |
|
14066 |
|
14067 status = add_record_message(tls_handshake_message); |
|
14068 if (status != eap_status_ok) |
|
14069 { |
|
14070 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14071 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14072 } |
|
14073 |
|
14074 // -------------------------------------------------------------------- |
|
14075 |
|
14076 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14077 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14078 } |
|
14079 |
|
14080 //-------------------------------------------------- |
|
14081 |
|
14082 EAP_FUNC_EXPORT eap_status_e tls_record_c::create_handshake_type_server_hello( |
|
14083 const u16_t /*selected_cipher_suite*/, |
|
14084 const u8_t /*selected_compression_method*/) |
|
14085 { |
|
14086 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14087 |
|
14088 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
14089 EAP_TRACE_DEBUG( |
|
14090 m_am_tools, |
|
14091 TRACE_FLAGS_DEFAULT, |
|
14092 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::create_handshake_type_server_hello()\n"), |
|
14093 this, |
|
14094 (m_is_client == true ? "client": "server"))); |
|
14095 |
|
14096 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::create_handshake_type_server_hello()"); |
|
14097 |
|
14098 // 0 1 2 3 |
|
14099 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
14100 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
14101 // | Version: 3 | Version: 1 | | |
|
14102 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
14103 // | | |
|
14104 // + + |
|
14105 // | | |
|
14106 // + + |
|
14107 // | ServerRandomValue | |
|
14108 // + (32 bytes) +-+-+-+-+-+-+-+-+ |
|
14109 // | | ID length | |
|
14110 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
14111 // | | |
|
14112 // + + |
|
14113 // | Session ID | |
|
14114 // + (maximum 32 bytes) + |
|
14115 // | | |
|
14116 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
14117 // | CipherSuite | Cmp | extensions ... |
|
14118 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
14119 |
|
14120 tls_handshake_message_c *tls_handshake_message = 0; |
|
14121 |
|
14122 eap_automatic_variable_c<tls_handshake_message_c> |
|
14123 automatic_tls_handshake_message(m_am_tools); |
|
14124 |
|
14125 eap_status_e status = allocate_handshake_message( |
|
14126 &tls_handshake_message, |
|
14127 &automatic_tls_handshake_message, |
|
14128 tls_handshake_type_server_hello); |
|
14129 if (status != eap_status_ok) |
|
14130 { |
|
14131 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14132 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14133 } |
|
14134 |
|
14135 // -------------------------------------------------------------------- |
|
14136 |
|
14137 u32_t tmp_gmt_unix_time_network_order = eap_htonl(m_am_tools->get_gmt_unix_time()); |
|
14138 eap_variable_data_c tmp_server_random(m_am_tools); |
|
14139 |
|
14140 status = tmp_server_random.set_buffer_length(TLS_HANDSHAKE_RANDOM_VALUE_SIZE); |
|
14141 if (status != eap_status_ok) |
|
14142 { |
|
14143 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14144 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14145 } |
|
14146 tmp_server_random.set_data_length(TLS_HANDSHAKE_RANDOM_VALUE_SIZE); |
|
14147 |
|
14148 crypto_random_c rand(m_am_tools); |
|
14149 |
|
14150 status = rand.get_rand_bytes( |
|
14151 tmp_server_random.get_data(tmp_server_random.get_data_length()), |
|
14152 tmp_server_random.get_data_length()); |
|
14153 if (status != eap_status_ok) |
|
14154 { |
|
14155 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14156 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14157 } |
|
14158 |
|
14159 // Sets the first bytes to GMT unix time. |
|
14160 u8_t *p_gmt_unix_time = reinterpret_cast<u8_t *>(tmp_server_random.get_data(sizeof(u32_t))); |
|
14161 if (p_gmt_unix_time == 0) |
|
14162 { |
|
14163 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14164 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
14165 } |
|
14166 m_am_tools->memmove(p_gmt_unix_time, &tmp_gmt_unix_time_network_order, sizeof(tmp_gmt_unix_time_network_order)); |
|
14167 |
|
14168 status = m_server_handshake_random_value.set_copy_of_buffer( |
|
14169 &tmp_server_random); |
|
14170 if (status != eap_status_ok) |
|
14171 { |
|
14172 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14173 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14174 } |
|
14175 |
|
14176 // -------------------------------------------------------------------- |
|
14177 |
|
14178 status = tls_handshake_message->set_random_value( |
|
14179 &tmp_server_random); |
|
14180 if (status != eap_status_ok) |
|
14181 { |
|
14182 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14183 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14184 } |
|
14185 |
|
14186 // -------------------------------------------------------------------- |
|
14187 |
|
14188 if ((m_tls_session_type == tls_session_type_full_authentication |
|
14189 #if defined(USE_FAST_EAP_TYPE) |
|
14190 || m_tls_session_type == tls_session_type_eap_fast_server_unauthenticated_provisioning_mode_ADHP |
|
14191 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
14192 ) |
|
14193 && m_server_offers_new_session_id == true) |
|
14194 { |
|
14195 // We create a new session. |
|
14196 status = m_session_id.set_buffer_length(TLS_SESSION_ID_SIZE); |
|
14197 if (status != eap_status_ok) |
|
14198 { |
|
14199 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14200 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14201 } |
|
14202 m_session_id.set_data_length(TLS_SESSION_ID_SIZE); |
|
14203 |
|
14204 status = rand.get_rand_bytes( |
|
14205 m_session_id.get_data(m_session_id.get_data_length()), |
|
14206 m_session_id.get_data_length()); |
|
14207 if (status != eap_status_ok) |
|
14208 { |
|
14209 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14210 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14211 } |
|
14212 } |
|
14213 |
|
14214 // -------------------------------------------------------------------- |
|
14215 |
|
14216 status = tls_handshake_message->set_session_id( |
|
14217 &m_session_id); |
|
14218 if (status != eap_status_ok) |
|
14219 { |
|
14220 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14221 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14222 } |
|
14223 |
|
14224 // -------------------------------------------------------------------- |
|
14225 |
|
14226 { |
|
14227 EAP_TRACE_DEBUG( |
|
14228 m_am_tools, |
|
14229 TRACE_FLAGS_DEFAULT, |
|
14230 (EAPL("%s: TLS/PEAP selected cipher_suite %s\n"), |
|
14231 (m_is_client == true ? "client": "server"), |
|
14232 eap_tls_trace_string_c::get_cipher_suite_string(m_selected_cipher_suite))); |
|
14233 } |
|
14234 |
|
14235 status = tls_handshake_message->set_selected_cipher_suite( |
|
14236 m_selected_cipher_suite); |
|
14237 if (status != eap_status_ok) |
|
14238 { |
|
14239 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14240 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14241 } |
|
14242 |
|
14243 // -------------------------------------------------------------------- |
|
14244 |
|
14245 status = tls_handshake_message->set_selected_compression_method( |
|
14246 m_selected_compression_method); |
|
14247 if (status != eap_status_ok) |
|
14248 { |
|
14249 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14250 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14251 } |
|
14252 |
|
14253 // -------------------------------------------------------------------- |
|
14254 |
|
14255 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
14256 |
|
14257 #if defined(USE_FAST_EAP_TYPE) |
|
14258 if (m_eap_type != eap_type_fast) // EAP-FAST does not use session ticket in ServerHello message. |
|
14259 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
14260 { |
|
14261 status = tls_handshake_message->set_tls_extensions(&m_supported_tls_extensions); |
|
14262 if (status != eap_status_ok) |
|
14263 { |
|
14264 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14265 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14266 } |
|
14267 } |
|
14268 |
|
14269 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
14270 |
|
14271 // -------------------------------------------------------------------- |
|
14272 |
|
14273 if (m_tls_session_type == tls_session_type_original_session_resumption |
|
14274 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
14275 || m_tls_session_type == tls_session_type_stateless_session_resumption |
|
14276 #if defined(USE_FAST_EAP_TYPE) |
|
14277 || m_tls_session_type == tls_session_type_eap_fast_pac_session_resumption |
|
14278 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
14279 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
14280 ) |
|
14281 { |
|
14282 |
|
14283 #if defined(USE_FAST_EAP_TYPE) |
|
14284 if (m_eap_type == eap_type_fast |
|
14285 && m_tls_session_type == tls_session_type_eap_fast_pac_session_resumption) |
|
14286 { |
|
14287 // Generates master secret from PAC-Key. |
|
14288 // Parameter resumed_master_secret includes PAC-Key. |
|
14289 status = generate_eap_fast_master_secret_from_pac_key( |
|
14290 &m_eap_fast_pac_key); |
|
14291 |
|
14292 m_eap_fast_pac_key.reset(); |
|
14293 |
|
14294 if (status != eap_status_ok) |
|
14295 { |
|
14296 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14297 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14298 } |
|
14299 } |
|
14300 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
14301 |
|
14302 // We must generate the key material. |
|
14303 status = generate_key_material(); |
|
14304 if (status != eap_status_ok) |
|
14305 { |
|
14306 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14307 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14308 } |
|
14309 |
|
14310 } |
|
14311 |
|
14312 // -------------------------------------------------------------------- |
|
14313 |
|
14314 // Note add_record_message() frees message on any case. |
|
14315 automatic_tls_handshake_message.do_not_free_variable(); |
|
14316 |
|
14317 status = add_record_message(tls_handshake_message); |
|
14318 if (status != eap_status_ok) |
|
14319 { |
|
14320 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14321 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14322 } |
|
14323 |
|
14324 // -------------------------------------------------------------------- |
|
14325 |
|
14326 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14327 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14328 } |
|
14329 |
|
14330 //-------------------------------------------------- |
|
14331 |
|
14332 EAP_FUNC_EXPORT eap_status_e tls_record_c::create_handshake_type_certificate( |
|
14333 EAP_TEMPLATE_CONST eap_array_c<eap_variable_data_c> * const certificate_chain) |
|
14334 { |
|
14335 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14336 |
|
14337 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
14338 |
|
14339 tls_identity_privacy_handshake_state_e tmp_identity_privacy_handshake_state = |
|
14340 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
14341 m_tls_identity_privacy_handshake_state; |
|
14342 #else |
|
14343 tls_identity_privacy_handshake_state_none; |
|
14344 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
14345 EAP_UNREFERENCED_PARAMETER(tmp_identity_privacy_handshake_state); |
|
14346 |
|
14347 EAP_TRACE_DEBUG( |
|
14348 m_am_tools, |
|
14349 TRACE_FLAGS_DEFAULT, |
|
14350 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::create_handshake_type_certificate(): state=%d=%s, privacy_handshake_state=%d=%s, session_type=%s\n"), |
|
14351 this, |
|
14352 (m_is_client == true ? "client": "server"), |
|
14353 m_tls_peap_state, |
|
14354 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
14355 tmp_identity_privacy_handshake_state, |
|
14356 eap_tls_trace_string_c::get_tls_identity_privacy_handshake_state_string(tmp_identity_privacy_handshake_state), |
|
14357 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type))); |
|
14358 |
|
14359 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::create_handshake_type_certificate()"); |
|
14360 |
|
14361 // 0 1 2 3 |
|
14362 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
14363 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
14364 // | Certificate Chain Length | |
|
14365 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
14366 // | Certificate 1 Length | | |
|
14367 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
14368 // | | |
|
14369 // + + |
|
14370 // | Certificate 1 | |
|
14371 // + + |
|
14372 // | | |
|
14373 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
14374 // . ... . |
|
14375 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
14376 // | Certificate n Length | | |
|
14377 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
14378 // | | |
|
14379 // + + |
|
14380 // | Certificate n | |
|
14381 // + + |
|
14382 // | | |
|
14383 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
14384 |
|
14385 tls_handshake_message_c *tls_handshake_message = 0; |
|
14386 |
|
14387 eap_automatic_variable_c<tls_handshake_message_c> |
|
14388 automatic_tls_handshake_message(m_am_tools); |
|
14389 |
|
14390 eap_status_e status = allocate_handshake_message( |
|
14391 &tls_handshake_message, |
|
14392 &automatic_tls_handshake_message, |
|
14393 tls_handshake_type_certificate); |
|
14394 if (status != eap_status_ok) |
|
14395 { |
|
14396 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14397 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14398 } |
|
14399 |
|
14400 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
14401 // Certificate chain is included when TLS identity privacy is not used, |
|
14402 // or send cipher is not NULL |
|
14403 // or sender is server |
|
14404 if (m_tls_session_type == tls_session_type_full_authentication |
|
14405 && (m_tls_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_none |
|
14406 || m_tls_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_runs |
|
14407 || m_is_client == false)) |
|
14408 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
14409 { |
|
14410 status = tls_handshake_message->set_certificate_chain( |
|
14411 certificate_chain); |
|
14412 if (status != eap_status_ok) |
|
14413 { |
|
14414 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14415 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14416 } |
|
14417 } |
|
14418 |
|
14419 // -------------------------------------------------------------------- |
|
14420 |
|
14421 // Note add_record_message() frees message on any case. |
|
14422 automatic_tls_handshake_message.do_not_free_variable(); |
|
14423 |
|
14424 status = add_record_message(tls_handshake_message); |
|
14425 if (status != eap_status_ok) |
|
14426 { |
|
14427 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14428 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14429 } |
|
14430 |
|
14431 // -------------------------------------------------------------------- |
|
14432 |
|
14433 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14434 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14435 } |
|
14436 |
|
14437 //-------------------------------------------------- |
|
14438 |
|
14439 EAP_FUNC_EXPORT eap_status_e tls_record_c::create_handshake_type_certificate_request( |
|
14440 EAP_TEMPLATE_CONST eap_array_c<u8_t> * const certificate_types, |
|
14441 EAP_TEMPLATE_CONST eap_array_c<eap_variable_data_c> * const certificate_authorities) |
|
14442 { |
|
14443 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14444 |
|
14445 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
14446 EAP_TRACE_DEBUG( |
|
14447 m_am_tools, |
|
14448 TRACE_FLAGS_DEFAULT, |
|
14449 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::create_handshake_type_certificate_request()\n"), |
|
14450 this, |
|
14451 (m_is_client == true ? "client": "server"))); |
|
14452 |
|
14453 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::create_handshake_type_certificate_request()"); |
|
14454 |
|
14455 // 0 1 2 3 |
|
14456 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
14457 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
14458 // | CT length | CT 1 | CT 2 | |
|
14459 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
14460 // | CT 3 | CT 4 | CAs length | |
|
14461 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
14462 // | CA 1 length | | |
|
14463 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
14464 // | | |
|
14465 // + + |
|
14466 // | Distinguished name of Certificate Authority 1 | |
|
14467 // + + |
|
14468 // | | |
|
14469 // + +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
14470 // | | CA 2 length | |
|
14471 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
14472 // | | |
|
14473 // + + |
|
14474 // | Distinguished name of Certificate Authority 2 | |
|
14475 // + + |
|
14476 // | | |
|
14477 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
14478 |
|
14479 tls_handshake_message_c *tls_handshake_message = 0; |
|
14480 |
|
14481 eap_automatic_variable_c<tls_handshake_message_c> |
|
14482 automatic_tls_handshake_message(m_am_tools); |
|
14483 |
|
14484 eap_status_e status = allocate_handshake_message( |
|
14485 &tls_handshake_message, |
|
14486 &automatic_tls_handshake_message, |
|
14487 tls_handshake_type_certificate_request); |
|
14488 if (status != eap_status_ok) |
|
14489 { |
|
14490 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14491 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14492 } |
|
14493 |
|
14494 status = tls_handshake_message->set_certificate_types( |
|
14495 certificate_types); |
|
14496 if (status != eap_status_ok) |
|
14497 { |
|
14498 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14499 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14500 } |
|
14501 |
|
14502 if (m_server_sends_empty_certificate_authorities_list == false) |
|
14503 { |
|
14504 status = tls_handshake_message->set_certificate_authorities( |
|
14505 certificate_authorities); |
|
14506 if (status != eap_status_ok) |
|
14507 { |
|
14508 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14509 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14510 } |
|
14511 } |
|
14512 |
|
14513 // -------------------------------------------------------------------- |
|
14514 |
|
14515 // Note add_record_message() frees message on any case. |
|
14516 automatic_tls_handshake_message.do_not_free_variable(); |
|
14517 |
|
14518 status = add_record_message(tls_handshake_message); |
|
14519 if (status != eap_status_ok) |
|
14520 { |
|
14521 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14522 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14523 } |
|
14524 |
|
14525 // -------------------------------------------------------------------- |
|
14526 |
|
14527 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14528 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14529 } |
|
14530 |
|
14531 //-------------------------------------------------- |
|
14532 |
|
14533 EAP_FUNC_EXPORT eap_status_e tls_record_c::create_handshake_type_server_hello_done() |
|
14534 { |
|
14535 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14536 |
|
14537 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
14538 EAP_TRACE_DEBUG( |
|
14539 m_am_tools, |
|
14540 TRACE_FLAGS_DEFAULT, |
|
14541 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::create_handshake_type_server_hello_done()\n"), |
|
14542 this, |
|
14543 (m_is_client == true ? "client": "server"))); |
|
14544 |
|
14545 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::create_handshake_type_server_hello_done()"); |
|
14546 |
|
14547 // 0 1 2 3 |
|
14548 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
14549 // |
|
14550 // ServerHelloDone message does not include payload. |
|
14551 |
|
14552 tls_handshake_message_c *tls_handshake_message = 0; |
|
14553 |
|
14554 eap_automatic_variable_c<tls_handshake_message_c> |
|
14555 automatic_tls_handshake_message(m_am_tools); |
|
14556 |
|
14557 eap_status_e status = allocate_handshake_message( |
|
14558 &tls_handshake_message, |
|
14559 &automatic_tls_handshake_message, |
|
14560 tls_handshake_type_server_hello_done); |
|
14561 if (status != eap_status_ok) |
|
14562 { |
|
14563 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14564 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14565 } |
|
14566 |
|
14567 // -------------------------------------------------------------------- |
|
14568 |
|
14569 // Note add_record_message() frees message on any case. |
|
14570 automatic_tls_handshake_message.do_not_free_variable(); |
|
14571 |
|
14572 status = add_record_message(tls_handshake_message); |
|
14573 if (status != eap_status_ok) |
|
14574 { |
|
14575 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14576 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14577 } |
|
14578 |
|
14579 // -------------------------------------------------------------------- |
|
14580 |
|
14581 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14582 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14583 } |
|
14584 |
|
14585 //-------------------------------------------------- |
|
14586 |
|
14587 EAP_FUNC_EXPORT eap_status_e tls_record_c::create_server_key_exchange_sha1_hash( |
|
14588 const eap_variable_data_c * const dhe_prime, |
|
14589 const eap_variable_data_c * const dhe_group_generator, |
|
14590 const eap_variable_data_c * const public_dhe_key, |
|
14591 eap_variable_data_c * const hash) |
|
14592 { |
|
14593 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
14594 EAP_TRACE_DEBUG( |
|
14595 m_am_tools, |
|
14596 TRACE_FLAGS_DEFAULT, |
|
14597 (EAPL("TLS: this = 0x%08x, %s: hash_function: starts: tls_record_c::create_server_key_exchange_sha1_hash()\n"), |
|
14598 this, |
|
14599 (m_is_client == true ? "client": "server"))); |
|
14600 |
|
14601 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::create_server_key_exchange_sha1_hash()"); |
|
14602 |
|
14603 if (m_client_handshake_random_value.get_is_valid_data() == false) |
|
14604 { |
|
14605 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14606 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_parameter); |
|
14607 } |
|
14608 |
|
14609 if (m_server_handshake_random_value.get_is_valid_data() == false) |
|
14610 { |
|
14611 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14612 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_parameter); |
|
14613 } |
|
14614 |
|
14615 u16_t dhe_prime_length_network_order |
|
14616 = eap_htons(static_cast<u16_t>(dhe_prime->get_data_length())); |
|
14617 |
|
14618 u16_t dhe_group_generator_length_network_order |
|
14619 = eap_htons(static_cast<u16_t>(dhe_group_generator->get_data_length())); |
|
14620 |
|
14621 u16_t public_dhe_key_length_network_order |
|
14622 = eap_htons(static_cast<u16_t>(public_dhe_key->get_data_length())); |
|
14623 |
|
14624 crypto_sha1_c sha1(m_am_tools); |
|
14625 |
|
14626 eap_status_e status = sha1.hash_init(); |
|
14627 if (status != eap_status_ok) |
|
14628 { |
|
14629 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14630 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14631 } |
|
14632 |
|
14633 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
14634 |
|
14635 EAP_TRACE_DATA_DEBUG( |
|
14636 m_am_tools, |
|
14637 TRACE_FLAGS_DEFAULT, |
|
14638 (EAPL("TLS: create_server_key_exchange_sha1_hash(): client random"), |
|
14639 m_client_handshake_random_value.get_data(m_client_handshake_random_value.get_data_length()), |
|
14640 m_client_handshake_random_value.get_data_length())); |
|
14641 |
|
14642 status = sha1.hash_update( |
|
14643 m_client_handshake_random_value.get_data(m_client_handshake_random_value.get_data_length()), |
|
14644 m_client_handshake_random_value.get_data_length()); |
|
14645 if (status != eap_status_ok) |
|
14646 { |
|
14647 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14648 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14649 } |
|
14650 |
|
14651 EAP_TRACE_DATA_DEBUG( |
|
14652 m_am_tools, |
|
14653 TRACE_FLAGS_DEFAULT, |
|
14654 (EAPL("TLS: create_server_key_exchange_sha1_hash(): server random"), |
|
14655 m_server_handshake_random_value.get_data(m_client_handshake_random_value.get_data_length()), |
|
14656 m_server_handshake_random_value.get_data_length())); |
|
14657 |
|
14658 status = sha1.hash_update( |
|
14659 m_server_handshake_random_value.get_data(m_client_handshake_random_value.get_data_length()), |
|
14660 m_server_handshake_random_value.get_data_length()); |
|
14661 if (status != eap_status_ok) |
|
14662 { |
|
14663 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14664 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14665 } |
|
14666 |
|
14667 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
14668 |
|
14669 EAP_TRACE_DATA_DEBUG( |
|
14670 m_am_tools, |
|
14671 TRACE_FLAGS_DEFAULT, |
|
14672 (EAPL("TLS: create_server_key_exchange_sha1_hash(): dhe_prime_length_network_order"), |
|
14673 &dhe_prime_length_network_order, |
|
14674 sizeof(dhe_prime_length_network_order))); |
|
14675 |
|
14676 EAP_TRACE_DATA_DEBUG( |
|
14677 m_am_tools, |
|
14678 TRACE_FLAGS_DEFAULT, |
|
14679 (EAPL("TLS: create_server_key_exchange_sha1_hash(): dhe_prime"), |
|
14680 dhe_prime->get_data(dhe_prime->get_data_length()), |
|
14681 dhe_prime->get_data_length())); |
|
14682 |
|
14683 status = sha1.hash_update( |
|
14684 &dhe_prime_length_network_order, |
|
14685 sizeof(dhe_prime_length_network_order)); |
|
14686 if (status != eap_status_ok) |
|
14687 { |
|
14688 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14689 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14690 } |
|
14691 |
|
14692 status = sha1.hash_update( |
|
14693 dhe_prime->get_data( |
|
14694 dhe_prime->get_data_length()), |
|
14695 dhe_prime->get_data_length()); |
|
14696 if (status != eap_status_ok) |
|
14697 { |
|
14698 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14699 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14700 } |
|
14701 |
|
14702 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
14703 |
|
14704 EAP_TRACE_DATA_DEBUG( |
|
14705 m_am_tools, |
|
14706 TRACE_FLAGS_DEFAULT, |
|
14707 (EAPL("TLS: create_server_key_exchange_sha1_hash(): ") |
|
14708 EAPL("dhe_group_generator_length_network_order"), |
|
14709 &dhe_group_generator_length_network_order, |
|
14710 sizeof(dhe_group_generator_length_network_order))); |
|
14711 |
|
14712 EAP_TRACE_DATA_DEBUG( |
|
14713 m_am_tools, |
|
14714 TRACE_FLAGS_DEFAULT, |
|
14715 (EAPL("TLS: create_server_key_exchange_sha1_hash(): dhe_group_generator"), |
|
14716 dhe_group_generator->get_data(dhe_group_generator->get_data_length()), |
|
14717 dhe_group_generator->get_data_length())); |
|
14718 |
|
14719 status = sha1.hash_update( |
|
14720 &dhe_group_generator_length_network_order, |
|
14721 sizeof(dhe_group_generator_length_network_order)); |
|
14722 if (status != eap_status_ok) |
|
14723 { |
|
14724 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14725 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14726 } |
|
14727 |
|
14728 status = sha1.hash_update( |
|
14729 dhe_group_generator->get_data( |
|
14730 dhe_group_generator->get_data_length()), |
|
14731 dhe_group_generator->get_data_length()); |
|
14732 if (status != eap_status_ok) |
|
14733 { |
|
14734 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14735 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14736 } |
|
14737 |
|
14738 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
14739 |
|
14740 EAP_TRACE_DATA_DEBUG( |
|
14741 m_am_tools, |
|
14742 TRACE_FLAGS_DEFAULT, |
|
14743 (EAPL("TLS: create_server_key_exchange_sha1_hash(): public_dhe_key_length_network_order"), |
|
14744 &public_dhe_key_length_network_order, |
|
14745 sizeof(public_dhe_key_length_network_order))); |
|
14746 |
|
14747 EAP_TRACE_DATA_DEBUG( |
|
14748 m_am_tools, |
|
14749 TRACE_FLAGS_DEFAULT, |
|
14750 (EAPL("TLS: create_server_key_exchange_sha1_hash(): public_dhe_key"), |
|
14751 public_dhe_key->get_data(public_dhe_key->get_data_length()), |
|
14752 public_dhe_key->get_data_length())); |
|
14753 |
|
14754 status = sha1.hash_update( |
|
14755 &public_dhe_key_length_network_order, |
|
14756 sizeof(public_dhe_key_length_network_order)); |
|
14757 if (status != eap_status_ok) |
|
14758 { |
|
14759 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14760 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14761 } |
|
14762 |
|
14763 status = sha1.hash_update( |
|
14764 public_dhe_key->get_data( |
|
14765 public_dhe_key->get_data_length()), |
|
14766 public_dhe_key->get_data_length()); |
|
14767 if (status != eap_status_ok) |
|
14768 { |
|
14769 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14770 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14771 } |
|
14772 |
|
14773 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
14774 |
|
14775 status = hash->set_buffer_length(sha1.get_digest_length()); |
|
14776 if (status != eap_status_ok) |
|
14777 { |
|
14778 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14779 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14780 } |
|
14781 hash->set_data_length(sha1.get_digest_length()); |
|
14782 |
|
14783 u32_t digest_length = hash->get_data_length(); |
|
14784 status = sha1.hash_final( |
|
14785 hash->get_data(hash->get_data_length()), |
|
14786 &digest_length); |
|
14787 if (digest_length != sha1.get_digest_length()) |
|
14788 { |
|
14789 status = eap_status_process_general_error; |
|
14790 } |
|
14791 if (status != eap_status_ok) |
|
14792 { |
|
14793 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14794 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14795 } |
|
14796 |
|
14797 EAP_TRACE_DATA_DEBUG( |
|
14798 m_am_tools, |
|
14799 TRACE_FLAGS_DEFAULT, |
|
14800 (EAPL("TLS: create_server_key_exchange_sha1_hash(): hash"), |
|
14801 hash->get_data(hash->get_data_length()), |
|
14802 hash->get_data_length())); |
|
14803 |
|
14804 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14805 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14806 } |
|
14807 |
|
14808 //-------------------------------------------------- |
|
14809 |
|
14810 EAP_FUNC_EXPORT eap_status_e tls_record_c::create_server_key_exchange_md5_hash( |
|
14811 const eap_variable_data_c * const dhe_prime, |
|
14812 const eap_variable_data_c * const dhe_group_generator, |
|
14813 const eap_variable_data_c * const public_dhe_key, |
|
14814 eap_variable_data_c * const hash) |
|
14815 { |
|
14816 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
14817 EAP_TRACE_DEBUG( |
|
14818 m_am_tools, |
|
14819 TRACE_FLAGS_DEFAULT, |
|
14820 (EAPL("TLS: this = 0x%08x, %s: hash_function: starts: tls_record_c::create_server_key_exchange_md5_hash()\n"), |
|
14821 this, |
|
14822 (m_is_client == true ? "client": "server"))); |
|
14823 |
|
14824 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::create_server_key_exchange_md5_hash()"); |
|
14825 |
|
14826 if (m_client_handshake_random_value.get_is_valid_data() == false) |
|
14827 { |
|
14828 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14829 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_parameter); |
|
14830 } |
|
14831 |
|
14832 if (m_server_handshake_random_value.get_is_valid_data() == false) |
|
14833 { |
|
14834 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14835 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_parameter); |
|
14836 } |
|
14837 |
|
14838 u16_t dhe_prime_length_network_order |
|
14839 = eap_htons(static_cast<u16_t>(dhe_prime->get_data_length())); |
|
14840 |
|
14841 u16_t dhe_group_generator_length_network_order |
|
14842 = eap_htons(static_cast<u16_t>(dhe_group_generator->get_data_length())); |
|
14843 |
|
14844 u16_t public_dhe_key_length_network_order |
|
14845 = eap_htons(static_cast<u16_t>(public_dhe_key->get_data_length())); |
|
14846 |
|
14847 crypto_md5_c md5(m_am_tools); |
|
14848 |
|
14849 eap_status_e status = md5.hash_init(); |
|
14850 if (status != eap_status_ok) |
|
14851 { |
|
14852 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14853 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14854 } |
|
14855 |
|
14856 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
14857 |
|
14858 EAP_TRACE_DATA_DEBUG( |
|
14859 m_am_tools, |
|
14860 TRACE_FLAGS_DEFAULT, |
|
14861 (EAPL("TLS: create_server_key_exchange_md5_hash(): client random"), |
|
14862 m_client_handshake_random_value.get_data(m_client_handshake_random_value.get_data_length()), |
|
14863 m_client_handshake_random_value.get_data_length())); |
|
14864 |
|
14865 status = md5.hash_update( |
|
14866 m_client_handshake_random_value.get_data(m_client_handshake_random_value.get_data_length()), |
|
14867 m_client_handshake_random_value.get_data_length()); |
|
14868 if (status != eap_status_ok) |
|
14869 { |
|
14870 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14871 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14872 } |
|
14873 |
|
14874 EAP_TRACE_DATA_DEBUG( |
|
14875 m_am_tools, |
|
14876 TRACE_FLAGS_DEFAULT, |
|
14877 (EAPL("TLS: create_server_key_exchange_md5_hash(): server random"), |
|
14878 m_server_handshake_random_value.get_data(m_client_handshake_random_value.get_data_length()), |
|
14879 m_server_handshake_random_value.get_data_length())); |
|
14880 |
|
14881 status = md5.hash_update( |
|
14882 m_server_handshake_random_value.get_data(m_client_handshake_random_value.get_data_length()), |
|
14883 m_server_handshake_random_value.get_data_length()); |
|
14884 if (status != eap_status_ok) |
|
14885 { |
|
14886 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14887 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14888 } |
|
14889 |
|
14890 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
14891 |
|
14892 EAP_TRACE_DATA_DEBUG( |
|
14893 m_am_tools, |
|
14894 TRACE_FLAGS_DEFAULT, |
|
14895 (EAPL("TLS: create_server_key_exchange_md5_hash(): dhe_prime_length_network_order"), |
|
14896 &dhe_prime_length_network_order, |
|
14897 sizeof(dhe_prime_length_network_order))); |
|
14898 |
|
14899 EAP_TRACE_DATA_DEBUG( |
|
14900 m_am_tools, |
|
14901 TRACE_FLAGS_DEFAULT, |
|
14902 (EAPL("TLS: create_server_key_exchange_md5_hash(): dhe_prime"), |
|
14903 dhe_prime->get_data(dhe_prime->get_data_length()), |
|
14904 dhe_prime->get_data_length())); |
|
14905 |
|
14906 status = md5.hash_update( |
|
14907 &dhe_prime_length_network_order, |
|
14908 sizeof(dhe_prime_length_network_order)); |
|
14909 if (status != eap_status_ok) |
|
14910 { |
|
14911 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14912 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14913 } |
|
14914 |
|
14915 status = md5.hash_update( |
|
14916 dhe_prime->get_data( |
|
14917 dhe_prime->get_data_length()), |
|
14918 dhe_prime->get_data_length()); |
|
14919 if (status != eap_status_ok) |
|
14920 { |
|
14921 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14922 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14923 } |
|
14924 |
|
14925 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
14926 |
|
14927 EAP_TRACE_DATA_DEBUG( |
|
14928 m_am_tools, |
|
14929 TRACE_FLAGS_DEFAULT, |
|
14930 (EAPL("TLS: create_server_key_exchange_md5_hash(): ") |
|
14931 EAPL("dhe_group_generator_length_network_order"), |
|
14932 &dhe_group_generator_length_network_order, |
|
14933 sizeof(dhe_group_generator_length_network_order))); |
|
14934 |
|
14935 EAP_TRACE_DATA_DEBUG( |
|
14936 m_am_tools, |
|
14937 TRACE_FLAGS_DEFAULT, |
|
14938 (EAPL("TLS: create_server_key_exchange_md5_hash(): dhe_group_generator"), |
|
14939 dhe_group_generator->get_data(dhe_group_generator->get_data_length()), |
|
14940 dhe_group_generator->get_data_length())); |
|
14941 |
|
14942 status = md5.hash_update( |
|
14943 &dhe_group_generator_length_network_order, |
|
14944 sizeof(dhe_group_generator_length_network_order)); |
|
14945 if (status != eap_status_ok) |
|
14946 { |
|
14947 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14948 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14949 } |
|
14950 |
|
14951 status = md5.hash_update( |
|
14952 dhe_group_generator->get_data( |
|
14953 dhe_group_generator->get_data_length()), |
|
14954 dhe_group_generator->get_data_length()); |
|
14955 if (status != eap_status_ok) |
|
14956 { |
|
14957 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14958 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14959 } |
|
14960 |
|
14961 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
14962 |
|
14963 EAP_TRACE_DATA_DEBUG( |
|
14964 m_am_tools, |
|
14965 TRACE_FLAGS_DEFAULT, |
|
14966 (EAPL("TLS: create_server_key_exchange_md5_hash(): public_dhe_key_length_network_order"), |
|
14967 &public_dhe_key_length_network_order, |
|
14968 sizeof(public_dhe_key_length_network_order))); |
|
14969 |
|
14970 EAP_TRACE_DATA_DEBUG( |
|
14971 m_am_tools, |
|
14972 TRACE_FLAGS_DEFAULT, |
|
14973 (EAPL("TLS: create_server_key_exchange_md5_hash(): public_dhe_key"), |
|
14974 public_dhe_key->get_data(public_dhe_key->get_data_length()), |
|
14975 public_dhe_key->get_data_length())); |
|
14976 |
|
14977 status = md5.hash_update( |
|
14978 &public_dhe_key_length_network_order, |
|
14979 sizeof(public_dhe_key_length_network_order)); |
|
14980 if (status != eap_status_ok) |
|
14981 { |
|
14982 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14983 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14984 } |
|
14985 |
|
14986 status = md5.hash_update( |
|
14987 public_dhe_key->get_data( |
|
14988 public_dhe_key->get_data_length()), |
|
14989 public_dhe_key->get_data_length()); |
|
14990 if (status != eap_status_ok) |
|
14991 { |
|
14992 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
14993 return EAP_STATUS_RETURN(m_am_tools, status); |
|
14994 } |
|
14995 |
|
14996 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
14997 |
|
14998 status = hash->set_buffer_length(md5.get_digest_length()); |
|
14999 if (status != eap_status_ok) |
|
15000 { |
|
15001 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15002 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15003 } |
|
15004 hash->set_data_length(md5.get_digest_length()); |
|
15005 |
|
15006 u32_t digest_length = hash->get_data_length(); |
|
15007 status = md5.hash_final( |
|
15008 hash->get_data(hash->get_data_length()), |
|
15009 &digest_length); |
|
15010 if (digest_length != md5.get_digest_length()) |
|
15011 { |
|
15012 status = eap_status_process_general_error; |
|
15013 } |
|
15014 if (status != eap_status_ok) |
|
15015 { |
|
15016 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15017 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15018 } |
|
15019 |
|
15020 EAP_TRACE_DATA_DEBUG( |
|
15021 m_am_tools, |
|
15022 TRACE_FLAGS_DEFAULT, |
|
15023 (EAPL("TLS: create_server_key_exchange_md5_hash(): hash"), |
|
15024 hash->get_data(hash->get_data_length()), |
|
15025 hash->get_data_length())); |
|
15026 |
|
15027 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15028 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15029 } |
|
15030 |
|
15031 //-------------------------------------------------- |
|
15032 |
|
15033 EAP_FUNC_EXPORT eap_status_e tls_record_c::verify_signature_of_server_key_exchange( |
|
15034 const eap_variable_data_c * const signed_server_key_exchange_hash) |
|
15035 { |
|
15036 EAP_TRACE_DEBUG( |
|
15037 m_am_tools, |
|
15038 TRACE_FLAGS_DEFAULT, |
|
15039 (EAPL("TLS: this = 0x%08x, %s: hash_function: starts: tls_record_c::verify_signature_of_server_key_exchange()\n"), |
|
15040 this, |
|
15041 (m_is_client == true ? "client": "server"))); |
|
15042 |
|
15043 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::verify_signature_of_server_key_exchange()"); |
|
15044 |
|
15045 eap_status_e status = eap_status_not_supported; |
|
15046 |
|
15047 eap_variable_data_c hash(m_am_tools); |
|
15048 |
|
15049 |
|
15050 if (cipher_suite_is_TLS_DHE_DSS() == true) |
|
15051 { |
|
15052 status = create_server_key_exchange_sha1_hash( |
|
15053 &m_dhe_prime, |
|
15054 &m_dhe_group_generator, |
|
15055 &m_peer_public_dhe_key, |
|
15056 &hash); |
|
15057 if (status != eap_status_ok) |
|
15058 { |
|
15059 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15060 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15061 } |
|
15062 } |
|
15063 else if (cipher_suite_is_TLS_DHE_RSA() == true) |
|
15064 { |
|
15065 eap_variable_data_c md5_hash(m_am_tools); |
|
15066 |
|
15067 status = create_server_key_exchange_md5_hash( |
|
15068 &m_dhe_prime, |
|
15069 &m_dhe_group_generator, |
|
15070 &m_peer_public_dhe_key, |
|
15071 &md5_hash); |
|
15072 if (status != eap_status_ok) |
|
15073 { |
|
15074 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15075 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15076 } |
|
15077 |
|
15078 eap_variable_data_c sha1_hash(m_am_tools); |
|
15079 |
|
15080 status = create_server_key_exchange_sha1_hash( |
|
15081 &m_dhe_prime, |
|
15082 &m_dhe_group_generator, |
|
15083 &m_peer_public_dhe_key, |
|
15084 &sha1_hash); |
|
15085 if (status != eap_status_ok) |
|
15086 { |
|
15087 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15088 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15089 } |
|
15090 |
|
15091 status = hash.add_data(&md5_hash); |
|
15092 if (status != eap_status_ok) |
|
15093 { |
|
15094 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15095 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15096 } |
|
15097 |
|
15098 status = hash.add_data(&sha1_hash); |
|
15099 if (status != eap_status_ok) |
|
15100 { |
|
15101 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15102 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15103 } |
|
15104 } |
|
15105 else |
|
15106 { |
|
15107 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15108 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_cipher_suite); |
|
15109 } |
|
15110 |
|
15111 |
|
15112 EAP_TRACE_DATA_DEBUG( |
|
15113 m_am_tools, |
|
15114 TRACE_FLAGS_DEFAULT, |
|
15115 (EAPL("TLS: verify_signature_of_server_key_exchange(): hash"), |
|
15116 hash.get_data(hash.get_data_length()), |
|
15117 hash.get_data_length())); |
|
15118 |
|
15119 EAP_TRACE_DATA_DEBUG( |
|
15120 m_am_tools, |
|
15121 TRACE_FLAGS_DEFAULT, |
|
15122 (EAPL("TLS: verify_signature_of_server_key_exchange(): signed_server_key_exchange_hash"), |
|
15123 signed_server_key_exchange_hash->get_data( |
|
15124 signed_server_key_exchange_hash->get_data_length()), |
|
15125 signed_server_key_exchange_hash->get_data_length())); |
|
15126 |
|
15127 EAP_TRACE_DEBUG( |
|
15128 m_am_tools, |
|
15129 TRACE_FLAGS_DEFAULT, |
|
15130 (EAPL("TLS: %s: pki_function: verify_with_public_key()\n"), |
|
15131 (m_is_client == true ? "client": "server"))); |
|
15132 |
|
15133 status = m_am_tls_services->verify_with_public_key( |
|
15134 &hash, |
|
15135 signed_server_key_exchange_hash); |
|
15136 if (status == eap_status_pending_request) |
|
15137 { |
|
15138 // This is pending query, that will be completed by complete_query_certificate_chain() call. |
|
15139 m_pending_verify_with_public_key = true; |
|
15140 } |
|
15141 else if (status == eap_status_completed_request) |
|
15142 { |
|
15143 // This is already completed by complete_query_certificate_chain() call. |
|
15144 } |
|
15145 else if (status == eap_status_ok) |
|
15146 { |
|
15147 // This is also an error case, because this call is always completed on success. |
|
15148 status = eap_status_process_general_error; |
|
15149 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15150 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15151 } |
|
15152 else // All other status values means error, because this call is always completed on success. |
|
15153 { |
|
15154 // This is an error case. |
|
15155 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15156 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
15157 } |
|
15158 |
|
15159 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15160 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15161 } |
|
15162 |
|
15163 //-------------------------------------------------- |
|
15164 |
|
15165 EAP_FUNC_EXPORT eap_status_e tls_record_c::complete_create_handshake_type_server_key_exchange() |
|
15166 { |
|
15167 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
15168 EAP_TRACE_DEBUG( |
|
15169 m_am_tools, |
|
15170 TRACE_FLAGS_DEFAULT, |
|
15171 (EAPL("TLS: this = 0x%08x, %s: parse_function: starts: tls_record_c::complete_create_handshake_type_server_key_exchange()\n"), |
|
15172 this, |
|
15173 (m_is_client == true ? "client": "server"))); |
|
15174 |
|
15175 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::complete_create_handshake_type_server_key_exchange()"); |
|
15176 |
|
15177 tls_handshake_message_c *tls_handshake_message = 0; |
|
15178 |
|
15179 eap_automatic_variable_c<tls_handshake_message_c> |
|
15180 automatic_tls_handshake_message(m_am_tools); |
|
15181 |
|
15182 eap_status_e status = allocate_handshake_message( |
|
15183 &tls_handshake_message, |
|
15184 &automatic_tls_handshake_message, |
|
15185 tls_handshake_type_server_key_exchange); |
|
15186 if (status != eap_status_ok) |
|
15187 { |
|
15188 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15189 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15190 } |
|
15191 |
|
15192 #if EAP_TLS_UNSUPPORTED_CIPHER_SUITE |
|
15193 #error This one needs more code. RSA key exchange with different parameters is NOT supported. |
|
15194 if (cipher_suite_is_TLS_RSA() == true) |
|
15195 { |
|
15196 // RSA modulus and exponent are included when selected cipher suite is |
|
15197 // using RSA key exchange |
|
15198 // and parameters are different than included in the certificate. |
|
15199 // 0 1 2 3 |
|
15200 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
15201 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15202 // | rsa_modulus length | | |
|
15203 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15204 // | | |
|
15205 // + + |
|
15206 // | rsa_modulus | |
|
15207 // + + |
|
15208 // | | |
|
15209 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15210 // | rsa_exponent length | | |
|
15211 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15212 // | | |
|
15213 // + rsa_exponent + |
|
15214 // | | |
|
15215 // + + |
|
15216 // | | |
|
15217 // + + |
|
15218 // | | |
|
15219 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15220 // | | |
|
15221 // + + |
|
15222 // | digitally-signed MD5 hash 16 bytes | |
|
15223 // + (ClientHello.random + ServerHello.random + ServerParams) + |
|
15224 // | | |
|
15225 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15226 // | | |
|
15227 // + + |
|
15228 // | digitally-signed SHA-1 hash 20 bytes | |
|
15229 // + (ClientHello.random + ServerHello.random + ServerParams) + |
|
15230 // | | |
|
15231 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15232 |
|
15233 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15234 return EAP_STATUS_RETURN(m_am_tools, eap_status_not_supported); |
|
15235 } |
|
15236 else |
|
15237 #endif |
|
15238 if (cipher_suite_is_TLS_DHE_DSS() == true) |
|
15239 { |
|
15240 // Diffie-Hellman prime modulus, generator and server's |
|
15241 // Diffie-Hellman public value (g^X mod p) |
|
15242 // are included when selected cipher suite is ephemeral Diffie-Hellman key exchange. |
|
15243 // 0 1 2 3 |
|
15244 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
15245 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15246 // | DH p length | | |
|
15247 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15248 // | | |
|
15249 // + + |
|
15250 // | DH p value (prime modulus) | |
|
15251 // + + |
|
15252 // | | |
|
15253 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15254 // | DH g length | | |
|
15255 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15256 // | | |
|
15257 // + + |
|
15258 // | DH g value (generator) | |
|
15259 // + + |
|
15260 // | | |
|
15261 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15262 // | DH Ys length | | |
|
15263 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15264 // | | |
|
15265 // + + |
|
15266 // | DH Ys value | |
|
15267 // + (server's Diffie-Hellman public value) + |
|
15268 // | | |
|
15269 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15270 // | | |
|
15271 // + + |
|
15272 // | digitally-signed SHA-1 hash 47 bytes | |
|
15273 // + (ClientHello.random + ServerHello.random + ServerParams) + |
|
15274 // | | |
|
15275 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15276 |
|
15277 EAP_TRACE_DATA_DEBUG( |
|
15278 m_am_tools, |
|
15279 TRACE_FLAGS_DEFAULT, |
|
15280 (EAPL("TLS: complete_create_handshake_type_server_key_exchange(): m_signed_message_hash"), |
|
15281 m_signed_message_hash.get_data(m_signed_message_hash.get_data_length()), |
|
15282 m_signed_message_hash.get_data_length())); |
|
15283 |
|
15284 status = tls_handshake_message->set_signed_message_hash( |
|
15285 &m_signed_message_hash); |
|
15286 if (status != eap_status_ok) |
|
15287 { |
|
15288 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15289 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15290 } |
|
15291 } |
|
15292 else if (cipher_suite_is_TLS_DHE_RSA() == true) |
|
15293 { |
|
15294 // Diffie-Hellman prime modulus, generator and server's |
|
15295 // Diffie-Hellman public value (g^X mod p) |
|
15296 // are included when selected cipher suite is ephemeral Diffie-Hellman key exchange. |
|
15297 // 0 1 2 3 |
|
15298 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
15299 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15300 // | DH p length | | |
|
15301 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15302 // | | |
|
15303 // + + |
|
15304 // | DH p value (prime modulus) | |
|
15305 // + + |
|
15306 // | | |
|
15307 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15308 // | DH g length | | |
|
15309 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15310 // | | |
|
15311 // + + |
|
15312 // | DH g value (generator) | |
|
15313 // + + |
|
15314 // | | |
|
15315 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15316 // | DH Ys length | | |
|
15317 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15318 // | | |
|
15319 // + + |
|
15320 // | DH Ys value | |
|
15321 // + (server's Diffie-Hellman public value) + |
|
15322 // | | |
|
15323 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15324 // | | |
|
15325 // + + |
|
15326 // | digitally-signed MD5 hash 16 bytes | |
|
15327 // + (ClientHello.random + ServerHello.random + ServerParams) + |
|
15328 // | | |
|
15329 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15330 // | | |
|
15331 // + + |
|
15332 // | digitally-signed SHA-1 hash 47 bytes | |
|
15333 // + (ClientHello.random + ServerHello.random + ServerParams) + |
|
15334 // | | |
|
15335 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15336 |
|
15337 EAP_TRACE_DATA_DEBUG( |
|
15338 m_am_tools, |
|
15339 TRACE_FLAGS_DEFAULT, |
|
15340 (EAPL("TLS: complete_create_handshake_type_server_key_exchange(): m_signed_message_hash"), |
|
15341 m_signed_message_hash.get_data(m_signed_message_hash.get_data_length()), |
|
15342 m_signed_message_hash.get_data_length())); |
|
15343 |
|
15344 status = tls_handshake_message->set_signed_message_hash( |
|
15345 &m_signed_message_hash); |
|
15346 if (status != eap_status_ok) |
|
15347 { |
|
15348 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15349 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15350 } |
|
15351 } |
|
15352 #if defined(USE_FAST_EAP_TYPE) |
|
15353 else if (m_eap_type == eap_type_fast |
|
15354 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true |
|
15355 && cipher_suite_is_TLS_DH_anon() == true) |
|
15356 { |
|
15357 // Diffie-Hellman prime modulus, generator and server's |
|
15358 // Diffie-Hellman public value (g^X mod p) |
|
15359 // are included when selected cipher suite is ephemeral Diffie-Hellman key exchange. |
|
15360 // NOTE: Here are no signed hash. This is not authenticated at all and vulnerable to |
|
15361 // man-in-the-middle attacks. |
|
15362 // 0 1 2 3 |
|
15363 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
15364 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15365 // | DH p length | | |
|
15366 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15367 // | | |
|
15368 // + + |
|
15369 // | DH p value (prime modulus) | |
|
15370 // + + |
|
15371 // | | |
|
15372 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15373 // | DH g length | | |
|
15374 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15375 // | | |
|
15376 // + + |
|
15377 // | DH g value (generator) | |
|
15378 // + + |
|
15379 // | | |
|
15380 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15381 // | DH Ys length | | |
|
15382 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15383 // | | |
|
15384 // + + |
|
15385 // | DH Ys value | |
|
15386 // + (server's Diffie-Hellman public value) + |
|
15387 // | | |
|
15388 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15389 |
|
15390 EAP_TRACE_DEBUG( |
|
15391 m_am_tools, |
|
15392 TRACE_FLAGS_DEFAULT, |
|
15393 (EAPL("TLS: complete_create_handshake_type_server_key_exchange() no m_signed_message_hash\n"))); |
|
15394 } |
|
15395 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
15396 else |
|
15397 { |
|
15398 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15399 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_cipher_suite); |
|
15400 } |
|
15401 |
|
15402 // -------------------------------------------------------------------- |
|
15403 |
|
15404 |
|
15405 status = tls_handshake_message->set_dhe_prime( |
|
15406 &m_dhe_prime); |
|
15407 if (status != eap_status_ok) |
|
15408 { |
|
15409 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15410 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15411 } |
|
15412 |
|
15413 status = tls_handshake_message->set_dhe_group_generator( |
|
15414 &m_dhe_group_generator); |
|
15415 if (status != eap_status_ok) |
|
15416 { |
|
15417 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15418 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15419 } |
|
15420 |
|
15421 status = tls_handshake_message->set_public_dhe_key( |
|
15422 &m_own_public_dhe_key); |
|
15423 if (status != eap_status_ok) |
|
15424 { |
|
15425 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15426 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15427 } |
|
15428 |
|
15429 // -------------------------------------------------------------------- |
|
15430 |
|
15431 // Note add_record_message() frees message on any case. |
|
15432 automatic_tls_handshake_message.do_not_free_variable(); |
|
15433 |
|
15434 status = add_record_message(tls_handshake_message); |
|
15435 if (status != eap_status_ok) |
|
15436 { |
|
15437 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15438 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15439 } |
|
15440 |
|
15441 // -------------------------------------------------------------------- |
|
15442 |
|
15443 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15444 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15445 } |
|
15446 |
|
15447 //-------------------------------------------------- |
|
15448 |
|
15449 EAP_FUNC_EXPORT eap_status_e tls_record_c::create_handshake_type_server_key_exchange() |
|
15450 { |
|
15451 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15452 |
|
15453 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
15454 EAP_TRACE_DEBUG( |
|
15455 m_am_tools, |
|
15456 TRACE_FLAGS_DEFAULT, |
|
15457 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::create_handshake_type_server_key_exchange()\n"), |
|
15458 this, |
|
15459 (m_is_client == true ? "client": "server"))); |
|
15460 |
|
15461 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::create_handshake_type_server_key_exchange()"); |
|
15462 |
|
15463 eap_status_e status = eap_status_process_general_error; |
|
15464 eap_variable_data_c hash(m_am_tools); |
|
15465 |
|
15466 |
|
15467 #if EAP_TLS_UNSUPPORTED_CIPHER_SUITE |
|
15468 #error This one needs more code. RSA key exchange with different parameters is NOT supported. |
|
15469 if (cipher_suite_is_TLS_RSA() == true) |
|
15470 { |
|
15471 // RSA modulus and exponent are included when selected |
|
15472 // cipher suite is using RSA key exchange |
|
15473 // and parameters are different than included in the certificate. |
|
15474 // 0 1 2 3 |
|
15475 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
15476 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15477 // | rsa_modulus length | | |
|
15478 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15479 // | | |
|
15480 // + + |
|
15481 // | rsa_modulus | |
|
15482 // + + |
|
15483 // | | |
|
15484 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15485 // | rsa_exponent length | | |
|
15486 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15487 // | | |
|
15488 // + rsa_exponent + |
|
15489 // | | |
|
15490 // + + |
|
15491 // | | |
|
15492 // + + |
|
15493 // | | |
|
15494 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15495 // | | |
|
15496 // + + |
|
15497 // | digitally-signed MD5 hash 16 bytes | |
|
15498 // + (ClientHello.random + ServerHello.random + ServerParams) + |
|
15499 // | | |
|
15500 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15501 // | | |
|
15502 // + + |
|
15503 // | digitally-signed SHA-1 hash 20 bytes | |
|
15504 // + (ClientHello.random + ServerHello.random + ServerParams) + |
|
15505 // | | |
|
15506 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15507 |
|
15508 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15509 return EAP_STATUS_RETURN(m_am_tools, eap_status_not_supported); |
|
15510 } |
|
15511 else |
|
15512 #endif |
|
15513 if (cipher_suite_is_TLS_DHE_DSS() == true) |
|
15514 { |
|
15515 // Diffie-Hellman prime modulus, generator and server's |
|
15516 // Diffie-Hellman public value (g^X mod p) |
|
15517 // are included when selected cipher suite is ephemeral Diffie-Hellman key exchange. |
|
15518 // 0 1 2 3 |
|
15519 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
15520 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15521 // | DH p length | | |
|
15522 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15523 // | | |
|
15524 // + + |
|
15525 // | DH p value (prime modulus) | |
|
15526 // + + |
|
15527 // | | |
|
15528 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15529 // | DH g length | | |
|
15530 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15531 // | | |
|
15532 // + + |
|
15533 // | DH g value (generator) | |
|
15534 // + + |
|
15535 // | | |
|
15536 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15537 // | DH Ys length | | |
|
15538 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15539 // | | |
|
15540 // + + |
|
15541 // | DH Ys value | |
|
15542 // + (server's Diffie-Hellman public value) + |
|
15543 // | | |
|
15544 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15545 // | | |
|
15546 // + + |
|
15547 // | digitally-signed SHA-1 hash 47 bytes | |
|
15548 // + (ClientHello.random + ServerHello.random + ServerParams) + |
|
15549 // | | |
|
15550 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15551 |
|
15552 status = create_server_key_exchange_sha1_hash( |
|
15553 &m_dhe_prime, |
|
15554 &m_dhe_group_generator, |
|
15555 &m_own_public_dhe_key, |
|
15556 &hash); |
|
15557 if (status != eap_status_ok) |
|
15558 { |
|
15559 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15560 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15561 } |
|
15562 |
|
15563 EAP_TRACE_DATA_DEBUG( |
|
15564 m_am_tools, |
|
15565 TRACE_FLAGS_DEFAULT, |
|
15566 (EAPL("TLS: create_handshake_type_server_key_exchange(): hash"), |
|
15567 hash.get_data(hash.get_data_length()), |
|
15568 hash.get_data_length())); |
|
15569 } |
|
15570 else if (cipher_suite_is_TLS_DHE_RSA() == true) |
|
15571 { |
|
15572 // Diffie-Hellman prime modulus, generator and server's |
|
15573 // Diffie-Hellman public value (g^X mod p) |
|
15574 // are included when selected cipher suite is ephemeral Diffie-Hellman key exchange. |
|
15575 // 0 1 2 3 |
|
15576 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
15577 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15578 // | DH p length | | |
|
15579 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15580 // | | |
|
15581 // + + |
|
15582 // | DH p value (prime modulus) | |
|
15583 // + + |
|
15584 // | | |
|
15585 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15586 // | DH g length | | |
|
15587 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15588 // | | |
|
15589 // + + |
|
15590 // | DH g value (generator) | |
|
15591 // + + |
|
15592 // | | |
|
15593 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15594 // | DH Ys length | | |
|
15595 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15596 // | | |
|
15597 // + + |
|
15598 // | DH Ys value | |
|
15599 // + (server's Diffie-Hellman public value) + |
|
15600 // | | |
|
15601 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15602 // | | |
|
15603 // + + |
|
15604 // | digitally-signed MD5 hash 16 bytes | |
|
15605 // + (ClientHello.random + ServerHello.random + ServerParams) + |
|
15606 // | | |
|
15607 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15608 // | | |
|
15609 // + + |
|
15610 // | digitally-signed SHA-1 hash 47 bytes | |
|
15611 // + (ClientHello.random + ServerHello.random + ServerParams) + |
|
15612 // | | |
|
15613 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15614 |
|
15615 eap_variable_data_c md5_hash(m_am_tools); |
|
15616 |
|
15617 status = create_server_key_exchange_md5_hash( |
|
15618 &m_dhe_prime, |
|
15619 &m_dhe_group_generator, |
|
15620 &m_own_public_dhe_key, |
|
15621 &md5_hash); |
|
15622 if (status != eap_status_ok) |
|
15623 { |
|
15624 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15625 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15626 } |
|
15627 |
|
15628 EAP_TRACE_DATA_DEBUG( |
|
15629 m_am_tools, |
|
15630 TRACE_FLAGS_DEFAULT, |
|
15631 (EAPL("TLS: create_handshake_type_server_key_exchange() md5_hash"), |
|
15632 md5_hash.get_data(md5_hash.get_data_length()), |
|
15633 md5_hash.get_data_length())); |
|
15634 |
|
15635 eap_variable_data_c sha1_hash(m_am_tools); |
|
15636 |
|
15637 status = create_server_key_exchange_sha1_hash( |
|
15638 &m_dhe_prime, |
|
15639 &m_dhe_group_generator, |
|
15640 &m_own_public_dhe_key, |
|
15641 &sha1_hash); |
|
15642 if (status != eap_status_ok) |
|
15643 { |
|
15644 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15645 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15646 } |
|
15647 |
|
15648 EAP_TRACE_DATA_DEBUG( |
|
15649 m_am_tools, |
|
15650 TRACE_FLAGS_DEFAULT, |
|
15651 (EAPL("TLS: create_handshake_type_server_key_exchange() sha1_hash"), |
|
15652 sha1_hash.get_data(sha1_hash.get_data_length()), |
|
15653 sha1_hash.get_data_length())); |
|
15654 |
|
15655 status = hash.add_data(&md5_hash); |
|
15656 if (status != eap_status_ok) |
|
15657 { |
|
15658 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15659 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15660 } |
|
15661 |
|
15662 status = hash.add_data(&sha1_hash); |
|
15663 if (status != eap_status_ok) |
|
15664 { |
|
15665 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15666 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15667 } |
|
15668 |
|
15669 EAP_TRACE_DATA_DEBUG( |
|
15670 m_am_tools, |
|
15671 TRACE_FLAGS_DEFAULT, |
|
15672 (EAPL("TLS: create_handshake_type_server_key_exchange(): hash"), |
|
15673 hash.get_data(hash.get_data_length()), |
|
15674 hash.get_data_length())); |
|
15675 } |
|
15676 #if defined(USE_FAST_EAP_TYPE) |
|
15677 else if (m_eap_type == eap_type_fast |
|
15678 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true |
|
15679 && cipher_suite_is_TLS_DH_anon() == true) |
|
15680 { |
|
15681 // Diffie-Hellman prime modulus, generator and server's |
|
15682 // Diffie-Hellman public value (g^X mod p) |
|
15683 // are included when selected cipher suite is ephemeral Diffie-Hellman key exchange. |
|
15684 // NOTE: Here are no signed hash. This is not authenticated at all and vulnerable to |
|
15685 // man-in-the-middle attacks. |
|
15686 // 0 1 2 3 |
|
15687 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
15688 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15689 // | DH p length | | |
|
15690 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15691 // | | |
|
15692 // + + |
|
15693 // | DH p value (prime modulus) | |
|
15694 // + + |
|
15695 // | | |
|
15696 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15697 // | DH g length | | |
|
15698 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15699 // | | |
|
15700 // + + |
|
15701 // | DH g value (generator) | |
|
15702 // + + |
|
15703 // | | |
|
15704 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15705 // | DH Ys length | | |
|
15706 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15707 // | | |
|
15708 // + + |
|
15709 // | DH Ys value | |
|
15710 // + (server's Diffie-Hellman public value) + |
|
15711 // | | |
|
15712 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15713 |
|
15714 |
|
15715 // NOTE: Here the return value is eap_status_pending_request to avoid error after return. |
|
15716 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15717 return EAP_STATUS_RETURN(m_am_tools, eap_status_pending_request); |
|
15718 } |
|
15719 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
15720 else |
|
15721 { |
|
15722 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15723 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_cipher_suite); |
|
15724 } |
|
15725 |
|
15726 EAP_TRACE_DEBUG( |
|
15727 m_am_tools, |
|
15728 TRACE_FLAGS_DEFAULT, |
|
15729 (EAPL("TLS: %s: pki_function: create_handshake_type_server_key_exchange()\n"), |
|
15730 (m_is_client == true ? "client": "server"))); |
|
15731 |
|
15732 m_signed_message_hash.reset(); |
|
15733 |
|
15734 // NOTE this function is asyncronous. This causes complex control flow. |
|
15735 // This function call will be completed always. |
|
15736 status = m_am_tls_services->sign_with_private_key( |
|
15737 &hash); |
|
15738 if (status == eap_status_pending_request) |
|
15739 { |
|
15740 // This is pending query, that will be completed by complete_sign_with_private_key() call. |
|
15741 m_pending_sign_with_private_key = true; |
|
15742 } |
|
15743 else if (status == eap_status_completed_request) |
|
15744 { |
|
15745 // This is already completed by complete_sign_with_private_key() call. |
|
15746 } |
|
15747 else if (status == eap_status_ok) |
|
15748 { |
|
15749 // This is also an error case, because this call is always completed on success. |
|
15750 status = eap_status_process_general_error; |
|
15751 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15752 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15753 } |
|
15754 else // All other status values means error, because this call is always completed on success. |
|
15755 { |
|
15756 // This is an error case. |
|
15757 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15758 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
15759 } |
|
15760 |
|
15761 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15762 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15763 } |
|
15764 |
|
15765 //-------------------------------------------------- |
|
15766 |
|
15767 EAP_FUNC_EXPORT eap_status_e tls_record_c::complete_create_handshake_type_client_key_exchange() |
|
15768 { |
|
15769 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15770 |
|
15771 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
15772 EAP_TRACE_DEBUG( |
|
15773 m_am_tools, |
|
15774 TRACE_FLAGS_DEFAULT, |
|
15775 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::complete_create_handshake_type_client_key_exchange(): cipher suite=%d=%s\n"), |
|
15776 this, |
|
15777 (m_is_client == true ? "client": "server"), |
|
15778 m_selected_cipher_suite, |
|
15779 eap_tls_trace_string_c::get_cipher_suite_string(m_selected_cipher_suite))); |
|
15780 |
|
15781 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::complete_create_handshake_type_client_key_exchange()"); |
|
15782 |
|
15783 tls_handshake_message_c *tls_handshake_message = 0; |
|
15784 |
|
15785 eap_automatic_variable_c<tls_handshake_message_c> |
|
15786 automatic_tls_handshake_message(m_am_tools); |
|
15787 |
|
15788 eap_status_e status = allocate_handshake_message( |
|
15789 &tls_handshake_message, |
|
15790 &automatic_tls_handshake_message, |
|
15791 tls_handshake_type_client_key_exchange); |
|
15792 if (status != eap_status_ok) |
|
15793 { |
|
15794 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15795 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15796 } |
|
15797 |
|
15798 // -------------------------------------------------------------------- |
|
15799 |
|
15800 if (cipher_suite_is_TLS_RSA() == true) |
|
15801 { |
|
15802 // Encrypted premaster secret is included when selected |
|
15803 // cipher suite is using RSA key exchange. |
|
15804 // First two bytes are version of TLS. |
|
15805 // 0 1 2 3 |
|
15806 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
15807 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15808 // | | |
|
15809 // +-+-+-+-+-+-+-+-+ + |
|
15810 // | | |
|
15811 // + + |
|
15812 // | Encrypted Premaster Secret (48 bytes) | |
|
15813 // + + |
|
15814 // | | |
|
15815 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15816 |
|
15817 if (m_own_encrypted_premaster_secret.get_is_valid_data() == false) |
|
15818 { |
|
15819 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15820 return EAP_STATUS_RETURN(m_am_tools, eap_status_process_general_error); |
|
15821 } |
|
15822 |
|
15823 EAP_TRACE_DATA_DEBUG( |
|
15824 m_am_tools, |
|
15825 TRACE_FLAGS_DEFAULT, |
|
15826 (EAPL("TLS: complete_create_handshake_type_client_key_exchange(): encrypted premaster_secret"), |
|
15827 m_own_encrypted_premaster_secret.get_data(), |
|
15828 m_own_encrypted_premaster_secret.get_data_length())); |
|
15829 |
|
15830 status = tls_handshake_message->set_encrypted_premaster_secret( |
|
15831 &m_own_encrypted_premaster_secret); |
|
15832 if (status != eap_status_ok) |
|
15833 { |
|
15834 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15835 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15836 } |
|
15837 } |
|
15838 else if (cipher_suite_is_TLS_DHE_DSS() == true |
|
15839 || cipher_suite_is_TLS_DHE_RSA() == true |
|
15840 #if defined(USE_FAST_EAP_TYPE) |
|
15841 || (m_eap_type == eap_type_fast |
|
15842 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true |
|
15843 && cipher_suite_is_TLS_DH_anon() == true) |
|
15844 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
15845 ) |
|
15846 { |
|
15847 // Diffie-Hellman Yc is included when selected cipher suite is |
|
15848 // ephemeral Diffie-Hellman key exchange. |
|
15849 // 0 1 2 3 |
|
15850 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
15851 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15852 // | DH Yc length | | |
|
15853 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15854 // | | |
|
15855 // + + |
|
15856 // | DH Yc value | |
|
15857 // + + |
|
15858 // | | |
|
15859 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15860 |
|
15861 if (m_own_public_dhe_key.get_is_valid_data() == false) |
|
15862 { |
|
15863 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15864 return EAP_STATUS_RETURN(m_am_tools, eap_status_process_general_error); |
|
15865 } |
|
15866 |
|
15867 status = tls_handshake_message->set_public_dhe_key( |
|
15868 &m_own_public_dhe_key); |
|
15869 if (status != eap_status_ok) |
|
15870 { |
|
15871 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15872 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15873 } |
|
15874 } |
|
15875 else |
|
15876 { |
|
15877 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15878 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_cipher_suite); |
|
15879 } |
|
15880 |
|
15881 // -------------------------------------------------------------------- |
|
15882 |
|
15883 // Note add_record_message() frees message on any case. |
|
15884 automatic_tls_handshake_message.do_not_free_variable(); |
|
15885 |
|
15886 status = add_record_message(tls_handshake_message); |
|
15887 if (status != eap_status_ok) |
|
15888 { |
|
15889 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15890 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15891 } |
|
15892 |
|
15893 // -------------------------------------------------------------------- |
|
15894 |
|
15895 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15896 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15897 } |
|
15898 |
|
15899 //-------------------------------------------------- |
|
15900 |
|
15901 EAP_FUNC_EXPORT eap_status_e tls_record_c::create_handshake_type_client_key_exchange() |
|
15902 { |
|
15903 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15904 |
|
15905 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
15906 EAP_TRACE_DEBUG( |
|
15907 m_am_tools, |
|
15908 TRACE_FLAGS_DEFAULT, |
|
15909 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::create_handshake_type_client_key_exchange()\n"), |
|
15910 this, |
|
15911 (m_is_client == true ? "client": "server"))); |
|
15912 |
|
15913 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::create_handshake_type_client_key_exchange()"); |
|
15914 |
|
15915 eap_status_e status = eap_status_process_general_error; |
|
15916 |
|
15917 if (cipher_suite_is_TLS_RSA() == true) |
|
15918 { |
|
15919 // Encrypted premaster secret is included when selected |
|
15920 // cipher suite is using RSA key exchange. |
|
15921 // First two bytes are version of TLS. |
|
15922 // 0 1 2 3 |
|
15923 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
15924 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15925 // | | |
|
15926 // +-+-+-+-+-+-+-+-+ + |
|
15927 // | | |
|
15928 // + + |
|
15929 // | Encrypted Premaster Secret (48 bytes) | |
|
15930 // + + |
|
15931 // | | |
|
15932 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15933 |
|
15934 if (m_premaster_secret.get_is_valid_data() == false) |
|
15935 { |
|
15936 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15937 return EAP_STATUS_RETURN(m_am_tools, eap_status_key_error); |
|
15938 } |
|
15939 |
|
15940 EAP_TRACE_DEBUG( |
|
15941 m_am_tools, |
|
15942 TRACE_FLAGS_DEFAULT, |
|
15943 (EAPL("TLS: %s: pki_function: rsa_encrypt_with_public_key()\n"), |
|
15944 (m_is_client == true ? "client": "server"))); |
|
15945 |
|
15946 EAP_TRACE_DATA_DEBUG( |
|
15947 m_am_tools, |
|
15948 TRACE_FLAGS_DEFAULT, |
|
15949 (EAPL("TLS: create_handshake_type_client_key_exchange(): premaster_secret"), |
|
15950 m_premaster_secret.get_data(), |
|
15951 m_premaster_secret.get_data_length())); |
|
15952 |
|
15953 status = m_am_tls_services->rsa_encrypt_with_public_key( |
|
15954 &m_premaster_secret); |
|
15955 |
|
15956 if (status == eap_status_pending_request) |
|
15957 { |
|
15958 // This is pending query, that will be completed by |
|
15959 // complete_rsa_encrypt_with_public_key() call. |
|
15960 m_pending_rsa_encrypt_with_public_key = true; |
|
15961 } |
|
15962 else if (status == eap_status_completed_request) |
|
15963 { |
|
15964 // This is already completed by complete_rsa_encrypt_with_public_key() call. |
|
15965 } |
|
15966 else if (status == eap_status_ok) |
|
15967 { |
|
15968 // This is also an error case, because this call is always completed on success. |
|
15969 status = eap_status_process_general_error; |
|
15970 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15971 return EAP_STATUS_RETURN(m_am_tools, status); |
|
15972 } |
|
15973 else // All other status values means error, because this |
|
15974 // call is always completed on success. |
|
15975 { |
|
15976 // This is an error case. |
|
15977 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
15978 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
15979 } |
|
15980 } |
|
15981 else if (cipher_suite_is_TLS_DHE_DSS() == true |
|
15982 || cipher_suite_is_TLS_DHE_RSA() == true |
|
15983 #if defined(USE_FAST_EAP_TYPE) |
|
15984 || (m_eap_type == eap_type_fast |
|
15985 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true |
|
15986 && cipher_suite_is_TLS_DH_anon() == true) |
|
15987 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
15988 ) |
|
15989 { |
|
15990 // Diffie-Hellman Yc is included when selected cipher suite is |
|
15991 // ephemeral Diffie-Hellman key exchange. |
|
15992 // 0 1 2 3 |
|
15993 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
15994 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
15995 // | DH Yc length | | |
|
15996 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
15997 // | | |
|
15998 // + + |
|
15999 // | DH Yc value | |
|
16000 // + + |
|
16001 // | | |
|
16002 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
16003 |
|
16004 // These cipher suites does not need asyncronous operations. |
|
16005 // Still these cipher suites are completed in |
|
16006 // complete_create_handshake_type_client_key_exchange(). |
|
16007 status = eap_status_ok; |
|
16008 } |
|
16009 else |
|
16010 { |
|
16011 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16012 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_cipher_suite); |
|
16013 } |
|
16014 |
|
16015 // -------------------------------------------------------------------- |
|
16016 |
|
16017 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16018 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16019 } |
|
16020 |
|
16021 //-------------------------------------------------- |
|
16022 |
|
16023 EAP_FUNC_EXPORT eap_status_e tls_record_c::complete_create_handshake_type_certificate_verify() |
|
16024 { |
|
16025 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16026 |
|
16027 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
16028 EAP_TRACE_DEBUG( |
|
16029 m_am_tools, |
|
16030 TRACE_FLAGS_DEFAULT, |
|
16031 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::complete_create_handshake_type_certificate_verify()\n"), |
|
16032 this, |
|
16033 (m_is_client == true ? "client": "server"))); |
|
16034 |
|
16035 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::complete_create_handshake_type_certificate_verify()"); |
|
16036 |
|
16037 tls_handshake_message_c *tls_handshake_message = 0; |
|
16038 |
|
16039 eap_automatic_variable_c<tls_handshake_message_c> |
|
16040 automatic_tls_handshake_message(m_am_tools); |
|
16041 |
|
16042 eap_status_e status = allocate_handshake_message( |
|
16043 &tls_handshake_message, |
|
16044 &automatic_tls_handshake_message, |
|
16045 tls_handshake_type_certificate_verify); |
|
16046 if (status != eap_status_ok) |
|
16047 { |
|
16048 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16049 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16050 } |
|
16051 |
|
16052 EAP_TRACE_DATA_DEBUG( |
|
16053 m_am_tools, |
|
16054 TRACE_FLAGS_DEFAULT, |
|
16055 (EAPL("TLS: complete_create_handshake_type_certificate_verify(): m_signed_message_hash"), |
|
16056 m_signed_message_hash.get_data(m_signed_message_hash.get_data_length()), |
|
16057 m_signed_message_hash.get_data_length())); |
|
16058 |
|
16059 status = tls_handshake_message->set_signed_message_hash( |
|
16060 &m_signed_message_hash); |
|
16061 if (status != eap_status_ok) |
|
16062 { |
|
16063 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16064 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16065 } |
|
16066 |
|
16067 // -------------------------------------------------------------------- |
|
16068 |
|
16069 // Note add_record_message() frees message on any case. |
|
16070 automatic_tls_handshake_message.do_not_free_variable(); |
|
16071 |
|
16072 status = add_record_message(tls_handshake_message); |
|
16073 if (status != eap_status_ok) |
|
16074 { |
|
16075 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16076 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16077 } |
|
16078 |
|
16079 // -------------------------------------------------------------------- |
|
16080 |
|
16081 // -------------------------------------------------------------------- |
|
16082 |
|
16083 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16084 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16085 } |
|
16086 |
|
16087 |
|
16088 //-------------------------------------------------- |
|
16089 |
|
16090 EAP_FUNC_EXPORT eap_status_e tls_record_c::create_handshake_type_certificate_verify() |
|
16091 { |
|
16092 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16093 |
|
16094 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
16095 EAP_TRACE_DEBUG( |
|
16096 m_am_tools, |
|
16097 TRACE_FLAGS_DEFAULT, |
|
16098 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::create_handshake_type_certificate_verify()\n"), |
|
16099 this, |
|
16100 (m_is_client == true ? "client": "server"))); |
|
16101 |
|
16102 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::create_handshake_type_certificate_verify()"); |
|
16103 |
|
16104 // -------------------------------------------------------------------- |
|
16105 |
|
16106 if (cipher_suite_is_TLS_RSA() == true) |
|
16107 { |
|
16108 // 0 1 2 3 |
|
16109 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
16110 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
16111 // | | |
|
16112 // +-+-+-+-+-+-+-+-+ + |
|
16113 // | | |
|
16114 // + Signed MD5 hash + |
|
16115 // | (16 bytes) | |
|
16116 // + + |
|
16117 // | | |
|
16118 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
16119 // | | |
|
16120 // + Signed SHA hash + |
|
16121 // | (20 bytes) | |
|
16122 // + + |
|
16123 // | | |
|
16124 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
16125 |
|
16126 // this will be created in tls_handshake_message_c::add_message_data(). |
|
16127 } |
|
16128 else if (cipher_suite_is_TLS_DHE_DSS() == true |
|
16129 || cipher_suite_is_TLS_DHE_RSA() == true) |
|
16130 { |
|
16131 // 0 1 2 3 |
|
16132 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
16133 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
16134 // | | |
|
16135 // +-+-+-+-+-+-+-+-+ + |
|
16136 // | | |
|
16137 // + Signed SHA hash + |
|
16138 // | (48 bytes) | |
|
16139 // + + |
|
16140 // | | |
|
16141 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
16142 |
|
16143 // this will be created in tls_handshake_message_c::add_message_data(). |
|
16144 } |
|
16145 else |
|
16146 { |
|
16147 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16148 return EAP_STATUS_RETURN(m_am_tools, eap_status_not_supported); |
|
16149 } |
|
16150 |
|
16151 eap_status_e status = message_hash_save_certificate_verify(); |
|
16152 if (status != eap_status_ok) |
|
16153 { |
|
16154 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16155 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16156 } |
|
16157 |
|
16158 eap_variable_data_c message_hash(m_am_tools); |
|
16159 |
|
16160 status = message_hash_create( |
|
16161 false, |
|
16162 tls_handshake_type_certificate_verify, |
|
16163 &message_hash, |
|
16164 m_is_client); |
|
16165 if (status != eap_status_ok) |
|
16166 { |
|
16167 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16168 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16169 } |
|
16170 |
|
16171 EAP_TRACE_DEBUG( |
|
16172 m_am_tools, |
|
16173 TRACE_FLAGS_DEFAULT, |
|
16174 (EAPL("TLS: %s: pki_function: sign_with_private_key()\n"), |
|
16175 (m_is_client == true ? "client": "server"))); |
|
16176 |
|
16177 EAP_TRACE_DATA_DEBUG( |
|
16178 m_am_tools, |
|
16179 TRACE_FLAGS_DEFAULT, |
|
16180 (EAPL("TLS: create_handshake_type_certificate_verify() message_hash"), |
|
16181 message_hash.get_data(message_hash.get_data_length()), |
|
16182 message_hash.get_data_length())); |
|
16183 |
|
16184 // NOTE this function is asyncronous. This causes complex control flow. |
|
16185 status = m_am_tls_services->sign_with_private_key( |
|
16186 &message_hash); |
|
16187 if (status == eap_status_pending_request) |
|
16188 { |
|
16189 // This is pending query, that will be completed by complete_query_certificate_chain() call. |
|
16190 m_pending_sign_with_private_key = true; |
|
16191 } |
|
16192 else if (status == eap_status_completed_request) |
|
16193 { |
|
16194 // This is already completed by complete_query_certificate_chain() call. |
|
16195 } |
|
16196 else if (status == eap_status_ok) |
|
16197 { |
|
16198 // This is also an error case, because this call is always completed on success. |
|
16199 status = eap_status_process_general_error; |
|
16200 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16201 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16202 } |
|
16203 else // All other status values means error, because this call is always completed on success. |
|
16204 { |
|
16205 // This is an error case. |
|
16206 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16207 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
16208 } |
|
16209 |
|
16210 // -------------------------------------------------------------------- |
|
16211 |
|
16212 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16213 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16214 } |
|
16215 |
|
16216 |
|
16217 //-------------------------------------------------- |
|
16218 |
|
16219 EAP_FUNC_EXPORT eap_status_e tls_record_c::create_handshake_type_finished() |
|
16220 { |
|
16221 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16222 |
|
16223 EAP_TRACE_DEBUG( |
|
16224 m_am_tools, |
|
16225 TRACE_FLAGS_DEFAULT, |
|
16226 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::create_handshake_type_finished()\n"), |
|
16227 this, |
|
16228 (m_is_client == true ? "client": "server"))); |
|
16229 |
|
16230 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::create_handshake_type_finished()"); |
|
16231 |
|
16232 // 0 1 2 3 |
|
16233 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
16234 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
16235 // | | |
|
16236 // +-+-+-+-+-+-+-+-+ + |
|
16237 // | | |
|
16238 // + + |
|
16239 // | PRF(master_secret, finished_label, | |
|
16240 // + MD5(handshake_messages) + + |
|
16241 // | SHA-1(handshake_messages)) [0..11] | |
|
16242 // + + |
|
16243 // | | |
|
16244 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
16245 |
|
16246 tls_handshake_message_c *tls_handshake_message = 0; |
|
16247 |
|
16248 eap_automatic_variable_c<tls_handshake_message_c> |
|
16249 automatic_tls_handshake_message(m_am_tools); |
|
16250 |
|
16251 eap_status_e status = allocate_handshake_message( |
|
16252 &tls_handshake_message, |
|
16253 &automatic_tls_handshake_message, |
|
16254 tls_handshake_type_finished); |
|
16255 if (status != eap_status_ok) |
|
16256 { |
|
16257 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16258 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16259 } |
|
16260 |
|
16261 // -------------------------------------------------------------------- |
|
16262 |
|
16263 // Note add_record_message() frees message on any case. |
|
16264 automatic_tls_handshake_message.do_not_free_variable(); |
|
16265 |
|
16266 status = add_record_message(tls_handshake_message); |
|
16267 if (status != eap_status_ok) |
|
16268 { |
|
16269 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16270 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16271 } |
|
16272 |
|
16273 // -------------------------------------------------------------------- |
|
16274 |
|
16275 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16276 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16277 } |
|
16278 |
|
16279 //-------------------------------------------------- |
|
16280 |
|
16281 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
16282 |
|
16283 EAP_FUNC_EXPORT eap_status_e tls_record_c::create_handshake_type_new_session_ticket() |
|
16284 { |
|
16285 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16286 |
|
16287 EAP_TRACE_DEBUG( |
|
16288 m_am_tools, |
|
16289 TRACE_FLAGS_DEFAULT, |
|
16290 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::create_handshake_type_new_session_ticket()\n"), |
|
16291 this, |
|
16292 (m_is_client == true ? "client": "server"))); |
|
16293 |
|
16294 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::create_handshake_type_new_session_ticket()"); |
|
16295 |
|
16296 // 0 1 2 3 |
|
16297 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
16298 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
16299 // | ticket lifetime hint (4 bytes) ... | |
|
16300 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
16301 // | ... | opaque ticket ... n bytes |
|
16302 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
16303 |
|
16304 tls_handshake_message_c *tls_handshake_message = 0; |
|
16305 |
|
16306 eap_automatic_variable_c<tls_handshake_message_c> |
|
16307 automatic_tls_handshake_message(m_am_tools); |
|
16308 |
|
16309 eap_status_e status = allocate_handshake_message( |
|
16310 &tls_handshake_message, |
|
16311 &automatic_tls_handshake_message, |
|
16312 tls_handshake_type_new_session_ticket); |
|
16313 if (status != eap_status_ok) |
|
16314 { |
|
16315 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16316 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16317 } |
|
16318 |
|
16319 // -------------------------------------------------------------------- |
|
16320 |
|
16321 |
|
16322 const tls_extension_c * const p_new_session_ticket = tls_extension_c::get_tls_extension( |
|
16323 tls_extension_type_session_ticket, |
|
16324 &m_supported_tls_extensions, |
|
16325 m_am_tools); |
|
16326 |
|
16327 if (p_new_session_ticket != 0) |
|
16328 { |
|
16329 eap_array_c<tls_extension_c> session_ticket_extension_array(m_am_tools); |
|
16330 |
|
16331 tls_extension_c * const p_new_session_ticket_copy = p_new_session_ticket->copy(); |
|
16332 if (p_new_session_ticket_copy == 0) |
|
16333 { |
|
16334 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16335 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
16336 } |
|
16337 |
|
16338 status = session_ticket_extension_array.add_object(p_new_session_ticket_copy, true); |
|
16339 if (status != eap_status_ok) |
|
16340 { |
|
16341 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16342 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16343 } |
|
16344 |
|
16345 status = tls_handshake_message->set_tls_extensions(&session_ticket_extension_array); |
|
16346 if (status != eap_status_ok) |
|
16347 { |
|
16348 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16349 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16350 } |
|
16351 } |
|
16352 |
|
16353 // -------------------------------------------------------------------- |
|
16354 |
|
16355 // Note add_record_message() frees message on any case. |
|
16356 automatic_tls_handshake_message.do_not_free_variable(); |
|
16357 |
|
16358 status = add_record_message(tls_handshake_message); |
|
16359 if (status != eap_status_ok) |
|
16360 { |
|
16361 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16362 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16363 } |
|
16364 |
|
16365 // -------------------------------------------------------------------- |
|
16366 |
|
16367 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16368 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16369 } |
|
16370 |
|
16371 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
16372 |
|
16373 //-------------------------------------------------- |
|
16374 |
|
16375 EAP_FUNC_EXPORT eap_status_e tls_record_c::create_change_cipher_spec_type_change_cipher_spec() |
|
16376 { |
|
16377 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16378 |
|
16379 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
16380 EAP_TRACE_DEBUG( |
|
16381 m_am_tools, |
|
16382 TRACE_FLAGS_DEFAULT, |
|
16383 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::create_change_cipher_spec_type_change_cipher_spec()\n"), |
|
16384 this, |
|
16385 (m_is_client == true ? "client": "server"))); |
|
16386 |
|
16387 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::create_change_cipher_spec_type_change_cipher_spec()"); |
|
16388 |
|
16389 // 0 1 2 3 |
|
16390 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
16391 // +-+-+-+-+-+-+-+-+ |
|
16392 // | CCS: 1 | |
|
16393 // +-+-+-+-+-+-+-+-+ |
|
16394 |
|
16395 tls_change_cipher_spec_message_c * const tls_change_cipher_spec_message |
|
16396 = new tls_change_cipher_spec_message_c(m_am_tools, this, m_is_client); |
|
16397 |
|
16398 eap_automatic_variable_c<tls_change_cipher_spec_message_c> |
|
16399 automatic_tls_change_cipher_spec_message( |
|
16400 m_am_tools, tls_change_cipher_spec_message); |
|
16401 |
|
16402 if (tls_change_cipher_spec_message == 0 |
|
16403 || tls_change_cipher_spec_message->get_is_valid() == false) |
|
16404 { |
|
16405 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16406 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
16407 } |
|
16408 |
|
16409 eap_status_e status = tls_change_cipher_spec_message->set_change_cipher_spec_type( |
|
16410 tls_change_cipher_spec_type_change_cipher_spec); |
|
16411 if (status != eap_status_ok) |
|
16412 { |
|
16413 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16414 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16415 } |
|
16416 |
|
16417 // -------------------------------------------------------------------- |
|
16418 |
|
16419 // Note add_record_message() frees message on any case. |
|
16420 automatic_tls_change_cipher_spec_message.do_not_free_variable(); |
|
16421 |
|
16422 status = add_record_message(tls_change_cipher_spec_message); |
|
16423 if (status != eap_status_ok) |
|
16424 { |
|
16425 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16426 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16427 } |
|
16428 |
|
16429 // -------------------------------------------------------------------- |
|
16430 |
|
16431 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16432 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16433 } |
|
16434 |
|
16435 //-------------------------------------------------- |
|
16436 |
|
16437 EAP_FUNC_EXPORT eap_status_e tls_record_c::finish_handshake() |
|
16438 { |
|
16439 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16440 |
|
16441 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
16442 |
|
16443 EAP_TRACE_DEBUG( |
|
16444 m_am_tools, |
|
16445 TRACE_FLAGS_DEFAULT, |
|
16446 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::finish_handshake(): m_tls_session_type=%d=%s, state=%d=%s\n"), |
|
16447 this, |
|
16448 (m_is_client == true ? "client": "server"), |
|
16449 m_tls_session_type, |
|
16450 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type), |
|
16451 m_tls_peap_state, |
|
16452 eap_tls_trace_string_c::get_state_string(m_tls_peap_state))); |
|
16453 |
|
16454 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::finish_handshake()"); |
|
16455 |
|
16456 EAP_TRACE_DATA_DEBUG( |
|
16457 m_am_tools, |
|
16458 TRACE_FLAGS_DEFAULT, |
|
16459 (EAPL("TLS: finish_handshake(): m_master_secret"), |
|
16460 m_master_secret.get_data(), |
|
16461 m_master_secret.get_data_length())); |
|
16462 |
|
16463 EAP_TRACE_DATA_DEBUG( |
|
16464 m_am_tools, |
|
16465 TRACE_FLAGS_DEFAULT, |
|
16466 (EAPL("TLS: finish_handshake(): m_client_handshake_random_value"), |
|
16467 m_client_handshake_random_value.get_data(), |
|
16468 m_client_handshake_random_value.get_data_length())); |
|
16469 |
|
16470 EAP_TRACE_DATA_DEBUG( |
|
16471 m_am_tools, |
|
16472 TRACE_FLAGS_DEFAULT, |
|
16473 (EAPL("TLS: finish_handshake(): m_server_handshake_random_value"), |
|
16474 m_server_handshake_random_value.get_data(), |
|
16475 m_server_handshake_random_value.get_data_length())); |
|
16476 |
|
16477 |
|
16478 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
16479 |
|
16480 eap_status_e status(eap_status_ok); |
|
16481 |
|
16482 tls_identity_privacy_handshake_state_e tmp_identity_privacy_handshake_state = |
|
16483 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
16484 m_tls_identity_privacy_handshake_state; |
|
16485 #else |
|
16486 tls_identity_privacy_handshake_state_none; |
|
16487 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
16488 |
|
16489 |
|
16490 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
16491 if (m_tls_use_identity_privacy == false |
|
16492 || tmp_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_runs |
|
16493 || m_tls_session_type != tls_session_type_full_authentication) |
|
16494 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
16495 { |
|
16496 status = set_tls_master_secret( |
|
16497 &m_master_secret, |
|
16498 &m_client_handshake_random_value, |
|
16499 &m_server_handshake_random_value); |
|
16500 if (status != eap_status_ok) |
|
16501 { |
|
16502 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16503 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16504 } |
|
16505 } |
|
16506 |
|
16507 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
16508 |
|
16509 #if defined(USE_EAP_DEBUG_TRACE) |
|
16510 // These are for debug break points. |
|
16511 |
|
16512 if (m_is_client == true) |
|
16513 { |
|
16514 if (m_tls_session_type == tls_session_type_full_authentication) |
|
16515 { |
|
16516 EAP_TRACE_DEBUG( |
|
16517 m_am_tools, |
|
16518 TRACE_FLAGS_DEFAULT, |
|
16519 (EAPL("TLS: client, m_tls_session_type=%d=%s, state=%d=%s, privacy_handshake_state=%d=%s\n"), |
|
16520 m_tls_session_type, |
|
16521 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type), |
|
16522 m_tls_peap_state, |
|
16523 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
16524 tmp_identity_privacy_handshake_state, |
|
16525 eap_tls_trace_string_c::get_tls_identity_privacy_handshake_state_string(tmp_identity_privacy_handshake_state))); |
|
16526 |
|
16527 } |
|
16528 else if (m_tls_session_type == tls_session_type_original_session_resumption) |
|
16529 { |
|
16530 EAP_TRACE_DEBUG( |
|
16531 m_am_tools, |
|
16532 TRACE_FLAGS_DEFAULT, |
|
16533 (EAPL("TLS: client, m_tls_session_type=%d=%s, state=%d=%s, privacy_handshake_state=%d=%s\n"), |
|
16534 m_tls_session_type, |
|
16535 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type), |
|
16536 m_tls_peap_state, |
|
16537 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
16538 tmp_identity_privacy_handshake_state, |
|
16539 eap_tls_trace_string_c::get_tls_identity_privacy_handshake_state_string(tmp_identity_privacy_handshake_state))); |
|
16540 |
|
16541 } |
|
16542 else if (m_tls_session_type == tls_session_type_stateless_session_resumption) |
|
16543 { |
|
16544 EAP_TRACE_DEBUG( |
|
16545 m_am_tools, |
|
16546 TRACE_FLAGS_DEFAULT, |
|
16547 (EAPL("TLS: client, m_tls_session_type=%d=%s, state=%d=%s, privacy_handshake_state=%d=%s\n"), |
|
16548 m_tls_session_type, |
|
16549 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type), |
|
16550 m_tls_peap_state, |
|
16551 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
16552 tmp_identity_privacy_handshake_state, |
|
16553 eap_tls_trace_string_c::get_tls_identity_privacy_handshake_state_string(tmp_identity_privacy_handshake_state))); |
|
16554 } |
|
16555 #if defined(USE_FAST_EAP_TYPE) |
|
16556 else if (m_tls_session_type == tls_session_type_eap_fast_pac_session_resumption) |
|
16557 { |
|
16558 EAP_TRACE_DEBUG( |
|
16559 m_am_tools, |
|
16560 TRACE_FLAGS_DEFAULT, |
|
16561 (EAPL("TLS: client, m_tls_session_type=%d=%s, state=%d=%s, privacy_handshake_state=%d=%s\n"), |
|
16562 m_tls_session_type, |
|
16563 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type), |
|
16564 m_tls_peap_state, |
|
16565 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
16566 tmp_identity_privacy_handshake_state, |
|
16567 eap_tls_trace_string_c::get_tls_identity_privacy_handshake_state_string(tmp_identity_privacy_handshake_state))); |
|
16568 } |
|
16569 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
16570 } |
|
16571 else // if (m_is_client == false) |
|
16572 { |
|
16573 if (m_tls_session_type == tls_session_type_full_authentication) |
|
16574 { |
|
16575 EAP_TRACE_DEBUG( |
|
16576 m_am_tools, |
|
16577 TRACE_FLAGS_DEFAULT, |
|
16578 (EAPL("TLS: server, m_tls_session_type=%d=%s, state=%d=%s, privacy_handshake_state=%d=%s\n"), |
|
16579 m_tls_session_type, |
|
16580 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type), |
|
16581 m_tls_peap_state, |
|
16582 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
16583 tmp_identity_privacy_handshake_state, |
|
16584 eap_tls_trace_string_c::get_tls_identity_privacy_handshake_state_string(tmp_identity_privacy_handshake_state))); |
|
16585 |
|
16586 } |
|
16587 else if (m_tls_session_type == tls_session_type_original_session_resumption) |
|
16588 { |
|
16589 EAP_TRACE_DEBUG( |
|
16590 m_am_tools, |
|
16591 TRACE_FLAGS_DEFAULT, |
|
16592 (EAPL("TLS: server, m_tls_session_type=%d=%s, state=%d=%s, privacy_handshake_state=%d=%s\n"), |
|
16593 m_tls_session_type, |
|
16594 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type), |
|
16595 m_tls_peap_state, |
|
16596 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
16597 tmp_identity_privacy_handshake_state, |
|
16598 eap_tls_trace_string_c::get_tls_identity_privacy_handshake_state_string(tmp_identity_privacy_handshake_state))); |
|
16599 |
|
16600 } |
|
16601 else if (m_tls_session_type == tls_session_type_stateless_session_resumption) |
|
16602 { |
|
16603 EAP_TRACE_DEBUG( |
|
16604 m_am_tools, |
|
16605 TRACE_FLAGS_DEFAULT, |
|
16606 (EAPL("TLS: server, m_tls_session_type=%d=%s, state=%d=%s, privacy_handshake_state=%d=%s\n"), |
|
16607 m_tls_session_type, |
|
16608 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type), |
|
16609 m_tls_peap_state, |
|
16610 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
16611 tmp_identity_privacy_handshake_state, |
|
16612 eap_tls_trace_string_c::get_tls_identity_privacy_handshake_state_string(tmp_identity_privacy_handshake_state))); |
|
16613 } |
|
16614 #if defined(USE_FAST_EAP_TYPE) |
|
16615 else if (m_tls_session_type == tls_session_type_eap_fast_pac_session_resumption) |
|
16616 { |
|
16617 EAP_TRACE_DEBUG( |
|
16618 m_am_tools, |
|
16619 TRACE_FLAGS_DEFAULT, |
|
16620 (EAPL("TLS: server, m_tls_session_type=%d=%s, state=%d=%s, privacy_handshake_state=%d=%s\n"), |
|
16621 m_tls_session_type, |
|
16622 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type), |
|
16623 m_tls_peap_state, |
|
16624 eap_tls_trace_string_c::get_state_string(m_tls_peap_state), |
|
16625 tmp_identity_privacy_handshake_state, |
|
16626 eap_tls_trace_string_c::get_tls_identity_privacy_handshake_state_string(tmp_identity_privacy_handshake_state))); |
|
16627 } |
|
16628 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
16629 } |
|
16630 #endif //#if defined(USE_EAP_DEBUG_TRACE) |
|
16631 |
|
16632 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
16633 |
|
16634 if (m_application != 0) |
|
16635 { |
|
16636 m_application->set_tunneled_state( |
|
16637 m_tls_session_type); |
|
16638 } |
|
16639 |
|
16640 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
16641 |
|
16642 #if defined(USE_FAST_EAP_TYPE) |
|
16643 if (m_is_client == false |
|
16644 && m_eap_type == eap_type_fast |
|
16645 && m_tls_session_type == tls_session_type_eap_fast_pac_session_resumption) |
|
16646 { |
|
16647 // This is server. |
|
16648 // EAP-FAST is using Tunnel PAC. |
|
16649 // Here we cannot start tunneled authentication immediately |
|
16650 // because client migth have sent a User Authorization PAC. |
|
16651 // We must process the optional TLS Application message(s) |
|
16652 // to see did client send the User Authorization PAC. |
|
16653 set_state(tls_peap_state_wait_tunneled_authentication_start); |
|
16654 |
|
16655 eap_status_e tunnel_ready_status = m_application->peap_tunnel_ready(); |
|
16656 if (tunnel_ready_status != eap_status_ok) |
|
16657 { |
|
16658 // This is an error case. |
|
16659 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16660 return EAP_STATUS_RETURN(m_am_tools, tunnel_ready_status); |
|
16661 } |
|
16662 |
|
16663 tunnel_ready_status = get_type_partner()->peap_tunnel_ready(); |
|
16664 if (tunnel_ready_status != eap_status_ok) |
|
16665 { |
|
16666 // This is an error case. |
|
16667 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16668 return EAP_STATUS_RETURN(m_am_tools, tunnel_ready_status); |
|
16669 } |
|
16670 } |
|
16671 else |
|
16672 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
16673 if (get_is_tunneled_tls() == false |
|
16674 || ((m_tls_session_type == tls_session_type_original_session_resumption |
|
16675 || m_tls_session_type == tls_session_type_stateless_session_resumption) |
|
16676 && ( |
|
16677 #if defined(USE_FAST_EAP_TYPE) |
|
16678 m_eap_type == eap_type_fast |
|
16679 || |
|
16680 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
16681 m_eap_type == eap_type_ttls |
|
16682 || (m_eap_type == eap_type_peap |
|
16683 #if defined(USE_EAP_TLS_PEAP_TPPD_PEAP_V1_NEW_FIXES) |
|
16684 && m_peap_version > peap_version_1 |
|
16685 #else |
|
16686 && m_peap_version > peap_version_0_xp |
|
16687 #endif //#if defined(USE_EAP_TLS_PEAP_TPPD_PEAP_V1_NEW_FIXES) |
|
16688 && m_peap_version < peap_version_2)))) |
|
16689 { |
|
16690 if (m_tls_session_type == tls_session_type_full_authentication |
|
16691 && tmp_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_negotiates) |
|
16692 { |
|
16693 // TLS-privacy negotiation running. |
|
16694 } |
|
16695 else |
|
16696 { |
|
16697 set_state(tls_peap_state_tls_success); |
|
16698 } |
|
16699 |
|
16700 // PEAPv2 does not use m_eap_master_session_key directly. |
|
16701 // PEAPv2 does derive an other master session key. |
|
16702 // EAP-TLS, PEAPv0 and PEAPv1 does use m_eap_master_session_key. |
|
16703 if (m_eap_type == eap_type_tls // Plain EAP-TLS. |
|
16704 || m_eap_type == eap_type_ttls |
|
16705 #if defined(USE_FAST_EAP_TYPE) |
|
16706 || m_eap_type == eap_type_fast |
|
16707 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
16708 || (m_eap_type == eap_type_peap |
|
16709 && (m_peap_version == peap_version_0_xp |
|
16710 || m_peap_version == peap_version_1))) |
|
16711 { |
|
16712 status = get_type_partner()->set_tls_master_secret(&m_eap_master_session_key); |
|
16713 if (status != eap_status_ok) |
|
16714 { |
|
16715 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16716 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16717 } |
|
16718 } |
|
16719 |
|
16720 if (( |
|
16721 #if defined(USE_FAST_EAP_TYPE) |
|
16722 m_eap_type == eap_type_fast |
|
16723 || |
|
16724 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
16725 m_eap_type == eap_type_ttls) |
|
16726 && (m_tls_session_type == tls_session_type_original_session_resumption |
|
16727 || m_tls_session_type == tls_session_type_stateless_session_resumption)) |
|
16728 { |
|
16729 eap_status_e notification_status = indicate_state_to_lower_layer(m_tls_peap_state); |
|
16730 if (notification_status != eap_status_ok) |
|
16731 { |
|
16732 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16733 return EAP_STATUS_RETURN(m_am_tools, notification_status); |
|
16734 } |
|
16735 } |
|
16736 } |
|
16737 else if (tmp_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_none |
|
16738 || tmp_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_runs) |
|
16739 { |
|
16740 if ((m_eap_type == eap_type_peap |
|
16741 && m_peap_version >= peap_version_0_xp |
|
16742 && m_peap_version <= peap_version_2) |
|
16743 || m_eap_type == eap_type_ttls |
|
16744 #if defined(USE_FAST_EAP_TYPE) |
|
16745 || m_eap_type == eap_type_fast |
|
16746 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
16747 ) |
|
16748 { |
|
16749 if (m_application == 0) |
|
16750 { |
|
16751 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16752 return EAP_STATUS_RETURN(m_am_tools, eap_status_process_general_error); |
|
16753 } |
|
16754 |
|
16755 set_state(tls_peap_state_peap_tunnel_ready); |
|
16756 |
|
16757 eap_status_e tunnel_ready_status = m_application->peap_tunnel_ready(); |
|
16758 if (tunnel_ready_status != eap_status_ok) |
|
16759 { |
|
16760 // This is an error case. |
|
16761 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16762 return EAP_STATUS_RETURN(m_am_tools, tunnel_ready_status); |
|
16763 } |
|
16764 |
|
16765 tunnel_ready_status = get_type_partner()->peap_tunnel_ready(); |
|
16766 if (tunnel_ready_status != eap_status_ok) |
|
16767 { |
|
16768 // This is an error case. |
|
16769 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16770 return EAP_STATUS_RETURN(m_am_tools, tunnel_ready_status); |
|
16771 } |
|
16772 |
|
16773 #if defined(USE_EAP_TLS_PEAP_TPPD_PEAP_V1_NEW_FIXES) |
|
16774 if ((m_tls_session_type == tls_session_type_original_session_resumption |
|
16775 || m_tls_session_type == tls_session_type_stateless_session_resumption) |
|
16776 && m_use_tppd_tls_peap == true |
|
16777 && m_peap_version == peap_version_1 |
|
16778 && m_use_tppd_peapv1_acknowledge_hack == true) |
|
16779 { |
|
16780 status = get_type_partner()->set_tls_master_secret(&m_eap_master_session_key); |
|
16781 if (status != eap_status_ok) |
|
16782 { |
|
16783 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16784 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16785 } |
|
16786 } |
|
16787 #endif //#if defined(USE_EAP_TLS_PEAP_TPPD_PEAP_V1_NEW_FIXES) |
|
16788 |
|
16789 |
|
16790 if (m_is_client == true |
|
16791 && m_eap_type == eap_type_ttls) |
|
16792 { |
|
16793 // EAP-TTLS client starts the tunneled authentication. |
|
16794 |
|
16795 // Here we swap the addresses. |
|
16796 eap_am_network_id_c receive_network_id(m_am_tools, |
|
16797 m_send_network_id.get_destination_id(), |
|
16798 m_send_network_id.get_source_id(), |
|
16799 m_send_network_id.get_type()); |
|
16800 |
|
16801 status = m_application->start_ttls_tunneled_authentication( |
|
16802 &receive_network_id, |
|
16803 m_received_eap_identifier); |
|
16804 if (status != eap_status_ok |
|
16805 && status != eap_status_pending_request) |
|
16806 { |
|
16807 // This is an error case. |
|
16808 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16809 return EAP_STATUS_RETURN(m_am_tools, tunnel_ready_status); |
|
16810 } |
|
16811 } |
|
16812 |
|
16813 |
|
16814 #if defined(USE_EAP_CORE_SERVER) |
|
16815 if (m_is_client == false) |
|
16816 { |
|
16817 // Server |
|
16818 |
|
16819 if ( |
|
16820 #if defined(USE_FAST_EAP_TYPE) |
|
16821 m_eap_type == eap_type_fast |
|
16822 || |
|
16823 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
16824 (m_eap_type == eap_type_peap |
|
16825 && (m_peap_version >= peap_version_2 |
|
16826 || ((m_tls_session_type == tls_session_type_original_session_resumption |
|
16827 || m_tls_session_type == tls_session_type_stateless_session_resumption) |
|
16828 && ( |
|
16829 m_peap_version == peap_version_0_xp |
|
16830 #if defined(USE_EAP_TLS_PEAP_TPPD_PEAP_V1_NEW_FIXES) |
|
16831 || m_peap_version == peap_version_1 |
|
16832 #endif //#if defined(USE_EAP_TLS_PEAP_TPPD_PEAP_V1_NEW_FIXES) |
|
16833 ) |
|
16834 ) |
|
16835 ) |
|
16836 ) |
|
16837 ) |
|
16838 { |
|
16839 #if defined(USE_FAST_EAP_TYPE) |
|
16840 if (m_eap_type == eap_type_fast |
|
16841 && m_send_piggypacked_eap_identity_request == false |
|
16842 && (m_tls_session_type == tls_session_type_eap_fast_server_unauthenticated_provisioning_mode_ADHP |
|
16843 || m_tls_session_type == tls_session_type_full_authentication)) |
|
16844 { |
|
16845 // Server does not start tunneled authentication yet. |
|
16846 // Instead server waits empty EAP-FAST acnowledge message from client. |
|
16847 |
|
16848 eap_state_notification_c notification( |
|
16849 m_am_tools, |
|
16850 &m_send_network_id, |
|
16851 m_is_client, |
|
16852 eap_state_notification_eap, |
|
16853 eap_protocol_layer_eap, |
|
16854 m_eap_type, |
|
16855 eap_state_none, |
|
16856 eap_state_authentication_wait_eap_fast_empty_acknowledge, |
|
16857 m_received_eap_identifier, |
|
16858 false); |
|
16859 get_type_partner()->state_notification(¬ification); |
|
16860 status = eap_status_ok; |
|
16861 } |
|
16862 else |
|
16863 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
16864 { |
|
16865 // Here we swap the addresses. |
|
16866 eap_am_network_id_c receive_network_id(m_am_tools, |
|
16867 m_send_network_id.get_destination_id(), |
|
16868 m_send_network_id.get_source_id(), |
|
16869 m_send_network_id.get_type()); |
|
16870 |
|
16871 set_state(tls_peap_state_wait_tunneled_authentication_start); |
|
16872 |
|
16873 // Here we must start the tunneled EAP-type. |
|
16874 status = start_peap_tunneled_authentication( |
|
16875 &receive_network_id, |
|
16876 m_received_eap_identifier, |
|
16877 m_tls_session_type); |
|
16878 if (status != eap_status_ok) |
|
16879 { |
|
16880 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16881 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16882 } |
|
16883 } |
|
16884 } |
|
16885 } |
|
16886 else |
|
16887 #endif //#if defined(USE_EAP_CORE_SERVER) |
|
16888 { |
|
16889 // Client |
|
16890 |
|
16891 #if defined(USE_FAST_EAP_TYPE) |
|
16892 if (m_eap_type == eap_type_fast) |
|
16893 { |
|
16894 // Here we swap the addresses. |
|
16895 eap_am_network_id_c receive_network_id(m_am_tools, |
|
16896 m_send_network_id.get_destination_id(), |
|
16897 m_send_network_id.get_source_id(), |
|
16898 m_send_network_id.get_type()); |
|
16899 |
|
16900 // Here we must start the tunneled EAP-type. |
|
16901 status = start_peap_tunneled_authentication( |
|
16902 &receive_network_id, |
|
16903 m_received_eap_identifier, |
|
16904 m_tls_session_type); |
|
16905 if (status != eap_status_ok) |
|
16906 { |
|
16907 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16908 return EAP_STATUS_RETURN(m_am_tools, status); |
|
16909 } |
|
16910 } |
|
16911 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
16912 |
|
16913 } |
|
16914 |
|
16915 |
|
16916 #if defined(USE_EAP_TLS_PEAP_TPPD_PEAP_V1_NEW_FIXES) |
|
16917 if ((m_tls_session_type == tls_session_type_original_session_resumption |
|
16918 || m_tls_session_type == tls_session_type_stateless_session_resumption) |
|
16919 && m_use_tppd_tls_peap == true |
|
16920 && m_peap_version == peap_version_1 |
|
16921 && m_use_tppd_peapv1_acknowledge_hack == true) |
|
16922 { |
|
16923 if (m_is_client == true) |
|
16924 { |
|
16925 eap_state_notification_c notification( |
|
16926 m_am_tools, |
|
16927 &m_send_network_id, |
|
16928 m_is_client, |
|
16929 eap_state_notification_eap, |
|
16930 eap_protocol_layer_internal_type, |
|
16931 m_eap_type, |
|
16932 eap_state_none, |
|
16933 tls_peap_state_tppd_peapv1_waits_eap_success_or_tunneled_packet, |
|
16934 m_received_eap_identifier, |
|
16935 false); |
|
16936 get_type_partner()->state_notification(¬ification); |
|
16937 } |
|
16938 } |
|
16939 #endif //#if defined(USE_EAP_TLS_PEAP_TPPD_PEAP_V1_NEW_FIXES) |
|
16940 |
|
16941 } |
|
16942 else |
|
16943 { |
|
16944 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16945 return EAP_STATUS_RETURN(m_am_tools, eap_status_no_matching_protocol_version); |
|
16946 } |
|
16947 } |
|
16948 |
|
16949 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
16950 |
|
16951 if (m_tls_peap_state == tls_peap_state_tls_success) |
|
16952 { |
|
16953 // Notify lower layer that TLS/PEAP ended successfully |
|
16954 |
|
16955 if (get_is_tunneled_tls() == false |
|
16956 || (get_is_tunneled_tls() == true |
|
16957 && m_tunneled_eap_type_authentication_state |
|
16958 == eap_state_authentication_finished_successfully) |
|
16959 || (get_is_tunneled_tls() == true |
|
16960 && m_tls_session_type == tls_session_type_original_session_resumption)) |
|
16961 { |
|
16962 eap_status_e save_status = m_am_tls_services->save_tls_session( |
|
16963 &m_session_id, |
|
16964 &m_master_secret, |
|
16965 m_selected_cipher_suite |
|
16966 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
16967 , tls_extension_c::get_tls_extension( |
|
16968 tls_extension_type_session_ticket, |
|
16969 &m_received_tls_extensions, |
|
16970 m_am_tools) |
|
16971 #endif //#if defined(USE_EAP_TLS_SESSION_TICKET) |
|
16972 ); |
|
16973 if (save_status != eap_status_ok) |
|
16974 { |
|
16975 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16976 return EAP_STATUS_RETURN(m_am_tools, save_status); |
|
16977 } |
|
16978 |
|
16979 eap_status_e notification_status = indicate_state_to_lower_layer(m_tls_peap_state); |
|
16980 if (notification_status != eap_status_ok) |
|
16981 { |
|
16982 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16983 return EAP_STATUS_RETURN(m_am_tools, notification_status); |
|
16984 } |
|
16985 } |
|
16986 } |
|
16987 else if (m_tls_peap_state == tls_peap_state_peap_tunnel_ready) |
|
16988 { |
|
16989 // Notify lower layer that TLS tunnel is ready. |
|
16990 |
|
16991 eap_status_e notification_status = indicate_state_to_lower_layer(m_tls_peap_state); |
|
16992 if (notification_status != eap_status_ok) |
|
16993 { |
|
16994 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
16995 return EAP_STATUS_RETURN(m_am_tools, notification_status); |
|
16996 } |
|
16997 |
|
16998 // Change state that only one indication is sent to lower layer. |
|
16999 if (m_is_client == true) |
|
17000 { |
|
17001 set_state(tls_peap_state_wait_application_data); |
|
17002 } |
|
17003 else |
|
17004 { |
|
17005 set_state(tls_peap_state_wait_tunneled_authentication_start); |
|
17006 } |
|
17007 } |
|
17008 else if (m_tls_peap_state == tls_peap_state_failure) |
|
17009 { |
|
17010 eap_status_e notification_status = indicate_state_to_lower_layer(m_tls_peap_state); |
|
17011 if (notification_status != eap_status_ok) |
|
17012 { |
|
17013 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17014 return EAP_STATUS_RETURN(m_am_tools, notification_status); |
|
17015 } |
|
17016 } |
|
17017 else |
|
17018 { |
|
17019 EAP_TRACE_DEBUG( |
|
17020 m_am_tools, |
|
17021 TRACE_FLAGS_DEFAULT, |
|
17022 (EAPL("TLS: tls_record_c::finish_handshake(): No notification, m_tls_session_type=%d=%s, state=%d=%s\n"), |
|
17023 m_tls_session_type, |
|
17024 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type), |
|
17025 m_tls_peap_state, |
|
17026 eap_tls_trace_string_c::get_state_string(m_tls_peap_state))); |
|
17027 } |
|
17028 |
|
17029 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
17030 |
|
17031 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17032 return EAP_STATUS_RETURN(m_am_tools, eap_status_ok); |
|
17033 } |
|
17034 |
|
17035 //-------------------------------------------------- |
|
17036 |
|
17037 EAP_FUNC_EXPORT eap_status_e tls_record_c::create_tls_protocol_alert( |
|
17038 const tls_alert_description_e par_alert_description, |
|
17039 const tls_alert_level_e par_alert_level, |
|
17040 const eap_status_e par_result) |
|
17041 { |
|
17042 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17043 |
|
17044 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
17045 EAP_TRACE_DEBUG( |
|
17046 m_am_tools, |
|
17047 TRACE_FLAGS_DEFAULT, |
|
17048 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::create_tls_protocol_alert()\n"), |
|
17049 this, |
|
17050 (m_is_client == true ? "client": "server"))); |
|
17051 |
|
17052 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::create_tls_protocol_alert()"); |
|
17053 |
|
17054 eap_status_e status = eap_status_authentication_failure; |
|
17055 |
|
17056 //-------------------------------------------------------------------- |
|
17057 |
|
17058 tls_alert_level_e alert_level = par_alert_level; |
|
17059 tls_alert_description_e alert_description = par_alert_description; |
|
17060 |
|
17061 if (alert_level == tls_alert_level_none) |
|
17062 { |
|
17063 alert_level = tls_alert_level_fatal; |
|
17064 } |
|
17065 |
|
17066 if (alert_description == tls_alert_description_none) |
|
17067 { |
|
17068 // Examine par_result. |
|
17069 switch(par_result) |
|
17070 { |
|
17071 #if EAP_TLS_UNSUPPORTED_ALERT_DESCRIPTION |
|
17072 #error Alert descriptions need more code. |
|
17073 case : |
|
17074 alert_description = tls_alert_description_close_notify; |
|
17075 break; |
|
17076 #endif //#if EAP_TLS_UNSUPPORTED_ALERT_DESCRIPTION |
|
17077 case eap_status_unexpected_message: |
|
17078 alert_description = tls_alert_description_unexpected_message; |
|
17079 break; |
|
17080 case eap_status_authentication_failure: |
|
17081 alert_description = tls_alert_description_bad_record_mac; |
|
17082 break; |
|
17083 case eap_status_decryption_failure: |
|
17084 case eap_status_illegal_padding: |
|
17085 alert_description = tls_alert_description_decryption_failed; |
|
17086 break; |
|
17087 #if EAP_TLS_UNSUPPORTED_ALERT_DESCRIPTION |
|
17088 case : |
|
17089 alert_description = tls_alert_description_record_overflow; |
|
17090 break; |
|
17091 case : |
|
17092 alert_description = tls_alert_description_decompression_failure; |
|
17093 break; |
|
17094 #endif //#if EAP_TLS_UNSUPPORTED_ALERT_DESCRIPTION |
|
17095 case eap_status_illegal_cipher_suite: |
|
17096 alert_description = tls_alert_description_handshake_failure; |
|
17097 break; |
|
17098 case eap_status_illegal_certificate: |
|
17099 case eap_status_bad_certificate: |
|
17100 alert_description = tls_alert_description_bad_certificate; |
|
17101 #if defined(USE_FAST_EAP_TYPE) |
|
17102 if (m_eap_type == eap_type_fast |
|
17103 && par_result == eap_status_bad_certificate) |
|
17104 { |
|
17105 alert_level = tls_alert_level_fatal; |
|
17106 } |
|
17107 else |
|
17108 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
17109 { |
|
17110 alert_level = tls_alert_level_warning; |
|
17111 } |
|
17112 break; |
|
17113 case eap_status_unsupported_certificate: |
|
17114 alert_description = tls_alert_description_unsupported_certificate; |
|
17115 alert_level = tls_alert_level_warning; |
|
17116 break; |
|
17117 case eap_status_certificate_revoked: |
|
17118 alert_description = tls_alert_description_certificate_revoked; |
|
17119 alert_level = tls_alert_level_warning; |
|
17120 break; |
|
17121 case eap_status_certificate_expired: |
|
17122 alert_description = tls_alert_description_certificate_expired; |
|
17123 alert_level = tls_alert_level_warning; |
|
17124 break; |
|
17125 case eap_status_user_certificate_unknown: |
|
17126 case eap_status_ca_certificate_unknown: |
|
17127 alert_description = tls_alert_description_certificate_unknown; |
|
17128 alert_level = tls_alert_level_warning; |
|
17129 break; |
|
17130 case eap_status_illegal_encryption_parameter_size: |
|
17131 case eap_status_illegal_parameter: |
|
17132 alert_description = tls_alert_description_illegal_parameter; |
|
17133 break; |
|
17134 case eap_status_unknown_ca: |
|
17135 alert_description = tls_alert_description_unknown_ca; |
|
17136 break; |
|
17137 case eap_status_access_denied: |
|
17138 alert_description = tls_alert_description_access_denied; |
|
17139 break; |
|
17140 case eap_status_process_illegal_packet_error: |
|
17141 case eap_status_illegal_eap_code: |
|
17142 case eap_status_illegal_eap_type: |
|
17143 case eap_status_illegal_eap_identity: |
|
17144 case eap_status_too_short_message: |
|
17145 case eap_status_too_long_message: |
|
17146 case eap_status_wrong_protocol: |
|
17147 case eap_status_wrong_type: |
|
17148 case eap_status_data_length_not_aligned_to_block_size: |
|
17149 case eap_status_illegal_data_payload: |
|
17150 case eap_status_illegal_payload: |
|
17151 case eap_status_header_corrupted: |
|
17152 case eap_status_illegal_nai: |
|
17153 case eap_status_illegal_nai_payload: |
|
17154 alert_description = tls_alert_description_decode_error; |
|
17155 break; |
|
17156 #if EAP_TLS_UNSUPPORTED_ALERT_DESCRIPTION |
|
17157 case : |
|
17158 alert_description = tls_alert_description_decrypt_error; |
|
17159 break; |
|
17160 case : |
|
17161 alert_description = tls_alert_description_export_restriction; |
|
17162 break; |
|
17163 #endif //#if EAP_TLS_UNSUPPORTED_ALERT_DESCRIPTION |
|
17164 case eap_status_no_matching_protocol_version: |
|
17165 alert_description = tls_alert_description_protocol_version; |
|
17166 break; |
|
17167 case eap_status_insufficient_security: |
|
17168 alert_description = tls_alert_description_insufficient_security; |
|
17169 break; |
|
17170 case eap_status_allocation_error: |
|
17171 case eap_status_not_supported: |
|
17172 case eap_status_process_general_error: |
|
17173 case eap_status_type_does_not_exists_error: |
|
17174 case eap_status_timed_out: |
|
17175 case eap_status_hardware_not_ready: |
|
17176 alert_description = tls_alert_description_internal_error; |
|
17177 break; |
|
17178 #if EAP_TLS_UNSUPPORTED_ALERT_DESCRIPTION |
|
17179 case : |
|
17180 alert_description = tls_alert_description_user_canceled; |
|
17181 break; |
|
17182 case : |
|
17183 alert_description = tls_alert_description_no_renegotiation; |
|
17184 break; |
|
17185 #endif //#if EAP_TLS_UNSUPPORTED_ALERT_DESCRIPTION |
|
17186 default: |
|
17187 alert_description = tls_alert_description_internal_error; |
|
17188 break; |
|
17189 } |
|
17190 } |
|
17191 else |
|
17192 { |
|
17193 alert_description = par_alert_description; |
|
17194 } |
|
17195 |
|
17196 if (alert_level == tls_alert_level_fatal |
|
17197 && m_could_send_fatal_alert_message == false) |
|
17198 { |
|
17199 // If alert message is received or we have sent a fatal alert, we do not send alert anymore. |
|
17200 |
|
17201 EAP_TRACE_DEBUG( |
|
17202 m_am_tools, |
|
17203 TRACE_FLAGS_DEFAULT, |
|
17204 (EAPL("TLS: %s: message_function: create_tls_protocol_alert(), ") |
|
17205 EAPL("do not send fatal alert message\n"), |
|
17206 (m_is_client == true ? "client": "server"))); |
|
17207 |
|
17208 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17209 return EAP_STATUS_RETURN(m_am_tools, par_result); |
|
17210 } |
|
17211 |
|
17212 if (alert_level == tls_alert_level_warning |
|
17213 && m_could_send_warning_alert_message == false) |
|
17214 { |
|
17215 // If alert message is received or we have sent a warning alert, |
|
17216 // we do not send alert anymore. |
|
17217 |
|
17218 EAP_TRACE_DEBUG( |
|
17219 m_am_tools, |
|
17220 TRACE_FLAGS_DEFAULT, |
|
17221 (EAPL("TLS: %s: message_function: create_tls_protocol_alert(), ") |
|
17222 EAPL("do not send warning alert message\n"), |
|
17223 (m_is_client == true ? "client": "server"))); |
|
17224 |
|
17225 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17226 return EAP_STATUS_RETURN(m_am_tools, par_result); |
|
17227 } |
|
17228 |
|
17229 //-------------------------------------------------------------------- |
|
17230 |
|
17231 |
|
17232 set_state(tls_peap_state_failure); |
|
17233 |
|
17234 // This will cause the session terminate immediately. |
|
17235 status = get_type_partner()->set_session_timeout(0ul); |
|
17236 if (status != eap_status_ok) |
|
17237 { |
|
17238 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17239 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17240 } |
|
17241 |
|
17242 // 0 1 2 3 |
|
17243 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
17244 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
17245 // | alert level | alert descrip.| |
|
17246 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
17247 |
|
17248 tls_alert_message_c * const tls_alert_message |
|
17249 = new tls_alert_message_c(m_am_tools, m_is_client); |
|
17250 |
|
17251 eap_automatic_variable_c<tls_alert_message_c> |
|
17252 automatic_tls_alert_message(m_am_tools, tls_alert_message); |
|
17253 |
|
17254 if (tls_alert_message == 0 |
|
17255 || tls_alert_message->get_is_valid() == false) |
|
17256 { |
|
17257 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17258 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
17259 } |
|
17260 |
|
17261 // -------------------------------------------------------------------- |
|
17262 |
|
17263 EAP_TRACE_ERROR( |
|
17264 m_am_tools, |
|
17265 TRACE_FLAGS_DEFAULT, |
|
17266 (EAPL("TLS: %s: message_function: create_tls_protocol_alert(): Alert message %s:%s\n"), |
|
17267 (m_is_client == true ? "client": "server"), |
|
17268 eap_tls_trace_string_c::get_alert_level_string(alert_level), |
|
17269 eap_tls_trace_string_c::get_alert_description_string(alert_description))); |
|
17270 |
|
17271 |
|
17272 status = tls_alert_message->set_alert_level(alert_level); |
|
17273 if (status != eap_status_ok) |
|
17274 { |
|
17275 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17276 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17277 } |
|
17278 |
|
17279 status = tls_alert_message->set_alert_description(alert_description); |
|
17280 if (status != eap_status_ok) |
|
17281 { |
|
17282 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17283 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17284 } |
|
17285 |
|
17286 // -------------------------------------------------------------------- |
|
17287 |
|
17288 // Note add_record_message() frees message on any case. |
|
17289 automatic_tls_alert_message.do_not_free_variable(); |
|
17290 |
|
17291 status = add_record_message(tls_alert_message); |
|
17292 if (status != eap_status_ok) |
|
17293 { |
|
17294 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17295 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17296 } |
|
17297 |
|
17298 // -------------------------------------------------------------------- |
|
17299 |
|
17300 m_force_tls_message_send = true; |
|
17301 |
|
17302 if (alert_level == tls_alert_level_fatal) |
|
17303 { |
|
17304 m_could_send_fatal_alert_message = false; |
|
17305 } |
|
17306 |
|
17307 if (alert_level == tls_alert_level_warning) |
|
17308 { |
|
17309 m_could_send_warning_alert_message = false; |
|
17310 } |
|
17311 |
|
17312 |
|
17313 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17314 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17315 } |
|
17316 |
|
17317 |
|
17318 //-------------------------------------------------- |
|
17319 |
|
17320 EAP_FUNC_EXPORT eap_status_e tls_record_c::create_tls_application_data( |
|
17321 eap_buf_chain_wr_c * const sent_packet, |
|
17322 const u32_t header_offset) |
|
17323 { |
|
17324 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17325 |
|
17326 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
17327 EAP_TRACE_DEBUG( |
|
17328 m_am_tools, |
|
17329 TRACE_FLAGS_DEFAULT, |
|
17330 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::create_tls_application_data()\n"), |
|
17331 this, |
|
17332 (m_is_client == true ? "client": "server"))); |
|
17333 |
|
17334 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::create_tls_application_data()"); |
|
17335 |
|
17336 // 0 1 2 3 |
|
17337 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
17338 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
17339 // | Application data n bytes | |
|
17340 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
17341 |
|
17342 tls_application_data_message_c * const tls_application_data_message |
|
17343 = new tls_application_data_message_c(m_am_tools, m_is_client); |
|
17344 |
|
17345 eap_automatic_variable_c<tls_application_data_message_c> |
|
17346 automatic_tls_application_data_message( |
|
17347 m_am_tools, tls_application_data_message); |
|
17348 |
|
17349 if (tls_application_data_message == 0 |
|
17350 || tls_application_data_message->get_is_valid() == false) |
|
17351 { |
|
17352 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17353 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
17354 } |
|
17355 |
|
17356 if (sent_packet->get_data_length() < header_offset) |
|
17357 { |
|
17358 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17359 return EAP_STATUS_RETURN(m_am_tools, eap_status_too_short_message); |
|
17360 } |
|
17361 |
|
17362 u32_t packet_length = sent_packet->get_data_length()-header_offset; |
|
17363 |
|
17364 eap_status_e status = tls_application_data_message->set_application_data( |
|
17365 sent_packet->get_data_offset(header_offset, packet_length), |
|
17366 packet_length); |
|
17367 if (status != eap_status_ok) |
|
17368 { |
|
17369 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17370 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17371 } |
|
17372 |
|
17373 // -------------------------------------------------------------------- |
|
17374 |
|
17375 // Note add_record_message() frees message on any case. |
|
17376 automatic_tls_application_data_message.do_not_free_variable(); |
|
17377 |
|
17378 status = add_record_message(tls_application_data_message); |
|
17379 if (status != eap_status_ok) |
|
17380 { |
|
17381 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17382 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17383 } |
|
17384 |
|
17385 // -------------------------------------------------------------------- |
|
17386 |
|
17387 if (status == eap_status_ok) |
|
17388 { |
|
17389 status = check_sent_tls_message(); |
|
17390 if (status != eap_status_ok) |
|
17391 { |
|
17392 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17393 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17394 } |
|
17395 } |
|
17396 |
|
17397 // -------------------------------------------------------------------- |
|
17398 |
|
17399 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17400 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17401 } |
|
17402 |
|
17403 |
|
17404 //-------------------------------------------------- |
|
17405 |
|
17406 EAP_FUNC_EXPORT bool tls_record_c::cipher_suite_is_3DES_EDE_CBC_SHA( |
|
17407 tls_cipher_suites_e cipher_suite) const |
|
17408 { |
|
17409 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17410 |
|
17411 if (cipher_suite == tls_cipher_suites_TLS_DHE_DSS_WITH_3DES_EDE_CBC_SHA |
|
17412 || cipher_suite == tls_cipher_suites_TLS_RSA_WITH_3DES_EDE_CBC_SHA |
|
17413 || cipher_suite == tls_cipher_suites_TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA) |
|
17414 { |
|
17415 return true; |
|
17416 } |
|
17417 |
|
17418 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17419 return false; |
|
17420 } |
|
17421 |
|
17422 //-------------------------------------------------- |
|
17423 |
|
17424 EAP_FUNC_EXPORT bool tls_record_c::cipher_suite_is_AES_128_CBC_SHA( |
|
17425 tls_cipher_suites_e cipher_suite) const |
|
17426 { |
|
17427 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17428 |
|
17429 if (cipher_suite == tls_cipher_suites_TLS_DHE_DSS_WITH_AES_128_CBC_SHA |
|
17430 || cipher_suite == tls_cipher_suites_TLS_RSA_WITH_AES_128_CBC_SHA |
|
17431 || cipher_suite == tls_cipher_suites_TLS_DHE_RSA_WITH_AES_128_CBC_SHA |
|
17432 #if defined(USE_FAST_EAP_TYPE) |
|
17433 || cipher_suite == tls_cipher_suites_TLS_DH_anon_WITH_AES_128_CBC_SHA |
|
17434 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
17435 ) |
|
17436 { |
|
17437 return true; |
|
17438 } |
|
17439 |
|
17440 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17441 return false; |
|
17442 } |
|
17443 |
|
17444 //-------------------------------------------------- |
|
17445 |
|
17446 EAP_FUNC_EXPORT bool tls_record_c::cipher_suite_is_RC4_128_MD5( |
|
17447 tls_cipher_suites_e cipher_suite) const |
|
17448 { |
|
17449 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17450 |
|
17451 if (cipher_suite == tls_cipher_suites_TLS_RSA_WITH_RC4_128_MD5) |
|
17452 { |
|
17453 return true; |
|
17454 } |
|
17455 |
|
17456 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17457 return false; |
|
17458 } |
|
17459 |
|
17460 //-------------------------------------------------- |
|
17461 |
|
17462 EAP_FUNC_EXPORT bool tls_record_c::cipher_suite_is_RC4_128_SHA( |
|
17463 tls_cipher_suites_e cipher_suite) const |
|
17464 { |
|
17465 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17466 |
|
17467 if (cipher_suite == tls_cipher_suites_TLS_RSA_WITH_RC4_128_SHA) |
|
17468 { |
|
17469 return true; |
|
17470 } |
|
17471 |
|
17472 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17473 return false; |
|
17474 } |
|
17475 |
|
17476 //-------------------------------------------------- |
|
17477 |
|
17478 EAP_FUNC_EXPORT bool tls_record_c::cipher_suite_is_TLS_RSA() const |
|
17479 { |
|
17480 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17481 |
|
17482 if (m_selected_cipher_suite == tls_cipher_suites_TLS_RSA_WITH_3DES_EDE_CBC_SHA |
|
17483 || m_selected_cipher_suite == tls_cipher_suites_TLS_RSA_WITH_AES_128_CBC_SHA |
|
17484 || m_selected_cipher_suite == tls_cipher_suites_TLS_RSA_WITH_RC4_128_MD5 |
|
17485 || m_selected_cipher_suite == tls_cipher_suites_TLS_RSA_WITH_RC4_128_SHA) |
|
17486 { |
|
17487 return true; |
|
17488 } |
|
17489 |
|
17490 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17491 return false; |
|
17492 } |
|
17493 |
|
17494 //-------------------------------------------------- |
|
17495 |
|
17496 EAP_FUNC_EXPORT bool tls_record_c::cipher_suite_is_TLS_DHE_RSA() const |
|
17497 { |
|
17498 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17499 |
|
17500 if (m_selected_cipher_suite == tls_cipher_suites_TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA |
|
17501 || m_selected_cipher_suite == tls_cipher_suites_TLS_DHE_RSA_WITH_AES_128_CBC_SHA) |
|
17502 { |
|
17503 return true; |
|
17504 } |
|
17505 |
|
17506 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17507 return false; |
|
17508 } |
|
17509 |
|
17510 //-------------------------------------------------- |
|
17511 |
|
17512 EAP_FUNC_EXPORT bool tls_record_c::cipher_suite_is_TLS_DHE_DSS() const |
|
17513 { |
|
17514 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17515 |
|
17516 if (m_selected_cipher_suite == tls_cipher_suites_TLS_DHE_DSS_WITH_3DES_EDE_CBC_SHA |
|
17517 || m_selected_cipher_suite == tls_cipher_suites_TLS_DHE_DSS_WITH_AES_128_CBC_SHA) |
|
17518 { |
|
17519 return true; |
|
17520 } |
|
17521 |
|
17522 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17523 return false; |
|
17524 } |
|
17525 |
|
17526 //-------------------------------------------------- |
|
17527 |
|
17528 #if defined(USE_FAST_EAP_TYPE) |
|
17529 |
|
17530 EAP_FUNC_EXPORT bool tls_record_c::cipher_suite_is_TLS_DH_anon() const |
|
17531 { |
|
17532 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17533 |
|
17534 if (m_selected_cipher_suite == tls_cipher_suites_TLS_DH_anon_WITH_AES_128_CBC_SHA) |
|
17535 { |
|
17536 return true; |
|
17537 } |
|
17538 |
|
17539 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17540 return false; |
|
17541 } |
|
17542 |
|
17543 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
17544 |
|
17545 //-------------------------------------------------- |
|
17546 |
|
17547 #if EAP_TLS_UNSUPPORTED_CIPHER_SUITE |
|
17548 #error This one needs more code. Diffie-Hellman sertificate key exchange with different parameters is NOT supported. |
|
17549 EAP_FUNC_EXPORT bool tls_record_c::cipher_suite_is_TLS_DH_DSS() const |
|
17550 { |
|
17551 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17552 |
|
17553 if (m_selected_cipher_suite == tls_cipher_suites_TLS_DH_DSS_WITH_3DES_EDE_CBC_SHA) |
|
17554 { |
|
17555 return true; |
|
17556 } |
|
17557 |
|
17558 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17559 return false; |
|
17560 } |
|
17561 #endif |
|
17562 |
|
17563 //-------------------------------------------------- |
|
17564 |
|
17565 EAP_FUNC_EXPORT eap_status_e tls_record_c::generate_dhe_keys() |
|
17566 { |
|
17567 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17568 |
|
17569 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
17570 EAP_TRACE_DEBUG( |
|
17571 m_am_tools, |
|
17572 TRACE_FLAGS_DEFAULT, |
|
17573 (EAPL("TLS: this = 0x%08x, %s: key_function: starts: tls_record_c::generate_dhe_keys()\n"), |
|
17574 this, |
|
17575 (m_is_client == true ? "client": "server"))); |
|
17576 |
|
17577 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::generate_dhe_keys()"); |
|
17578 |
|
17579 eap_status_e status = eap_status_not_supported; |
|
17580 |
|
17581 if (cipher_suite_is_TLS_DHE_DSS() == true |
|
17582 || cipher_suite_is_TLS_DHE_RSA() == true |
|
17583 #if defined(USE_FAST_EAP_TYPE) |
|
17584 || (m_eap_type == eap_type_fast |
|
17585 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true |
|
17586 && cipher_suite_is_TLS_DH_anon() == true) |
|
17587 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
17588 ) |
|
17589 { |
|
17590 if (m_dhe_prime.get_is_valid_data() == false |
|
17591 || m_dhe_group_generator.get_is_valid_data() == false) |
|
17592 { |
|
17593 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17594 return EAP_STATUS_RETURN(m_am_tools, eap_status_process_general_error); |
|
17595 } |
|
17596 |
|
17597 crypto_ephemeral_diffie_hellman_c dhe(m_am_tools); |
|
17598 |
|
17599 if (dhe.get_is_valid() == false) |
|
17600 { |
|
17601 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17602 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
17603 } |
|
17604 |
|
17605 EAP_TRACE_DEBUG( |
|
17606 m_am_tools, |
|
17607 TRACE_FLAGS_DEFAULT, |
|
17608 (EAPL("TLS: %s: key_function: dhe.generate_diffie_hellman_keys()\n"), |
|
17609 (m_is_client == true ? "client": "server"))); |
|
17610 |
|
17611 status = dhe.generate_diffie_hellman_keys( |
|
17612 &m_own_private_dhe_key, |
|
17613 &m_own_public_dhe_key, |
|
17614 m_dhe_prime.get_data(m_dhe_prime.get_data_length()), |
|
17615 m_dhe_prime.get_data_length(), |
|
17616 m_dhe_group_generator.get_data(m_dhe_group_generator.get_data_length()), |
|
17617 m_dhe_group_generator.get_data_length()); |
|
17618 if (status != eap_status_ok) |
|
17619 { |
|
17620 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17621 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17622 } |
|
17623 } |
|
17624 else |
|
17625 { |
|
17626 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17627 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_cipher_suite); |
|
17628 } |
|
17629 |
|
17630 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17631 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17632 } |
|
17633 |
|
17634 //-------------------------------------------------- |
|
17635 |
|
17636 EAP_FUNC_EXPORT eap_status_e tls_record_c::generate_premaster_secret() |
|
17637 { |
|
17638 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17639 |
|
17640 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
17641 EAP_TRACE_DEBUG( |
|
17642 m_am_tools, |
|
17643 TRACE_FLAGS_DEFAULT, |
|
17644 (EAPL("TLS: this = 0x%08x, %s: key_function: starts: tls_record_c::generate_premaster_secret()\n"), |
|
17645 this, |
|
17646 (m_is_client == true ? "client": "server"))); |
|
17647 |
|
17648 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::generate_premaster_secret()"); |
|
17649 |
|
17650 eap_status_e status = eap_status_not_supported; |
|
17651 |
|
17652 m_key_material_generated = false; |
|
17653 |
|
17654 if (cipher_suite_is_TLS_RSA() == true) |
|
17655 { |
|
17656 // Encrypted premaster secret is included when selected |
|
17657 // cipher suite is using RSA key exchange. |
|
17658 // First two bytes are version of TLS. |
|
17659 // 0 1 2 3 |
|
17660 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
17661 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
17662 // | | |
|
17663 // +-+-+-+-+-+-+-+-+ + |
|
17664 // | | |
|
17665 // + + |
|
17666 // | Encrypted Premaster Secret (48 bytes) | |
|
17667 // + + |
|
17668 // | | |
|
17669 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
17670 |
|
17671 crypto_random_c rand(m_am_tools); |
|
17672 |
|
17673 status = m_premaster_secret.set_buffer_length(TLS_PREMASTER_SECRET_SIZE); |
|
17674 if (status != eap_status_ok) |
|
17675 { |
|
17676 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17677 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17678 } |
|
17679 m_premaster_secret.set_data_length(TLS_PREMASTER_SECRET_SIZE); |
|
17680 |
|
17681 u16_t version = eap_htons(tls_version_3_1); |
|
17682 status = m_premaster_secret.add_data_to_offset(0ul, &version, sizeof(version)); |
|
17683 if (status != eap_status_ok) |
|
17684 { |
|
17685 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17686 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17687 } |
|
17688 |
|
17689 if (m_premaster_secret.get_data_length() < sizeof(version)) |
|
17690 { |
|
17691 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17692 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
17693 } |
|
17694 |
|
17695 status = rand.get_rand_bytes( |
|
17696 m_premaster_secret.get_data_offset( |
|
17697 sizeof(version), |
|
17698 m_premaster_secret.get_data_length()-sizeof(version)), |
|
17699 m_premaster_secret.get_data_length()-sizeof(version)); |
|
17700 if (status != eap_status_ok) |
|
17701 { |
|
17702 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17703 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17704 } |
|
17705 |
|
17706 EAP_TRACE_DATA_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("TLS: m_premaster_secret"), |
|
17707 m_premaster_secret.get_data(m_premaster_secret.get_data_length()), |
|
17708 m_premaster_secret.get_data_length())); |
|
17709 } |
|
17710 else if (cipher_suite_is_TLS_DHE_DSS() == true |
|
17711 || cipher_suite_is_TLS_DHE_RSA() == true |
|
17712 #if defined(USE_FAST_EAP_TYPE) |
|
17713 || (m_eap_type == eap_type_fast |
|
17714 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true |
|
17715 && cipher_suite_is_TLS_DH_anon() == true) |
|
17716 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
17717 ) |
|
17718 { |
|
17719 // Diffie-Hellman Yc is included when selected cipher suite is |
|
17720 // ephemeral Diffie-Hellman key exchange. |
|
17721 // 0 1 2 3 |
|
17722 // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
|
17723 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
17724 // | DH Yc length | | |
|
17725 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + |
|
17726 // | | |
|
17727 // + + |
|
17728 // | DH Yc value | |
|
17729 // + + |
|
17730 // | | |
|
17731 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
|
17732 |
|
17733 if (m_dhe_prime.get_is_valid_data() == false |
|
17734 || m_dhe_group_generator.get_is_valid_data() == false |
|
17735 || m_peer_public_dhe_key.get_is_valid_data() == false) |
|
17736 { |
|
17737 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17738 return EAP_STATUS_RETURN(m_am_tools, eap_status_process_general_error); |
|
17739 } |
|
17740 |
|
17741 crypto_ephemeral_diffie_hellman_c dhe(m_am_tools); |
|
17742 |
|
17743 if (dhe.get_is_valid() == false) |
|
17744 { |
|
17745 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17746 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
17747 } |
|
17748 |
|
17749 EAP_TRACE_DEBUG( |
|
17750 m_am_tools, |
|
17751 TRACE_FLAGS_DEFAULT, |
|
17752 (EAPL("TLS: %s: key_function: dhe.generate_g_power_to_xy()\n"), |
|
17753 (m_is_client == true ? "client": "server"))); |
|
17754 |
|
17755 status = dhe.generate_g_power_to_xy( |
|
17756 &m_own_private_dhe_key, |
|
17757 &m_peer_public_dhe_key, |
|
17758 &m_premaster_secret, |
|
17759 m_dhe_prime.get_data(m_dhe_prime.get_data_length()), |
|
17760 m_dhe_prime.get_data_length(), |
|
17761 m_dhe_group_generator.get_data(m_dhe_group_generator.get_data_length()), |
|
17762 m_dhe_group_generator.get_data_length()); |
|
17763 if (status != eap_status_ok) |
|
17764 { |
|
17765 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17766 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17767 } |
|
17768 |
|
17769 EAP_TRACE_DATA_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("TLS: m_premaster_secret"), |
|
17770 m_premaster_secret.get_data(m_premaster_secret.get_data_length()), |
|
17771 m_premaster_secret.get_data_length())); |
|
17772 } |
|
17773 else |
|
17774 { |
|
17775 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17776 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_cipher_suite); |
|
17777 } |
|
17778 |
|
17779 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17780 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17781 } |
|
17782 |
|
17783 //-------------------------------------------------- |
|
17784 |
|
17785 EAP_FUNC_EXPORT eap_status_e tls_record_c::generate_master_secret() |
|
17786 { |
|
17787 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17788 |
|
17789 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
17790 EAP_TRACE_DEBUG( |
|
17791 m_am_tools, |
|
17792 TRACE_FLAGS_DEFAULT, |
|
17793 (EAPL("TLS: this = 0x%08x, %s: key_function: starts: tls_record_c::generate_master_secret()\n"), |
|
17794 this, |
|
17795 (m_is_client == true ? "client": "server"))); |
|
17796 |
|
17797 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::generate_master_secret()"); |
|
17798 |
|
17799 EAP_TRACE_DATA_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("TLS: tls_record_c::generate_master_secret(): m_premaster_secret"), |
|
17800 m_premaster_secret.get_data(), |
|
17801 m_premaster_secret.get_data_length())); |
|
17802 |
|
17803 EAP_TRACE_DATA_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("TLS: tls_record_c::generate_master_secret(): m_client_handshake_random_value"), |
|
17804 m_client_handshake_random_value.get_data(), |
|
17805 m_client_handshake_random_value.get_data_length())); |
|
17806 |
|
17807 EAP_TRACE_DATA_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("TLS: tls_record_c::generate_master_secret(): m_server_handshake_random_value"), |
|
17808 m_server_handshake_random_value.get_data(), |
|
17809 m_server_handshake_random_value.get_data_length())); |
|
17810 |
|
17811 if (m_premaster_secret.get_is_valid_data() == false |
|
17812 || m_client_handshake_random_value.get_is_valid_data() == false |
|
17813 || m_server_handshake_random_value.get_is_valid_data() == false) |
|
17814 { |
|
17815 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17816 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_parameter); |
|
17817 } |
|
17818 |
|
17819 eap_status_e status = eap_status_not_supported; |
|
17820 |
|
17821 EAP_TRACE_DEBUG( |
|
17822 m_am_tools, |
|
17823 TRACE_FLAGS_DEFAULT, |
|
17824 (EAPL("TLS: %s: prf_function: tls_prf.tls_prf_output()\n"), |
|
17825 (m_is_client == true ? "client": "server"))); |
|
17826 |
|
17827 crypto_tls_prf_c tls_prf(m_am_tools); |
|
17828 |
|
17829 eap_variable_data_c label(m_am_tools); |
|
17830 if (label.get_is_valid() == false) |
|
17831 { |
|
17832 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
17833 } |
|
17834 |
|
17835 status = label.add_data( |
|
17836 TLS_MASTER_SECRET_LABEL, |
|
17837 TLS_MASTER_SECRET_LABEL_LENGTH); |
|
17838 if (status != eap_status_ok) |
|
17839 { |
|
17840 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17841 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17842 } |
|
17843 |
|
17844 eap_variable_data_c seed(m_am_tools); |
|
17845 if (seed.get_is_valid() == false) |
|
17846 { |
|
17847 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
17848 } |
|
17849 status = seed.set_copy_of_buffer(&m_client_handshake_random_value); |
|
17850 if (status != eap_status_ok) |
|
17851 { |
|
17852 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17853 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17854 } |
|
17855 |
|
17856 status = seed.add_data(&m_server_handshake_random_value); |
|
17857 if (status != eap_status_ok) |
|
17858 { |
|
17859 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17860 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17861 } |
|
17862 |
|
17863 status = tls_prf.tls_prf_init( |
|
17864 &m_premaster_secret, |
|
17865 &label, |
|
17866 &seed); |
|
17867 if (status != eap_status_ok) |
|
17868 { |
|
17869 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17870 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17871 } |
|
17872 |
|
17873 status = m_master_secret.set_buffer_length(TLS_MASTER_SECRET_SIZE); |
|
17874 if (status != eap_status_ok) |
|
17875 { |
|
17876 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17877 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17878 } |
|
17879 m_master_secret.set_data_length(TLS_MASTER_SECRET_SIZE); |
|
17880 |
|
17881 status = tls_prf.tls_prf_output( |
|
17882 m_master_secret.get_data(m_master_secret.get_data_length()), |
|
17883 m_master_secret.get_data_length()); |
|
17884 if (status != eap_status_ok) |
|
17885 { |
|
17886 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17887 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17888 } |
|
17889 |
|
17890 EAP_TRACE_DATA_DEBUG( |
|
17891 m_am_tools, |
|
17892 TRACE_FLAGS_DEFAULT, |
|
17893 (EAPL("TLS: tls_record_c::generate_master_secret(): m_master_secret"), |
|
17894 m_master_secret.get_data(), |
|
17895 m_master_secret.get_data_length())); |
|
17896 |
|
17897 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17898 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17899 } |
|
17900 |
|
17901 //-------------------------------------------------- |
|
17902 |
|
17903 #if defined(USE_FAST_EAP_TYPE) |
|
17904 |
|
17905 EAP_FUNC_EXPORT eap_status_e tls_record_c::generate_eap_fast_master_secret_from_pac_key( |
|
17906 const eap_variable_data_c * const pac_key) |
|
17907 { |
|
17908 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17909 |
|
17910 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
17911 EAP_TRACE_DEBUG( |
|
17912 m_am_tools, |
|
17913 TRACE_FLAGS_DEFAULT, |
|
17914 (EAPL("TLS: this = 0x%08x, %s: key_function: starts: tls_record_c::generate_eap_fast_master_secret_from_pac_key()\n"), |
|
17915 this, |
|
17916 (m_is_client == true ? "client": "server"))); |
|
17917 |
|
17918 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::generate_eap_fast_master_secret_from_pac_key()"); |
|
17919 |
|
17920 EAP_TRACE_DATA_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("TLS: tls_record_c::generate_eap_fast_master_secret_from_pac_key(): PAC_Key"), |
|
17921 pac_key->get_data(), |
|
17922 pac_key->get_data_length())); |
|
17923 |
|
17924 EAP_TRACE_DATA_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("TLS: tls_record_c::generate_eap_fast_master_secret_from_pac_key(): m_server_handshake_random_value"), |
|
17925 m_server_handshake_random_value.get_data(), |
|
17926 m_server_handshake_random_value.get_data_length())); |
|
17927 |
|
17928 EAP_TRACE_DATA_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("TLS: tls_record_c::generate_eap_fast_master_secret_from_pac_key(): m_client_handshake_random_value"), |
|
17929 m_client_handshake_random_value.get_data(), |
|
17930 m_client_handshake_random_value.get_data_length())); |
|
17931 |
|
17932 if (pac_key == 0 |
|
17933 || pac_key->get_is_valid_data() == false |
|
17934 || m_client_handshake_random_value.get_is_valid_data() == false |
|
17935 || m_server_handshake_random_value.get_is_valid_data() == false) |
|
17936 { |
|
17937 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17938 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_parameter); |
|
17939 } |
|
17940 |
|
17941 eap_status_e status(eap_status_not_supported); |
|
17942 |
|
17943 |
|
17944 crypto_eap_fast_hmac_sha1_prf_c tls_prf(m_am_tools); |
|
17945 |
|
17946 eap_variable_data_c label(m_am_tools); |
|
17947 if (label.get_is_valid() == false) |
|
17948 { |
|
17949 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
17950 } |
|
17951 |
|
17952 status = label.add_data( |
|
17953 EAP_FAST_PAC_TO_MASTER_SECRET_LABEL, |
|
17954 EAP_FAST_PAC_TO_MASTER_SECRET_LABEL_LENGTH); |
|
17955 if (status != eap_status_ok) |
|
17956 { |
|
17957 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17958 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17959 } |
|
17960 |
|
17961 eap_variable_data_c seed(m_am_tools); |
|
17962 if (seed.get_is_valid() == false) |
|
17963 { |
|
17964 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
17965 } |
|
17966 |
|
17967 status = seed.set_copy_of_buffer(&m_server_handshake_random_value); |
|
17968 if (status != eap_status_ok) |
|
17969 { |
|
17970 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17971 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17972 } |
|
17973 |
|
17974 status = seed.add_data(&m_client_handshake_random_value); |
|
17975 if (status != eap_status_ok) |
|
17976 { |
|
17977 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17978 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17979 } |
|
17980 |
|
17981 status = tls_prf.t_prf_init( |
|
17982 pac_key, |
|
17983 &label, |
|
17984 &seed); |
|
17985 if (status != eap_status_ok) |
|
17986 { |
|
17987 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17988 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17989 } |
|
17990 |
|
17991 status = m_master_secret.set_buffer_length(TLS_MASTER_SECRET_SIZE); |
|
17992 if (status != eap_status_ok) |
|
17993 { |
|
17994 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
17995 return EAP_STATUS_RETURN(m_am_tools, status); |
|
17996 } |
|
17997 m_master_secret.set_data_length(TLS_MASTER_SECRET_SIZE); |
|
17998 |
|
17999 status = tls_prf.t_prf_output( |
|
18000 m_master_secret.get_data(), |
|
18001 static_cast<u16_t>(m_master_secret.get_data_length())); |
|
18002 if (status != eap_status_ok) |
|
18003 { |
|
18004 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18005 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18006 } |
|
18007 |
|
18008 EAP_TRACE_DATA_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("EAP-FAST: m_master_secret"), |
|
18009 m_master_secret.get_data(), |
|
18010 m_master_secret.get_data_length())); |
|
18011 |
|
18012 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18013 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18014 } |
|
18015 |
|
18016 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
18017 |
|
18018 //-------------------------------------------------- |
|
18019 |
|
18020 EAP_FUNC_EXPORT eap_status_e tls_record_c::complete_query_cipher_suites_and_previous_session( |
|
18021 const tls_session_type_e /* tls_session_type */, |
|
18022 EAP_TEMPLATE_CONST eap_array_c<u16_t> * const cipher_suites, |
|
18023 EAP_TEMPLATE_CONST eap_array_c<u8_t> * const compression_methods, |
|
18024 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
18025 EAP_TEMPLATE_CONST eap_array_c<tls_extension_c> * const tls_extensions, |
|
18026 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
18027 const eap_variable_data_c * const resumed_session_id, |
|
18028 const eap_variable_data_c * const resumed_master_secret, |
|
18029 const tls_cipher_suites_e resumed_cipher_suite, |
|
18030 const eap_status_e completion_status) |
|
18031 { |
|
18032 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18033 |
|
18034 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
18035 EAP_TRACE_DEBUG( |
|
18036 m_am_tools, |
|
18037 TRACE_FLAGS_DEFAULT, |
|
18038 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::complete_query_cipher_suites_and_previous_session()\n"), |
|
18039 this, |
|
18040 (m_is_client == true ? "client": "server"))); |
|
18041 |
|
18042 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::complete_query_cipher_suites_and_previous_session()"); |
|
18043 |
|
18044 m_pending_query_cipher_suites_and_previous_session = false; |
|
18045 |
|
18046 m_proposed_cipher_suites.reset(); |
|
18047 m_proposed_compression_methods.reset(); |
|
18048 |
|
18049 eap_status_e status = eap_status_process_general_error; |
|
18050 |
|
18051 |
|
18052 if (completion_status != eap_status_ok) |
|
18053 { |
|
18054 status = create_tls_protocol_alert( |
|
18055 tls_alert_description_none, |
|
18056 tls_alert_level_none, |
|
18057 completion_status); |
|
18058 if (status != eap_status_ok) |
|
18059 { |
|
18060 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18061 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18062 } |
|
18063 } |
|
18064 else |
|
18065 { |
|
18066 status = copy_simple<u16_t>( |
|
18067 cipher_suites, |
|
18068 &m_proposed_cipher_suites, |
|
18069 m_am_tools, |
|
18070 false); |
|
18071 if (status != eap_status_ok) |
|
18072 { |
|
18073 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18074 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18075 } |
|
18076 |
|
18077 status = for_each<u16_t>(&m_proposed_cipher_suites, u16_t_to_host_order, m_am_tools, false); |
|
18078 if (status != eap_status_ok |
|
18079 || m_proposed_cipher_suites.get_object_count() == 0ul) |
|
18080 { |
|
18081 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18082 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_parameter); |
|
18083 } |
|
18084 |
|
18085 #if defined(USE_FAST_EAP_TYPE) |
|
18086 if (m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == false) |
|
18087 { |
|
18088 // TLS_DH_anon_WITH_AES_128_CBC_SHA is allowed only with EAP-FAST unauthenticated provisioning mode. |
|
18089 u16_t illegal_cipher_suite(static_cast<u16_t>(tls_cipher_suites_TLS_DH_anon_WITH_AES_128_CBC_SHA)); |
|
18090 |
|
18091 i32_t index = find_simple( |
|
18092 &m_proposed_cipher_suites, |
|
18093 &illegal_cipher_suite, |
|
18094 m_am_tools); |
|
18095 if (index >= 0) |
|
18096 { |
|
18097 status = m_proposed_cipher_suites.remove_object(index); |
|
18098 if (status != eap_status_ok) |
|
18099 { |
|
18100 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18101 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18102 } |
|
18103 } |
|
18104 } |
|
18105 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
18106 |
|
18107 status = copy_simple<u8_t>( |
|
18108 compression_methods, |
|
18109 &m_proposed_compression_methods, |
|
18110 m_am_tools, |
|
18111 false); |
|
18112 if (status != eap_status_ok) |
|
18113 { |
|
18114 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18115 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18116 } |
|
18117 |
|
18118 |
|
18119 |
|
18120 #if defined(USE_FAST_EAP_TYPE) |
|
18121 if (m_eap_type == eap_type_fast |
|
18122 && m_tls_session_type == tls_session_type_eap_fast_pac_session_resumption) |
|
18123 { |
|
18124 // Let's try tunnel PAC authentication. |
|
18125 |
|
18126 // We will use the first cipher suite as an default one. |
|
18127 u16_t * cipher_suite = m_proposed_cipher_suites.get_object(0ul); |
|
18128 if (cipher_suite != 0) |
|
18129 { |
|
18130 m_resumed_cipher_suite = static_cast<tls_cipher_suites_e>(*cipher_suite); |
|
18131 } |
|
18132 else |
|
18133 { |
|
18134 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18135 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_parameter); |
|
18136 } |
|
18137 } |
|
18138 else |
|
18139 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
18140 if (resumed_session_id != 0 |
|
18141 && resumed_session_id->get_is_valid_data() == true |
|
18142 && resumed_session_id->get_data_length() > 0ul |
|
18143 && resumed_master_secret != 0 |
|
18144 && resumed_master_secret->get_is_valid_data() == true |
|
18145 && resumed_master_secret->get_data_length() == TLS_MASTER_SECRET_SIZE |
|
18146 && resumed_cipher_suite != tls_cipher_suites_none) |
|
18147 { |
|
18148 // Resume previous session. |
|
18149 |
|
18150 status = m_session_id.set_copy_of_buffer(resumed_session_id); |
|
18151 if (status != eap_status_ok) |
|
18152 { |
|
18153 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18154 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18155 } |
|
18156 |
|
18157 status = m_master_secret.set_copy_of_buffer(resumed_master_secret); |
|
18158 if (status != eap_status_ok) |
|
18159 { |
|
18160 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18161 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18162 } |
|
18163 |
|
18164 EAP_TRACE_DEBUG( |
|
18165 m_am_tools, |
|
18166 TRACE_FLAGS_DEFAULT, |
|
18167 (EAPL("TLS: %s: message_function: complete_query_cipher_suites_and_previous_session(): ") |
|
18168 EAPL("Resume previous session.\n"), |
|
18169 (m_is_client == true ? "client": "server"))); |
|
18170 |
|
18171 EAP_TRACE_DATA_DEBUG( |
|
18172 m_am_tools, |
|
18173 TRACE_FLAGS_DEFAULT, |
|
18174 (EAPL("TLS: complete_query_cipher_suites_and_previous_session(): resumed m_master_secret"), |
|
18175 m_master_secret.get_data(m_master_secret.get_data_length()), |
|
18176 m_master_secret.get_data_length())); |
|
18177 |
|
18178 m_resumed_cipher_suite = resumed_cipher_suite; |
|
18179 |
|
18180 set_tls_session_type(tls_session_type_original_session_resumption); |
|
18181 } |
|
18182 else |
|
18183 { |
|
18184 |
|
18185 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
18186 if (m_is_client == true |
|
18187 && m_tls_use_identity_privacy == true |
|
18188 && m_tls_identity_privacy_handshake_state == tls_identity_privacy_handshake_state_none) |
|
18189 { |
|
18190 set_tls_identity_privacy_handshake_state(tls_identity_privacy_handshake_state_negotiates); |
|
18191 } |
|
18192 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
18193 |
|
18194 set_tls_session_type(tls_session_type_full_authentication); |
|
18195 |
|
18196 EAP_TRACE_DEBUG( |
|
18197 m_am_tools, |
|
18198 TRACE_FLAGS_DEFAULT, |
|
18199 (EAPL("TLS: %s: message_function: complete_query_cipher_suites_and_previous_session(): ") |
|
18200 EAPL("full authentication.\n"), |
|
18201 (m_is_client == true ? "client": "server"))); |
|
18202 |
|
18203 eap_status_e notification_status = indicate_state_to_lower_layer( |
|
18204 tls_peap_state_full_authentication); |
|
18205 if (notification_status != eap_status_ok) |
|
18206 { |
|
18207 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18208 return EAP_STATUS_RETURN(m_am_tools, notification_status); |
|
18209 } |
|
18210 } |
|
18211 |
|
18212 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
18213 if (tls_extensions != 0) |
|
18214 { |
|
18215 |
|
18216 #if defined(USE_FAST_EAP_TYPE) |
|
18217 if (m_eap_type == eap_type_fast) |
|
18218 { |
|
18219 // Nothing to do. |
|
18220 } |
|
18221 else |
|
18222 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
18223 { |
|
18224 status = copy<tls_extension_c>( |
|
18225 tls_extensions, |
|
18226 &m_supported_tls_extensions, |
|
18227 m_am_tools, |
|
18228 false); |
|
18229 } |
|
18230 |
|
18231 if (status != eap_status_ok) |
|
18232 { |
|
18233 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18234 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18235 } |
|
18236 |
|
18237 #if defined(USE_FAST_EAP_TYPE) |
|
18238 eap_fast_pac_type_e required_pac_type(eap_fast_pac_type_none); |
|
18239 |
|
18240 if (m_eap_type == eap_type_fast) |
|
18241 { |
|
18242 // In EAP-FAST we are interested only Tunnel PAC. |
|
18243 required_pac_type = eap_fast_pac_type_tunnel_pac; |
|
18244 } |
|
18245 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
18246 |
|
18247 const tls_extension_c * const supported_session_ticket_extension = tls_extension_c::get_tls_extension( |
|
18248 tls_extension_type_session_ticket, |
|
18249 #if defined(USE_FAST_EAP_TYPE) |
|
18250 required_pac_type, |
|
18251 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
18252 &m_supported_tls_extensions, |
|
18253 m_am_tools); |
|
18254 |
|
18255 if (supported_session_ticket_extension != 0 |
|
18256 && supported_session_ticket_extension->get_is_valid_data() == true |
|
18257 && supported_session_ticket_extension->get_data_length() > 0ul) |
|
18258 { |
|
18259 #if defined(USE_FAST_EAP_TYPE) |
|
18260 if (m_eap_type == eap_type_fast) |
|
18261 { |
|
18262 EAP_TRACE_DEBUG( |
|
18263 m_am_tools, |
|
18264 TRACE_FLAGS_DEFAULT, |
|
18265 (EAPL("TLS: %s: message_function: complete_query_cipher_suites_and_previous_session(): ") |
|
18266 EAPL("SST: EAP-FAST PAC stateless session resumption, length = %d.\n"), |
|
18267 (m_is_client == true ? "client": "server"), |
|
18268 supported_session_ticket_extension->get_data_length())); |
|
18269 } |
|
18270 else |
|
18271 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
18272 //if (m_tls_session_type == tls_session_type_original_session_resumption) |
|
18273 { |
|
18274 EAP_TRACE_DEBUG( |
|
18275 m_am_tools, |
|
18276 TRACE_FLAGS_DEFAULT, |
|
18277 (EAPL("TLS: %s: message_function: complete_query_cipher_suites_and_previous_session(): ") |
|
18278 EAPL("SST: stateless session resumption, length = %d.\n"), |
|
18279 (m_is_client == true ? "client": "server"), |
|
18280 supported_session_ticket_extension->get_data_length())); |
|
18281 |
|
18282 set_tls_session_type(tls_session_type_stateless_session_resumption); |
|
18283 } |
|
18284 } |
|
18285 } |
|
18286 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
18287 |
|
18288 |
|
18289 #if defined(USE_FAST_EAP_TYPE) |
|
18290 if (m_eap_type == eap_type_fast |
|
18291 //&& m_tls_session_type == tls_session_type_full_authentication |
|
18292 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true) |
|
18293 { |
|
18294 // Try dynamic provisioning of PAC. |
|
18295 |
|
18296 set_tls_session_type(tls_session_type_eap_fast_server_unauthenticated_provisioning_mode_ADHP); |
|
18297 |
|
18298 EAP_TRACE_DEBUG( |
|
18299 m_am_tools, |
|
18300 TRACE_FLAGS_DEFAULT, |
|
18301 (EAPL("TLS: %s: message_function: complete_query_cipher_suites_and_previous_session(): ") |
|
18302 EAPL("server unauthenticated provisioning mode ADHP.\n"), |
|
18303 (m_is_client == true ? "client": "server"))); |
|
18304 |
|
18305 m_proposed_cipher_suites.reset(); |
|
18306 |
|
18307 u16_t * const anonymous_cipher_suite = new u16_t; |
|
18308 |
|
18309 if (anonymous_cipher_suite == 0) |
|
18310 { |
|
18311 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18312 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
18313 } |
|
18314 |
|
18315 *anonymous_cipher_suite = static_cast<u16_t>(tls_cipher_suites_TLS_DH_anon_WITH_AES_128_CBC_SHA); |
|
18316 |
|
18317 status = m_proposed_cipher_suites.add_object( |
|
18318 anonymous_cipher_suite, |
|
18319 true); |
|
18320 if (status != eap_status_ok) |
|
18321 { |
|
18322 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18323 return EAP_STATUS_RETURN(m_am_tools, eap_status_illegal_payload); |
|
18324 } |
|
18325 } |
|
18326 else |
|
18327 { |
|
18328 EAP_TRACE_DEBUG( |
|
18329 m_am_tools, |
|
18330 TRACE_FLAGS_DEFAULT, |
|
18331 (EAPL("TLS: %s: complete_query_cipher_suites_and_previous_session(): ") |
|
18332 EAPL("m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP = %d.\n"), |
|
18333 (m_is_client == true ? "client": "server"), |
|
18334 m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP)); |
|
18335 } |
|
18336 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
18337 |
|
18338 |
|
18339 } |
|
18340 |
|
18341 |
|
18342 if (status == eap_status_ok) |
|
18343 { |
|
18344 status = check_sent_tls_message(); |
|
18345 if (status != eap_status_ok) |
|
18346 { |
|
18347 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18348 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18349 } |
|
18350 |
|
18351 status = eap_status_completed_request; |
|
18352 } |
|
18353 |
|
18354 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18355 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18356 } |
|
18357 |
|
18358 //-------------------------------------------------- |
|
18359 |
|
18360 EAP_FUNC_EXPORT eap_status_e tls_record_c::complete_select_cipher_suite_and_check_session_id( |
|
18361 const tls_session_type_e tls_session_type, |
|
18362 const u16_t selected_cipher_suite, |
|
18363 const eap_variable_data_c * const resumed_session_id, |
|
18364 const eap_variable_data_c * const resumed_master_secret, |
|
18365 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
18366 const tls_extension_c * const new_session_ticket_or_null, |
|
18367 #endif //#if defined(USE_EAP_TLS_SESSION_TICKET) |
|
18368 const eap_status_e completion_status) |
|
18369 { |
|
18370 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18371 |
|
18372 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
18373 EAP_TRACE_DEBUG( |
|
18374 m_am_tools, |
|
18375 TRACE_FLAGS_DEFAULT, |
|
18376 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::complete_select_cipher_suite_and_check_session_id()\n"), |
|
18377 this, |
|
18378 (m_is_client == true ? "client": "server"))); |
|
18379 |
|
18380 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::complete_select_cipher_suite_and_check_session_id()"); |
|
18381 |
|
18382 EAP_ASSERT_ALWAYS(m_is_client == false); |
|
18383 |
|
18384 eap_status_e status = eap_status_ok; |
|
18385 |
|
18386 m_pending_select_cipher_suite_and_check_session_id = false; |
|
18387 |
|
18388 |
|
18389 if (completion_status != eap_status_ok) |
|
18390 { |
|
18391 status = create_tls_protocol_alert( |
|
18392 tls_alert_description_none, |
|
18393 tls_alert_level_none, |
|
18394 completion_status); |
|
18395 if (status != eap_status_ok) |
|
18396 { |
|
18397 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18398 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18399 } |
|
18400 } |
|
18401 else |
|
18402 { |
|
18403 set_tls_session_type(tls_session_type); |
|
18404 |
|
18405 set_selected_cipher_suite(static_cast<tls_cipher_suites_e>(selected_cipher_suite)); |
|
18406 m_selected_compression_method = tls_compression_method_null; |
|
18407 |
|
18408 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
18409 |
|
18410 #if defined(USE_FAST_EAP_TYPE) |
|
18411 if (m_eap_type == eap_type_fast |
|
18412 && m_tls_session_type == tls_session_type_full_authentication |
|
18413 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == true |
|
18414 && m_selected_cipher_suite == tls_cipher_suites_TLS_DH_anon_WITH_AES_128_CBC_SHA) |
|
18415 { |
|
18416 // Try dynamic provisioning of PAC. |
|
18417 |
|
18418 set_tls_session_type(tls_session_type_eap_fast_server_unauthenticated_provisioning_mode_ADHP); |
|
18419 } |
|
18420 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
18421 |
|
18422 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
18423 |
|
18424 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
18425 if (new_session_ticket_or_null != 0) |
|
18426 { |
|
18427 // We are using the session ticket payload. |
|
18428 |
|
18429 tls_extension_c * copy_of_new_session_ticket = new_session_ticket_or_null->copy(); |
|
18430 if (copy_of_new_session_ticket == 0) |
|
18431 { |
|
18432 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18433 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
18434 } |
|
18435 |
|
18436 // Save the new session ticket to be included in next NewSessionTicket message. |
|
18437 status = m_supported_tls_extensions.add_object(copy_of_new_session_ticket, true); |
|
18438 if (status != eap_status_ok) |
|
18439 { |
|
18440 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18441 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18442 } |
|
18443 } |
|
18444 |
|
18445 if (m_tls_session_type == tls_session_type_stateless_session_resumption) |
|
18446 { |
|
18447 if (resumed_session_id != 0 |
|
18448 && resumed_session_id->get_is_valid_data() == true) |
|
18449 { |
|
18450 // The session ID is needed if client did include it to the ClientHello. |
|
18451 status = m_session_id.set_copy_of_buffer(resumed_session_id); |
|
18452 if (status != eap_status_ok) |
|
18453 { |
|
18454 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18455 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18456 } |
|
18457 } |
|
18458 |
|
18459 if (resumed_master_secret != 0 |
|
18460 && resumed_master_secret->get_is_valid_data() == true |
|
18461 && resumed_master_secret->get_data_length() == TLS_MASTER_SECRET_SIZE) |
|
18462 { |
|
18463 status = m_master_secret.set_copy_of_buffer(resumed_master_secret); |
|
18464 if (status != eap_status_ok) |
|
18465 { |
|
18466 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18467 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18468 } |
|
18469 |
|
18470 EAP_TRACE_DATA_DEBUG( |
|
18471 m_am_tools, |
|
18472 TRACE_FLAGS_DEFAULT, |
|
18473 (EAPL("TLS: complete_select_cipher_suite_and_check_session_id(): session ticket resumed m_master_secret"), |
|
18474 m_master_secret.get_data(m_master_secret.get_data_length()), |
|
18475 m_master_secret.get_data_length())); |
|
18476 |
|
18477 EAP_TRACE_DEBUG( |
|
18478 m_am_tools, |
|
18479 TRACE_FLAGS_DEFAULT, |
|
18480 (EAPL("TLS: %s: message_function: ") |
|
18481 EAPL("complete_select_cipher_suite_and_check_session_id(): restores session using session ticket\n"), |
|
18482 (m_is_client == true ? "client": "server"))); |
|
18483 |
|
18484 eap_status_e notification_status = indicate_state_to_lower_layer( |
|
18485 tls_peap_state_original_session_resumption); |
|
18486 if (notification_status != eap_status_ok) |
|
18487 { |
|
18488 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18489 return EAP_STATUS_RETURN(m_am_tools, notification_status); |
|
18490 } |
|
18491 } |
|
18492 } |
|
18493 else |
|
18494 #endif //#if defined(USE_EAP_TLS_SESSION_TICKET) |
|
18495 if (m_tls_session_type == tls_session_type_original_session_resumption |
|
18496 && ((m_eap_type == eap_type_peap |
|
18497 /** @{ PEAPv2 does not support session resumption yet. } */ |
|
18498 && m_peap_version != peap_version_2) |
|
18499 || m_eap_type == eap_type_tls |
|
18500 || m_eap_type == eap_type_ttls |
|
18501 #if defined(USE_FAST_EAP_TYPE) |
|
18502 || m_eap_type == eap_type_fast |
|
18503 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
18504 ) |
|
18505 && resumed_session_id != 0 |
|
18506 && resumed_session_id->get_is_valid_data() == true |
|
18507 && resumed_session_id->get_data_length() > 0ul |
|
18508 && resumed_master_secret != 0 |
|
18509 && resumed_master_secret->get_is_valid_data() == true |
|
18510 && resumed_master_secret->get_data_length() == TLS_MASTER_SECRET_SIZE |
|
18511 ) |
|
18512 { |
|
18513 // Restore previous session. |
|
18514 |
|
18515 status = m_session_id.set_copy_of_buffer(resumed_session_id); |
|
18516 if (status != eap_status_ok) |
|
18517 { |
|
18518 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18519 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18520 } |
|
18521 |
|
18522 status = m_master_secret.set_copy_of_buffer(resumed_master_secret); |
|
18523 if (status != eap_status_ok) |
|
18524 { |
|
18525 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18526 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18527 } |
|
18528 |
|
18529 EAP_TRACE_DATA_DEBUG( |
|
18530 m_am_tools, |
|
18531 TRACE_FLAGS_DEFAULT, |
|
18532 (EAPL("TLS: complete_select_cipher_suite_and_check_session_id(): resumed m_master_secret"), |
|
18533 m_master_secret.get_data(m_master_secret.get_data_length()), |
|
18534 m_master_secret.get_data_length())); |
|
18535 |
|
18536 EAP_TRACE_DEBUG( |
|
18537 m_am_tools, |
|
18538 TRACE_FLAGS_DEFAULT, |
|
18539 (EAPL("TLS: %s: message_function: ") |
|
18540 EAPL("complete_select_cipher_suite_and_check_session_id(): restores session\n"), |
|
18541 (m_is_client == true ? "client": "server"))); |
|
18542 |
|
18543 eap_status_e notification_status = indicate_state_to_lower_layer( |
|
18544 tls_peap_state_original_session_resumption); |
|
18545 if (notification_status != eap_status_ok) |
|
18546 { |
|
18547 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18548 return EAP_STATUS_RETURN(m_am_tools, notification_status); |
|
18549 } |
|
18550 } |
|
18551 #if defined(USE_FAST_EAP_TYPE) |
|
18552 else if (m_tls_session_type == tls_session_type_eap_fast_pac_session_resumption) |
|
18553 { |
|
18554 EAP_TRACE_DEBUG( |
|
18555 m_am_tools, |
|
18556 TRACE_FLAGS_DEFAULT, |
|
18557 (EAPL("TLS: complete_select_cipher_suite_and_check_session_id(): EAP-FAST server: %s\n"), |
|
18558 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type))); |
|
18559 |
|
18560 // Parameter resumed_master_secret includes PAC-Key. |
|
18561 status = m_eap_fast_pac_key.set_copy_of_buffer(resumed_master_secret); |
|
18562 if (status != eap_status_ok) |
|
18563 { |
|
18564 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18565 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18566 } |
|
18567 |
|
18568 EAP_TRACE_DATA_DEBUG( |
|
18569 m_am_tools, |
|
18570 TRACE_FLAGS_DEFAULT, |
|
18571 (EAPL("TLS: complete_select_cipher_suite_and_check_session_id(): resumed m_master_secret"), |
|
18572 m_master_secret.get_data(m_master_secret.get_data_length()), |
|
18573 m_master_secret.get_data_length())); |
|
18574 |
|
18575 eap_status_e notification_status = indicate_state_to_lower_layer( |
|
18576 tls_peap_state_original_session_resumption); |
|
18577 if (notification_status != eap_status_ok) |
|
18578 { |
|
18579 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18580 return EAP_STATUS_RETURN(m_am_tools, notification_status); |
|
18581 } |
|
18582 } |
|
18583 else if (m_tls_session_type == tls_session_type_eap_fast_server_unauthenticated_provisioning_mode_ADHP) |
|
18584 { |
|
18585 EAP_TRACE_DEBUG( |
|
18586 m_am_tools, |
|
18587 TRACE_FLAGS_DEFAULT, |
|
18588 (EAPL("TLS: complete_select_cipher_suite_and_check_session_id(): EAP-FAST server unauthenticated provisioning mode\n"))); |
|
18589 |
|
18590 eap_status_e notification_status = indicate_state_to_lower_layer( |
|
18591 tls_peap_state_full_authentication); |
|
18592 if (notification_status != eap_status_ok) |
|
18593 { |
|
18594 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18595 return EAP_STATUS_RETURN(m_am_tools, notification_status); |
|
18596 } |
|
18597 } |
|
18598 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
18599 else |
|
18600 { |
|
18601 set_tls_session_type(tls_session_type_full_authentication); |
|
18602 |
|
18603 EAP_TRACE_DEBUG( |
|
18604 m_am_tools, |
|
18605 TRACE_FLAGS_DEFAULT, |
|
18606 (EAPL("TLS: complete_select_cipher_suite_and_check_session_id(): full authentication\n"))); |
|
18607 |
|
18608 eap_status_e notification_status = indicate_state_to_lower_layer( |
|
18609 tls_peap_state_full_authentication); |
|
18610 if (notification_status != eap_status_ok) |
|
18611 { |
|
18612 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18613 return EAP_STATUS_RETURN(m_am_tools, notification_status); |
|
18614 } |
|
18615 } |
|
18616 |
|
18617 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
18618 |
|
18619 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
18620 |
|
18621 #if defined(USE_FAST_EAP_TYPE) |
|
18622 if (m_eap_type != eap_type_fast) |
|
18623 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
18624 { |
|
18625 if (m_tls_session_type == tls_session_type_original_session_resumption |
|
18626 || m_tls_session_type == tls_session_type_stateless_session_resumption) |
|
18627 { |
|
18628 const tls_extension_c * const supported_session_ticket_extension = tls_extension_c::get_tls_extension( |
|
18629 tls_extension_type_session_ticket, |
|
18630 &m_supported_tls_extensions, |
|
18631 m_am_tools); |
|
18632 if (supported_session_ticket_extension != 0) |
|
18633 { |
|
18634 EAP_TRACE_DEBUG( |
|
18635 m_am_tools, |
|
18636 TRACE_FLAGS_DEFAULT, |
|
18637 (EAPL("TLS: %s: message_function: complete_select_cipher_suite_and_check_session_id(): ") |
|
18638 EAPL("SST: Server will send a new session ticket to client, length = %d.\n"), |
|
18639 (m_is_client == true ? "client": "server"), |
|
18640 supported_session_ticket_extension->get_data_length())); |
|
18641 |
|
18642 // Server will send a new session ticket to client. |
|
18643 status = completion_action_add( |
|
18644 tls_completion_action_create_handshake_type_new_session_ticket); |
|
18645 if (status != eap_status_ok) |
|
18646 { |
|
18647 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18648 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18649 } |
|
18650 } |
|
18651 } |
|
18652 } |
|
18653 |
|
18654 #endif //#if defined(USE_EAP_TLS_SESSION_TICKET) |
|
18655 |
|
18656 |
|
18657 // The following sequence depends on whether the previous |
|
18658 // session is restored and on the selected cipher suite. |
|
18659 |
|
18660 if (m_tls_session_type == tls_session_type_original_session_resumption |
|
18661 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
18662 || m_tls_session_type == tls_session_type_stateless_session_resumption |
|
18663 #if defined(USE_FAST_EAP_TYPE) |
|
18664 || m_tls_session_type == tls_session_type_eap_fast_pac_session_resumption |
|
18665 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
18666 #endif //#if defined(USE_EAP_TLS_SESSION_TICKET) |
|
18667 ) |
|
18668 { |
|
18669 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
18670 if (m_will_receive_new_session_ticket == true) |
|
18671 { |
|
18672 set_state(tls_peap_state_wait_handshake_type_new_session_ticket); |
|
18673 } |
|
18674 else |
|
18675 #endif // #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
18676 { |
|
18677 set_state(tls_peap_state_wait_change_cipher_spec); |
|
18678 } |
|
18679 |
|
18680 status = completion_action_add( |
|
18681 tls_completion_action_create_change_cipher_spec_type_change_cipher_spec); |
|
18682 if (status != eap_status_ok) |
|
18683 { |
|
18684 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18685 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18686 } |
|
18687 |
|
18688 status = completion_action_add(tls_completion_action_create_handshake_type_finished); |
|
18689 if (status != eap_status_ok) |
|
18690 { |
|
18691 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18692 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18693 } |
|
18694 } |
|
18695 #if defined(USE_FAST_EAP_TYPE) |
|
18696 else if (m_tls_session_type == tls_session_type_eap_fast_server_unauthenticated_provisioning_mode_ADHP) |
|
18697 { |
|
18698 // Ephemeral DH key exchange causes creation of server_key_exchange message. |
|
18699 // Server sends DH public key and related parameters to client. |
|
18700 |
|
18701 status = completion_action_add(tls_completion_action_query_dh_parameters); |
|
18702 if (status != eap_status_ok) |
|
18703 { |
|
18704 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18705 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18706 } |
|
18707 |
|
18708 status = completion_action_add( |
|
18709 tls_completion_action_create_handshake_type_server_key_exchange); |
|
18710 if (status != eap_status_ok) |
|
18711 { |
|
18712 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18713 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18714 } |
|
18715 |
|
18716 // This will complete creation of handshake_type_server_key_exchange message. |
|
18717 status = completion_action_add( |
|
18718 tls_completion_action_complete_create_handshake_type_server_key_exchange); |
|
18719 if (status != eap_status_ok) |
|
18720 { |
|
18721 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18722 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18723 } |
|
18724 |
|
18725 // Also the other pending messages will be processed after this action is completed. |
|
18726 eap_status_e compl_status = completion_action_add( |
|
18727 tls_completion_action_process_tls_records); |
|
18728 if (compl_status != eap_status_ok) |
|
18729 { |
|
18730 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18731 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18732 } |
|
18733 |
|
18734 status = completion_action_add( |
|
18735 tls_completion_action_create_handshake_type_server_hello_done); |
|
18736 if (status != eap_status_ok) |
|
18737 { |
|
18738 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18739 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18740 } |
|
18741 |
|
18742 set_state(tls_peap_state_wait_handshake_type_client_key_exchange); |
|
18743 } |
|
18744 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
18745 else |
|
18746 { |
|
18747 if (m_tls_peap_server_authenticates_client_config_server == true) |
|
18748 { |
|
18749 set_state(tls_peap_state_wait_handshake_type_certificate); |
|
18750 } |
|
18751 else |
|
18752 { |
|
18753 set_state(tls_peap_state_wait_handshake_type_client_key_exchange); |
|
18754 } |
|
18755 |
|
18756 status = completion_action_add(tls_completion_action_create_handshake_type_certificate); |
|
18757 if (status != eap_status_ok) |
|
18758 { |
|
18759 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18760 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18761 } |
|
18762 |
|
18763 if (cipher_suite_is_TLS_DHE_DSS() == true |
|
18764 || cipher_suite_is_TLS_DHE_RSA() == true) |
|
18765 { |
|
18766 // Ephemeral DH key exchange causes creation of server_key_exchange message. |
|
18767 // Server sends DH public key and related parameters to client. |
|
18768 |
|
18769 status = completion_action_add(tls_completion_action_query_dh_parameters); |
|
18770 if (status != eap_status_ok) |
|
18771 { |
|
18772 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18773 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18774 } |
|
18775 |
|
18776 status = completion_action_add( |
|
18777 tls_completion_action_create_handshake_type_server_key_exchange); |
|
18778 if (status != eap_status_ok) |
|
18779 { |
|
18780 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18781 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18782 } |
|
18783 |
|
18784 // This will complete creation of handshake_type_server_key_exchange message. |
|
18785 status = completion_action_add( |
|
18786 tls_completion_action_complete_create_handshake_type_server_key_exchange); |
|
18787 if (status != eap_status_ok) |
|
18788 { |
|
18789 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18790 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18791 } |
|
18792 |
|
18793 // Also the other pending messages will be processed after this action is completed. |
|
18794 eap_status_e compl_status = completion_action_add( |
|
18795 tls_completion_action_process_tls_records); |
|
18796 if (compl_status != eap_status_ok) |
|
18797 { |
|
18798 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18799 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18800 } |
|
18801 } |
|
18802 |
|
18803 if (m_tls_peap_server_authenticates_client_config_server == true) |
|
18804 { |
|
18805 // Server initiates client authentication. |
|
18806 status = completion_action_add( |
|
18807 tls_completion_action_create_handshake_type_certificate_request); |
|
18808 if (status != eap_status_ok) |
|
18809 { |
|
18810 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18811 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18812 } |
|
18813 } |
|
18814 |
|
18815 status = completion_action_add( |
|
18816 tls_completion_action_create_handshake_type_server_hello_done); |
|
18817 if (status != eap_status_ok) |
|
18818 { |
|
18819 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18820 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18821 } |
|
18822 |
|
18823 |
|
18824 EAP_TRACE_DEBUG( |
|
18825 m_am_tools, |
|
18826 TRACE_FLAGS_DEFAULT, |
|
18827 (EAPL("TLS: %s: pki_function: query_certificate_chain()\n"), |
|
18828 (m_is_client == true ? "client": "server"))); |
|
18829 |
|
18830 status = m_am_tls_services->query_certificate_chain( |
|
18831 &m_own_certificate_authorities, |
|
18832 &m_own_certificate_types, |
|
18833 m_selected_cipher_suite); |
|
18834 if (status == eap_status_pending_request) |
|
18835 { |
|
18836 // This is pending query, that will be completed by |
|
18837 // complete_query_certificate_chain() call. |
|
18838 m_pending_query_certificate_chain = true; |
|
18839 } |
|
18840 else if (status == eap_status_completed_request) |
|
18841 { |
|
18842 // This is already completed by complete_query_certificate_chain() call. |
|
18843 } |
|
18844 else if (status == eap_status_ok) |
|
18845 { |
|
18846 // This is also an error case, because this call is always completed on success. |
|
18847 status = eap_status_process_general_error; |
|
18848 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18849 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18850 } |
|
18851 else // All other status values means error, because this |
|
18852 // call is always completed on success. |
|
18853 { |
|
18854 // This is an error case. |
|
18855 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18856 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
18857 } |
|
18858 |
|
18859 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
18860 |
|
18861 if (m_tls_peap_server_authenticates_client_config_server == true) |
|
18862 { |
|
18863 // Server initiates client authentication. |
|
18864 status = m_am_tls_services->query_certificate_authorities_and_types(); |
|
18865 if (status == eap_status_pending_request) |
|
18866 { |
|
18867 // This is pending query, that will be completed by |
|
18868 // complete_query_certificate_authorities_and_types() call. |
|
18869 m_pending_query_certificate_authorities_and_types = true; |
|
18870 } |
|
18871 else if (status == eap_status_completed_request) |
|
18872 { |
|
18873 // This is already completed by |
|
18874 // complete_query_certificate_authorities_and_types() call. |
|
18875 } |
|
18876 else if (status == eap_status_ok) |
|
18877 { |
|
18878 // This is also an error case, because this call is |
|
18879 // always completed on success. |
|
18880 status = eap_status_process_general_error; |
|
18881 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18882 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18883 } |
|
18884 else // All other status values means error, because this |
|
18885 // call is always completed on success. |
|
18886 { |
|
18887 // This is an error case. |
|
18888 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18889 return EAP_STATUS_RETURN_AND_CREATE_TLS_PROTOCOL_ALERT(m_am_tools, status); |
|
18890 } |
|
18891 } |
|
18892 } |
|
18893 } |
|
18894 |
|
18895 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - |
|
18896 |
|
18897 if (status == eap_status_ok) |
|
18898 { |
|
18899 status = check_sent_tls_message(); |
|
18900 if (status != eap_status_ok) |
|
18901 { |
|
18902 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18903 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18904 } |
|
18905 |
|
18906 status = eap_status_completed_request; |
|
18907 } |
|
18908 |
|
18909 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18910 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18911 } |
|
18912 |
|
18913 //-------------------------------------------------- |
|
18914 |
|
18915 #if defined(USE_EAP_TLS_SESSION_TICKET) |
|
18916 |
|
18917 EAP_FUNC_EXPORT eap_status_e tls_record_c::complete_query_new_session_ticket( |
|
18918 const tls_extension_c * const new_session_ticket_or_null) |
|
18919 { |
|
18920 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18921 |
|
18922 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
18923 EAP_TRACE_DEBUG( |
|
18924 m_am_tools, |
|
18925 TRACE_FLAGS_DEFAULT, |
|
18926 (EAPL("TLS: this = 0x%08x, %s: pki_function: starts: tls_record_c::complete_query_new_session_ticket()\n"), |
|
18927 this, |
|
18928 (m_is_client == true ? "client": "server"))); |
|
18929 |
|
18930 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::complete_query_new_session_ticket()"); |
|
18931 |
|
18932 eap_status_e status(eap_status_ok); |
|
18933 |
|
18934 if (new_session_ticket_or_null != 0) |
|
18935 { |
|
18936 tls_extension_c * const copy_of_session_ticket = new_session_ticket_or_null->copy(); |
|
18937 |
|
18938 if (copy_of_session_ticket == 0) |
|
18939 { |
|
18940 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18941 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
18942 } |
|
18943 |
|
18944 status = m_supported_tls_extensions.add_object(copy_of_session_ticket, true); |
|
18945 } |
|
18946 |
|
18947 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18948 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18949 } |
|
18950 |
|
18951 #endif //#if defined(USE_EAP_TLS_SESSION_TICKET) |
|
18952 |
|
18953 //-------------------------------------------------- |
|
18954 |
|
18955 EAP_FUNC_EXPORT eap_status_e tls_record_c::complete_verify_certificate_chain( |
|
18956 const eap_status_e result) |
|
18957 { |
|
18958 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18959 |
|
18960 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
18961 EAP_TRACE_DEBUG( |
|
18962 m_am_tools, |
|
18963 TRACE_FLAGS_DEFAULT, |
|
18964 (EAPL("TLS: this = 0x%08x, %s: pki_function: starts: tls_record_c::complete_verify_certificate_chain()\n"), |
|
18965 this, |
|
18966 (m_is_client == true ? "client": "server"))); |
|
18967 |
|
18968 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::complete_verify_certificate_chain()"); |
|
18969 |
|
18970 eap_status_e status = result; |
|
18971 |
|
18972 m_pending_verify_certificate_chain = false; |
|
18973 |
|
18974 m_peer_certificate_chain_result = result; |
|
18975 |
|
18976 if (m_peer_certificate_chain_result == eap_status_ok) |
|
18977 { |
|
18978 // Ok certificate. |
|
18979 } |
|
18980 else |
|
18981 { |
|
18982 // Illegal certificate. |
|
18983 |
|
18984 status = create_tls_protocol_alert( |
|
18985 tls_alert_description_none, |
|
18986 tls_alert_level_none, |
|
18987 m_peer_certificate_chain_result); |
|
18988 if (status != eap_status_ok) |
|
18989 { |
|
18990 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
18991 return EAP_STATUS_RETURN(m_am_tools, status); |
|
18992 } |
|
18993 } |
|
18994 |
|
18995 if (status == eap_status_ok) |
|
18996 { |
|
18997 status = check_sent_tls_message(); |
|
18998 if (status != eap_status_ok) |
|
18999 { |
|
19000 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19001 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19002 } |
|
19003 |
|
19004 status = eap_status_completed_request; |
|
19005 } |
|
19006 |
|
19007 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19008 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19009 } |
|
19010 |
|
19011 //-------------------------------------------------- |
|
19012 |
|
19013 EAP_FUNC_EXPORT eap_status_e tls_record_c::complete_query_certificate_chain( |
|
19014 EAP_TEMPLATE_CONST eap_array_c<eap_variable_data_c> * const certificate_chain, |
|
19015 const eap_status_e completion_status) |
|
19016 { |
|
19017 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19018 |
|
19019 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
19020 EAP_TRACE_DEBUG( |
|
19021 m_am_tools, |
|
19022 TRACE_FLAGS_DEFAULT, |
|
19023 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::complete_query_certificate_chain()\n"), |
|
19024 this, |
|
19025 (m_is_client == true ? "client": "server"))); |
|
19026 |
|
19027 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::complete_query_certificate_chain()"); |
|
19028 |
|
19029 eap_status_e status = eap_status_not_supported; |
|
19030 |
|
19031 m_pending_query_certificate_chain = false; |
|
19032 |
|
19033 { |
|
19034 if (completion_status != eap_status_ok |
|
19035 || certificate_chain == 0 |
|
19036 || certificate_chain->get_object_count() == 0) |
|
19037 { |
|
19038 if (completion_status != eap_status_ok) |
|
19039 { |
|
19040 (void)EAP_STATUS_RETURN(m_am_tools, completion_status); |
|
19041 } |
|
19042 |
|
19043 if (m_is_client == false) |
|
19044 { |
|
19045 // Server fails immediately. |
|
19046 |
|
19047 status = create_tls_protocol_alert( |
|
19048 tls_alert_description_none, |
|
19049 tls_alert_level_none, |
|
19050 completion_status); |
|
19051 if (status != eap_status_ok) |
|
19052 { |
|
19053 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19054 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19055 } |
|
19056 |
|
19057 EAP_TRACE_DEBUG( |
|
19058 m_am_tools, |
|
19059 TRACE_FLAGS_DEFAULT, |
|
19060 (EAPL("ERROR: TLS: %s: pki_function: complete_query_certificate_chain(): ") |
|
19061 EAPL("Server have illegal sertificate for this cipher suite.\n"), |
|
19062 (m_is_client == true ? "client": "server"))); |
|
19063 } |
|
19064 else |
|
19065 { |
|
19066 if (m_tls_peap_server_authenticates_client_policy_flag == true |
|
19067 || (m_tls_peap_server_authenticates_client_policy_flag == false |
|
19068 && completion_status != eap_status_illegal_certificate |
|
19069 && completion_status != eap_status_ca_certificate_unknown)) |
|
19070 { |
|
19071 // Client does fail immediately. |
|
19072 // This session could NOT use server only authentication. |
|
19073 if (completion_status == eap_status_illegal_certificate) |
|
19074 { |
|
19075 EAP_TRACE_DEBUG( |
|
19076 m_am_tools, |
|
19077 TRACE_FLAGS_DEFAULT, |
|
19078 (EAPL("ERROR: TLS: %s: pki_function: complete_query_certificate_chain(): ") |
|
19079 EAPL("Client have illegal sertificate for this cipher suite.\n"), |
|
19080 (m_is_client == true ? "client": "server"))); |
|
19081 |
|
19082 status = eap_status_illegal_certificate; |
|
19083 (void)EAP_STATUS_RETURN(m_am_tools, status); |
|
19084 } |
|
19085 else |
|
19086 { |
|
19087 EAP_TRACE_DEBUG( |
|
19088 m_am_tools, |
|
19089 TRACE_FLAGS_DEFAULT, |
|
19090 (EAPL("ERROR: TLS: %s: pki_function: complete_query_certificate_chain(): ") |
|
19091 EAPL("Client does NOT allow anonymous client.\n"), |
|
19092 (m_is_client == true ? "client": "server"))); |
|
19093 |
|
19094 status = eap_status_insufficient_security; |
|
19095 (void)EAP_STATUS_RETURN(m_am_tools, status); |
|
19096 } |
|
19097 |
|
19098 // This will cause the session terminate immediately. |
|
19099 status = get_type_partner()->set_session_timeout(0ul); |
|
19100 if (status != eap_status_ok) |
|
19101 { |
|
19102 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19103 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19104 } |
|
19105 |
|
19106 #if defined(USE_FAST_EAP_TYPE) |
|
19107 if (m_eap_type == eap_type_fast) |
|
19108 { |
|
19109 send_error_notification(eap_status_no_pac_nor_certs_to_authenticate_with_provision_disabled); |
|
19110 |
|
19111 status = create_tls_protocol_alert( |
|
19112 tls_alert_description_internal_error, |
|
19113 tls_alert_level_fatal, |
|
19114 status); |
|
19115 if (status != eap_status_ok) |
|
19116 { |
|
19117 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19118 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19119 } |
|
19120 } |
|
19121 else |
|
19122 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
19123 { |
|
19124 status = create_tls_protocol_alert( |
|
19125 tls_alert_description_none, |
|
19126 tls_alert_level_none, |
|
19127 completion_status); |
|
19128 if (status != eap_status_ok) |
|
19129 { |
|
19130 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19131 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19132 } |
|
19133 } |
|
19134 } |
|
19135 else |
|
19136 { |
|
19137 |
|
19138 #if defined(USE_FAST_EAP_TYPE) |
|
19139 if (m_eap_type == eap_type_fast |
|
19140 && m_eap_fast_allow_server_unauthenticated_provisioning_mode_ADHP == false |
|
19141 && m_fast_allow_server_authenticated_provisioning_mode == false) |
|
19142 { |
|
19143 // No PAC, no sertificate, no provision allowed. |
|
19144 // This will cause the session terminate immediately. |
|
19145 status = get_type_partner()->set_session_timeout(0ul); |
|
19146 if (status != eap_status_ok) |
|
19147 { |
|
19148 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19149 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19150 } |
|
19151 |
|
19152 send_error_notification(eap_status_no_pac_nor_certs_to_authenticate_with_provision_disabled); |
|
19153 |
|
19154 status = create_tls_protocol_alert( |
|
19155 tls_alert_description_internal_error, |
|
19156 tls_alert_level_fatal, |
|
19157 status); |
|
19158 if (status != eap_status_ok) |
|
19159 { |
|
19160 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19161 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19162 } |
|
19163 } |
|
19164 else |
|
19165 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
19166 { |
|
19167 // Client does not fail immediately. |
|
19168 // This session could use server only authentication. |
|
19169 // NOTE, in this case client must send empty certificate message to server. |
|
19170 EAP_TRACE_DEBUG( |
|
19171 m_am_tools, |
|
19172 TRACE_FLAGS_DEFAULT, |
|
19173 (EAPL("INFO: TLS: %s: pki_function: complete_query_certificate_chain(): ") |
|
19174 EAPL("Client allows anonymous client.\n"), |
|
19175 (m_is_client == true ? "client": "server"))); |
|
19176 |
|
19177 m_tls_peap_server_authenticates_client_action = false; |
|
19178 status = eap_status_ok; |
|
19179 } |
|
19180 } |
|
19181 } |
|
19182 } |
|
19183 else |
|
19184 { |
|
19185 status = copy<eap_variable_data_c>( |
|
19186 certificate_chain, |
|
19187 &m_own_certificate_chain, |
|
19188 m_am_tools, |
|
19189 false); |
|
19190 if (status != eap_status_ok) |
|
19191 { |
|
19192 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19193 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19194 } |
|
19195 } |
|
19196 } |
|
19197 |
|
19198 if (status == eap_status_ok) |
|
19199 { |
|
19200 status = check_sent_tls_message(); |
|
19201 if (status != eap_status_ok) |
|
19202 { |
|
19203 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19204 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19205 } |
|
19206 |
|
19207 status = eap_status_completed_request; |
|
19208 } |
|
19209 |
|
19210 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19211 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19212 } |
|
19213 |
|
19214 //-------------------------------------------------- |
|
19215 |
|
19216 EAP_FUNC_EXPORT eap_status_e tls_record_c::complete_query_certificate_authorities_and_types( |
|
19217 EAP_TEMPLATE_CONST eap_array_c<eap_variable_data_c> * const certificate_authorities, |
|
19218 EAP_TEMPLATE_CONST eap_array_c<u8_t> * const certificate_types, |
|
19219 const eap_status_e completion_status) |
|
19220 { |
|
19221 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19222 |
|
19223 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
19224 EAP_TRACE_DEBUG( |
|
19225 m_am_tools, |
|
19226 TRACE_FLAGS_DEFAULT, |
|
19227 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::complete_query_certificate_authorities_and_types()\n"), |
|
19228 this, |
|
19229 (m_is_client == true ? "client": "server"))); |
|
19230 |
|
19231 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::complete_query_certificate_authorities_and_types()"); |
|
19232 |
|
19233 m_pending_query_certificate_authorities_and_types = false; |
|
19234 |
|
19235 eap_status_e status = eap_status_not_supported; |
|
19236 |
|
19237 if (completion_status != eap_status_ok) |
|
19238 { |
|
19239 status = create_tls_protocol_alert( |
|
19240 tls_alert_description_none, |
|
19241 tls_alert_level_none, |
|
19242 completion_status); |
|
19243 if (status != eap_status_ok) |
|
19244 { |
|
19245 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19246 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19247 } |
|
19248 } |
|
19249 else |
|
19250 { |
|
19251 status = copy<eap_variable_data_c>( |
|
19252 certificate_authorities, |
|
19253 &m_own_certificate_authorities, |
|
19254 m_am_tools, |
|
19255 false); |
|
19256 if (status != eap_status_ok) |
|
19257 { |
|
19258 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19259 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19260 } |
|
19261 |
|
19262 status = copy_simple<u8_t>( |
|
19263 certificate_types, |
|
19264 &m_own_certificate_types, |
|
19265 m_am_tools, |
|
19266 false); |
|
19267 if (status != eap_status_ok) |
|
19268 { |
|
19269 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19270 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19271 } |
|
19272 } |
|
19273 |
|
19274 |
|
19275 if (status == eap_status_ok) |
|
19276 { |
|
19277 status = check_sent_tls_message(); |
|
19278 if (status != eap_status_ok) |
|
19279 { |
|
19280 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19281 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19282 } |
|
19283 |
|
19284 status = eap_status_completed_request; |
|
19285 } |
|
19286 |
|
19287 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19288 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19289 } |
|
19290 |
|
19291 //-------------------------------------------------- |
|
19292 |
|
19293 EAP_FUNC_EXPORT eap_status_e tls_record_c::complete_query_dh_parameters( |
|
19294 const eap_variable_data_c * const dhe_prime, |
|
19295 const eap_variable_data_c * const dhe_group_generator, |
|
19296 const eap_status_e completion_status) |
|
19297 { |
|
19298 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19299 |
|
19300 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
19301 EAP_TRACE_DEBUG( |
|
19302 m_am_tools, |
|
19303 TRACE_FLAGS_DEFAULT, |
|
19304 (EAPL("TLS: this = 0x%08x, %s: pki_function: starts: tls_record_c::complete_query_dh_parameters()\n"), |
|
19305 this, |
|
19306 (m_is_client == true ? "client": "server"))); |
|
19307 |
|
19308 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::complete_query_dh_parameters()"); |
|
19309 |
|
19310 m_pending_query_dh_parameters = false; |
|
19311 |
|
19312 eap_status_e status = eap_status_not_supported; |
|
19313 |
|
19314 if (completion_status != eap_status_ok) |
|
19315 { |
|
19316 status = create_tls_protocol_alert( |
|
19317 tls_alert_description_none, |
|
19318 tls_alert_level_none, |
|
19319 completion_status); |
|
19320 if (status != eap_status_ok) |
|
19321 { |
|
19322 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19323 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19324 } |
|
19325 } |
|
19326 else |
|
19327 { |
|
19328 status = m_dhe_prime.set_copy_of_buffer(dhe_prime); |
|
19329 if (status != eap_status_ok) |
|
19330 { |
|
19331 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19332 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19333 } |
|
19334 |
|
19335 status = m_dhe_group_generator.set_copy_of_buffer(dhe_group_generator); |
|
19336 if (status != eap_status_ok) |
|
19337 { |
|
19338 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19339 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19340 } |
|
19341 } |
|
19342 |
|
19343 if (status == eap_status_ok) |
|
19344 { |
|
19345 status = check_sent_tls_message(); |
|
19346 if (status != eap_status_ok) |
|
19347 { |
|
19348 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19349 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19350 } |
|
19351 |
|
19352 status = eap_status_completed_request; |
|
19353 } |
|
19354 |
|
19355 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19356 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19357 } |
|
19358 |
|
19359 //-------------------------------------------------- |
|
19360 |
|
19361 EAP_FUNC_EXPORT eap_status_e tls_record_c::complete_query_realm( |
|
19362 const eap_variable_data_c * const realm, |
|
19363 const eap_status_e completion_status) |
|
19364 { |
|
19365 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19366 |
|
19367 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
19368 EAP_TRACE_DEBUG( |
|
19369 m_am_tools, |
|
19370 TRACE_FLAGS_DEFAULT, |
|
19371 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::complete_query_realm()\n"), |
|
19372 this, |
|
19373 (m_is_client == true ? "client": "server"))); |
|
19374 |
|
19375 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::complete_query_realm()"); |
|
19376 |
|
19377 m_pending_query_realm = false; |
|
19378 |
|
19379 eap_status_e status = eap_status_not_supported; |
|
19380 |
|
19381 if (completion_status != eap_status_ok) |
|
19382 { |
|
19383 status = create_tls_protocol_alert( |
|
19384 tls_alert_description_none, |
|
19385 tls_alert_level_none, |
|
19386 completion_status); |
|
19387 if (status != eap_status_ok) |
|
19388 { |
|
19389 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19390 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19391 } |
|
19392 } |
|
19393 else |
|
19394 { |
|
19395 status = m_NAI_realm.set_copy_of_buffer(realm); |
|
19396 } |
|
19397 |
|
19398 if (status == eap_status_ok) |
|
19399 { |
|
19400 status = check_sent_tls_message(); |
|
19401 if (status != eap_status_ok) |
|
19402 { |
|
19403 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19404 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19405 } |
|
19406 |
|
19407 status = eap_status_completed_request; |
|
19408 } |
|
19409 |
|
19410 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19411 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19412 } |
|
19413 |
|
19414 //-------------------------------------------------- |
|
19415 |
|
19416 EAP_FUNC_EXPORT eap_status_e tls_record_c::complete_rsa_decrypt_with_private_key( |
|
19417 const eap_variable_data_c * const premaster_secret, |
|
19418 const eap_status_e completion_status) |
|
19419 { |
|
19420 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19421 |
|
19422 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
19423 EAP_TRACE_DEBUG( |
|
19424 m_am_tools, |
|
19425 TRACE_FLAGS_DEFAULT, |
|
19426 (EAPL("TLS: this = 0x%08x, %s: pki_function: starts: tls_record_c::complete_rsa_decrypt_with_private_key()\n"), |
|
19427 this, |
|
19428 (m_is_client == true ? "client": "server"))); |
|
19429 |
|
19430 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::complete_rsa_decrypt_with_private_key()"); |
|
19431 |
|
19432 m_pending_rsa_decrypt_with_private_key = false; |
|
19433 |
|
19434 eap_status_e status = eap_status_not_supported; |
|
19435 |
|
19436 if (completion_status != eap_status_ok) |
|
19437 { |
|
19438 status = create_tls_protocol_alert( |
|
19439 tls_alert_description_none, |
|
19440 tls_alert_level_none, |
|
19441 completion_status); |
|
19442 if (status != eap_status_ok) |
|
19443 { |
|
19444 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19445 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19446 } |
|
19447 } |
|
19448 else |
|
19449 { |
|
19450 EAP_TRACE_DATA_DEBUG( |
|
19451 m_am_tools, |
|
19452 TRACE_FLAGS_DEFAULT, |
|
19453 (EAPL("TLS: complete_rsa_decrypt_with_private_key(): premaster_secret"), |
|
19454 premaster_secret->get_data(), |
|
19455 premaster_secret->get_data_length())); |
|
19456 |
|
19457 status = m_premaster_secret.set_copy_of_buffer(premaster_secret); |
|
19458 if (status != eap_status_ok) |
|
19459 { |
|
19460 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19461 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19462 } |
|
19463 |
|
19464 EAP_TRACE_DATA_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("TLS: m_premaster_secret"), |
|
19465 m_premaster_secret.get_data(m_premaster_secret.get_data_length()), |
|
19466 m_premaster_secret.get_data_length())); |
|
19467 |
|
19468 m_key_material_generated = false; |
|
19469 |
|
19470 // We must generate master secret. |
|
19471 status = generate_master_secret(); |
|
19472 if (status != eap_status_ok) |
|
19473 { |
|
19474 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19475 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19476 } |
|
19477 |
|
19478 // We must generate the key material. |
|
19479 status = generate_key_material(); |
|
19480 if (status != eap_status_ok) |
|
19481 { |
|
19482 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19483 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19484 } |
|
19485 } |
|
19486 |
|
19487 if (status == eap_status_ok) |
|
19488 { |
|
19489 status = check_sent_tls_message(); |
|
19490 if (status != eap_status_ok) |
|
19491 { |
|
19492 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19493 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19494 } |
|
19495 |
|
19496 status = eap_status_completed_request; |
|
19497 } |
|
19498 |
|
19499 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19500 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19501 } |
|
19502 |
|
19503 //-------------------------------------------------- |
|
19504 |
|
19505 EAP_FUNC_EXPORT eap_status_e tls_record_c::complete_rsa_encrypt_with_public_key( |
|
19506 const eap_variable_data_c * const encrypted_premaster_secret, |
|
19507 const eap_status_e completion_status) |
|
19508 { |
|
19509 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19510 |
|
19511 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
19512 EAP_TRACE_DEBUG( |
|
19513 m_am_tools, |
|
19514 TRACE_FLAGS_DEFAULT, |
|
19515 (EAPL("TLS: this = 0x%08x, %s: pki_function: starts: tls_record_c::complete_rsa_encrypt_with_public_key()\n"), |
|
19516 this, |
|
19517 (m_is_client == true ? "client": "server"))); |
|
19518 |
|
19519 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::complete_rsa_encrypt_with_public_key()"); |
|
19520 |
|
19521 m_pending_rsa_encrypt_with_public_key = false; |
|
19522 |
|
19523 eap_status_e status = eap_status_not_supported; |
|
19524 |
|
19525 if (completion_status != eap_status_ok) |
|
19526 { |
|
19527 status = create_tls_protocol_alert( |
|
19528 tls_alert_description_none, |
|
19529 tls_alert_level_none, |
|
19530 completion_status); |
|
19531 if (status != eap_status_ok) |
|
19532 { |
|
19533 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19534 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19535 } |
|
19536 } |
|
19537 else |
|
19538 { |
|
19539 EAP_TRACE_DATA_DEBUG( |
|
19540 m_am_tools, |
|
19541 TRACE_FLAGS_DEFAULT, |
|
19542 (EAPL("TLS: complete_rsa_encrypt_with_public_key(): encrypted premaster_secret"), |
|
19543 encrypted_premaster_secret->get_data(), |
|
19544 encrypted_premaster_secret->get_data_length())); |
|
19545 |
|
19546 status = m_own_encrypted_premaster_secret.set_copy_of_buffer(encrypted_premaster_secret); |
|
19547 if (status != eap_status_ok) |
|
19548 { |
|
19549 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19550 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19551 } |
|
19552 } |
|
19553 |
|
19554 if (status == eap_status_ok) |
|
19555 { |
|
19556 status = check_sent_tls_message(); |
|
19557 if (status != eap_status_ok) |
|
19558 { |
|
19559 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19560 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19561 } |
|
19562 |
|
19563 status = eap_status_completed_request; |
|
19564 } |
|
19565 |
|
19566 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19567 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19568 } |
|
19569 |
|
19570 //-------------------------------------------------- |
|
19571 |
|
19572 EAP_FUNC_EXPORT eap_status_e tls_record_c::complete_sign_with_private_key( |
|
19573 const eap_variable_data_c * const signed_message_hash, |
|
19574 const eap_status_e completion_status) |
|
19575 { |
|
19576 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19577 |
|
19578 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
19579 EAP_TRACE_DEBUG( |
|
19580 m_am_tools, |
|
19581 TRACE_FLAGS_DEFAULT, |
|
19582 (EAPL("TLS: this = 0x%08x, %s: pki_function: starts: tls_record_c::complete_sign_with_private_key()\n"), |
|
19583 this, |
|
19584 (m_is_client == true ? "client": "server"))); |
|
19585 |
|
19586 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::complete_sign_with_private_key()"); |
|
19587 |
|
19588 m_pending_sign_with_private_key = false; |
|
19589 |
|
19590 eap_status_e status = eap_status_not_supported; |
|
19591 |
|
19592 if (completion_status != eap_status_ok) |
|
19593 { |
|
19594 status = create_tls_protocol_alert( |
|
19595 tls_alert_description_none, |
|
19596 tls_alert_level_none, |
|
19597 completion_status); |
|
19598 if (status != eap_status_ok) |
|
19599 { |
|
19600 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19601 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19602 } |
|
19603 } |
|
19604 else |
|
19605 { |
|
19606 if (signed_message_hash->get_is_valid_data() == false) |
|
19607 { |
|
19608 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19609 return EAP_STATUS_RETURN(m_am_tools, eap_status_process_general_error); |
|
19610 } |
|
19611 |
|
19612 status = m_signed_message_hash.set_copy_of_buffer(signed_message_hash); |
|
19613 if (status != eap_status_ok) |
|
19614 { |
|
19615 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19616 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19617 } |
|
19618 |
|
19619 EAP_TRACE_DATA_DEBUG( |
|
19620 m_am_tools, |
|
19621 TRACE_FLAGS_DEFAULT, |
|
19622 (EAPL("TLS: complete_sign_with_private_key(): m_signed_message_hash"), |
|
19623 m_signed_message_hash.get_data(m_signed_message_hash.get_data_length()), |
|
19624 m_signed_message_hash.get_data_length())); |
|
19625 } |
|
19626 |
|
19627 |
|
19628 if (status == eap_status_ok) |
|
19629 { |
|
19630 status = check_sent_tls_message(); |
|
19631 if (status != eap_status_ok) |
|
19632 { |
|
19633 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19634 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19635 } |
|
19636 |
|
19637 status = eap_status_completed_request; |
|
19638 } |
|
19639 |
|
19640 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19641 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19642 } |
|
19643 |
|
19644 //-------------------------------------------------- |
|
19645 |
|
19646 EAP_FUNC_EXPORT eap_status_e tls_record_c::complete_verify_with_public_key( |
|
19647 const eap_status_e verify_status) |
|
19648 { |
|
19649 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19650 |
|
19651 EAP_TRACE_DEBUG(m_am_tools, TRACE_FLAGS_DEFAULT, (EAPL("\n"))); |
|
19652 EAP_TRACE_DEBUG( |
|
19653 m_am_tools, |
|
19654 TRACE_FLAGS_DEFAULT, |
|
19655 (EAPL("TLS: this = 0x%08x, %s: pki_function: starts: tls_record_c::complete_verify_with_public_key()\n"), |
|
19656 this, |
|
19657 (m_is_client == true ? "client": "server"))); |
|
19658 |
|
19659 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::complete_verify_with_public_key()"); |
|
19660 |
|
19661 m_pending_verify_with_public_key = false; |
|
19662 |
|
19663 eap_status_e status = eap_status_ok; |
|
19664 |
|
19665 m_verify_signature = verify_status; |
|
19666 |
|
19667 if (m_verify_signature != eap_status_ok) |
|
19668 { |
|
19669 // Verification failed. |
|
19670 |
|
19671 status = create_tls_protocol_alert( |
|
19672 tls_alert_description_none, |
|
19673 tls_alert_level_none, |
|
19674 m_verify_signature); |
|
19675 if (status != eap_status_ok) |
|
19676 { |
|
19677 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19678 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19679 } |
|
19680 } |
|
19681 |
|
19682 if (status == eap_status_ok) |
|
19683 { |
|
19684 status = check_sent_tls_message(); |
|
19685 if (status != eap_status_ok) |
|
19686 { |
|
19687 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19688 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19689 } |
|
19690 |
|
19691 status = eap_status_completed_request; |
|
19692 } |
|
19693 |
|
19694 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19695 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19696 } |
|
19697 |
|
19698 //-------------------------------------------------- |
|
19699 |
|
19700 EAP_FUNC_EXPORT eap_status_e tls_record_c::get_eap_tls_master_session_key( |
|
19701 eap_variable_data_c * const eap_tls_master_session_key, |
|
19702 eap_variable_data_c * const mschapv2_challenges |
|
19703 ) |
|
19704 { |
|
19705 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19706 |
|
19707 EAP_TRACE_DEBUG( |
|
19708 m_am_tools, |
|
19709 TRACE_FLAGS_DEFAULT, |
|
19710 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::get_eap_tls_master_session_key()\n"), |
|
19711 this, |
|
19712 (m_is_client == true ? "client": "server"))); |
|
19713 |
|
19714 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::get_eap_tls_master_session_key()"); |
|
19715 |
|
19716 eap_status_e status(eap_status_process_general_error); |
|
19717 |
|
19718 #if defined(USE_FAST_EAP_TYPE) |
|
19719 if (m_eap_type == eap_type_fast) |
|
19720 { |
|
19721 status = eap_tls_master_session_key->set_copy_of_buffer(&m_session_key_seed); |
|
19722 if (status != eap_status_ok) |
|
19723 { |
|
19724 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19725 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19726 } |
|
19727 |
|
19728 if (mschapv2_challenges != 0 |
|
19729 && mschapv2_challenges->get_is_valid() == true |
|
19730 && m_mschapv2_challenges.get_is_valid_data() == true) |
|
19731 { |
|
19732 status = mschapv2_challenges->set_copy_of_buffer(&m_mschapv2_challenges); |
|
19733 } |
|
19734 } |
|
19735 else |
|
19736 #else |
|
19737 EAP_UNREFERENCED_PARAMETER(mschapv2_challenges); |
|
19738 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
19739 { |
|
19740 status = eap_tls_master_session_key->set_copy_of_buffer(&m_eap_master_session_key); |
|
19741 } |
|
19742 |
|
19743 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19744 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19745 } |
|
19746 |
|
19747 //-------------------------------------------------- |
|
19748 |
|
19749 EAP_FUNC_EXPORT eap_status_e tls_record_c::add_rogue_ap( |
|
19750 eap_array_c<eap_rogue_ap_entry_c> & rogue_ap_list) |
|
19751 { |
|
19752 return EAP_STATUS_RETURN(m_am_tools, get_type_partner()->add_rogue_ap(rogue_ap_list)); |
|
19753 } |
|
19754 |
|
19755 //-------------------------------------------------- |
|
19756 |
|
19757 // |
|
19758 EAP_FUNC_EXPORT eap_status_e tls_record_c::set_session_timeout( |
|
19759 const u32_t session_timeout_ms) |
|
19760 { |
|
19761 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19762 |
|
19763 eap_status_e status = get_type_partner()->set_session_timeout(session_timeout_ms); |
|
19764 if (status != eap_status_ok) |
|
19765 { |
|
19766 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19767 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19768 } |
|
19769 |
|
19770 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19771 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19772 } |
|
19773 |
|
19774 //-------------------------------------------------- |
|
19775 |
|
19776 EAP_FUNC_EXPORT eap_status_e tls_record_c::set_tls_session_type(const tls_session_type_e tls_session_type) |
|
19777 { |
|
19778 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19779 |
|
19780 EAP_TRACE_DEBUG( |
|
19781 m_am_tools, |
|
19782 TRACE_FLAGS_DEFAULT, |
|
19783 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::set_tls_session_type(): m_tls_session_type=%d=%s\n"), |
|
19784 this, |
|
19785 (m_is_client == true ? "client": "server"), |
|
19786 tls_session_type, |
|
19787 eap_tls_trace_string_c::get_tls_session_type_string(tls_session_type))); |
|
19788 |
|
19789 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::set_tls_session_type()"); |
|
19790 |
|
19791 m_tls_session_type = tls_session_type; |
|
19792 |
|
19793 eap_status_e status = get_type_partner()->set_tls_session_type(tls_session_type); |
|
19794 |
|
19795 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19796 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19797 } |
|
19798 |
|
19799 //-------------------------------------------------- |
|
19800 |
|
19801 EAP_FUNC_EXPORT tls_session_type_e tls_record_c::get_tls_session_type() |
|
19802 { |
|
19803 return m_tls_session_type; |
|
19804 } |
|
19805 |
|
19806 //-------------------------------------------------- |
|
19807 |
|
19808 EAP_FUNC_EXPORT void tls_record_c::set_tls_identity_privacy_handshake_state(const tls_identity_privacy_handshake_state_e state) |
|
19809 { |
|
19810 #if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
19811 EAP_TRACE_DEBUG( |
|
19812 m_am_tools, |
|
19813 TRACE_FLAGS_DEFAULT, |
|
19814 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::set_tls_identity_privacy_handshake_state(): Changes from %d=%s to %d=%s\n"), |
|
19815 this, |
|
19816 (m_is_client == true ? "client": "server"), |
|
19817 m_tls_identity_privacy_handshake_state, |
|
19818 eap_tls_trace_string_c::get_tls_identity_privacy_handshake_state_string(m_tls_identity_privacy_handshake_state), |
|
19819 state, |
|
19820 eap_tls_trace_string_c::get_tls_identity_privacy_handshake_state_string(state))); |
|
19821 |
|
19822 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::set_tls_identity_privacy_handshake_state()"); |
|
19823 |
|
19824 m_tls_identity_privacy_handshake_state = state; |
|
19825 #else |
|
19826 EAP_UNREFERENCED_PARAMETER(state); |
|
19827 #endif //#if defined(USE_EAP_TLS_IDENTITY_PRIVACY) |
|
19828 } |
|
19829 |
|
19830 //-------------------------------------------------- |
|
19831 |
|
19832 EAP_FUNC_EXPORT void tls_record_c::set_selected_cipher_suite(const tls_cipher_suites_e cipher_suite) |
|
19833 { |
|
19834 EAP_TRACE_DEBUG( |
|
19835 m_am_tools, |
|
19836 TRACE_FLAGS_DEFAULT, |
|
19837 (EAPL("TLS: this = 0x%08x, %s: suite_function: starts: tls_record_c::set_selected_cipher_suite(): Changes from %d=%s to %d=%s\n"), |
|
19838 this, |
|
19839 (m_is_client == true ? "client": "server"), |
|
19840 m_selected_cipher_suite, |
|
19841 eap_tls_trace_string_c::get_cipher_suite_string(m_selected_cipher_suite), |
|
19842 cipher_suite, |
|
19843 eap_tls_trace_string_c::get_cipher_suite_string(cipher_suite))); |
|
19844 |
|
19845 m_selected_cipher_suite = cipher_suite; |
|
19846 } |
|
19847 |
|
19848 //-------------------------------------------------- |
|
19849 |
|
19850 EAP_FUNC_EXPORT eap_status_e tls_record_c::set_receive_cipher_suite(const tls_cipher_suites_e cipher_suite) |
|
19851 { |
|
19852 EAP_TRACE_DEBUG( |
|
19853 m_am_tools, |
|
19854 TRACE_FLAGS_DEFAULT, |
|
19855 (EAPL("TLS: this = 0x%08x, %s: suite_function: starts: tls_record_c::set_receive_cipher_suite(): Changes from %d=%s to %d=%s\n"), |
|
19856 this, |
|
19857 (m_is_client == true ? "client": "server"), |
|
19858 m_receive_cipher_suite, |
|
19859 eap_tls_trace_string_c::get_cipher_suite_string(m_receive_cipher_suite), |
|
19860 cipher_suite, |
|
19861 eap_tls_trace_string_c::get_cipher_suite_string(cipher_suite))); |
|
19862 |
|
19863 m_receive_cipher_suite = cipher_suite; |
|
19864 |
|
19865 m_receive_record_sequence_number = 0ul; |
|
19866 |
|
19867 |
|
19868 EAP_TRACE_DATA_DEBUG( |
|
19869 m_am_tools, |
|
19870 TRACE_FLAGS_DEFAULT, |
|
19871 (EAPL("set_receive_cipher_suite(): m_receive_encryption_key"), |
|
19872 m_receive_encryption_key.get_data(), |
|
19873 m_receive_encryption_key.get_data_length())); |
|
19874 |
|
19875 EAP_TRACE_DATA_DEBUG( |
|
19876 m_am_tools, |
|
19877 TRACE_FLAGS_DEFAULT, |
|
19878 (EAPL("set_receive_cipher_suite(): m_new_receive_encryption_key"), |
|
19879 m_new_receive_encryption_key.get_data(), |
|
19880 m_new_receive_encryption_key.get_data_length())); |
|
19881 |
|
19882 EAP_TRACE_DATA_DEBUG( |
|
19883 m_am_tools, |
|
19884 TRACE_FLAGS_DEFAULT, |
|
19885 (EAPL("set_receive_cipher_suite(): m_receive_mac_key"), |
|
19886 m_receive_mac_key.get_data(), |
|
19887 m_receive_mac_key.get_data_length())); |
|
19888 |
|
19889 EAP_TRACE_DATA_DEBUG( |
|
19890 m_am_tools, |
|
19891 TRACE_FLAGS_DEFAULT, |
|
19892 (EAPL("set_receive_cipher_suite(): m_new_receive_mac_key"), |
|
19893 m_new_receive_mac_key.get_data(), |
|
19894 m_new_receive_mac_key.get_data_length())); |
|
19895 |
|
19896 EAP_TRACE_DATA_DEBUG( |
|
19897 m_am_tools, |
|
19898 TRACE_FLAGS_DEFAULT, |
|
19899 (EAPL("set_receive_cipher_suite(): m_receive_iv"), |
|
19900 m_receive_iv.get_data(), |
|
19901 m_receive_iv.get_data_length())); |
|
19902 |
|
19903 EAP_TRACE_DATA_DEBUG( |
|
19904 m_am_tools, |
|
19905 TRACE_FLAGS_DEFAULT, |
|
19906 (EAPL("set_receive_cipher_suite(): m_new_receive_iv"), |
|
19907 m_new_receive_iv.get_data(), |
|
19908 m_new_receive_iv.get_data_length())); |
|
19909 |
|
19910 |
|
19911 eap_status_e status = m_receive_mac_key.set_copy_of_buffer(&m_new_receive_mac_key); |
|
19912 if (status != eap_status_ok) |
|
19913 { |
|
19914 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19915 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19916 } |
|
19917 |
|
19918 status = m_receive_encryption_key.set_copy_of_buffer(&m_new_receive_encryption_key); |
|
19919 if (status != eap_status_ok) |
|
19920 { |
|
19921 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19922 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19923 } |
|
19924 |
|
19925 status = m_receive_iv.set_copy_of_buffer(&m_new_receive_iv); |
|
19926 if (status != eap_status_ok) |
|
19927 { |
|
19928 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19929 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19930 } |
|
19931 |
|
19932 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
19933 return EAP_STATUS_RETURN(m_am_tools, status); |
|
19934 } |
|
19935 |
|
19936 //-------------------------------------------------- |
|
19937 |
|
19938 EAP_FUNC_EXPORT eap_status_e tls_record_c::set_send_cipher_suite(const tls_cipher_suites_e cipher_suite) |
|
19939 { |
|
19940 EAP_TRACE_DEBUG( |
|
19941 m_am_tools, |
|
19942 TRACE_FLAGS_DEFAULT, |
|
19943 (EAPL("TLS: this = 0x%08x, %s: suite_function: starts: tls_record_c::set_send_cipher_suite(): Changes from %d=%s to %d=%s\n"), |
|
19944 this, |
|
19945 (m_is_client == true ? "client": "server"), |
|
19946 m_send_cipher_suite, |
|
19947 eap_tls_trace_string_c::get_cipher_suite_string(m_send_cipher_suite), |
|
19948 cipher_suite, |
|
19949 eap_tls_trace_string_c::get_cipher_suite_string(cipher_suite))); |
|
19950 |
|
19951 m_send_cipher_suite = cipher_suite; |
|
19952 |
|
19953 m_send_record_sequence_number = 0ul; |
|
19954 |
|
19955 |
|
19956 EAP_TRACE_DATA_DEBUG( |
|
19957 m_am_tools, |
|
19958 TRACE_FLAGS_DEFAULT, |
|
19959 (EAPL("set_send_cipher_suite(): m_send_encryption_key"), |
|
19960 m_send_encryption_key.get_data(), |
|
19961 m_send_encryption_key.get_data_length())); |
|
19962 |
|
19963 EAP_TRACE_DATA_DEBUG( |
|
19964 m_am_tools, |
|
19965 TRACE_FLAGS_DEFAULT, |
|
19966 (EAPL("set_send_cipher_suite(): m_new_send_encryption_key"), |
|
19967 m_new_send_encryption_key.get_data(), |
|
19968 m_new_send_encryption_key.get_data_length())); |
|
19969 |
|
19970 EAP_TRACE_DATA_DEBUG( |
|
19971 m_am_tools, |
|
19972 TRACE_FLAGS_DEFAULT, |
|
19973 (EAPL("set_send_cipher_suite(): m_send_mac_key"), |
|
19974 m_send_mac_key.get_data(), |
|
19975 m_send_mac_key.get_data_length())); |
|
19976 |
|
19977 EAP_TRACE_DATA_DEBUG( |
|
19978 m_am_tools, |
|
19979 TRACE_FLAGS_DEFAULT, |
|
19980 (EAPL("set_send_cipher_suite(): m_new_send_mac_key"), |
|
19981 m_new_send_mac_key.get_data(), |
|
19982 m_new_send_mac_key.get_data_length())); |
|
19983 |
|
19984 EAP_TRACE_DATA_DEBUG( |
|
19985 m_am_tools, |
|
19986 TRACE_FLAGS_DEFAULT, |
|
19987 (EAPL("set_send_cipher_suite(): m_send_iv"), |
|
19988 m_send_iv.get_data(), |
|
19989 m_send_iv.get_data_length())); |
|
19990 |
|
19991 EAP_TRACE_DATA_DEBUG( |
|
19992 m_am_tools, |
|
19993 TRACE_FLAGS_DEFAULT, |
|
19994 (EAPL("set_send_cipher_suite(): m_new_send_iv"), |
|
19995 m_new_send_iv.get_data(), |
|
19996 m_new_send_iv.get_data_length())); |
|
19997 |
|
19998 |
|
19999 eap_status_e status = m_send_mac_key.set_copy_of_buffer(&m_new_send_mac_key); |
|
20000 if (status != eap_status_ok) |
|
20001 { |
|
20002 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
20003 return EAP_STATUS_RETURN(m_am_tools, status); |
|
20004 } |
|
20005 |
|
20006 status = m_send_encryption_key.set_copy_of_buffer(&m_new_send_encryption_key); |
|
20007 if (status != eap_status_ok) |
|
20008 { |
|
20009 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
20010 return EAP_STATUS_RETURN(m_am_tools, status); |
|
20011 } |
|
20012 |
|
20013 status = m_send_iv.set_copy_of_buffer(&m_new_send_iv); |
|
20014 if (status != eap_status_ok) |
|
20015 { |
|
20016 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
20017 return EAP_STATUS_RETURN(m_am_tools, status); |
|
20018 } |
|
20019 |
|
20020 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
20021 return EAP_STATUS_RETURN(m_am_tools, status); |
|
20022 } |
|
20023 |
|
20024 //-------------------------------------------------- |
|
20025 |
|
20026 EAP_FUNC_EXPORT eap_status_e tls_record_c::read_authority_identity(eap_variable_data_c * const authority_identity_payload) |
|
20027 { |
|
20028 return m_application->read_authority_identity(authority_identity_payload); |
|
20029 } |
|
20030 |
|
20031 //-------------------------------------------------- |
|
20032 |
|
20033 #if defined(USE_FAST_EAP_TYPE) |
|
20034 |
|
20035 EAP_FUNC_EXPORT eap_status_e tls_record_c::complete_query_tunnel_PAC( |
|
20036 const eap_status_e in_completion_status, |
|
20037 const eap_fast_pac_type_e in_pac_type, |
|
20038 const eap_fast_variable_data_c * const in_tunnel_PAC_key_tlv, |
|
20039 const eap_fast_variable_data_c * const in_tunnel_PAC_opaque_tlv) |
|
20040 { |
|
20041 EAP_TRACE_BEGIN(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
20042 |
|
20043 EAP_TRACE_DEBUG( |
|
20044 m_am_tools, |
|
20045 TRACE_FLAGS_DEFAULT, |
|
20046 (EAPL("TLS: this = 0x%08x, %s: message_function: starts: tls_record_c::complete_query_tunnel_PAC(): m_tls_session_type=%d=%s\n"), |
|
20047 this, |
|
20048 (m_is_client == true ? "client": "server"), |
|
20049 m_tls_session_type, |
|
20050 eap_tls_trace_string_c::get_tls_session_type_string(m_tls_session_type))); |
|
20051 |
|
20052 EAP_TRACE_RETURN_STRING(m_am_tools, "returns: tls_record_c::complete_query_tunnel_PAC()"); |
|
20053 |
|
20054 eap_status_e status(eap_status_process_general_error); |
|
20055 |
|
20056 m_pending_query_tunnel_PAC = false; |
|
20057 |
|
20058 if (in_completion_status == eap_status_ok) |
|
20059 { |
|
20060 tls_extension_c extension(m_am_tools); |
|
20061 if (extension.get_is_valid() == false) |
|
20062 { |
|
20063 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
20064 return EAP_STATUS_RETURN(m_am_tools, eap_status_allocation_error); |
|
20065 } |
|
20066 |
|
20067 if (in_tunnel_PAC_opaque_tlv != 0 |
|
20068 && in_tunnel_PAC_opaque_tlv->get_is_valid_data() == true) |
|
20069 { |
|
20070 status = extension.set_copy_of_buffer(in_tunnel_PAC_opaque_tlv->get_full_tlv_buffer()); |
|
20071 if (status != eap_status_ok) |
|
20072 { |
|
20073 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
20074 return EAP_STATUS_RETURN(m_am_tools, status); |
|
20075 } |
|
20076 |
|
20077 extension.set_type(tls_extension_type_session_ticket); |
|
20078 extension.set_pac_type(in_pac_type); |
|
20079 |
|
20080 status = m_supported_tls_extensions.add_object(extension.copy(), true); |
|
20081 if (status != eap_status_ok) |
|
20082 { |
|
20083 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
20084 return EAP_STATUS_RETURN(m_am_tools, status); |
|
20085 } |
|
20086 } |
|
20087 |
|
20088 if (in_tunnel_PAC_key_tlv != 0 |
|
20089 && in_tunnel_PAC_key_tlv->get_is_valid_data() == true) |
|
20090 { |
|
20091 status = m_eap_fast_pac_key.set_copy_of_buffer( |
|
20092 in_tunnel_PAC_key_tlv->get_data(in_tunnel_PAC_key_tlv->get_data_length()), |
|
20093 in_tunnel_PAC_key_tlv->get_data_length()); |
|
20094 if (status != eap_status_ok) |
|
20095 { |
|
20096 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
20097 return EAP_STATUS_RETURN(m_am_tools, status); |
|
20098 } |
|
20099 } |
|
20100 |
|
20101 set_tls_session_type(tls_session_type_eap_fast_pac_session_resumption); |
|
20102 |
|
20103 if (m_application != 0) |
|
20104 { |
|
20105 m_application->set_tunneled_state(get_tls_session_type()); |
|
20106 } |
|
20107 } |
|
20108 |
|
20109 status = check_sent_tls_message(); |
|
20110 |
|
20111 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
20112 return EAP_STATUS_RETURN(m_am_tools, eap_status_completed_request); |
|
20113 } |
|
20114 |
|
20115 #endif //#if defined(USE_FAST_EAP_TYPE) |
|
20116 |
|
20117 //-------------------------------------------------- |
|
20118 |
|
20119 |
|
20120 EAP_FUNC_EXPORT eap_status_e tls_record_c::query_ttls_pap_username_and_password( |
|
20121 const eap_variable_data_c * const reply_message) |
|
20122 { |
|
20123 eap_status_e status(eap_status_process_general_error); |
|
20124 |
|
20125 status = m_am_tls_services->query_ttls_pap_username_and_password(reply_message); |
|
20126 |
|
20127 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
20128 return EAP_STATUS_RETURN(m_am_tools, status); |
|
20129 } |
|
20130 |
|
20131 |
|
20132 //-------------------------------------------------- |
|
20133 |
|
20134 |
|
20135 EAP_FUNC_EXPORT eap_status_e tls_record_c::complete_query_ttls_pap_username_and_password( |
|
20136 const eap_variable_data_c * const ttls_pap_username, |
|
20137 const eap_variable_data_c * const ttls_pap_password, |
|
20138 const eap_status_e query_result) |
|
20139 { |
|
20140 eap_status_e status(eap_status_process_general_error); |
|
20141 |
|
20142 status = m_application->complete_query_ttls_pap_username_and_password( |
|
20143 ttls_pap_username, |
|
20144 ttls_pap_password, |
|
20145 query_result); |
|
20146 |
|
20147 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
20148 return EAP_STATUS_RETURN(m_am_tools, status); |
|
20149 } |
|
20150 |
|
20151 |
|
20152 //-------------------------------------------------- |
|
20153 |
|
20154 |
|
20155 EAP_FUNC_EXPORT eap_status_e tls_record_c::verify_ttls_pap_username_and_password( |
|
20156 const eap_variable_data_c * const user_name, |
|
20157 const eap_variable_data_c * const user_password) |
|
20158 { |
|
20159 eap_status_e status(eap_status_process_general_error); |
|
20160 |
|
20161 status = m_am_tls_services->verify_ttls_pap_username_and_password( |
|
20162 user_name, |
|
20163 user_password); |
|
20164 |
|
20165 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
20166 return EAP_STATUS_RETURN(m_am_tools, status); |
|
20167 } |
|
20168 |
|
20169 |
|
20170 //-------------------------------------------------- |
|
20171 |
|
20172 |
|
20173 EAP_FUNC_EXPORT eap_status_e tls_record_c::complete_verify_ttls_pap_username_and_password( |
|
20174 const eap_status_e authentication_result, |
|
20175 const eap_variable_data_c * const ttls_pap_reply_message) |
|
20176 { |
|
20177 eap_status_e status(eap_status_process_general_error); |
|
20178 |
|
20179 status = m_application->complete_verify_ttls_pap_username_and_password( |
|
20180 authentication_result, |
|
20181 ttls_pap_reply_message); |
|
20182 |
|
20183 EAP_TRACE_END(m_am_tools, TRACE_FLAGS_DEFAULT); |
|
20184 return EAP_STATUS_RETURN(m_am_tools, status); |
|
20185 } |
|
20186 |
|
20187 |
|
20188 //-------------------------------------------------- |
|
20189 |
|
20190 // End. |