summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorWenhui Xie <[email protected]>2023-12-22 15:11:20 +0800
committerGitHub <[email protected]>2023-12-22 15:11:20 +0800
commit3a144c22015cebfbb4449692f24bcee3120ed3bb (patch)
tree98d1d8b11ec3396d383d123794db920fc281670d
parent162e03f1a89b5d4d8679f85418ade056fb7815c4 (diff)
Add secure interoperability test. (#222)
-rw-r--r--.github/workflows/regression_test.yml20
-rwxr-xr-xscripts/build_secure_interoperability.sh3
-rwxr-xr-xscripts/install_secure.sh27
-rwxr-xr-xscripts/test_secure_interoperability.sh3
-rw-r--r--test/cmake/nx_secure_interoperability/CMakeLists.txt28
l---------test/cmake/nx_secure_interoperability/coverage.sh1
l---------test/cmake/nx_secure_interoperability/libs1
-rw-r--r--test/cmake/nx_secure_interoperability/regression/CMakeLists.txt393
-rw-r--r--test/cmake/nx_secure_interoperability/regression/network_config.cmake55
-rwxr-xr-xtest/cmake/nx_secure_interoperability/run.sh8
-rw-r--r--test/regression/interoperability_test/certificates/test.crt34
-rw-r--r--test/regression/interoperability_test/certificates/test.der.c99
-rw-r--r--test/regression/interoperability_test/certificates/test_client.crt33
-rw-r--r--test/regression/interoperability_test/certificates/test_client.der.c96
-rw-r--r--test/regression/interoperability_test/certificates/test_client.key28
-rw-r--r--test/regression/interoperability_test/certificates/test_client.key.der.c78
-rw-r--r--test/regression/interoperability_test/certificates/test_server.crt34
-rw-r--r--test/regression/interoperability_test/certificates/test_server.der.c98
-rw-r--r--test/regression/interoperability_test/certificates/test_server.key28
-rw-r--r--test/regression/interoperability_test/certificates/test_server.key.der.c78
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECCA.crt19
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECCA.key15
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECCA2.crt11
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECCA2.key8
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECCA3.crt14
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECCA3.key10
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECCA4.crlbin0 -> 272 bytes
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECCA4.crt12
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECCA4.key9
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECIntm.crlbin0 -> 246 bytes
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECIntm.crt54
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECIntm.key8
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECRevoked.crt55
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECRevoked.key8
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECRevoked2.crt51
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECRevoked2.key8
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTest.crt15
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTest.key5
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTestClient1.crt89
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTestClient1.key8
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTestServer10.crt52
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTestServer10.key8
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTestServer2.crt52
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTestServer2.key8
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTestServer3.crt63
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTestServer3.key10
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTestServer4.crt57
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTestServer4.key9
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTestServer6.crt71
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTestServer6.key27
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTestServer7_256.crt55
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTestServer7_256.key8
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTestServer8_224.crt51
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTestServer8_224.key8
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTestServer9_192.crt51
-rw-r--r--test/regression/interoperability_test/ecc_certificates/ECTestServer9_192.key8
-rw-r--r--test/regression/interoperability_test/nx_pcap_network_driver.c634
-rw-r--r--test/regression/interoperability_test/nx_secure_test/cert.c68
-rw-r--r--test/regression/interoperability_test/nx_secure_test/cert.pem24
-rw-r--r--test/regression/interoperability_test/nx_secure_test/demo_background_test_process_test.c83
-rw-r--r--test/regression/interoperability_test/nx_secure_test/demo_dtls_test.c97
-rw-r--r--test/regression/interoperability_test/nx_secure_test/demo_dtls_test_server.c224
-rw-r--r--test/regression/interoperability_test/nx_secure_test/demo_ping_test.c194
-rw-r--r--test/regression/interoperability_test/nx_secure_test/demo_semaphore_test.c117
-rw-r--r--test/regression/interoperability_test/nx_secure_test/demo_shared_buffer_test.c105
-rw-r--r--test/regression/interoperability_test/nx_secure_test/demo_timeout_test.c53
-rw-r--r--test/regression/interoperability_test/nx_secure_test/demo_tls_test.c97
-rw-r--r--test/regression/interoperability_test/nx_secure_test/demo_tls_test_icmp_server.c87
-rw-r--r--test/regression/interoperability_test/nx_secure_test/demo_tls_test_server.c233
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_aes128_gcm_nx_secure_client_entry.c236
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_client_certificate_verify_test_client_entry.c228
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_client_certificate_verify_test_server_entry.c224
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_ecc_test_client_entry.c231
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_ecc_test_server_entry.c234
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_server_entry.c301
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_openssl_client_certificate_verify_test_client_entry.c43
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_openssl_client_certificate_verify_test_server_entry.c38
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_openssl_ecc_test_client_entry.c40
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_openssl_ecc_test_server_entry.c38
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_openssl_echo_server_entry.c33
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_openssl_server_entry.c31
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_reuse_nx_secure_server_entry.c218
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_reuse_openssl_client_entry.c43
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_rsa_aes128_gcm_openssl_client_entry.c35
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_rsa_aes128_sha_openssl_client_entry.c35
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_rsa_aes256_sha_openssl_client_entry.c35
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_two_instance_test.c73
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_version_1_0_nx_secure_client_entry.c298
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_version_1_0_openssl_client_entry.c40
-rw-r--r--test/regression/interoperability_test/nx_secure_test/dtls_version_1_0_openssl_server_entry.c31
-rw-r--r--test/regression/interoperability_test/nx_secure_test/ecc_tls_1_2_openssl_client_cert_test_server_entry.c53
-rw-r--r--test/regression/interoperability_test/nx_secure_test/ecc_tls_1_2_openssl_curves_test_server_entry.c150
-rw-r--r--test/regression/interoperability_test/nx_secure_test/ecc_tls_1_2_openssl_echo_server_entry.c193
-rw-r--r--test/regression/interoperability_test/nx_secure_test/ica_test_device_cert.c191
-rw-r--r--test/regression/interoperability_test/nx_secure_test/ica_test_ica_cert.c86
-rw-r--r--test/regression/interoperability_test/nx_secure_test/key.pem28
-rw-r--r--test/regression/interoperability_test/nx_secure_test/nx_secure_1_0_1_1_echo_client_entry.c283
-rw-r--r--test/regression/interoperability_test/nx_secure_test/nx_secure_1_0_1_1_echo_server_entry.c271
-rw-r--r--test/regression/interoperability_test/nx_secure_test/nx_secure_client_certificate_verify_test_client_entry.c226
-rw-r--r--test/regression/interoperability_test/nx_secure_test/nx_secure_client_certificate_verify_test_server_entry.c199
-rw-r--r--test/regression/interoperability_test/nx_secure_test/nx_secure_dtls_echo_client_entry.c213
-rw-r--r--test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_1_0_1_1_server_entry.c493
-rw-r--r--test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_client_cert_test_client_entry.c273
-rw-r--r--test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_curves_test_client_entry.c442
-rw-r--r--test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_echo_client_entry.c595
-rw-r--r--test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_echo_server_entry.c215
-rw-r--r--test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_server_cert_entry.c231
-rw-r--r--test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_server_ciphersuites_entry.c391
-rw-r--r--test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_server_curves_entry.c355
-rw-r--r--test/regression/interoperability_test/nx_secure_test/nx_secure_echo_client_aes128_gcm_entry.c242
-rw-r--r--test/regression/interoperability_test/nx_secure_test/nx_secure_echo_client_entry.c221
-rw-r--r--test/regression/interoperability_test/nx_secure_test/nx_secure_echo_server_entry.c209
-rw-r--r--test/regression/interoperability_test/nx_secure_test/nx_secure_override_tls_1_1_echo_client_entry.c285
-rw-r--r--test/regression/interoperability_test/nx_secure_test/openssl_client_certificate_verify_test_client_entry.c42
-rw-r--r--test/regression/interoperability_test/nx_secure_test/openssl_client_certificate_verify_test_server_entry.c42
-rw-r--r--test/regression/interoperability_test/nx_secure_test/openssl_echo_server_nx_secure_echo_client_long_time_test.c75
-rw-r--r--test/regression/interoperability_test/nx_secure_test/openssl_echo_server_nx_secure_echo_client_test.c75
-rw-r--r--test/regression/interoperability_test/nx_secure_test/rsa_aes128_gcm_openssl_echo_client_entry.c35
-rw-r--r--test/regression/interoperability_test/nx_secure_test/rsa_aes128_sha_openssl_echo_client_entry.c35
-rw-r--r--test/regression/interoperability_test/nx_secure_test/rsa_aes256_sha_openssl_echo_client_entry.c35
-rw-r--r--test/regression/interoperability_test/nx_secure_test/signature_algorithm_test_nx_secure_echo_client_entry.c376
-rw-r--r--test/regression/interoperability_test/nx_secure_test/signature_algorithm_test_nx_secure_echo_server_entry.c305
-rw-r--r--test/regression/interoperability_test/nx_secure_test/signature_algorithm_test_openssl_echo_client_entry.c82
-rw-r--r--test/regression/interoperability_test/nx_secure_test/signature_algorithm_test_openssl_echo_server_entry.c107
-rw-r--r--test/regression/interoperability_test/nx_secure_test/test.der.c99
-rw-r--r--test/regression/interoperability_test/nx_secure_test/test_client.der.c96
-rw-r--r--test/regression/interoperability_test/nx_secure_test/test_client.key.der.c78
-rw-r--r--test/regression/interoperability_test/nx_secure_test/test_device_cert.c188
-rwxr-xr-xtest/regression/interoperability_test/nx_secure_test/test_scripts/demo_openssl_client.sh8
-rwxr-xr-xtest/regression/interoperability_test/nx_secure_test/test_scripts/openssl_1_1_echo_client.sh12
-rwxr-xr-xtest/regression/interoperability_test/nx_secure_test/test_scripts/openssl_1_1_echo_server.sh12
-rwxr-xr-xtest/regression/interoperability_test/nx_secure_test/test_scripts/openssl_echo_client.sh12
-rwxr-xr-xtest/regression/interoperability_test/nx_secure_test/test_scripts/openssl_echo_server.sh12
-rwxr-xr-xtest/regression/interoperability_test/nx_secure_test/test_scripts/sleep.sh5
-rwxr-xr-xtest/regression/interoperability_test/nx_secure_test/test_scripts/sleep_5_secs_then_echo_hello.sh4
-rwxr-xr-xtest/regression/interoperability_test/nx_secure_test/test_scripts/tcp_test.py7
-rwxr-xr-xtest/regression/interoperability_test/nx_secure_test/test_scripts/test.sh6
-rw-r--r--test/regression/interoperability_test/nx_secure_test/test_server.der.c98
-rw-r--r--test/regression/interoperability_test/nx_secure_test/test_server.key.der.c78
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_0_1_1_ecc_server_test.c210
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_0_openssl_echo_client_entry.c35
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_0_openssl_echo_server_entry.c33
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_1_openssl_echo_client_entry.c35
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_1_openssl_echo_server_entry.c33
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_2_openssl_echo_client_entry.c35
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_2_openssl_echo_server_entry.c33
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_3_alert_test_nx_secure_echo_server_entry.c269
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_3_alert_test_openssl_echo_client_entry.c38
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_3_client_certificate_verify_test_nx_secure_echo_client_entry.c250
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_3_client_certificate_verify_test_nx_secure_echo_server_entry.c242
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_3_client_certificate_verify_test_openssl_echo_client_entry.c47
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_3_client_certificate_verify_test_openssl_echo_server_entry.c41
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_3_client_session_reuse_test_nx_secure_echo_client_entry.c256
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_3_client_session_reuse_test_openssl_echo_server_entry.c38
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_3_hello_retry_cookie_test_nx_secure_echo_client_entry.c249
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_3_hello_retry_cookie_test_openssl_echo_server_entry.c43
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_3_hello_retry_request_test_openssl_echo_server_entry.c42
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_3_nx_secure_echo_client_entry.c241
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_3_openssl_echo_server_entry.c44
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_hello_retry_test_openssl_echo_client_entry.c38
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_test_nx_secure_echo_client_entry.c248
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_test_nx_secure_echo_server_entry.c215
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_test_openssl_echo_client_entry.c38
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_test_openssl_echo_server_entry.c39
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_ecc_negotiation_test.c73
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_ecc_server_cert_test.c103
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_ecc_server_ciphersuites_test.c213
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_ecc_server_curves_test.c213
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_negotiation_test.c73
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_openssl_1_1_echo_client_entry.c41
-rw-r--r--test/regression/interoperability_test/nx_secure_test/tls_openssl_1_1_prime256v1_echo_client_entry.c41
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_director_clean_all.c16
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_director_cleanup_registered_instances.c24
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_director_create.c27
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_director_destroy.c9
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_director_register_test_instance.c51
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_director_test_start.c169
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_frame.h227
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_get_external_test_process_output.c64
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_instance_append.c16
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_instance_attributes_access.c45
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_instance_create.c50
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_instance_destroy.c12
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_instance_find_next.c11
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_instance_set_exit_status.c33
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_instance_shared_buffer_manipulate.c80
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_kill_external_test_process.c14
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_launch_external_test_process.c42
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_launch_external_test_process_in_background.c29
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_semaphore_create.c20
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_semaphore_destroy.c9
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_semaphore_post.c8
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_semaphore_wait.c14
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_uninterruptable_wait.c18
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_wait_all_child_process.c12
-rw-r--r--test/regression/interoperability_test/test_frame/tls_test_wait_external_test_process.c24
196 files changed, 18923 insertions, 2 deletions
diff --git a/.github/workflows/regression_test.yml b/.github/workflows/regression_test.yml
index 3745bb9f..e694f838 100644
--- a/.github/workflows/regression_test.yml
+++ b/.github/workflows/regression_test.yml
@@ -158,6 +158,22 @@ jobs:
cmake_path: ./test/cmake/crypto
result_affix: Crypto
skip_deploy: true
+ Secure_Interoperability:
+ permissions:
+ contents: read
+ issues: read
+ checks: write
+ pull-requests: write
+ pages: write
+ id-token: write
+ uses: azure-rtos/threadx/.github/workflows/regression_template.yml@master
+ with:
+ install_script: ./scripts/install_secure.sh
+ build_script: ./scripts/build_secure_interoperability.sh
+ test_script: ./scripts/test_secure_interoperability.sh
+ cmake_path: ./test/cmake/nx_secure_interoperability
+ result_affix: Secure_Interoperability
+ skip_deploy: true
Deploy:
permissions:
contents: read
@@ -166,8 +182,8 @@ jobs:
pull-requests: write
pages: write
id-token: write
- needs: [NetXDuo, Web, MQTT, NetXDuo64, NetXDuo_Fast, Azure_IoT, Secure, Crypto]
+ needs: [NetXDuo, Web, MQTT, NetXDuo64, NetXDuo_Fast, Azure_IoT, Secure, Crypto, Secure_Interoperability]
uses: azure-rtos/threadx/.github/workflows/regression_template.yml@master
with:
skip_test: true
- deploy_list: "NetXDuo Web MQTT NetXDuo64 NetXDuo_Fast Azure_IoT Secure Crypto" \ No newline at end of file
+ deploy_list: "NetXDuo Web MQTT NetXDuo64 NetXDuo_Fast Azure_IoT Secure Crypto Secure_Interoperability" \ No newline at end of file
diff --git a/scripts/build_secure_interoperability.sh b/scripts/build_secure_interoperability.sh
new file mode 100755
index 00000000..a1ada03b
--- /dev/null
+++ b/scripts/build_secure_interoperability.sh
@@ -0,0 +1,3 @@
+#! /bin/bash
+
+$(dirname `realpath $0`)/../test/cmake/nx_secure_interoperability/run.sh build all
diff --git a/scripts/install_secure.sh b/scripts/install_secure.sh
new file mode 100755
index 00000000..9b1c5074
--- /dev/null
+++ b/scripts/install_secure.sh
@@ -0,0 +1,27 @@
+#! /bin/bash
+
+sudo dpkg --add-architecture i386
+
+sudo cp /usr/bin/openssl /usr/bin/openssl-1.1
+
+sudo apt update
+sudo apt install -y \
+ gcc-multilib \
+ g++ \
+ python3-pip \
+ ninja-build \
+ unifdef \
+ tofrodos \
+ gcovr \
+ libpcap-dev:i386 libgcc-s1:i386 \
+ ethtool
+
+wget https://www.openssl.org/source/old/1.0.2/openssl-1.0.2n.tar.gz
+tar -xzvf openssl-1.0.2n.tar.gz
+cd openssl-1.0.2n
+sudo ./config
+sudo make install
+
+sudo ln -sf /usr/local/ssl/bin/openssl /usr/bin/openssl
+
+openssl version -v
diff --git a/scripts/test_secure_interoperability.sh b/scripts/test_secure_interoperability.sh
new file mode 100755
index 00000000..6c2ff019
--- /dev/null
+++ b/scripts/test_secure_interoperability.sh
@@ -0,0 +1,3 @@
+#! /bin/bash
+
+sudo CTEST_PARALLEL_LEVEL=1 $(dirname `realpath $0`)/../test/cmake/nx_secure_interoperability/run.sh test all
diff --git a/test/cmake/nx_secure_interoperability/CMakeLists.txt b/test/cmake/nx_secure_interoperability/CMakeLists.txt
new file mode 100644
index 00000000..22582827
--- /dev/null
+++ b/test/cmake/nx_secure_interoperability/CMakeLists.txt
@@ -0,0 +1,28 @@
+cmake_minimum_required(VERSION 3.13 FATAL_ERROR)
+cmake_policy(SET CMP0054 NEW)
+cmake_policy(SET CMP0057 NEW)
+cmake_policy(SET CMP0077 NEW)
+
+project(nx_secure_test LANGUAGES C)
+include(${CMAKE_CURRENT_SOURCE_DIR}/../nx_secure/CMakeLists.txt)
+
+# Set build configurations
+set(BUILD_CONFIGURATIONS
+ default_build_coverage
+ psk_build_coverage
+ tls_1_0_enable_build
+ tls_1_1_enable_build
+ tls_1_3_enable_build_coverage
+ client_disable_build
+ server_disable_build
+ tls_1_3_client_disable_build
+ tls_1_3_server_disable_build
+ ecjpake_build
+ dtls_build_coverage
+ eal4_build_coverage
+ sesip_build_coverage
+ no_ecc_build_coverage
+ no_renegotiation_build
+ no_client_renegotiation_build
+ hash_clone_build
+ curve25519_448_build)
diff --git a/test/cmake/nx_secure_interoperability/coverage.sh b/test/cmake/nx_secure_interoperability/coverage.sh
new file mode 120000
index 00000000..6550c33f
--- /dev/null
+++ b/test/cmake/nx_secure_interoperability/coverage.sh
@@ -0,0 +1 @@
+../nx_secure/coverage.sh \ No newline at end of file
diff --git a/test/cmake/nx_secure_interoperability/libs b/test/cmake/nx_secure_interoperability/libs
new file mode 120000
index 00000000..ea95e534
--- /dev/null
+++ b/test/cmake/nx_secure_interoperability/libs
@@ -0,0 +1 @@
+../nx_secure/libs \ No newline at end of file
diff --git a/test/cmake/nx_secure_interoperability/regression/CMakeLists.txt b/test/cmake/nx_secure_interoperability/regression/CMakeLists.txt
new file mode 100644
index 00000000..a2d3008a
--- /dev/null
+++ b/test/cmake/nx_secure_interoperability/regression/CMakeLists.txt
@@ -0,0 +1,393 @@
+cmake_minimum_required(VERSION 3.0.0 FATAL_ERROR)
+cmake_policy(SET CMP0057 NEW)
+
+project(regression_test LANGUAGES C)
+
+get_filename_component(
+ SOURCE_DIR ${CMAKE_CURRENT_LIST_DIR}/../../../regression/interoperability_test/nx_secure_test
+ ABSOLUTE)
+
+list(APPEND nx_secure_test_cases demo_ping_test)
+set(demo_ping_test_file_list ${SOURCE_DIR}/demo_ping_test.c)
+
+list(APPEND nx_secure_test_cases demo_tls_test)
+set(demo_tls_test_file_list ${SOURCE_DIR}/demo_tls_test.c
+ ${SOURCE_DIR}/demo_tls_test_server.c)
+
+list(APPEND nx_secure_test_cases
+ tls_1_0_openssl_echo_server_nx_secure_echo_client_test)
+set(tls_1_0_openssl_echo_server_nx_secure_echo_client_test_file_list
+ ${SOURCE_DIR}/tls_1_0_openssl_echo_server_entry.c
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_test.c
+ ${SOURCE_DIR}/nx_secure_1_0_1_1_echo_client_entry.c)
+
+list(APPEND nx_secure_test_cases
+ tls_1_1_openssl_echo_server_nx_secure_echo_client_test)
+set(tls_1_1_openssl_echo_server_nx_secure_echo_client_test_file_list
+ ${SOURCE_DIR}/tls_1_1_openssl_echo_server_entry.c
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_test.c
+ ${SOURCE_DIR}/nx_secure_1_0_1_1_echo_client_entry.c)
+
+list(APPEND nx_secure_test_cases
+ tls_1_2_openssl_echo_server_nx_secure_echo_client_test)
+set(tls_1_2_openssl_echo_server_nx_secure_echo_client_test_file_list
+ ${SOURCE_DIR}/tls_1_2_openssl_echo_server_entry.c
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_test.c
+ ${SOURCE_DIR}/nx_secure_echo_client_entry.c)
+
+list(APPEND nx_secure_test_cases
+ override_tls_1_1_openssl_echo_server_nx_secure_echo_client_test)
+set(override_tls_1_1_openssl_echo_server_nx_secure_echo_client_test_file_list
+ ${SOURCE_DIR}/tls_1_1_openssl_echo_server_entry.c
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_long_time_test.c
+ ${SOURCE_DIR}/nx_secure_override_tls_1_1_echo_client_entry.c)
+
+list(APPEND nx_secure_test_cases tls_1_2_protocol_version_negotiation_test)
+set(tls_1_2_protocol_version_negotiation_test_file_list
+ ${SOURCE_DIR}/tls_negotiation_test.c
+ ${SOURCE_DIR}/nx_secure_echo_server_entry.c
+ ${SOURCE_DIR}/tls_1_2_openssl_echo_client_entry.c)
+
+list(APPEND nx_secure_test_cases openssl_1_1_protocol_version_negotiation_test)
+set(openssl_1_1_protocol_version_negotiation_test_file_list
+ ${SOURCE_DIR}/tls_ecc_negotiation_test.c
+ ${SOURCE_DIR}/nx_secure_ecc_echo_server_entry.c
+ ${SOURCE_DIR}/tls_openssl_1_1_prime256v1_echo_client_entry.c)
+
+list(APPEND nx_secure_test_cases tls_1_1_protocol_version_negotiation_test)
+set(tls_1_1_protocol_version_negotiation_test_file_list
+ ${SOURCE_DIR}/tls_negotiation_test.c
+ ${SOURCE_DIR}/nx_secure_1_0_1_1_echo_server_entry.c
+ ${SOURCE_DIR}/tls_1_1_openssl_echo_client_entry.c)
+
+list(APPEND nx_secure_test_cases tls_1_0_protocol_version_negotiation_test)
+set(tls_1_0_protocol_version_negotiation_test_file_list
+ ${SOURCE_DIR}/tls_negotiation_test.c
+ ${SOURCE_DIR}/nx_secure_echo_server_entry.c
+ ${SOURCE_DIR}/tls_1_0_openssl_echo_client_entry.c)
+
+list(APPEND nx_secure_test_cases tls_ecc_client_ciphersuites_test)
+set(tls_ecc_client_ciphersuites_test_file_list
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_long_time_test.c
+ ${SOURCE_DIR}/nx_secure_ecc_echo_client_entry.c
+ ${SOURCE_DIR}/ecc_tls_1_2_openssl_echo_server_entry.c)
+
+list(APPEND nx_secure_test_cases rsa_aes128_sha_ciphersuite_test)
+set(rsa_aes128_sha_ciphersuite_test_file_list
+ ${SOURCE_DIR}/tls_negotiation_test.c
+ ${SOURCE_DIR}/nx_secure_echo_server_entry.c
+ ${SOURCE_DIR}/rsa_aes128_sha_openssl_echo_client_entry.c)
+
+list(APPEND nx_secure_test_cases rsa_aes256_sha_ciphersuite_test)
+set(rsa_aes256_sha_ciphersuite_test_file_list
+ ${SOURCE_DIR}/tls_negotiation_test.c
+ ${SOURCE_DIR}/nx_secure_echo_server_entry.c
+ ${SOURCE_DIR}/rsa_aes256_sha_openssl_echo_client_entry.c)
+
+list(APPEND nx_secure_test_cases rsa_aes128_gcm_ciphersuite_test)
+set(rsa_aes128_gcm_ciphersuite_test_file_list
+ ${SOURCE_DIR}/tls_negotiation_test.c
+ ${SOURCE_DIR}/nx_secure_echo_server_entry.c
+ ${SOURCE_DIR}/rsa_aes128_gcm_openssl_echo_client_entry.c)
+
+list(APPEND nx_secure_test_cases rsa_aes128_gcm_ciphersuite_client_test)
+set(rsa_aes128_gcm_ciphersuite_client_test_file_list
+ ${SOURCE_DIR}/tls_1_2_openssl_echo_server_entry.c
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_test.c
+ ${SOURCE_DIR}/nx_secure_echo_client_aes128_gcm_entry.c)
+
+list(APPEND nx_secure_test_cases tls_ecc_server_basic_test)
+set(tls_ecc_server_basic_test_file_list
+ ${SOURCE_DIR}/tls_ecc_negotiation_test.c
+ ${SOURCE_DIR}/nx_secure_ecc_echo_server_entry.c
+ ${SOURCE_DIR}/tls_1_2_openssl_echo_client_entry.c)
+
+list(APPEND nx_secure_test_cases client_certificate_verify_server_test)
+set(client_certificate_verify_server_test_file_list
+ ${SOURCE_DIR}/tls_negotiation_test.c
+ ${SOURCE_DIR}/openssl_client_certificate_verify_test_client_entry.c
+ ${SOURCE_DIR}/nx_secure_client_certificate_verify_test_server_entry.c)
+
+list(APPEND nx_secure_test_cases client_certificate_verify_client_test)
+set(client_certificate_verify_client_test_file_list
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_test.c
+ ${SOURCE_DIR}/openssl_client_certificate_verify_test_server_entry.c
+ ${SOURCE_DIR}/nx_secure_client_certificate_verify_test_client_entry.c)
+
+list(APPEND nx_secure_test_cases tls_ecc_server_ciphersuites_test)
+set(tls_ecc_server_ciphersuites_test_file_list
+ ${SOURCE_DIR}/tls_ecc_server_ciphersuites_test.c
+ ${SOURCE_DIR}/nx_secure_ecc_server_ciphersuites_entry.c)
+
+list(APPEND nx_secure_test_cases tls_ecc_server_curves_test)
+set(tls_ecc_server_curves_test_file_list
+ ${SOURCE_DIR}/tls_ecc_server_curves_test.c
+ ${SOURCE_DIR}/nx_secure_ecc_server_curves_entry.c)
+
+list(APPEND nx_secure_test_cases tls_ecc_client_curves_test)
+set(tls_ecc_client_curves_test_file_list
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_long_time_test.c
+ ${SOURCE_DIR}/ecc_tls_1_2_openssl_curves_test_server_entry.c
+ ${SOURCE_DIR}/nx_secure_ecc_curves_test_client_entry.c)
+
+list(APPEND nx_secure_test_cases tls_ecc_server_cert_test)
+set(tls_ecc_server_cert_test_file_list
+ ${SOURCE_DIR}/tls_ecc_server_cert_test.c
+ ${SOURCE_DIR}/nx_secure_ecc_server_cert_entry.c)
+
+list(APPEND nx_secure_test_cases tls_ecc_client_cert_test)
+set(tls_ecc_client_cert_test_file_list
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_test.c
+ ${SOURCE_DIR}/ecc_tls_1_2_openssl_client_cert_test_server_entry.c
+ ${SOURCE_DIR}/nx_secure_ecc_client_cert_test_client_entry.c)
+
+list(APPEND nx_secure_test_cases tls_1_0_1_1_ecc_server_test)
+set(tls_1_0_1_1_ecc_server_test_file_list
+ ${SOURCE_DIR}/tls_1_0_1_1_ecc_server_test.c
+ ${SOURCE_DIR}/nx_secure_ecc_1_0_1_1_server_entry.c)
+
+if("-DNX_SECURE_ENABLE_DTLS" IN_LIST ${CMAKE_BUILD_TYPE})
+ list(APPEND nx_secure_test_cases demo_dtls_test)
+ set(demo_dtls_test_file_list ${SOURCE_DIR}/demo_dtls_test.c
+ ${SOURCE_DIR}/demo_dtls_test_server.c)
+
+ list(APPEND nx_secure_test_cases
+ dtls_openssl_echo_server_nx_secure_echo_client_test)
+ set(dtls_openssl_echo_server_nx_secure_echo_client_test_file_list
+ ${SOURCE_DIR}/dtls_openssl_echo_server_entry.c
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_test.c
+ ${SOURCE_DIR}/nx_secure_dtls_echo_client_entry.c)
+
+ list(APPEND nx_secure_test_cases
+ dtls_reuse_nx_secure_server_openssl_client_test)
+ set(dtls_reuse_nx_secure_server_openssl_client_test_file_list
+ ${SOURCE_DIR}/dtls_two_instance_test.c
+ ${SOURCE_DIR}/dtls_reuse_nx_secure_server_entry.c
+ ${SOURCE_DIR}/dtls_reuse_openssl_client_entry.c)
+
+ list(APPEND nx_secure_test_cases dtls_rsa_aes128_sha_ciphersuite_test)
+ set(dtls_rsa_aes128_sha_ciphersuite_test_file_list
+ ${SOURCE_DIR}/dtls_two_instance_test.c
+ ${SOURCE_DIR}/dtls_nx_secure_server_entry.c
+ ${SOURCE_DIR}/dtls_rsa_aes128_sha_openssl_client_entry.c)
+
+ list(APPEND nx_secure_test_cases dtls_rsa_aes256_sha_ciphersuite_test)
+ set(dtls_rsa_aes256_sha_ciphersuite_test_file_list
+ ${SOURCE_DIR}/dtls_two_instance_test.c
+ ${SOURCE_DIR}/dtls_nx_secure_server_entry.c
+ ${SOURCE_DIR}/dtls_rsa_aes256_sha_openssl_client_entry.c)
+
+ list(APPEND nx_secure_test_cases dtls_rsa_aes128_gcm_ciphersuite_test)
+ set(dtls_rsa_aes128_gcm_ciphersuite_test_file_list
+ ${SOURCE_DIR}/dtls_two_instance_test.c
+ ${SOURCE_DIR}/dtls_nx_secure_server_entry.c
+ ${SOURCE_DIR}/dtls_rsa_aes128_gcm_openssl_client_entry.c)
+
+ list(APPEND nx_secure_test_cases dtls_rsa_aes128_gcm_ciphersuite_client_test)
+ set(dtls_rsa_aes128_gcm_ciphersuite_client_test_file_list
+ ${SOURCE_DIR}/dtls_two_instance_test.c
+ ${SOURCE_DIR}/dtls_openssl_server_entry.c
+ ${SOURCE_DIR}/dtls_aes128_gcm_nx_secure_client_entry.c)
+
+ list(APPEND nx_secure_test_cases dtls_client_certificate_verify_client_test)
+ set(dtls_client_certificate_verify_client_test_file_list
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_test.c
+ ${SOURCE_DIR}/dtls_openssl_client_certificate_verify_test_server_entry.c
+ ${SOURCE_DIR}/dtls_nx_secure_client_certificate_verify_test_client_entry.c
+ )
+
+ list(APPEND nx_secure_test_cases dtls_client_certificate_verify_server_test)
+ set(dtls_client_certificate_verify_server_test_file_list
+ ${SOURCE_DIR}/dtls_two_instance_test.c
+ ${SOURCE_DIR}/dtls_openssl_client_certificate_verify_test_client_entry.c
+ ${SOURCE_DIR}/dtls_nx_secure_client_certificate_verify_test_server_entry.c
+ )
+
+ list(APPEND nx_secure_test_cases dtls_version_1_0_server_test)
+ set(dtls_version_1_0_server_test_file_list
+ ${SOURCE_DIR}/dtls_two_instance_test.c
+ ${SOURCE_DIR}/dtls_version_1_0_openssl_client_entry.c
+ ${SOURCE_DIR}/dtls_nx_secure_server_entry.c)
+
+ list(APPEND nx_secure_test_cases dtls_version_1_0_client_test)
+ set(dtls_version_1_0_client_test_file_list
+ ${SOURCE_DIR}/dtls_two_instance_test.c
+ ${SOURCE_DIR}/dtls_version_1_0_openssl_server_entry.c
+ ${SOURCE_DIR}/dtls_version_1_0_nx_secure_client_entry.c)
+
+ list(APPEND nx_secure_test_cases dtls_ecc_server_test)
+ set(dtls_ecc_server_test_file_list
+ ${SOURCE_DIR}/dtls_two_instance_test.c
+ ${SOURCE_DIR}/dtls_openssl_ecc_test_client_entry.c
+ ${SOURCE_DIR}/dtls_nx_secure_ecc_test_server_entry.c)
+
+ list(APPEND nx_secure_test_cases dtls_ecc_client_test)
+ set(dtls_ecc_client_test_file_list
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_test.c
+ ${SOURCE_DIR}/dtls_openssl_ecc_test_server_entry.c
+ ${SOURCE_DIR}/dtls_nx_secure_ecc_test_client_entry.c)
+endif()
+
+list(APPEND nx_secure_test_cases signature_algorithm_client_test)
+set(signature_algorithm_client_test_file_list
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_long_time_test.c
+ ${SOURCE_DIR}/signature_algorithm_test_openssl_echo_server_entry.c
+ ${SOURCE_DIR}/signature_algorithm_test_nx_secure_echo_client_entry.c)
+
+list(APPEND nx_secure_test_cases signature_algorithm_server_test)
+set(signature_algorithm_server_test_file_list
+ ${SOURCE_DIR}/tls_ecc_negotiation_test.c
+ ${SOURCE_DIR}/signature_algorithm_test_openssl_echo_client_entry.c
+ ${SOURCE_DIR}/signature_algorithm_test_nx_secure_echo_server_entry.c)
+
+if("-DNX_SECURE_TLS_ENABLE_TLS_1_3" IN_LIST ${CMAKE_BUILD_TYPE})
+ list(APPEND nx_secure_test_cases
+ tls_1_3_openssl_echo_server_nx_secure_echo_client_test)
+ set(tls_1_3_openssl_echo_server_nx_secure_echo_client_test_file_list
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_test.c
+ ${SOURCE_DIR}/tls_1_3_openssl_echo_server_entry.c
+ ${SOURCE_DIR}/tls_1_3_nx_secure_echo_client_entry.c)
+
+ list(APPEND nx_secure_test_cases
+ tls_1_3_client_certificate_verify_client_test)
+ set(tls_1_3_client_certificate_verify_client_test_file_list
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_test.c
+ ${SOURCE_DIR}/tls_1_3_client_certificate_verify_test_openssl_echo_server_entry.c
+ ${SOURCE_DIR}/tls_1_3_client_certificate_verify_test_nx_secure_echo_client_entry.c
+ )
+
+ list(APPEND nx_secure_test_cases
+ tls_1_3_client_certificate_verify_server_test)
+ set(tls_1_3_client_certificate_verify_server_test_file_list
+ ${SOURCE_DIR}/tls_negotiation_test.c
+ ${SOURCE_DIR}/tls_1_3_client_certificate_verify_test_openssl_echo_client_entry.c
+ ${SOURCE_DIR}/tls_1_3_client_certificate_verify_test_nx_secure_echo_server_entry.c
+ )
+
+ list(APPEND nx_secure_test_cases tls_1_3_client_session_reuse_test)
+ set(tls_1_3_client_session_reuse_test_file_list
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_test.c
+ ${SOURCE_DIR}/tls_1_3_client_session_reuse_test_openssl_echo_server_entry.c
+ ${SOURCE_DIR}/tls_1_3_client_session_reuse_test_nx_secure_echo_client_entry.c
+ )
+
+ list(APPEND nx_secure_test_cases tls_1_3_client_hello_retry_request_test)
+ set(tls_1_3_client_hello_retry_request_test_file_list
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_test.c
+ ${SOURCE_DIR}/tls_1_3_hello_retry_request_test_openssl_echo_server_entry.c
+ ${SOURCE_DIR}/tls_1_3_nx_secure_echo_client_entry.c)
+
+ list(APPEND nx_secure_test_cases tls_1_3_server_hello_retry_request_test)
+ set(tls_1_3_server_hello_retry_request_test_file_list
+ ${SOURCE_DIR}/tls_ecc_negotiation_test.c
+ ${SOURCE_DIR}/nx_secure_ecc_echo_server_entry.c
+ ${SOURCE_DIR}/tls_openssl_1_1_echo_client_entry.c)
+
+ list(APPEND nx_secure_test_cases tls_1_3_hello_retry_cookie_test)
+ set(tls_1_3_hello_retry_cookie_test_file_list
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_test.c
+ ${SOURCE_DIR}/tls_1_3_hello_retry_cookie_test_openssl_echo_server_entry.c
+ ${SOURCE_DIR}/tls_1_3_hello_retry_cookie_test_nx_secure_echo_client_entry.c
+ )
+
+ list(APPEND nx_secure_test_cases tls_1_3_alert_server_test)
+ set(tls_1_3_alert_server_test_file_list
+ ${SOURCE_DIR}/tls_ecc_negotiation_test.c
+ ${SOURCE_DIR}/tls_1_3_alert_test_openssl_echo_client_entry.c
+ ${SOURCE_DIR}/tls_1_3_alert_test_nx_secure_echo_server_entry.c)
+
+ list(APPEND nx_secure_test_cases tls_1_3_psk_client_test)
+ set(tls_1_3_psk_client_test_file_list
+ ${SOURCE_DIR}/openssl_echo_server_nx_secure_echo_client_test.c
+ ${SOURCE_DIR}/tls_1_3_psk_test_openssl_echo_server_entry.c
+ ${SOURCE_DIR}/tls_1_3_psk_test_nx_secure_echo_client_entry.c)
+
+ list(APPEND nx_secure_test_cases tls_1_3_psk_server_test)
+ set(tls_1_3_psk_server_test_file_list
+ ${SOURCE_DIR}/tls_ecc_negotiation_test.c
+ ${SOURCE_DIR}/tls_1_3_psk_test_openssl_echo_client_entry.c
+ ${SOURCE_DIR}/tls_1_3_psk_test_nx_secure_echo_server_entry.c)
+
+ list(APPEND nx_secure_test_cases tls_1_3_psk_hello_retry_server_test)
+ set(tls_1_3_psk_hello_retry_server_test_file_list
+ ${SOURCE_DIR}/tls_ecc_negotiation_test.c
+ ${SOURCE_DIR}/tls_1_3_psk_hello_retry_test_openssl_echo_client_entry.c
+ ${SOURCE_DIR}/tls_1_3_psk_test_nx_secure_echo_server_entry.c)
+endif()
+
+set(test_utility_files
+ ${SOURCE_DIR}/netxtestcontrol.c
+ ${SOURCE_DIR}/nx_crypto_ciphersuites_regression.c
+ ${SOURCE_DIR}/nx_ram_network_driver_test_1500.c
+ ${SOURCE_DIR}/nx_secure_fips_test_utility.c)
+
+get_filename_component(
+ UTILITY_SOURCE_DIR
+ ${CMAKE_CURRENT_LIST_DIR}/../../../regression/interoperability_test/test_frame
+ ABSOLUTE)
+set(test_utility_files
+ ${UTILITY_SOURCE_DIR}/tls_test_get_external_test_process_output.c
+ ${UTILITY_SOURCE_DIR}/tls_test_launch_external_test_process.c
+ ${UTILITY_SOURCE_DIR}/tls_test_launch_external_test_process_in_background.c
+ ${UTILITY_SOURCE_DIR}/tls_test_director_clean_all.c
+ ${UTILITY_SOURCE_DIR}/tls_test_director_cleanup_registered_instances.c
+ ${UTILITY_SOURCE_DIR}/tls_test_director_create.c
+ ${UTILITY_SOURCE_DIR}/tls_test_director_destroy.c
+ ${UTILITY_SOURCE_DIR}/tls_test_director_register_test_instance.c
+ ${UTILITY_SOURCE_DIR}/tls_test_director_test_start.c
+ ${UTILITY_SOURCE_DIR}/tls_test_instance_attributes_access.c
+ ${UTILITY_SOURCE_DIR}/tls_test_instance_append.c
+ ${UTILITY_SOURCE_DIR}/tls_test_instance_create.c
+ ${UTILITY_SOURCE_DIR}/tls_test_instance_destroy.c
+ ${UTILITY_SOURCE_DIR}/tls_test_instance_find_next.c
+ ${UTILITY_SOURCE_DIR}/tls_test_instance_set_exit_status.c
+ ${UTILITY_SOURCE_DIR}/tls_test_instance_shared_buffer_manipulate.c
+ ${UTILITY_SOURCE_DIR}/tls_test_kill_external_test_process.c
+ ${UTILITY_SOURCE_DIR}/tls_test_semaphore_create.c
+ ${UTILITY_SOURCE_DIR}/tls_test_semaphore_destroy.c
+ ${UTILITY_SOURCE_DIR}/tls_test_semaphore_post.c
+ ${UTILITY_SOURCE_DIR}/tls_test_semaphore_wait.c
+ ${UTILITY_SOURCE_DIR}/tls_test_wait_all_child_process.c
+ ${UTILITY_SOURCE_DIR}/tls_test_wait_external_test_process.c
+ ${UTILITY_SOURCE_DIR}/tls_test_uninterruptable_wait.c)
+
+if("s${CMAKE_BUILD_TYPE}" STREQUAL "shash_clone_build")
+list(APPEND test_utility_files
+ ${CMAKE_CURRENT_LIST_DIR}/../../../regression/nx_secure_test/hash_clone/nx_crypto_clone_cleanup_test.c
+ ${CMAKE_CURRENT_LIST_DIR}/../../../regression/nx_secure_test/hash_clone/nx_crypto_hash_clone_test.c
+ ${CMAKE_CURRENT_LIST_DIR}/../../../regression/nx_secure_test/hash_clone/nx_crypto_ciphersuites_hc.c)
+endif()
+
+add_library(test_utility ${test_utility_files})
+target_link_libraries(test_utility PUBLIC azrtos::netxduo)
+target_include_directories(test_utility PUBLIC ${UTILITY_SOURCE_DIR})
+target_compile_definitions(test_utility PUBLIC BATCH_TEST CTEST)
+
+include(network_config.cmake)
+
+set(PCAP_SOURCE
+ ${CMAKE_CURRENT_LIST_DIR}/../../../regression/interoperability_test/nx_pcap_network_driver.c
+)
+foreach(test_case ${nx_secure_test_cases})
+ add_executable(${test_case} ${${test_case}_file_list} ${PCAP_SOURCE})
+ network_config(${test_case})
+ target_link_libraries(${test_case} PRIVATE test_utility pcap)
+ add_test(
+ NAME ${CMAKE_BUILD_TYPE}::${test_case}
+ COMMAND
+ bash -c
+ "export PATH=${SOURCE_DIR}/test_scripts/:$PATH;
+ ip link del ${${test_case}_interface}>/dev/null 2>&1;
+ ip link add ${${test_case}_interface} type veth peer name ${${test_case}_remote_interface} || exit 1;
+ ifconfig ${${test_case}_interface} up || { ip link del ${${test_case}_interface}; exit 1; };
+ ifconfig ${${test_case}_remote_interface} ${${test_case}_remote_ip} up netmask ${TEST_NETMASK} || { ip link del ${${test_case}_interface};exit 1; };
+ ethtool --offload ${${test_case}_remote_interface} tx off || { ip link del ${${test_case}_interface}; exit 1; };
+ tcpdump -i ${${test_case}_remote_interface} -s 0 -w ${CMAKE_CURRENT_BINARY_DIR}/${test_case}.pcap&
+ pid=$!
+ ${CMAKE_CURRENT_BINARY_DIR}/${test_case};
+ exit_code=$?
+ sleep 1;
+ kill -TERM $pid
+ [[ $exit_code = 0 ]] || [[ $exit_code = 233 ]] || { echo Exit code: $exit_code; exit $exit_code; };"
+ WORKING_DIRECTORY ${SOURCE_DIR})
+endforeach()
diff --git a/test/cmake/nx_secure_interoperability/regression/network_config.cmake b/test/cmake/nx_secure_interoperability/regression/network_config.cmake
new file mode 100644
index 00000000..5f75b945
--- /dev/null
+++ b/test/cmake/nx_secure_interoperability/regression/network_config.cmake
@@ -0,0 +1,55 @@
+if(NOT ALLOCATION_PARAMETER)
+ execute_process(COMMAND bash "-c" "git rev-parse --verify HEAD|cut -c1-1"
+ OUTPUT_VARIABLE ALLOCATION_PARAMETER)
+ math(EXPR ALLOCATION_PARAMETER "0x${ALLOCATION_PARAMETER}")
+endif()
+
+if(NOT TEST_SUBNET_SIZE)
+ set(TEST_SUBNET_SIZE 4)
+endif()
+
+# NX_MAX_PORT is 0xffff.
+math(EXPR PORT_NUMBER "65535 - (${ALLOCATION_PARAMETER} + 1) * 256")
+set(INTERFACE_NUMBER ${PORT_NUMBER})
+math(EXPR TMP "256 - ${TEST_SUBNET_SIZE}")
+set(TEST_NETMASK 255.255.255.${TMP})
+
+set(IP_BYTE_0 10)
+set(IP_BYTE_1 10)
+set(IP_BYTE_2 ${ALLOCATION_PARAMETER})
+set(IP_BYTE_3 1)
+set(IP_BYTE_4 2)
+
+macro(network_config target)
+ target_compile_definitions(
+ ${target}
+ PRIVATE
+ -DINTEROPERABILITY_TEST_ENABLE_PARALLEL_PROCESSING
+ -DTLS_TEST_IP_BYTE_0=${IP_BYTE_0}
+ -DTLS_TEST_IP_BYTE_1=${IP_BYTE_1}
+ -DTLS_TEST_IP_BYTE_2=${IP_BYTE_2}
+ -DTLS_TEST_IP_BYTE_3=${IP_BYTE_3}
+ -DREMOTE_IP_BYTE_0=${IP_BYTE_0}
+ -DREMOTE_IP_BYTE_1=${IP_BYTE_1}
+ -DREMOTE_IP_BYTE_2=${IP_BYTE_2}
+ -DREMOTE_IP_BYTE_3=${IP_BYTE_4}
+ -DDEVICE_SERVER_PORT=${PORT_NUMBER}
+ -DNX_PCAP_SOURCE_NAME=\"veth${INTERFACE_NUMBER}\")
+ set(${target}_interface veth${INTERFACE_NUMBER})
+ set(${target}_ip ${IP_BYTE_0}.${IP_BYTE_1}.${IP_BYTE_2}.${IP_BYTE_3})
+ math(EXPR INTERFACE_NUMBER "${INTERFACE_NUMBER} + 1")
+ set(${target}_remote_interface veth${INTERFACE_NUMBER})
+ set(${target}_remote_ip ${IP_BYTE_0}.${IP_BYTE_1}.${IP_BYTE_2}.${IP_BYTE_4})
+ set(${target}_port ${PORT_NUMBER})
+
+ # Increase numbers for next setup
+ math(EXPR INTERFACE_NUMBER "${INTERFACE_NUMBER} + 1")
+ math(EXPR IP_BYTE_3 "${IP_BYTE_3} + ${TEST_SUBNET_SIZE}")
+ if(${IP_BYTE_3} GREATER 253)
+ math(EXPR IP_BYTE_2 "${IP_BYTE_2} + 1")
+ set(IP_BYTE_3 1)
+ endif()
+ math(EXPR IP_BYTE_4 "${IP_BYTE_3} + 1")
+ math(EXPR PORT_NUMBER "${PORT_NUMBER} + 1")
+
+endmacro()
diff --git a/test/cmake/nx_secure_interoperability/run.sh b/test/cmake/nx_secure_interoperability/run.sh
new file mode 100755
index 00000000..a1e78d3e
--- /dev/null
+++ b/test/cmake/nx_secure_interoperability/run.sh
@@ -0,0 +1,8 @@
+#!/bin/bash
+
+cd $(dirname $0)
+
+# if threadx repo does not exist, clone it
+[ -d ../threadx ] || git clone https://github.com/azure-rtos/threadx.git ../threadx --depth 1
+[ -f .run.sh ] || ln -sf ../threadx/scripts/cmake_bootstrap.sh .run.sh
+./.run.sh $* \ No newline at end of file
diff --git a/test/regression/interoperability_test/certificates/test.crt b/test/regression/interoperability_test/certificates/test.crt
new file mode 100644
index 00000000..b4f6837f
--- /dev/null
+++ b/test/regression/interoperability_test/certificates/test.crt
@@ -0,0 +1,34 @@
+-----BEGIN CERTIFICATE-----
+MIIF8jCCA9qgAwIBAgIBATANBgkqhkiG9w0BAQsFADCBiTELMAkGA1UEBhMCVVMx
+EzARBgNVBAgMCkNhbGlmb3JuaWExFjAUBgNVBAcMDVNhbiBGcmFuY2lzY28xEDAO
+BgNVBAoMB0VMIEluYy4xEzARBgNVBAsMCk9wZXJhdGlvbnMxJjAkBgNVBAMMHUVM
+IEluYy4gQ2VydGlmaWNhdGUgQXV0aG9yaXR5MB4XDTE3MDMwOTA4MDA1M1oXDTI3
+MDMwOTA4MDA1M1owgYkxCzAJBgNVBAYTAlVTMRMwEQYDVQQIDApDYWxpZm9ybmlh
+MRYwFAYDVQQHDA1TYW4gRnJhbmNpc2NvMRAwDgYDVQQKDAdFTCBJbmMuMRMwEQYD
+VQQLDApPcGVyYXRpb25zMSYwJAYDVQQDDB1FTCBJbmMuIENlcnRpZmljYXRlIEF1
+dGhvcml0eTCCAiIwDQYJKoZIhvcNAQEBBQADggIPADCCAgoCggIBAMvZ/YIv2UJy
+m9F9VLJ6fTcL+fnX7BzOx2pZiAltg9fp0KbD3Mml5f9ZkzOelAWfDlJSmwYr7KkS
+ceids0cIpZUNZxZLCH6GDu+TQbrmQ8BOsSLlP07hq1+CooSdK4eDSQcKgseLY8ig
+y47FNoHOwmG29+4+m81YuY1cdGxsNequsi7LTV/Jf1LejcAUBYcEmh5woa19uj2L
+s6dvMpyh1WGnvhE8gjNbbq/JRwcj7FjwwsU7qFR3fd5xjqV9CHsJ7lXascbiqH8g
+09ByhSuOBunCEBxJYX4eMYl/+hID20m0Al7lZJ45IxXevIpfudj2lkc5k8SyhZuj
+F2eatid5yFVPCCeTohnZhO8+b7vmh9xaWO3Crz5u9VhDxkdJxQKW/w62G5G4Mpw2
+3AkK9i/MRB3Tsw6HDOO71pY305sh6x0tSHlGlBCng/JxuMXFUNcBQcXiDUtDTgml
+AxRfx4Gh56gDNStzJJyZj5XI4CRVzGc8oIUUxgljhcxo7R3TUjwGLXfDF8VX1OG/
+Oc7aZ3UQhyHKVjRanCvNDyWpzdFcvr26BshNkCZIESuWeFEaCdD7uDzH2N9dhcD9
+HmcNIOOKjAUMQ2n8yUPOQymtxaeSuh2P03XfMEQcZqtnxUSMUbATFhB/aUd7wftg
+R9JLswW86tlOztmK2sPVUQeNLgcAPfYRAgMBAAGjYzBhMA4GA1UdDwEB/wQEAwIB
+BjAPBgNVHRMBAf8EBTADAQH/MB0GA1UdDgQWBBQtfEici1QUIT/idaWZindk3yvW
+iDAfBgNVHSMEGDAWgBQtfEici1QUIT/idaWZindk3yvWiDANBgkqhkiG9w0BAQsF
+AAOCAgEAG9e2wS2InvXlo/BYefkxGPC3LuUKg8ueIkV7Y2i7OfCMxT++h1BAbHlt
+iRZ09aGMua3Y5+BBbh19y4mEzhkbp+TYMJrMMW6vFdP2W21JuV97Va1Gy0FkBx2z
+FOOjFr5cz6EdLvCNvGlTMozuFlNmfmF1/aRnBFUpsTh2hZMESae/iIiUrXFGfILr
+qq7G02ti1oytDZWezhD6THXI9ILal2z35Xs2sxPVXMMnfIX+nBiqtaK6qux666XY
+76c4gHF0h3CUTQNLxsJhjcMk3XeGzSUU0o4gUqntaPAnhU4iHOlSkme24SpcX0tK
+p1/xlGDp1ZYBQ9s5iHCtNGk2SSf5kjMs1gOvIjdyFoajAcqMkNwdI8oPUMMnnXC3
+D0mwQlr65FGMwNA87WPaQImAxIJlX4KFbc3BTnS0FeF+UeCKaaOxIrgOPPZlUHAt
+sheSewry3vnPzCzY0FCgUTFTxPdruFfaBEa/ujwn7yurKAwnVRbCDUJTJsZjf0q/
+2ljRs7xRmr9NZruXwocllsPkkW88ww5jTRvs2kd+jFcuHPFFH+hzLPPBmmxZ1Mop
+f2BU/lL4t5mf1zgd0U00xep6L5BeYeX8H4n9khMHEg/26cMXJmxPwORsP8Q77ZDv
+Oq3RUvtyr7fChA7voQkW0QjeowDKlDgZ+HnGkmnVWwW1o4ofXmc=
+-----END CERTIFICATE----- \ No newline at end of file
diff --git a/test/regression/interoperability_test/certificates/test.der.c b/test/regression/interoperability_test/certificates/test.der.c
new file mode 100644
index 00000000..b2f8f8be
--- /dev/null
+++ b/test/regression/interoperability_test/certificates/test.der.c
@@ -0,0 +1,99 @@
+unsigned char test_der[] = {
+ 0x30, 0x82, 0x05, 0xf2, 0x30, 0x82, 0x03, 0xda, 0xa0, 0x03, 0x02, 0x01, 0x02, 0x02, 0x01, 0x01,
+ 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05, 0x00, 0x30,
+ 0x81, 0x89, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31,
+ 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x0a, 0x43, 0x61, 0x6c, 0x69, 0x66, 0x6f,
+ 0x72, 0x6e, 0x69, 0x61, 0x31, 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x07, 0x0c, 0x0d, 0x53,
+ 0x61, 0x6e, 0x20, 0x46, 0x72, 0x61, 0x6e, 0x63, 0x69, 0x73, 0x63, 0x6f, 0x31, 0x10, 0x30, 0x0e,
+ 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x07, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x31, 0x13,
+ 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x0b, 0x0c, 0x0a, 0x4f, 0x70, 0x65, 0x72, 0x61, 0x74, 0x69,
+ 0x6f, 0x6e, 0x73, 0x31, 0x26, 0x30, 0x24, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c, 0x1d, 0x45, 0x4c,
+ 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74,
+ 0x65, 0x20, 0x41, 0x75, 0x74, 0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x30, 0x1e, 0x17, 0x0d, 0x31,
+ 0x37, 0x30, 0x33, 0x30, 0x39, 0x30, 0x38, 0x30, 0x30, 0x35, 0x33, 0x5a, 0x17, 0x0d, 0x32, 0x37,
+ 0x30, 0x33, 0x30, 0x39, 0x30, 0x38, 0x30, 0x30, 0x35, 0x33, 0x5a, 0x30, 0x81, 0x89, 0x31, 0x0b,
+ 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31, 0x13, 0x30, 0x11, 0x06,
+ 0x03, 0x55, 0x04, 0x08, 0x0c, 0x0a, 0x43, 0x61, 0x6c, 0x69, 0x66, 0x6f, 0x72, 0x6e, 0x69, 0x61,
+ 0x31, 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x07, 0x0c, 0x0d, 0x53, 0x61, 0x6e, 0x20, 0x46,
+ 0x72, 0x61, 0x6e, 0x63, 0x69, 0x73, 0x63, 0x6f, 0x31, 0x10, 0x30, 0x0e, 0x06, 0x03, 0x55, 0x04,
+ 0x0a, 0x0c, 0x07, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03,
+ 0x55, 0x04, 0x0b, 0x0c, 0x0a, 0x4f, 0x70, 0x65, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x31,
+ 0x26, 0x30, 0x24, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c, 0x1d, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63,
+ 0x2e, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74, 0x65, 0x20, 0x41, 0x75,
+ 0x74, 0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x30, 0x82, 0x02, 0x22, 0x30, 0x0d, 0x06, 0x09, 0x2a,
+ 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x01, 0x05, 0x00, 0x03, 0x82, 0x02, 0x0f, 0x00, 0x30,
+ 0x82, 0x02, 0x0a, 0x02, 0x82, 0x02, 0x01, 0x00, 0xcb, 0xd9, 0xfd, 0x82, 0x2f, 0xd9, 0x42, 0x72,
+ 0x9b, 0xd1, 0x7d, 0x54, 0xb2, 0x7a, 0x7d, 0x37, 0x0b, 0xf9, 0xf9, 0xd7, 0xec, 0x1c, 0xce, 0xc7,
+ 0x6a, 0x59, 0x88, 0x09, 0x6d, 0x83, 0xd7, 0xe9, 0xd0, 0xa6, 0xc3, 0xdc, 0xc9, 0xa5, 0xe5, 0xff,
+ 0x59, 0x93, 0x33, 0x9e, 0x94, 0x05, 0x9f, 0x0e, 0x52, 0x52, 0x9b, 0x06, 0x2b, 0xec, 0xa9, 0x12,
+ 0x71, 0xe8, 0x9d, 0xb3, 0x47, 0x08, 0xa5, 0x95, 0x0d, 0x67, 0x16, 0x4b, 0x08, 0x7e, 0x86, 0x0e,
+ 0xef, 0x93, 0x41, 0xba, 0xe6, 0x43, 0xc0, 0x4e, 0xb1, 0x22, 0xe5, 0x3f, 0x4e, 0xe1, 0xab, 0x5f,
+ 0x82, 0xa2, 0x84, 0x9d, 0x2b, 0x87, 0x83, 0x49, 0x07, 0x0a, 0x82, 0xc7, 0x8b, 0x63, 0xc8, 0xa0,
+ 0xcb, 0x8e, 0xc5, 0x36, 0x81, 0xce, 0xc2, 0x61, 0xb6, 0xf7, 0xee, 0x3e, 0x9b, 0xcd, 0x58, 0xb9,
+ 0x8d, 0x5c, 0x74, 0x6c, 0x6c, 0x35, 0xea, 0xae, 0xb2, 0x2e, 0xcb, 0x4d, 0x5f, 0xc9, 0x7f, 0x52,
+ 0xde, 0x8d, 0xc0, 0x14, 0x05, 0x87, 0x04, 0x9a, 0x1e, 0x70, 0xa1, 0xad, 0x7d, 0xba, 0x3d, 0x8b,
+ 0xb3, 0xa7, 0x6f, 0x32, 0x9c, 0xa1, 0xd5, 0x61, 0xa7, 0xbe, 0x11, 0x3c, 0x82, 0x33, 0x5b, 0x6e,
+ 0xaf, 0xc9, 0x47, 0x07, 0x23, 0xec, 0x58, 0xf0, 0xc2, 0xc5, 0x3b, 0xa8, 0x54, 0x77, 0x7d, 0xde,
+ 0x71, 0x8e, 0xa5, 0x7d, 0x08, 0x7b, 0x09, 0xee, 0x55, 0xda, 0xb1, 0xc6, 0xe2, 0xa8, 0x7f, 0x20,
+ 0xd3, 0xd0, 0x72, 0x85, 0x2b, 0x8e, 0x06, 0xe9, 0xc2, 0x10, 0x1c, 0x49, 0x61, 0x7e, 0x1e, 0x31,
+ 0x89, 0x7f, 0xfa, 0x12, 0x03, 0xdb, 0x49, 0xb4, 0x02, 0x5e, 0xe5, 0x64, 0x9e, 0x39, 0x23, 0x15,
+ 0xde, 0xbc, 0x8a, 0x5f, 0xb9, 0xd8, 0xf6, 0x96, 0x47, 0x39, 0x93, 0xc4, 0xb2, 0x85, 0x9b, 0xa3,
+ 0x17, 0x67, 0x9a, 0xb6, 0x27, 0x79, 0xc8, 0x55, 0x4f, 0x08, 0x27, 0x93, 0xa2, 0x19, 0xd9, 0x84,
+ 0xef, 0x3e, 0x6f, 0xbb, 0xe6, 0x87, 0xdc, 0x5a, 0x58, 0xed, 0xc2, 0xaf, 0x3e, 0x6e, 0xf5, 0x58,
+ 0x43, 0xc6, 0x47, 0x49, 0xc5, 0x02, 0x96, 0xff, 0x0e, 0xb6, 0x1b, 0x91, 0xb8, 0x32, 0x9c, 0x36,
+ 0xdc, 0x09, 0x0a, 0xf6, 0x2f, 0xcc, 0x44, 0x1d, 0xd3, 0xb3, 0x0e, 0x87, 0x0c, 0xe3, 0xbb, 0xd6,
+ 0x96, 0x37, 0xd3, 0x9b, 0x21, 0xeb, 0x1d, 0x2d, 0x48, 0x79, 0x46, 0x94, 0x10, 0xa7, 0x83, 0xf2,
+ 0x71, 0xb8, 0xc5, 0xc5, 0x50, 0xd7, 0x01, 0x41, 0xc5, 0xe2, 0x0d, 0x4b, 0x43, 0x4e, 0x09, 0xa5,
+ 0x03, 0x14, 0x5f, 0xc7, 0x81, 0xa1, 0xe7, 0xa8, 0x03, 0x35, 0x2b, 0x73, 0x24, 0x9c, 0x99, 0x8f,
+ 0x95, 0xc8, 0xe0, 0x24, 0x55, 0xcc, 0x67, 0x3c, 0xa0, 0x85, 0x14, 0xc6, 0x09, 0x63, 0x85, 0xcc,
+ 0x68, 0xed, 0x1d, 0xd3, 0x52, 0x3c, 0x06, 0x2d, 0x77, 0xc3, 0x17, 0xc5, 0x57, 0xd4, 0xe1, 0xbf,
+ 0x39, 0xce, 0xda, 0x67, 0x75, 0x10, 0x87, 0x21, 0xca, 0x56, 0x34, 0x5a, 0x9c, 0x2b, 0xcd, 0x0f,
+ 0x25, 0xa9, 0xcd, 0xd1, 0x5c, 0xbe, 0xbd, 0xba, 0x06, 0xc8, 0x4d, 0x90, 0x26, 0x48, 0x11, 0x2b,
+ 0x96, 0x78, 0x51, 0x1a, 0x09, 0xd0, 0xfb, 0xb8, 0x3c, 0xc7, 0xd8, 0xdf, 0x5d, 0x85, 0xc0, 0xfd,
+ 0x1e, 0x67, 0x0d, 0x20, 0xe3, 0x8a, 0x8c, 0x05, 0x0c, 0x43, 0x69, 0xfc, 0xc9, 0x43, 0xce, 0x43,
+ 0x29, 0xad, 0xc5, 0xa7, 0x92, 0xba, 0x1d, 0x8f, 0xd3, 0x75, 0xdf, 0x30, 0x44, 0x1c, 0x66, 0xab,
+ 0x67, 0xc5, 0x44, 0x8c, 0x51, 0xb0, 0x13, 0x16, 0x10, 0x7f, 0x69, 0x47, 0x7b, 0xc1, 0xfb, 0x60,
+ 0x47, 0xd2, 0x4b, 0xb3, 0x05, 0xbc, 0xea, 0xd9, 0x4e, 0xce, 0xd9, 0x8a, 0xda, 0xc3, 0xd5, 0x51,
+ 0x07, 0x8d, 0x2e, 0x07, 0x00, 0x3d, 0xf6, 0x11, 0x02, 0x03, 0x01, 0x00, 0x01, 0xa3, 0x63, 0x30,
+ 0x61, 0x30, 0x0e, 0x06, 0x03, 0x55, 0x1d, 0x0f, 0x01, 0x01, 0xff, 0x04, 0x04, 0x03, 0x02, 0x01,
+ 0x06, 0x30, 0x0f, 0x06, 0x03, 0x55, 0x1d, 0x13, 0x01, 0x01, 0xff, 0x04, 0x05, 0x30, 0x03, 0x01,
+ 0x01, 0xff, 0x30, 0x1d, 0x06, 0x03, 0x55, 0x1d, 0x0e, 0x04, 0x16, 0x04, 0x14, 0x2d, 0x7c, 0x48,
+ 0x9c, 0x8b, 0x54, 0x14, 0x21, 0x3f, 0xe2, 0x75, 0xa5, 0x99, 0x8a, 0x77, 0x64, 0xdf, 0x2b, 0xd6,
+ 0x88, 0x30, 0x1f, 0x06, 0x03, 0x55, 0x1d, 0x23, 0x04, 0x18, 0x30, 0x16, 0x80, 0x14, 0x2d, 0x7c,
+ 0x48, 0x9c, 0x8b, 0x54, 0x14, 0x21, 0x3f, 0xe2, 0x75, 0xa5, 0x99, 0x8a, 0x77, 0x64, 0xdf, 0x2b,
+ 0xd6, 0x88, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05,
+ 0x00, 0x03, 0x82, 0x02, 0x01, 0x00, 0x1b, 0xd7, 0xb6, 0xc1, 0x2d, 0x88, 0x9e, 0xf5, 0xe5, 0xa3,
+ 0xf0, 0x58, 0x79, 0xf9, 0x31, 0x18, 0xf0, 0xb7, 0x2e, 0xe5, 0x0a, 0x83, 0xcb, 0x9e, 0x22, 0x45,
+ 0x7b, 0x63, 0x68, 0xbb, 0x39, 0xf0, 0x8c, 0xc5, 0x3f, 0xbe, 0x87, 0x50, 0x40, 0x6c, 0x79, 0x6d,
+ 0x89, 0x16, 0x74, 0xf5, 0xa1, 0x8c, 0xb9, 0xad, 0xd8, 0xe7, 0xe0, 0x41, 0x6e, 0x1d, 0x7d, 0xcb,
+ 0x89, 0x84, 0xce, 0x19, 0x1b, 0xa7, 0xe4, 0xd8, 0x30, 0x9a, 0xcc, 0x31, 0x6e, 0xaf, 0x15, 0xd3,
+ 0xf6, 0x5b, 0x6d, 0x49, 0xb9, 0x5f, 0x7b, 0x55, 0xad, 0x46, 0xcb, 0x41, 0x64, 0x07, 0x1d, 0xb3,
+ 0x14, 0xe3, 0xa3, 0x16, 0xbe, 0x5c, 0xcf, 0xa1, 0x1d, 0x2e, 0xf0, 0x8d, 0xbc, 0x69, 0x53, 0x32,
+ 0x8c, 0xee, 0x16, 0x53, 0x66, 0x7e, 0x61, 0x75, 0xfd, 0xa4, 0x67, 0x04, 0x55, 0x29, 0xb1, 0x38,
+ 0x76, 0x85, 0x93, 0x04, 0x49, 0xa7, 0xbf, 0x88, 0x88, 0x94, 0xad, 0x71, 0x46, 0x7c, 0x82, 0xeb,
+ 0xaa, 0xae, 0xc6, 0xd3, 0x6b, 0x62, 0xd6, 0x8c, 0xad, 0x0d, 0x95, 0x9e, 0xce, 0x10, 0xfa, 0x4c,
+ 0x75, 0xc8, 0xf4, 0x82, 0xda, 0x97, 0x6c, 0xf7, 0xe5, 0x7b, 0x36, 0xb3, 0x13, 0xd5, 0x5c, 0xc3,
+ 0x27, 0x7c, 0x85, 0xfe, 0x9c, 0x18, 0xaa, 0xb5, 0xa2, 0xba, 0xaa, 0xec, 0x7a, 0xeb, 0xa5, 0xd8,
+ 0xef, 0xa7, 0x38, 0x80, 0x71, 0x74, 0x87, 0x70, 0x94, 0x4d, 0x03, 0x4b, 0xc6, 0xc2, 0x61, 0x8d,
+ 0xc3, 0x24, 0xdd, 0x77, 0x86, 0xcd, 0x25, 0x14, 0xd2, 0x8e, 0x20, 0x52, 0xa9, 0xed, 0x68, 0xf0,
+ 0x27, 0x85, 0x4e, 0x22, 0x1c, 0xe9, 0x52, 0x92, 0x67, 0xb6, 0xe1, 0x2a, 0x5c, 0x5f, 0x4b, 0x4a,
+ 0xa7, 0x5f, 0xf1, 0x94, 0x60, 0xe9, 0xd5, 0x96, 0x01, 0x43, 0xdb, 0x39, 0x88, 0x70, 0xad, 0x34,
+ 0x69, 0x36, 0x49, 0x27, 0xf9, 0x92, 0x33, 0x2c, 0xd6, 0x03, 0xaf, 0x22, 0x37, 0x72, 0x16, 0x86,
+ 0xa3, 0x01, 0xca, 0x8c, 0x90, 0xdc, 0x1d, 0x23, 0xca, 0x0f, 0x50, 0xc3, 0x27, 0x9d, 0x70, 0xb7,
+ 0x0f, 0x49, 0xb0, 0x42, 0x5a, 0xfa, 0xe4, 0x51, 0x8c, 0xc0, 0xd0, 0x3c, 0xed, 0x63, 0xda, 0x40,
+ 0x89, 0x80, 0xc4, 0x82, 0x65, 0x5f, 0x82, 0x85, 0x6d, 0xcd, 0xc1, 0x4e, 0x74, 0xb4, 0x15, 0xe1,
+ 0x7e, 0x51, 0xe0, 0x8a, 0x69, 0xa3, 0xb1, 0x22, 0xb8, 0x0e, 0x3c, 0xf6, 0x65, 0x50, 0x70, 0x2d,
+ 0xb2, 0x17, 0x92, 0x7b, 0x0a, 0xf2, 0xde, 0xf9, 0xcf, 0xcc, 0x2c, 0xd8, 0xd0, 0x50, 0xa0, 0x51,
+ 0x31, 0x53, 0xc4, 0xf7, 0x6b, 0xb8, 0x57, 0xda, 0x04, 0x46, 0xbf, 0xba, 0x3c, 0x27, 0xef, 0x2b,
+ 0xab, 0x28, 0x0c, 0x27, 0x55, 0x16, 0xc2, 0x0d, 0x42, 0x53, 0x26, 0xc6, 0x63, 0x7f, 0x4a, 0xbf,
+ 0xda, 0x58, 0xd1, 0xb3, 0xbc, 0x51, 0x9a, 0xbf, 0x4d, 0x66, 0xbb, 0x97, 0xc2, 0x87, 0x25, 0x96,
+ 0xc3, 0xe4, 0x91, 0x6f, 0x3c, 0xc3, 0x0e, 0x63, 0x4d, 0x1b, 0xec, 0xda, 0x47, 0x7e, 0x8c, 0x57,
+ 0x2e, 0x1c, 0xf1, 0x45, 0x1f, 0xe8, 0x73, 0x2c, 0xf3, 0xc1, 0x9a, 0x6c, 0x59, 0xd4, 0xca, 0x29,
+ 0x7f, 0x60, 0x54, 0xfe, 0x52, 0xf8, 0xb7, 0x99, 0x9f, 0xd7, 0x38, 0x1d, 0xd1, 0x4d, 0x34, 0xc5,
+ 0xea, 0x7a, 0x2f, 0x90, 0x5e, 0x61, 0xe5, 0xfc, 0x1f, 0x89, 0xfd, 0x92, 0x13, 0x07, 0x12, 0x0f,
+ 0xf6, 0xe9, 0xc3, 0x17, 0x26, 0x6c, 0x4f, 0xc0, 0xe4, 0x6c, 0x3f, 0xc4, 0x3b, 0xed, 0x90, 0xef,
+ 0x3a, 0xad, 0xd1, 0x52, 0xfb, 0x72, 0xaf, 0xb7, 0xc2, 0x84, 0x0e, 0xef, 0xa1, 0x09, 0x16, 0xd1,
+ 0x08, 0xde, 0xa3, 0x00, 0xca, 0x94, 0x38, 0x19, 0xf8, 0x79, 0xc6, 0x92, 0x69, 0xd5, 0x5b, 0x05,
+ 0xb5, 0xa3, 0x8a, 0x1f, 0x5e, 0x67
+};
+unsigned int test_der_len = 1526;
diff --git a/test/regression/interoperability_test/certificates/test_client.crt b/test/regression/interoperability_test/certificates/test_client.crt
new file mode 100644
index 00000000..6e537078
--- /dev/null
+++ b/test/regression/interoperability_test/certificates/test_client.crt
@@ -0,0 +1,33 @@
+-----BEGIN CERTIFICATE-----
+MIIFxjCCA66gAwIBAgIBCDANBgkqhkiG9w0BAQsFADCBiTELMAkGA1UEBhMCVVMx
+EzARBgNVBAgMCkNhbGlmb3JuaWExFjAUBgNVBAcMDVNhbiBGcmFuY2lzY28xEDAO
+BgNVBAoMB0VMIEluYy4xEzARBgNVBAsMCk9wZXJhdGlvbnMxJjAkBgNVBAMMHUVM
+IEluYy4gQ2VydGlmaWNhdGUgQXV0aG9yaXR5MB4XDTE4MDYwNTA3MTc0MVoXDTI4
+MDYwMjA3MTc0MVowgYIxCzAJBgNVBAYTAlVTMRMwEQYDVQQIEwpDYWxpZm9ybmlh
+MRYwFAYDVQQHEw1TYW4gRnJhbmNpc2NvMQ8wDQYDVQQKEwZFTCBJbmMxGTAXBgkq
+hkiG9w0BCQEWCk9wZXJhdGlvbnMxGjAYBgNVBAMUEXRlc3RfY2xpZW50LmxvY2Fs
+MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAoThHaqx3v4Bdq82Ea2/9
+lB4oTStLtvLlSp9Z5ZQSAKvcTNzepjJylF3RxU2dNVAT+WSEaK7u8jkyxUbndb+Z
+xm1bYts1pHLq4Q6060gI0E4cHMLt50+R4akHdGmgfxS3xDcwu2Xv6X8KkPMG7NZI
+yB3gjq2+mMOcYDBj6KRQbNdQ4h8A+2c0/XK4Y0nDxnqMcwknj+2BVlpQV97rlrZg
+NzfycPsWm4gQsIMrAmT1QvNDVfPbX/BAdSx0HrRSY3WLdkmk01x8J4HqhHin4u6b
+9vDcaxQCSwOXpy5DamDEzz+1k4jpIhrN35endPQN4pfgEoM9Pom/1K9etsi0eKw3
+8QIDAQABo4IBPDCCATgwCQYDVR0TBAIwADALBgNVHQ8EBAMCBeAwMQYJYIZIAYb4
+QgENBCQWIk9wZW5TU0wgR2VuZXJhdGVkIFVzZXIgQ2VydGlmaWNhdGUwHQYDVR0O
+BBYEFBQ5W6jdDuT832WtrDXzBLzOuO6oMIG2BgNVHSMEga4wgauAFC18SJyLVBQh
+P+J1pZmKd2TfK9aIoYGPpIGMMIGJMQswCQYDVQQGEwJVUzETMBEGA1UECAwKQ2Fs
+aWZvcm5pYTEWMBQGA1UEBwwNU2FuIEZyYW5jaXNjbzEQMA4GA1UECgwHRUwgSW5j
+LjETMBEGA1UECwwKT3BlcmF0aW9uczEmMCQGA1UEAwwdRUwgSW5jLiBDZXJ0aWZp
+Y2F0ZSBBdXRob3JpdHmCAQEwEwYDVR0lBAwwCgYIKwYBBQUHAwIwDQYJKoZIhvcN
+AQELBQADggIBAHUSBnRtKIHwF+yPBQHrmJvwPBJWCuCgHX69dYZ1uirIKgSMHlYc
+RSjsnjqVtDBvvg2MHSZTlZKg3gHLxlIyAfPev3vyi8iGO6Ij1ZikSXHPkV5f9yeg
+/dGxmnCJFElSR/ho42nDi3lHNbGMiUh6s3Gj9+QaSTkykjV6iBDMriw2orcgIVke
+fdg0IxWLFHegqx/AJQCl2hDpg5KWePVpjhuAsk71lzhz6NDL7JgbHoRszmVh3Dfn
+67qO56jjqnEehbl4VopA6YdyzYlJeasqnQUz9otkw74W5mGVFI2Rdn5NpuC6f5wl
+QoWTJFJyQyg3OEkxF3onPp+UXsf+bBNAk09GkbYt2KFWHDb501+0wims6+ldBSZ4
+hCOZW8Wf8EQh6Bww0rvByao56RJwfSZIgfd1xY6ai+oVqP9XucDyCX7SuNyhgScV
+o/yBTdmVsWHXhhVnbdyOuc2dZI5eNEwjhvqiWj1OCl9aJ44Y8F7fkCLEiLqy7E8u
+gH3dA2PKd+7rv+IGo9gZvKogv+TqSJ5svCUPWsUEgnOBPs9ipukd3A0cRQiL7zOB
+mGw0dCr5WjoTmG/lSxB93ZeHkmejWFbFhmQPOqY/ZMW695HC9oEazOdnHSGeIxg4
+lR+3yHdErvu7MhtKCQ7e3EPGZ72n5KlcztAu8nvKLHHbH4Swk6nt8VNz
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/certificates/test_client.der.c b/test/regression/interoperability_test/certificates/test_client.der.c
new file mode 100644
index 00000000..1f54b400
--- /dev/null
+++ b/test/regression/interoperability_test/certificates/test_client.der.c
@@ -0,0 +1,96 @@
+unsigned char test_client_der[] = {
+ 0x30, 0x82, 0x05, 0xc6, 0x30, 0x82, 0x03, 0xae, 0xa0, 0x03, 0x02, 0x01, 0x02, 0x02, 0x01, 0x08,
+ 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05, 0x00, 0x30,
+ 0x81, 0x89, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31,
+ 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x0a, 0x43, 0x61, 0x6c, 0x69, 0x66, 0x6f,
+ 0x72, 0x6e, 0x69, 0x61, 0x31, 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x07, 0x0c, 0x0d, 0x53,
+ 0x61, 0x6e, 0x20, 0x46, 0x72, 0x61, 0x6e, 0x63, 0x69, 0x73, 0x63, 0x6f, 0x31, 0x10, 0x30, 0x0e,
+ 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x07, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x31, 0x13,
+ 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x0b, 0x0c, 0x0a, 0x4f, 0x70, 0x65, 0x72, 0x61, 0x74, 0x69,
+ 0x6f, 0x6e, 0x73, 0x31, 0x26, 0x30, 0x24, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c, 0x1d, 0x45, 0x4c,
+ 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74,
+ 0x65, 0x20, 0x41, 0x75, 0x74, 0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x30, 0x1e, 0x17, 0x0d, 0x31,
+ 0x38, 0x30, 0x36, 0x30, 0x35, 0x30, 0x37, 0x31, 0x37, 0x34, 0x31, 0x5a, 0x17, 0x0d, 0x32, 0x38,
+ 0x30, 0x36, 0x30, 0x32, 0x30, 0x37, 0x31, 0x37, 0x34, 0x31, 0x5a, 0x30, 0x81, 0x82, 0x31, 0x0b,
+ 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31, 0x13, 0x30, 0x11, 0x06,
+ 0x03, 0x55, 0x04, 0x08, 0x13, 0x0a, 0x43, 0x61, 0x6c, 0x69, 0x66, 0x6f, 0x72, 0x6e, 0x69, 0x61,
+ 0x31, 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x07, 0x13, 0x0d, 0x53, 0x61, 0x6e, 0x20, 0x46,
+ 0x72, 0x61, 0x6e, 0x63, 0x69, 0x73, 0x63, 0x6f, 0x31, 0x0f, 0x30, 0x0d, 0x06, 0x03, 0x55, 0x04,
+ 0x0a, 0x13, 0x06, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63, 0x31, 0x19, 0x30, 0x17, 0x06, 0x09, 0x2a,
+ 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x09, 0x01, 0x16, 0x0a, 0x4f, 0x70, 0x65, 0x72, 0x61, 0x74,
+ 0x69, 0x6f, 0x6e, 0x73, 0x31, 0x1a, 0x30, 0x18, 0x06, 0x03, 0x55, 0x04, 0x03, 0x14, 0x11, 0x74,
+ 0x65, 0x73, 0x74, 0x5f, 0x63, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x2e, 0x6c, 0x6f, 0x63, 0x61, 0x6c,
+ 0x30, 0x82, 0x01, 0x22, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01,
+ 0x01, 0x05, 0x00, 0x03, 0x82, 0x01, 0x0f, 0x00, 0x30, 0x82, 0x01, 0x0a, 0x02, 0x82, 0x01, 0x01,
+ 0x00, 0xa1, 0x38, 0x47, 0x6a, 0xac, 0x77, 0xbf, 0x80, 0x5d, 0xab, 0xcd, 0x84, 0x6b, 0x6f, 0xfd,
+ 0x94, 0x1e, 0x28, 0x4d, 0x2b, 0x4b, 0xb6, 0xf2, 0xe5, 0x4a, 0x9f, 0x59, 0xe5, 0x94, 0x12, 0x00,
+ 0xab, 0xdc, 0x4c, 0xdc, 0xde, 0xa6, 0x32, 0x72, 0x94, 0x5d, 0xd1, 0xc5, 0x4d, 0x9d, 0x35, 0x50,
+ 0x13, 0xf9, 0x64, 0x84, 0x68, 0xae, 0xee, 0xf2, 0x39, 0x32, 0xc5, 0x46, 0xe7, 0x75, 0xbf, 0x99,
+ 0xc6, 0x6d, 0x5b, 0x62, 0xdb, 0x35, 0xa4, 0x72, 0xea, 0xe1, 0x0e, 0xb4, 0xeb, 0x48, 0x08, 0xd0,
+ 0x4e, 0x1c, 0x1c, 0xc2, 0xed, 0xe7, 0x4f, 0x91, 0xe1, 0xa9, 0x07, 0x74, 0x69, 0xa0, 0x7f, 0x14,
+ 0xb7, 0xc4, 0x37, 0x30, 0xbb, 0x65, 0xef, 0xe9, 0x7f, 0x0a, 0x90, 0xf3, 0x06, 0xec, 0xd6, 0x48,
+ 0xc8, 0x1d, 0xe0, 0x8e, 0xad, 0xbe, 0x98, 0xc3, 0x9c, 0x60, 0x30, 0x63, 0xe8, 0xa4, 0x50, 0x6c,
+ 0xd7, 0x50, 0xe2, 0x1f, 0x00, 0xfb, 0x67, 0x34, 0xfd, 0x72, 0xb8, 0x63, 0x49, 0xc3, 0xc6, 0x7a,
+ 0x8c, 0x73, 0x09, 0x27, 0x8f, 0xed, 0x81, 0x56, 0x5a, 0x50, 0x57, 0xde, 0xeb, 0x96, 0xb6, 0x60,
+ 0x37, 0x37, 0xf2, 0x70, 0xfb, 0x16, 0x9b, 0x88, 0x10, 0xb0, 0x83, 0x2b, 0x02, 0x64, 0xf5, 0x42,
+ 0xf3, 0x43, 0x55, 0xf3, 0xdb, 0x5f, 0xf0, 0x40, 0x75, 0x2c, 0x74, 0x1e, 0xb4, 0x52, 0x63, 0x75,
+ 0x8b, 0x76, 0x49, 0xa4, 0xd3, 0x5c, 0x7c, 0x27, 0x81, 0xea, 0x84, 0x78, 0xa7, 0xe2, 0xee, 0x9b,
+ 0xf6, 0xf0, 0xdc, 0x6b, 0x14, 0x02, 0x4b, 0x03, 0x97, 0xa7, 0x2e, 0x43, 0x6a, 0x60, 0xc4, 0xcf,
+ 0x3f, 0xb5, 0x93, 0x88, 0xe9, 0x22, 0x1a, 0xcd, 0xdf, 0x97, 0xa7, 0x74, 0xf4, 0x0d, 0xe2, 0x97,
+ 0xe0, 0x12, 0x83, 0x3d, 0x3e, 0x89, 0xbf, 0xd4, 0xaf, 0x5e, 0xb6, 0xc8, 0xb4, 0x78, 0xac, 0x37,
+ 0xf1, 0x02, 0x03, 0x01, 0x00, 0x01, 0xa3, 0x82, 0x01, 0x3c, 0x30, 0x82, 0x01, 0x38, 0x30, 0x09,
+ 0x06, 0x03, 0x55, 0x1d, 0x13, 0x04, 0x02, 0x30, 0x00, 0x30, 0x0b, 0x06, 0x03, 0x55, 0x1d, 0x0f,
+ 0x04, 0x04, 0x03, 0x02, 0x05, 0xe0, 0x30, 0x31, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01, 0x86, 0xf8,
+ 0x42, 0x01, 0x0d, 0x04, 0x24, 0x16, 0x22, 0x4f, 0x70, 0x65, 0x6e, 0x53, 0x53, 0x4c, 0x20, 0x47,
+ 0x65, 0x6e, 0x65, 0x72, 0x61, 0x74, 0x65, 0x64, 0x20, 0x55, 0x73, 0x65, 0x72, 0x20, 0x43, 0x65,
+ 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74, 0x65, 0x30, 0x1d, 0x06, 0x03, 0x55, 0x1d, 0x0e,
+ 0x04, 0x16, 0x04, 0x14, 0x14, 0x39, 0x5b, 0xa8, 0xdd, 0x0e, 0xe4, 0xfc, 0xdf, 0x65, 0xad, 0xac,
+ 0x35, 0xf3, 0x04, 0xbc, 0xce, 0xb8, 0xee, 0xa8, 0x30, 0x81, 0xb6, 0x06, 0x03, 0x55, 0x1d, 0x23,
+ 0x04, 0x81, 0xae, 0x30, 0x81, 0xab, 0x80, 0x14, 0x2d, 0x7c, 0x48, 0x9c, 0x8b, 0x54, 0x14, 0x21,
+ 0x3f, 0xe2, 0x75, 0xa5, 0x99, 0x8a, 0x77, 0x64, 0xdf, 0x2b, 0xd6, 0x88, 0xa1, 0x81, 0x8f, 0xa4,
+ 0x81, 0x8c, 0x30, 0x81, 0x89, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02,
+ 0x55, 0x53, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x0a, 0x43, 0x61, 0x6c,
+ 0x69, 0x66, 0x6f, 0x72, 0x6e, 0x69, 0x61, 0x31, 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x07,
+ 0x0c, 0x0d, 0x53, 0x61, 0x6e, 0x20, 0x46, 0x72, 0x61, 0x6e, 0x63, 0x69, 0x73, 0x63, 0x6f, 0x31,
+ 0x10, 0x30, 0x0e, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x07, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63,
+ 0x2e, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x0b, 0x0c, 0x0a, 0x4f, 0x70, 0x65, 0x72,
+ 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x31, 0x26, 0x30, 0x24, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c,
+ 0x1d, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69,
+ 0x63, 0x61, 0x74, 0x65, 0x20, 0x41, 0x75, 0x74, 0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x82, 0x01,
+ 0x01, 0x30, 0x13, 0x06, 0x03, 0x55, 0x1d, 0x25, 0x04, 0x0c, 0x30, 0x0a, 0x06, 0x08, 0x2b, 0x06,
+ 0x01, 0x05, 0x05, 0x07, 0x03, 0x02, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d,
+ 0x01, 0x01, 0x0b, 0x05, 0x00, 0x03, 0x82, 0x02, 0x01, 0x00, 0x75, 0x12, 0x06, 0x74, 0x6d, 0x28,
+ 0x81, 0xf0, 0x17, 0xec, 0x8f, 0x05, 0x01, 0xeb, 0x98, 0x9b, 0xf0, 0x3c, 0x12, 0x56, 0x0a, 0xe0,
+ 0xa0, 0x1d, 0x7e, 0xbd, 0x75, 0x86, 0x75, 0xba, 0x2a, 0xc8, 0x2a, 0x04, 0x8c, 0x1e, 0x56, 0x1c,
+ 0x45, 0x28, 0xec, 0x9e, 0x3a, 0x95, 0xb4, 0x30, 0x6f, 0xbe, 0x0d, 0x8c, 0x1d, 0x26, 0x53, 0x95,
+ 0x92, 0xa0, 0xde, 0x01, 0xcb, 0xc6, 0x52, 0x32, 0x01, 0xf3, 0xde, 0xbf, 0x7b, 0xf2, 0x8b, 0xc8,
+ 0x86, 0x3b, 0xa2, 0x23, 0xd5, 0x98, 0xa4, 0x49, 0x71, 0xcf, 0x91, 0x5e, 0x5f, 0xf7, 0x27, 0xa0,
+ 0xfd, 0xd1, 0xb1, 0x9a, 0x70, 0x89, 0x14, 0x49, 0x52, 0x47, 0xf8, 0x68, 0xe3, 0x69, 0xc3, 0x8b,
+ 0x79, 0x47, 0x35, 0xb1, 0x8c, 0x89, 0x48, 0x7a, 0xb3, 0x71, 0xa3, 0xf7, 0xe4, 0x1a, 0x49, 0x39,
+ 0x32, 0x92, 0x35, 0x7a, 0x88, 0x10, 0xcc, 0xae, 0x2c, 0x36, 0xa2, 0xb7, 0x20, 0x21, 0x59, 0x1e,
+ 0x7d, 0xd8, 0x34, 0x23, 0x15, 0x8b, 0x14, 0x77, 0xa0, 0xab, 0x1f, 0xc0, 0x25, 0x00, 0xa5, 0xda,
+ 0x10, 0xe9, 0x83, 0x92, 0x96, 0x78, 0xf5, 0x69, 0x8e, 0x1b, 0x80, 0xb2, 0x4e, 0xf5, 0x97, 0x38,
+ 0x73, 0xe8, 0xd0, 0xcb, 0xec, 0x98, 0x1b, 0x1e, 0x84, 0x6c, 0xce, 0x65, 0x61, 0xdc, 0x37, 0xe7,
+ 0xeb, 0xba, 0x8e, 0xe7, 0xa8, 0xe3, 0xaa, 0x71, 0x1e, 0x85, 0xb9, 0x78, 0x56, 0x8a, 0x40, 0xe9,
+ 0x87, 0x72, 0xcd, 0x89, 0x49, 0x79, 0xab, 0x2a, 0x9d, 0x05, 0x33, 0xf6, 0x8b, 0x64, 0xc3, 0xbe,
+ 0x16, 0xe6, 0x61, 0x95, 0x14, 0x8d, 0x91, 0x76, 0x7e, 0x4d, 0xa6, 0xe0, 0xba, 0x7f, 0x9c, 0x25,
+ 0x42, 0x85, 0x93, 0x24, 0x52, 0x72, 0x43, 0x28, 0x37, 0x38, 0x49, 0x31, 0x17, 0x7a, 0x27, 0x3e,
+ 0x9f, 0x94, 0x5e, 0xc7, 0xfe, 0x6c, 0x13, 0x40, 0x93, 0x4f, 0x46, 0x91, 0xb6, 0x2d, 0xd8, 0xa1,
+ 0x56, 0x1c, 0x36, 0xf9, 0xd3, 0x5f, 0xb4, 0xc2, 0x29, 0xac, 0xeb, 0xe9, 0x5d, 0x05, 0x26, 0x78,
+ 0x84, 0x23, 0x99, 0x5b, 0xc5, 0x9f, 0xf0, 0x44, 0x21, 0xe8, 0x1c, 0x30, 0xd2, 0xbb, 0xc1, 0xc9,
+ 0xaa, 0x39, 0xe9, 0x12, 0x70, 0x7d, 0x26, 0x48, 0x81, 0xf7, 0x75, 0xc5, 0x8e, 0x9a, 0x8b, 0xea,
+ 0x15, 0xa8, 0xff, 0x57, 0xb9, 0xc0, 0xf2, 0x09, 0x7e, 0xd2, 0xb8, 0xdc, 0xa1, 0x81, 0x27, 0x15,
+ 0xa3, 0xfc, 0x81, 0x4d, 0xd9, 0x95, 0xb1, 0x61, 0xd7, 0x86, 0x15, 0x67, 0x6d, 0xdc, 0x8e, 0xb9,
+ 0xcd, 0x9d, 0x64, 0x8e, 0x5e, 0x34, 0x4c, 0x23, 0x86, 0xfa, 0xa2, 0x5a, 0x3d, 0x4e, 0x0a, 0x5f,
+ 0x5a, 0x27, 0x8e, 0x18, 0xf0, 0x5e, 0xdf, 0x90, 0x22, 0xc4, 0x88, 0xba, 0xb2, 0xec, 0x4f, 0x2e,
+ 0x80, 0x7d, 0xdd, 0x03, 0x63, 0xca, 0x77, 0xee, 0xeb, 0xbf, 0xe2, 0x06, 0xa3, 0xd8, 0x19, 0xbc,
+ 0xaa, 0x20, 0xbf, 0xe4, 0xea, 0x48, 0x9e, 0x6c, 0xbc, 0x25, 0x0f, 0x5a, 0xc5, 0x04, 0x82, 0x73,
+ 0x81, 0x3e, 0xcf, 0x62, 0xa6, 0xe9, 0x1d, 0xdc, 0x0d, 0x1c, 0x45, 0x08, 0x8b, 0xef, 0x33, 0x81,
+ 0x98, 0x6c, 0x34, 0x74, 0x2a, 0xf9, 0x5a, 0x3a, 0x13, 0x98, 0x6f, 0xe5, 0x4b, 0x10, 0x7d, 0xdd,
+ 0x97, 0x87, 0x92, 0x67, 0xa3, 0x58, 0x56, 0xc5, 0x86, 0x64, 0x0f, 0x3a, 0xa6, 0x3f, 0x64, 0xc5,
+ 0xba, 0xf7, 0x91, 0xc2, 0xf6, 0x81, 0x1a, 0xcc, 0xe7, 0x67, 0x1d, 0x21, 0x9e, 0x23, 0x18, 0x38,
+ 0x95, 0x1f, 0xb7, 0xc8, 0x77, 0x44, 0xae, 0xfb, 0xbb, 0x32, 0x1b, 0x4a, 0x09, 0x0e, 0xde, 0xdc,
+ 0x43, 0xc6, 0x67, 0xbd, 0xa7, 0xe4, 0xa9, 0x5c, 0xce, 0xd0, 0x2e, 0xf2, 0x7b, 0xca, 0x2c, 0x71,
+ 0xdb, 0x1f, 0x84, 0xb0, 0x93, 0xa9, 0xed, 0xf1, 0x53, 0x73
+};
+unsigned int test_client_der_len = 1482;
diff --git a/test/regression/interoperability_test/certificates/test_client.key b/test/regression/interoperability_test/certificates/test_client.key
new file mode 100644
index 00000000..7d0a9382
--- /dev/null
+++ b/test/regression/interoperability_test/certificates/test_client.key
@@ -0,0 +1,28 @@
+-----BEGIN PRIVATE KEY-----
+MIIEvwIBADANBgkqhkiG9w0BAQEFAASCBKkwggSlAgEAAoIBAQChOEdqrHe/gF2r
+zYRrb/2UHihNK0u28uVKn1nllBIAq9xM3N6mMnKUXdHFTZ01UBP5ZIRoru7yOTLF
+Rud1v5nGbVti2zWkcurhDrTrSAjQThwcwu3nT5HhqQd0aaB/FLfENzC7Ze/pfwqQ
+8wbs1kjIHeCOrb6Yw5xgMGPopFBs11DiHwD7ZzT9crhjScPGeoxzCSeP7YFWWlBX
+3uuWtmA3N/Jw+xabiBCwgysCZPVC80NV89tf8EB1LHQetFJjdYt2SaTTXHwngeqE
+eKfi7pv28NxrFAJLA5enLkNqYMTPP7WTiOkiGs3fl6d09A3il+ASgz0+ib/Ur162
+yLR4rDfxAgMBAAECggEBAJ/3Go2S0UKXWNo2EpUTytUj0zM2qWq+uZoAYQ91iyNV
+Y0J0yQq49Y2XRaPyrfEPIrKK9QJ1yKtY67Jo9xKTaT5Ela+R+DjSuZFTqVnm4K/n
+QOec1rdz8TiqIbZ1dAWEBg7QAC+BJrpVDqPiL9XhjNfbJUwMwxgKx2d9vDRCjXZf
+3pzaLALZBwLpDARH7n8cUQHLw1PQvxeIrj32Ft6vIiKJ65ZFz3JEvwIC1lOvFPn7
+sKX4tpNHfi1wUNZN5WHyMGuEQFhjcQSU5HUqHasyPckjDBrDvvAQt2xSzwHmi+J7
+fbtx3Ejl+4wK0ACAfbzWB/YMpYSSE7U/Ls41nhbcR+0CgYEA1tmFS0WQq0v/dw8E
+59Zx/8nR4GRHXLQiKObkZQ8wNe/MzNwUvKsQQ040lldg87r1Do1rvV5ITw9H2z50
+XXWzYdREu0B994anEYdn5pKOUqOqS0fYD/D76JPqsStmbLNXKzvbMGB8fUA4TQAj
+d4Eu/cqREwGYwrQUjCKtYM2Ae/cCgYEAwBkv53nEDxe/mC+jE31x5wPAhOvZN0YA
+Bg/4UEztqDssv2OExTOoM1ZCyOBMihZww+17ONH6Ez5BSueZ1vRRooew5Kh0prqi
+MU2aT/u7E9yYxFU2d8F2r0mld481T5Dkw56gMSAwE/7NvOM1lvY9B0lxiOr5a5z1
+Li7Zk6Pi4VcCgYAjG3Y5f4uNQiTjepPNonAMYRkndptmnZS7ZEdL8Dhrh9zKWOgW
+kElfBid3rZ2NFi63Cwrg7cgZCyEtxT3Ui8gdI0d75aTvzpP8PEkRFz+kZ1QLaxj2
+OeWf8pO2EaZx+rgyu1wswod1HApXIr+o5nYcSH5+QZOJtU1qPLxiBhKJrwKBgQCQ
+xyrciWAjg+GJoHWGrefXlXNWeq52QxKnfwfF9YS0Ywzhne6l9b3SGzQwUyQ8epc4
+g1Z4R4DzWds5yf2fDPotxZijbPal5klxYSxpFa80U/DrH9HyRePeTmIgDtW+BtTz
+Pi07eSfjGgoTTybHhQQP5uFjsLyUx3HeAb9Hz5+h9wKBgQCUu3K5/6OQcWOypdyR
+LZHJiT/4IOkJu5mZML1C5KiyUvaxxaOPRdN0htilFIGBvNkCTmW/SYTj8uEZdR5e
+hxqLv0R3oLkARyTGiiOjgu9Dy6Wfx1GZlQKZW6UiEz/8B811mqMxTZJ7zSqZe+U9
+a8ZytpMWLH8hgG9f+SBTL0EDVQ==
+-----END PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/certificates/test_client.key.der.c b/test/regression/interoperability_test/certificates/test_client.key.der.c
new file mode 100644
index 00000000..49e80e3c
--- /dev/null
+++ b/test/regression/interoperability_test/certificates/test_client.key.der.c
@@ -0,0 +1,78 @@
+unsigned char test_client_key_der[] = {
+ 0x30, 0x82, 0x04, 0xa5, 0x02, 0x01, 0x00, 0x02, 0x82, 0x01, 0x01, 0x00, 0xa1, 0x38, 0x47, 0x6a,
+ 0xac, 0x77, 0xbf, 0x80, 0x5d, 0xab, 0xcd, 0x84, 0x6b, 0x6f, 0xfd, 0x94, 0x1e, 0x28, 0x4d, 0x2b,
+ 0x4b, 0xb6, 0xf2, 0xe5, 0x4a, 0x9f, 0x59, 0xe5, 0x94, 0x12, 0x00, 0xab, 0xdc, 0x4c, 0xdc, 0xde,
+ 0xa6, 0x32, 0x72, 0x94, 0x5d, 0xd1, 0xc5, 0x4d, 0x9d, 0x35, 0x50, 0x13, 0xf9, 0x64, 0x84, 0x68,
+ 0xae, 0xee, 0xf2, 0x39, 0x32, 0xc5, 0x46, 0xe7, 0x75, 0xbf, 0x99, 0xc6, 0x6d, 0x5b, 0x62, 0xdb,
+ 0x35, 0xa4, 0x72, 0xea, 0xe1, 0x0e, 0xb4, 0xeb, 0x48, 0x08, 0xd0, 0x4e, 0x1c, 0x1c, 0xc2, 0xed,
+ 0xe7, 0x4f, 0x91, 0xe1, 0xa9, 0x07, 0x74, 0x69, 0xa0, 0x7f, 0x14, 0xb7, 0xc4, 0x37, 0x30, 0xbb,
+ 0x65, 0xef, 0xe9, 0x7f, 0x0a, 0x90, 0xf3, 0x06, 0xec, 0xd6, 0x48, 0xc8, 0x1d, 0xe0, 0x8e, 0xad,
+ 0xbe, 0x98, 0xc3, 0x9c, 0x60, 0x30, 0x63, 0xe8, 0xa4, 0x50, 0x6c, 0xd7, 0x50, 0xe2, 0x1f, 0x00,
+ 0xfb, 0x67, 0x34, 0xfd, 0x72, 0xb8, 0x63, 0x49, 0xc3, 0xc6, 0x7a, 0x8c, 0x73, 0x09, 0x27, 0x8f,
+ 0xed, 0x81, 0x56, 0x5a, 0x50, 0x57, 0xde, 0xeb, 0x96, 0xb6, 0x60, 0x37, 0x37, 0xf2, 0x70, 0xfb,
+ 0x16, 0x9b, 0x88, 0x10, 0xb0, 0x83, 0x2b, 0x02, 0x64, 0xf5, 0x42, 0xf3, 0x43, 0x55, 0xf3, 0xdb,
+ 0x5f, 0xf0, 0x40, 0x75, 0x2c, 0x74, 0x1e, 0xb4, 0x52, 0x63, 0x75, 0x8b, 0x76, 0x49, 0xa4, 0xd3,
+ 0x5c, 0x7c, 0x27, 0x81, 0xea, 0x84, 0x78, 0xa7, 0xe2, 0xee, 0x9b, 0xf6, 0xf0, 0xdc, 0x6b, 0x14,
+ 0x02, 0x4b, 0x03, 0x97, 0xa7, 0x2e, 0x43, 0x6a, 0x60, 0xc4, 0xcf, 0x3f, 0xb5, 0x93, 0x88, 0xe9,
+ 0x22, 0x1a, 0xcd, 0xdf, 0x97, 0xa7, 0x74, 0xf4, 0x0d, 0xe2, 0x97, 0xe0, 0x12, 0x83, 0x3d, 0x3e,
+ 0x89, 0xbf, 0xd4, 0xaf, 0x5e, 0xb6, 0xc8, 0xb4, 0x78, 0xac, 0x37, 0xf1, 0x02, 0x03, 0x01, 0x00,
+ 0x01, 0x02, 0x82, 0x01, 0x01, 0x00, 0x9f, 0xf7, 0x1a, 0x8d, 0x92, 0xd1, 0x42, 0x97, 0x58, 0xda,
+ 0x36, 0x12, 0x95, 0x13, 0xca, 0xd5, 0x23, 0xd3, 0x33, 0x36, 0xa9, 0x6a, 0xbe, 0xb9, 0x9a, 0x00,
+ 0x61, 0x0f, 0x75, 0x8b, 0x23, 0x55, 0x63, 0x42, 0x74, 0xc9, 0x0a, 0xb8, 0xf5, 0x8d, 0x97, 0x45,
+ 0xa3, 0xf2, 0xad, 0xf1, 0x0f, 0x22, 0xb2, 0x8a, 0xf5, 0x02, 0x75, 0xc8, 0xab, 0x58, 0xeb, 0xb2,
+ 0x68, 0xf7, 0x12, 0x93, 0x69, 0x3e, 0x44, 0x95, 0xaf, 0x91, 0xf8, 0x38, 0xd2, 0xb9, 0x91, 0x53,
+ 0xa9, 0x59, 0xe6, 0xe0, 0xaf, 0xe7, 0x40, 0xe7, 0x9c, 0xd6, 0xb7, 0x73, 0xf1, 0x38, 0xaa, 0x21,
+ 0xb6, 0x75, 0x74, 0x05, 0x84, 0x06, 0x0e, 0xd0, 0x00, 0x2f, 0x81, 0x26, 0xba, 0x55, 0x0e, 0xa3,
+ 0xe2, 0x2f, 0xd5, 0xe1, 0x8c, 0xd7, 0xdb, 0x25, 0x4c, 0x0c, 0xc3, 0x18, 0x0a, 0xc7, 0x67, 0x7d,
+ 0xbc, 0x34, 0x42, 0x8d, 0x76, 0x5f, 0xde, 0x9c, 0xda, 0x2c, 0x02, 0xd9, 0x07, 0x02, 0xe9, 0x0c,
+ 0x04, 0x47, 0xee, 0x7f, 0x1c, 0x51, 0x01, 0xcb, 0xc3, 0x53, 0xd0, 0xbf, 0x17, 0x88, 0xae, 0x3d,
+ 0xf6, 0x16, 0xde, 0xaf, 0x22, 0x22, 0x89, 0xeb, 0x96, 0x45, 0xcf, 0x72, 0x44, 0xbf, 0x02, 0x02,
+ 0xd6, 0x53, 0xaf, 0x14, 0xf9, 0xfb, 0xb0, 0xa5, 0xf8, 0xb6, 0x93, 0x47, 0x7e, 0x2d, 0x70, 0x50,
+ 0xd6, 0x4d, 0xe5, 0x61, 0xf2, 0x30, 0x6b, 0x84, 0x40, 0x58, 0x63, 0x71, 0x04, 0x94, 0xe4, 0x75,
+ 0x2a, 0x1d, 0xab, 0x32, 0x3d, 0xc9, 0x23, 0x0c, 0x1a, 0xc3, 0xbe, 0xf0, 0x10, 0xb7, 0x6c, 0x52,
+ 0xcf, 0x01, 0xe6, 0x8b, 0xe2, 0x7b, 0x7d, 0xbb, 0x71, 0xdc, 0x48, 0xe5, 0xfb, 0x8c, 0x0a, 0xd0,
+ 0x00, 0x80, 0x7d, 0xbc, 0xd6, 0x07, 0xf6, 0x0c, 0xa5, 0x84, 0x92, 0x13, 0xb5, 0x3f, 0x2e, 0xce,
+ 0x35, 0x9e, 0x16, 0xdc, 0x47, 0xed, 0x02, 0x81, 0x81, 0x00, 0xd6, 0xd9, 0x85, 0x4b, 0x45, 0x90,
+ 0xab, 0x4b, 0xff, 0x77, 0x0f, 0x04, 0xe7, 0xd6, 0x71, 0xff, 0xc9, 0xd1, 0xe0, 0x64, 0x47, 0x5c,
+ 0xb4, 0x22, 0x28, 0xe6, 0xe4, 0x65, 0x0f, 0x30, 0x35, 0xef, 0xcc, 0xcc, 0xdc, 0x14, 0xbc, 0xab,
+ 0x10, 0x43, 0x4e, 0x34, 0x96, 0x57, 0x60, 0xf3, 0xba, 0xf5, 0x0e, 0x8d, 0x6b, 0xbd, 0x5e, 0x48,
+ 0x4f, 0x0f, 0x47, 0xdb, 0x3e, 0x74, 0x5d, 0x75, 0xb3, 0x61, 0xd4, 0x44, 0xbb, 0x40, 0x7d, 0xf7,
+ 0x86, 0xa7, 0x11, 0x87, 0x67, 0xe6, 0x92, 0x8e, 0x52, 0xa3, 0xaa, 0x4b, 0x47, 0xd8, 0x0f, 0xf0,
+ 0xfb, 0xe8, 0x93, 0xea, 0xb1, 0x2b, 0x66, 0x6c, 0xb3, 0x57, 0x2b, 0x3b, 0xdb, 0x30, 0x60, 0x7c,
+ 0x7d, 0x40, 0x38, 0x4d, 0x00, 0x23, 0x77, 0x81, 0x2e, 0xfd, 0xca, 0x91, 0x13, 0x01, 0x98, 0xc2,
+ 0xb4, 0x14, 0x8c, 0x22, 0xad, 0x60, 0xcd, 0x80, 0x7b, 0xf7, 0x02, 0x81, 0x81, 0x00, 0xc0, 0x19,
+ 0x2f, 0xe7, 0x79, 0xc4, 0x0f, 0x17, 0xbf, 0x98, 0x2f, 0xa3, 0x13, 0x7d, 0x71, 0xe7, 0x03, 0xc0,
+ 0x84, 0xeb, 0xd9, 0x37, 0x46, 0x00, 0x06, 0x0f, 0xf8, 0x50, 0x4c, 0xed, 0xa8, 0x3b, 0x2c, 0xbf,
+ 0x63, 0x84, 0xc5, 0x33, 0xa8, 0x33, 0x56, 0x42, 0xc8, 0xe0, 0x4c, 0x8a, 0x16, 0x70, 0xc3, 0xed,
+ 0x7b, 0x38, 0xd1, 0xfa, 0x13, 0x3e, 0x41, 0x4a, 0xe7, 0x99, 0xd6, 0xf4, 0x51, 0xa2, 0x87, 0xb0,
+ 0xe4, 0xa8, 0x74, 0xa6, 0xba, 0xa2, 0x31, 0x4d, 0x9a, 0x4f, 0xfb, 0xbb, 0x13, 0xdc, 0x98, 0xc4,
+ 0x55, 0x36, 0x77, 0xc1, 0x76, 0xaf, 0x49, 0xa5, 0x77, 0x8f, 0x35, 0x4f, 0x90, 0xe4, 0xc3, 0x9e,
+ 0xa0, 0x31, 0x20, 0x30, 0x13, 0xfe, 0xcd, 0xbc, 0xe3, 0x35, 0x96, 0xf6, 0x3d, 0x07, 0x49, 0x71,
+ 0x88, 0xea, 0xf9, 0x6b, 0x9c, 0xf5, 0x2e, 0x2e, 0xd9, 0x93, 0xa3, 0xe2, 0xe1, 0x57, 0x02, 0x81,
+ 0x80, 0x23, 0x1b, 0x76, 0x39, 0x7f, 0x8b, 0x8d, 0x42, 0x24, 0xe3, 0x7a, 0x93, 0xcd, 0xa2, 0x70,
+ 0x0c, 0x61, 0x19, 0x27, 0x76, 0x9b, 0x66, 0x9d, 0x94, 0xbb, 0x64, 0x47, 0x4b, 0xf0, 0x38, 0x6b,
+ 0x87, 0xdc, 0xca, 0x58, 0xe8, 0x16, 0x90, 0x49, 0x5f, 0x06, 0x27, 0x77, 0xad, 0x9d, 0x8d, 0x16,
+ 0x2e, 0xb7, 0x0b, 0x0a, 0xe0, 0xed, 0xc8, 0x19, 0x0b, 0x21, 0x2d, 0xc5, 0x3d, 0xd4, 0x8b, 0xc8,
+ 0x1d, 0x23, 0x47, 0x7b, 0xe5, 0xa4, 0xef, 0xce, 0x93, 0xfc, 0x3c, 0x49, 0x11, 0x17, 0x3f, 0xa4,
+ 0x67, 0x54, 0x0b, 0x6b, 0x18, 0xf6, 0x39, 0xe5, 0x9f, 0xf2, 0x93, 0xb6, 0x11, 0xa6, 0x71, 0xfa,
+ 0xb8, 0x32, 0xbb, 0x5c, 0x2c, 0xc2, 0x87, 0x75, 0x1c, 0x0a, 0x57, 0x22, 0xbf, 0xa8, 0xe6, 0x76,
+ 0x1c, 0x48, 0x7e, 0x7e, 0x41, 0x93, 0x89, 0xb5, 0x4d, 0x6a, 0x3c, 0xbc, 0x62, 0x06, 0x12, 0x89,
+ 0xaf, 0x02, 0x81, 0x81, 0x00, 0x90, 0xc7, 0x2a, 0xdc, 0x89, 0x60, 0x23, 0x83, 0xe1, 0x89, 0xa0,
+ 0x75, 0x86, 0xad, 0xe7, 0xd7, 0x95, 0x73, 0x56, 0x7a, 0xae, 0x76, 0x43, 0x12, 0xa7, 0x7f, 0x07,
+ 0xc5, 0xf5, 0x84, 0xb4, 0x63, 0x0c, 0xe1, 0x9d, 0xee, 0xa5, 0xf5, 0xbd, 0xd2, 0x1b, 0x34, 0x30,
+ 0x53, 0x24, 0x3c, 0x7a, 0x97, 0x38, 0x83, 0x56, 0x78, 0x47, 0x80, 0xf3, 0x59, 0xdb, 0x39, 0xc9,
+ 0xfd, 0x9f, 0x0c, 0xfa, 0x2d, 0xc5, 0x98, 0xa3, 0x6c, 0xf6, 0xa5, 0xe6, 0x49, 0x71, 0x61, 0x2c,
+ 0x69, 0x15, 0xaf, 0x34, 0x53, 0xf0, 0xeb, 0x1f, 0xd1, 0xf2, 0x45, 0xe3, 0xde, 0x4e, 0x62, 0x20,
+ 0x0e, 0xd5, 0xbe, 0x06, 0xd4, 0xf3, 0x3e, 0x2d, 0x3b, 0x79, 0x27, 0xe3, 0x1a, 0x0a, 0x13, 0x4f,
+ 0x26, 0xc7, 0x85, 0x04, 0x0f, 0xe6, 0xe1, 0x63, 0xb0, 0xbc, 0x94, 0xc7, 0x71, 0xde, 0x01, 0xbf,
+ 0x47, 0xcf, 0x9f, 0xa1, 0xf7, 0x02, 0x81, 0x81, 0x00, 0x94, 0xbb, 0x72, 0xb9, 0xff, 0xa3, 0x90,
+ 0x71, 0x63, 0xb2, 0xa5, 0xdc, 0x91, 0x2d, 0x91, 0xc9, 0x89, 0x3f, 0xf8, 0x20, 0xe9, 0x09, 0xbb,
+ 0x99, 0x99, 0x30, 0xbd, 0x42, 0xe4, 0xa8, 0xb2, 0x52, 0xf6, 0xb1, 0xc5, 0xa3, 0x8f, 0x45, 0xd3,
+ 0x74, 0x86, 0xd8, 0xa5, 0x14, 0x81, 0x81, 0xbc, 0xd9, 0x02, 0x4e, 0x65, 0xbf, 0x49, 0x84, 0xe3,
+ 0xf2, 0xe1, 0x19, 0x75, 0x1e, 0x5e, 0x87, 0x1a, 0x8b, 0xbf, 0x44, 0x77, 0xa0, 0xb9, 0x00, 0x47,
+ 0x24, 0xc6, 0x8a, 0x23, 0xa3, 0x82, 0xef, 0x43, 0xcb, 0xa5, 0x9f, 0xc7, 0x51, 0x99, 0x95, 0x02,
+ 0x99, 0x5b, 0xa5, 0x22, 0x13, 0x3f, 0xfc, 0x07, 0xcd, 0x75, 0x9a, 0xa3, 0x31, 0x4d, 0x92, 0x7b,
+ 0xcd, 0x2a, 0x99, 0x7b, 0xe5, 0x3d, 0x6b, 0xc6, 0x72, 0xb6, 0x93, 0x16, 0x2c, 0x7f, 0x21, 0x80,
+ 0x6f, 0x5f, 0xf9, 0x20, 0x53, 0x2f, 0x41, 0x03, 0x55
+};
+unsigned int test_client_key_der_len = 1193;
diff --git a/test/regression/interoperability_test/certificates/test_server.crt b/test/regression/interoperability_test/certificates/test_server.crt
new file mode 100644
index 00000000..81851ed7
--- /dev/null
+++ b/test/regression/interoperability_test/certificates/test_server.crt
@@ -0,0 +1,34 @@
+-----BEGIN CERTIFICATE-----
+MIIF5TCCA82gAwIBAgIBBzANBgkqhkiG9w0BAQsFADCBiTELMAkGA1UEBhMCVVMx
+EzARBgNVBAgMCkNhbGlmb3JuaWExFjAUBgNVBAcMDVNhbiBGcmFuY2lzY28xEDAO
+BgNVBAoMB0VMIEluYy4xEzARBgNVBAsMCk9wZXJhdGlvbnMxJjAkBgNVBAMMHUVM
+IEluYy4gQ2VydGlmaWNhdGUgQXV0aG9yaXR5MB4XDTE4MDYwNTA3MTcxOFoXDTI4
+MDYwMjA3MTcxOFowgYIxCzAJBgNVBAYTAlVTMRMwEQYDVQQIEwpDYWxpZm9ybmlh
+MRYwFAYDVQQHEw1TYW4gRnJhbmNpc2NvMQ8wDQYDVQQKEwZFTCBJbmMxGTAXBgkq
+hkiG9w0BCQEWCk9wZXJhdGlvbnMxGjAYBgNVBAMUEXRlc3Rfc2VydmVyLmxvY2Fs
+MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA0GpSbuY2RAhijLv+os+m
+0oDXVohD+0jr/lOSv+5qokQ8afqeL0QNmC4vcmT3hv5MGBqZy4XJt2aeyPsz7W8y
+h5ausWIR7TD0h/IyRiEAJZf/9/hxu36E8tYaW9dXoB74juAE5nGkzdDhjA092SB8
+LFbeAuzbP05Kd98jpMGMCwNGIXZMhSxVp20FLQ+RlMNg/B3V1pQZCyKwW8CUFmYs
+5HpcEa19QLGEeASxphxzqrX6zRilUP65q7B9zg1JRldlU0zsVeHFBZW9Un7xDK2E
+JNnOyI5HVwCvA4sxKD68xGwUecKHY9iJ3DUfj1Vi8KiO3YLwa5ACyI+AGoK0gtNL
++QIDAQABo4IBWzCCAVcwCQYDVR0TBAIwADARBglghkgBhvhCAQEEBAMCBkAwMwYJ
+YIZIAYb4QgENBCYWJE9wZW5TU0wgR2VuZXJhdGVkIFNlcnZlciBDZXJ0aWZpY2F0
+ZTAdBgNVHQ4EFgQUNiDTUqIWB5QEtTe2q1Ol8+klyzowgbYGA1UdIwSBrjCBq4AU
+LXxInItUFCE/4nWlmYp3ZN8r1oihgY+kgYwwgYkxCzAJBgNVBAYTAlVTMRMwEQYD
+VQQIDApDYWxpZm9ybmlhMRYwFAYDVQQHDA1TYW4gRnJhbmNpc2NvMRAwDgYDVQQK
+DAdFTCBJbmMuMRMwEQYDVQQLDApPcGVyYXRpb25zMSYwJAYDVQQDDB1FTCBJbmMu
+IENlcnRpZmljYXRlIEF1dGhvcml0eYIBATAdBgNVHSUEFjAUBggrBgEFBQcDAQYI
+KwYBBQUIAgIwCwYDVR0PBAQDAgWgMA0GCSqGSIb3DQEBCwUAA4ICAQC+nzyI3IrD
+3Fq+aFvqrCqDbbnQsHsZWu8JRjtuWOvsCAvIe5Rdq2cDbIo1GE0qH42ieK6JkHhJ
+muusukRM6uBnt/u8Q9e+HOOoQysewMmIqStcEOhPI5ZAekEfoHFvXK9l8Z9hxSG7
+BX+JclWacTdFNuR1Z/hbPGx78F0jxkYtZCdYJsVUyYZ1dpX092ThG3pr9VKOBZP5
+nVCV0a99/Yl9ML7XFrewOwPj/mRXHnCfVKTVdUWtNF+Gu7kgAZrXyJ20wnDTfgbU
+YP0+Z9aRJcgfQwrMP2j8aOL4+OjDrsuau2hl8ZOJSiOGRufhS4X5tkkADQDoZpI4
+dcD2mmGuJuBPXEssBVSDtBLEwT/eSFSpdFt3FQ8b8iHjKQu2O8lmbnYy0YaL5x+1
+w8ZXNd0ofElAOkXG/f4VV2l0EQnQXFVgI9OgZNC4EdJrxZsbQDcPBWvf3rGI2x6K
+sjaeKFE0+Rzi47D53xIaOl6OtUVMZNxw9ifRA8JVq50lSRPs0O6sK0bozFERUCWU
+otFe7ftHTr26tgpyrE5g1DiwWCVG/x+yBCvSP7XL/p8/wmtoEjYKvmbeyYCrFFWS
+Ci/BHlu7qXHaksr87VlzcGqdqv9GEu2g27H99ATE1qphTNzX1fomBpMGXDtEVVwy
+a+khEBzGvZrZY36ut2aGNGs/u2PtOQ6eBA==
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/certificates/test_server.der.c b/test/regression/interoperability_test/certificates/test_server.der.c
new file mode 100644
index 00000000..0cbd741b
--- /dev/null
+++ b/test/regression/interoperability_test/certificates/test_server.der.c
@@ -0,0 +1,98 @@
+unsigned char test_server_der[] = {
+ 0x30, 0x82, 0x05, 0xe5, 0x30, 0x82, 0x03, 0xcd, 0xa0, 0x03, 0x02, 0x01, 0x02, 0x02, 0x01, 0x07,
+ 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05, 0x00, 0x30,
+ 0x81, 0x89, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31,
+ 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x0a, 0x43, 0x61, 0x6c, 0x69, 0x66, 0x6f,
+ 0x72, 0x6e, 0x69, 0x61, 0x31, 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x07, 0x0c, 0x0d, 0x53,
+ 0x61, 0x6e, 0x20, 0x46, 0x72, 0x61, 0x6e, 0x63, 0x69, 0x73, 0x63, 0x6f, 0x31, 0x10, 0x30, 0x0e,
+ 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x07, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x31, 0x13,
+ 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x0b, 0x0c, 0x0a, 0x4f, 0x70, 0x65, 0x72, 0x61, 0x74, 0x69,
+ 0x6f, 0x6e, 0x73, 0x31, 0x26, 0x30, 0x24, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c, 0x1d, 0x45, 0x4c,
+ 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74,
+ 0x65, 0x20, 0x41, 0x75, 0x74, 0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x30, 0x1e, 0x17, 0x0d, 0x31,
+ 0x38, 0x30, 0x36, 0x30, 0x35, 0x30, 0x37, 0x31, 0x37, 0x31, 0x38, 0x5a, 0x17, 0x0d, 0x32, 0x38,
+ 0x30, 0x36, 0x30, 0x32, 0x30, 0x37, 0x31, 0x37, 0x31, 0x38, 0x5a, 0x30, 0x81, 0x82, 0x31, 0x0b,
+ 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31, 0x13, 0x30, 0x11, 0x06,
+ 0x03, 0x55, 0x04, 0x08, 0x13, 0x0a, 0x43, 0x61, 0x6c, 0x69, 0x66, 0x6f, 0x72, 0x6e, 0x69, 0x61,
+ 0x31, 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x07, 0x13, 0x0d, 0x53, 0x61, 0x6e, 0x20, 0x46,
+ 0x72, 0x61, 0x6e, 0x63, 0x69, 0x73, 0x63, 0x6f, 0x31, 0x0f, 0x30, 0x0d, 0x06, 0x03, 0x55, 0x04,
+ 0x0a, 0x13, 0x06, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63, 0x31, 0x19, 0x30, 0x17, 0x06, 0x09, 0x2a,
+ 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x09, 0x01, 0x16, 0x0a, 0x4f, 0x70, 0x65, 0x72, 0x61, 0x74,
+ 0x69, 0x6f, 0x6e, 0x73, 0x31, 0x1a, 0x30, 0x18, 0x06, 0x03, 0x55, 0x04, 0x03, 0x14, 0x11, 0x74,
+ 0x65, 0x73, 0x74, 0x5f, 0x73, 0x65, 0x72, 0x76, 0x65, 0x72, 0x2e, 0x6c, 0x6f, 0x63, 0x61, 0x6c,
+ 0x30, 0x82, 0x01, 0x22, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01,
+ 0x01, 0x05, 0x00, 0x03, 0x82, 0x01, 0x0f, 0x00, 0x30, 0x82, 0x01, 0x0a, 0x02, 0x82, 0x01, 0x01,
+ 0x00, 0xd0, 0x6a, 0x52, 0x6e, 0xe6, 0x36, 0x44, 0x08, 0x62, 0x8c, 0xbb, 0xfe, 0xa2, 0xcf, 0xa6,
+ 0xd2, 0x80, 0xd7, 0x56, 0x88, 0x43, 0xfb, 0x48, 0xeb, 0xfe, 0x53, 0x92, 0xbf, 0xee, 0x6a, 0xa2,
+ 0x44, 0x3c, 0x69, 0xfa, 0x9e, 0x2f, 0x44, 0x0d, 0x98, 0x2e, 0x2f, 0x72, 0x64, 0xf7, 0x86, 0xfe,
+ 0x4c, 0x18, 0x1a, 0x99, 0xcb, 0x85, 0xc9, 0xb7, 0x66, 0x9e, 0xc8, 0xfb, 0x33, 0xed, 0x6f, 0x32,
+ 0x87, 0x96, 0xae, 0xb1, 0x62, 0x11, 0xed, 0x30, 0xf4, 0x87, 0xf2, 0x32, 0x46, 0x21, 0x00, 0x25,
+ 0x97, 0xff, 0xf7, 0xf8, 0x71, 0xbb, 0x7e, 0x84, 0xf2, 0xd6, 0x1a, 0x5b, 0xd7, 0x57, 0xa0, 0x1e,
+ 0xf8, 0x8e, 0xe0, 0x04, 0xe6, 0x71, 0xa4, 0xcd, 0xd0, 0xe1, 0x8c, 0x0d, 0x3d, 0xd9, 0x20, 0x7c,
+ 0x2c, 0x56, 0xde, 0x02, 0xec, 0xdb, 0x3f, 0x4e, 0x4a, 0x77, 0xdf, 0x23, 0xa4, 0xc1, 0x8c, 0x0b,
+ 0x03, 0x46, 0x21, 0x76, 0x4c, 0x85, 0x2c, 0x55, 0xa7, 0x6d, 0x05, 0x2d, 0x0f, 0x91, 0x94, 0xc3,
+ 0x60, 0xfc, 0x1d, 0xd5, 0xd6, 0x94, 0x19, 0x0b, 0x22, 0xb0, 0x5b, 0xc0, 0x94, 0x16, 0x66, 0x2c,
+ 0xe4, 0x7a, 0x5c, 0x11, 0xad, 0x7d, 0x40, 0xb1, 0x84, 0x78, 0x04, 0xb1, 0xa6, 0x1c, 0x73, 0xaa,
+ 0xb5, 0xfa, 0xcd, 0x18, 0xa5, 0x50, 0xfe, 0xb9, 0xab, 0xb0, 0x7d, 0xce, 0x0d, 0x49, 0x46, 0x57,
+ 0x65, 0x53, 0x4c, 0xec, 0x55, 0xe1, 0xc5, 0x05, 0x95, 0xbd, 0x52, 0x7e, 0xf1, 0x0c, 0xad, 0x84,
+ 0x24, 0xd9, 0xce, 0xc8, 0x8e, 0x47, 0x57, 0x00, 0xaf, 0x03, 0x8b, 0x31, 0x28, 0x3e, 0xbc, 0xc4,
+ 0x6c, 0x14, 0x79, 0xc2, 0x87, 0x63, 0xd8, 0x89, 0xdc, 0x35, 0x1f, 0x8f, 0x55, 0x62, 0xf0, 0xa8,
+ 0x8e, 0xdd, 0x82, 0xf0, 0x6b, 0x90, 0x02, 0xc8, 0x8f, 0x80, 0x1a, 0x82, 0xb4, 0x82, 0xd3, 0x4b,
+ 0xf9, 0x02, 0x03, 0x01, 0x00, 0x01, 0xa3, 0x82, 0x01, 0x5b, 0x30, 0x82, 0x01, 0x57, 0x30, 0x09,
+ 0x06, 0x03, 0x55, 0x1d, 0x13, 0x04, 0x02, 0x30, 0x00, 0x30, 0x11, 0x06, 0x09, 0x60, 0x86, 0x48,
+ 0x01, 0x86, 0xf8, 0x42, 0x01, 0x01, 0x04, 0x04, 0x03, 0x02, 0x06, 0x40, 0x30, 0x33, 0x06, 0x09,
+ 0x60, 0x86, 0x48, 0x01, 0x86, 0xf8, 0x42, 0x01, 0x0d, 0x04, 0x26, 0x16, 0x24, 0x4f, 0x70, 0x65,
+ 0x6e, 0x53, 0x53, 0x4c, 0x20, 0x47, 0x65, 0x6e, 0x65, 0x72, 0x61, 0x74, 0x65, 0x64, 0x20, 0x53,
+ 0x65, 0x72, 0x76, 0x65, 0x72, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74,
+ 0x65, 0x30, 0x1d, 0x06, 0x03, 0x55, 0x1d, 0x0e, 0x04, 0x16, 0x04, 0x14, 0x36, 0x20, 0xd3, 0x52,
+ 0xa2, 0x16, 0x07, 0x94, 0x04, 0xb5, 0x37, 0xb6, 0xab, 0x53, 0xa5, 0xf3, 0xe9, 0x25, 0xcb, 0x3a,
+ 0x30, 0x81, 0xb6, 0x06, 0x03, 0x55, 0x1d, 0x23, 0x04, 0x81, 0xae, 0x30, 0x81, 0xab, 0x80, 0x14,
+ 0x2d, 0x7c, 0x48, 0x9c, 0x8b, 0x54, 0x14, 0x21, 0x3f, 0xe2, 0x75, 0xa5, 0x99, 0x8a, 0x77, 0x64,
+ 0xdf, 0x2b, 0xd6, 0x88, 0xa1, 0x81, 0x8f, 0xa4, 0x81, 0x8c, 0x30, 0x81, 0x89, 0x31, 0x0b, 0x30,
+ 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03,
+ 0x55, 0x04, 0x08, 0x0c, 0x0a, 0x43, 0x61, 0x6c, 0x69, 0x66, 0x6f, 0x72, 0x6e, 0x69, 0x61, 0x31,
+ 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x07, 0x0c, 0x0d, 0x53, 0x61, 0x6e, 0x20, 0x46, 0x72,
+ 0x61, 0x6e, 0x63, 0x69, 0x73, 0x63, 0x6f, 0x31, 0x10, 0x30, 0x0e, 0x06, 0x03, 0x55, 0x04, 0x0a,
+ 0x0c, 0x07, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55,
+ 0x04, 0x0b, 0x0c, 0x0a, 0x4f, 0x70, 0x65, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x31, 0x26,
+ 0x30, 0x24, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c, 0x1d, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63, 0x2e,
+ 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74, 0x65, 0x20, 0x41, 0x75, 0x74,
+ 0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x82, 0x01, 0x01, 0x30, 0x1d, 0x06, 0x03, 0x55, 0x1d, 0x25,
+ 0x04, 0x16, 0x30, 0x14, 0x06, 0x08, 0x2b, 0x06, 0x01, 0x05, 0x05, 0x07, 0x03, 0x01, 0x06, 0x08,
+ 0x2b, 0x06, 0x01, 0x05, 0x05, 0x08, 0x02, 0x02, 0x30, 0x0b, 0x06, 0x03, 0x55, 0x1d, 0x0f, 0x04,
+ 0x04, 0x03, 0x02, 0x05, 0xa0, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01,
+ 0x01, 0x0b, 0x05, 0x00, 0x03, 0x82, 0x02, 0x01, 0x00, 0xbe, 0x9f, 0x3c, 0x88, 0xdc, 0x8a, 0xc3,
+ 0xdc, 0x5a, 0xbe, 0x68, 0x5b, 0xea, 0xac, 0x2a, 0x83, 0x6d, 0xb9, 0xd0, 0xb0, 0x7b, 0x19, 0x5a,
+ 0xef, 0x09, 0x46, 0x3b, 0x6e, 0x58, 0xeb, 0xec, 0x08, 0x0b, 0xc8, 0x7b, 0x94, 0x5d, 0xab, 0x67,
+ 0x03, 0x6c, 0x8a, 0x35, 0x18, 0x4d, 0x2a, 0x1f, 0x8d, 0xa2, 0x78, 0xae, 0x89, 0x90, 0x78, 0x49,
+ 0x9a, 0xeb, 0xac, 0xba, 0x44, 0x4c, 0xea, 0xe0, 0x67, 0xb7, 0xfb, 0xbc, 0x43, 0xd7, 0xbe, 0x1c,
+ 0xe3, 0xa8, 0x43, 0x2b, 0x1e, 0xc0, 0xc9, 0x88, 0xa9, 0x2b, 0x5c, 0x10, 0xe8, 0x4f, 0x23, 0x96,
+ 0x40, 0x7a, 0x41, 0x1f, 0xa0, 0x71, 0x6f, 0x5c, 0xaf, 0x65, 0xf1, 0x9f, 0x61, 0xc5, 0x21, 0xbb,
+ 0x05, 0x7f, 0x89, 0x72, 0x55, 0x9a, 0x71, 0x37, 0x45, 0x36, 0xe4, 0x75, 0x67, 0xf8, 0x5b, 0x3c,
+ 0x6c, 0x7b, 0xf0, 0x5d, 0x23, 0xc6, 0x46, 0x2d, 0x64, 0x27, 0x58, 0x26, 0xc5, 0x54, 0xc9, 0x86,
+ 0x75, 0x76, 0x95, 0xf4, 0xf7, 0x64, 0xe1, 0x1b, 0x7a, 0x6b, 0xf5, 0x52, 0x8e, 0x05, 0x93, 0xf9,
+ 0x9d, 0x50, 0x95, 0xd1, 0xaf, 0x7d, 0xfd, 0x89, 0x7d, 0x30, 0xbe, 0xd7, 0x16, 0xb7, 0xb0, 0x3b,
+ 0x03, 0xe3, 0xfe, 0x64, 0x57, 0x1e, 0x70, 0x9f, 0x54, 0xa4, 0xd5, 0x75, 0x45, 0xad, 0x34, 0x5f,
+ 0x86, 0xbb, 0xb9, 0x20, 0x01, 0x9a, 0xd7, 0xc8, 0x9d, 0xb4, 0xc2, 0x70, 0xd3, 0x7e, 0x06, 0xd4,
+ 0x60, 0xfd, 0x3e, 0x67, 0xd6, 0x91, 0x25, 0xc8, 0x1f, 0x43, 0x0a, 0xcc, 0x3f, 0x68, 0xfc, 0x68,
+ 0xe2, 0xf8, 0xf8, 0xe8, 0xc3, 0xae, 0xcb, 0x9a, 0xbb, 0x68, 0x65, 0xf1, 0x93, 0x89, 0x4a, 0x23,
+ 0x86, 0x46, 0xe7, 0xe1, 0x4b, 0x85, 0xf9, 0xb6, 0x49, 0x00, 0x0d, 0x00, 0xe8, 0x66, 0x92, 0x38,
+ 0x75, 0xc0, 0xf6, 0x9a, 0x61, 0xae, 0x26, 0xe0, 0x4f, 0x5c, 0x4b, 0x2c, 0x05, 0x54, 0x83, 0xb4,
+ 0x12, 0xc4, 0xc1, 0x3f, 0xde, 0x48, 0x54, 0xa9, 0x74, 0x5b, 0x77, 0x15, 0x0f, 0x1b, 0xf2, 0x21,
+ 0xe3, 0x29, 0x0b, 0xb6, 0x3b, 0xc9, 0x66, 0x6e, 0x76, 0x32, 0xd1, 0x86, 0x8b, 0xe7, 0x1f, 0xb5,
+ 0xc3, 0xc6, 0x57, 0x35, 0xdd, 0x28, 0x7c, 0x49, 0x40, 0x3a, 0x45, 0xc6, 0xfd, 0xfe, 0x15, 0x57,
+ 0x69, 0x74, 0x11, 0x09, 0xd0, 0x5c, 0x55, 0x60, 0x23, 0xd3, 0xa0, 0x64, 0xd0, 0xb8, 0x11, 0xd2,
+ 0x6b, 0xc5, 0x9b, 0x1b, 0x40, 0x37, 0x0f, 0x05, 0x6b, 0xdf, 0xde, 0xb1, 0x88, 0xdb, 0x1e, 0x8a,
+ 0xb2, 0x36, 0x9e, 0x28, 0x51, 0x34, 0xf9, 0x1c, 0xe2, 0xe3, 0xb0, 0xf9, 0xdf, 0x12, 0x1a, 0x3a,
+ 0x5e, 0x8e, 0xb5, 0x45, 0x4c, 0x64, 0xdc, 0x70, 0xf6, 0x27, 0xd1, 0x03, 0xc2, 0x55, 0xab, 0x9d,
+ 0x25, 0x49, 0x13, 0xec, 0xd0, 0xee, 0xac, 0x2b, 0x46, 0xe8, 0xcc, 0x51, 0x11, 0x50, 0x25, 0x94,
+ 0xa2, 0xd1, 0x5e, 0xed, 0xfb, 0x47, 0x4e, 0xbd, 0xba, 0xb6, 0x0a, 0x72, 0xac, 0x4e, 0x60, 0xd4,
+ 0x38, 0xb0, 0x58, 0x25, 0x46, 0xff, 0x1f, 0xb2, 0x04, 0x2b, 0xd2, 0x3f, 0xb5, 0xcb, 0xfe, 0x9f,
+ 0x3f, 0xc2, 0x6b, 0x68, 0x12, 0x36, 0x0a, 0xbe, 0x66, 0xde, 0xc9, 0x80, 0xab, 0x14, 0x55, 0x92,
+ 0x0a, 0x2f, 0xc1, 0x1e, 0x5b, 0xbb, 0xa9, 0x71, 0xda, 0x92, 0xca, 0xfc, 0xed, 0x59, 0x73, 0x70,
+ 0x6a, 0x9d, 0xaa, 0xff, 0x46, 0x12, 0xed, 0xa0, 0xdb, 0xb1, 0xfd, 0xf4, 0x04, 0xc4, 0xd6, 0xaa,
+ 0x61, 0x4c, 0xdc, 0xd7, 0xd5, 0xfa, 0x26, 0x06, 0x93, 0x06, 0x5c, 0x3b, 0x44, 0x55, 0x5c, 0x32,
+ 0x6b, 0xe9, 0x21, 0x10, 0x1c, 0xc6, 0xbd, 0x9a, 0xd9, 0x63, 0x7e, 0xae, 0xb7, 0x66, 0x86, 0x34,
+ 0x6b, 0x3f, 0xbb, 0x63, 0xed, 0x39, 0x0e, 0x9e, 0x04
+};
+unsigned int test_server_der_len = 1513;
diff --git a/test/regression/interoperability_test/certificates/test_server.key b/test/regression/interoperability_test/certificates/test_server.key
new file mode 100644
index 00000000..c9c06366
--- /dev/null
+++ b/test/regression/interoperability_test/certificates/test_server.key
@@ -0,0 +1,28 @@
+-----BEGIN PRIVATE KEY-----
+MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDQalJu5jZECGKM
+u/6iz6bSgNdWiEP7SOv+U5K/7mqiRDxp+p4vRA2YLi9yZPeG/kwYGpnLhcm3Zp7I
++zPtbzKHlq6xYhHtMPSH8jJGIQAll//3+HG7foTy1hpb11egHviO4ATmcaTN0OGM
+DT3ZIHwsVt4C7Ns/Tkp33yOkwYwLA0YhdkyFLFWnbQUtD5GUw2D8HdXWlBkLIrBb
+wJQWZizkelwRrX1AsYR4BLGmHHOqtfrNGKVQ/rmrsH3ODUlGV2VTTOxV4cUFlb1S
+fvEMrYQk2c7IjkdXAK8DizEoPrzEbBR5wodj2IncNR+PVWLwqI7dgvBrkALIj4Aa
+grSC00v5AgMBAAECggEBAL8aTr3rj6SwP5UmKGWnnCL3Cv0Ic7Vtdx88CJq/Bb4G
+bZMLv5I9h22cI9tz41g/wwxzD8SDx6PIkB5f4Ix9YsrbCxIRh7iDJCWnmhud1OGj
+z4zTnY27hDKayY6fFXT4ERgJJ9UaLXCfcMEXvzdhxxptCKOMBbm1kyj5TVicNEo/
+Las8TSGEp1vzkB3OE2MpR9/+jpuVkZ5zt/j5GEOeECGzs3xUmTBZ0AA3EX8TLQzs
+tmQc0jl125tKc7hkrwETiblp1AIoqq458FeFgBwu5ex5LRyAEi9rQ9+Mlcy5jTsp
+7jtB2m+wUaD7XZoF9EYbtGX29m/60z1HXbFo0QQIWaUCgYEA58k9XNsBHMMuVwdC
+7iZvxpTV5Dg6I8aEVDBbcU74VYVtTQZCOADtCltjj5NKCjJW/UNuSv9/GZrhmbaB
+nFOam1FTkA0S1U7hji4D1QReGeInu6e4RH3Im7UrXVGFzcu5TDtJ+h1gVi9KlFyW
+v6vGy+uHk2tn4tDGoi6Gl0BgTvcCgYEA5jARMl6b59u7yzVPN5CtSBXGkUBFeqVy
+ymIHtABlwtJeDOBIAORvnFu98fSbT9HmzMPZNkowG0u+8yS4YzQIjQib4Df4Ph3J
+RfdJW5gNoXcRgqu/UshCAAe4Hr38qhd7HCmHL70vjtKO4bkD57caUOIpqPHsOSLL
+wV0Bo0X2UI8CgYBEJxHZ6bNMB7/qawItEDQxibXSow3FUyu5rXZVvMicLN1UlpCF
+8w+/ydtebgqJMQAO+/LELpfqqXXIQredhZ+iJ6mQY6ez/LupmLIbwmsA5VSVgt1V
+lj6UOhMEH2JefpZ/abd4yYZ4EPO25/qTZSjQ8PIuUJh9QrIFIfUFKDKpRQKBgQC7
+/2P8JGLmsYKly4tAUWwEpKxBMyHLslaXTgsGixCRVii0EXUdLXSuWgs/EkzKmx8J
++6ZqfZreoDV69XGWrAeT0AUm0e9wI/mfqACEyyHOzqVBeK3QmXe1+Jf6m6ZA8N5+
+OLiNV9EAr508Y1P6KoRWrO/jaHpKi82nxiMxS1GJpwKBgDjc2y4yBfWBpwqdCI4J
+DjPSQt2GE+Vf6+XpvRYhbjAOxExArIjaERvWFtM6YQNDAmnwCqihpGYUwixoyENd
+GXVL7k/T/9NnR50asWsdMdSpcewJh8n44jvvbpvSo13LJxzvyyU2AAX+JtftoLF/
+GttK1g6wBlGpkCxacaGpwD+v
+-----END PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/certificates/test_server.key.der.c b/test/regression/interoperability_test/certificates/test_server.key.der.c
new file mode 100644
index 00000000..b8cb7f6d
--- /dev/null
+++ b/test/regression/interoperability_test/certificates/test_server.key.der.c
@@ -0,0 +1,78 @@
+unsigned char test_server_key_der[] = {
+ 0x30, 0x82, 0x04, 0xa4, 0x02, 0x01, 0x00, 0x02, 0x82, 0x01, 0x01, 0x00, 0xd0, 0x6a, 0x52, 0x6e,
+ 0xe6, 0x36, 0x44, 0x08, 0x62, 0x8c, 0xbb, 0xfe, 0xa2, 0xcf, 0xa6, 0xd2, 0x80, 0xd7, 0x56, 0x88,
+ 0x43, 0xfb, 0x48, 0xeb, 0xfe, 0x53, 0x92, 0xbf, 0xee, 0x6a, 0xa2, 0x44, 0x3c, 0x69, 0xfa, 0x9e,
+ 0x2f, 0x44, 0x0d, 0x98, 0x2e, 0x2f, 0x72, 0x64, 0xf7, 0x86, 0xfe, 0x4c, 0x18, 0x1a, 0x99, 0xcb,
+ 0x85, 0xc9, 0xb7, 0x66, 0x9e, 0xc8, 0xfb, 0x33, 0xed, 0x6f, 0x32, 0x87, 0x96, 0xae, 0xb1, 0x62,
+ 0x11, 0xed, 0x30, 0xf4, 0x87, 0xf2, 0x32, 0x46, 0x21, 0x00, 0x25, 0x97, 0xff, 0xf7, 0xf8, 0x71,
+ 0xbb, 0x7e, 0x84, 0xf2, 0xd6, 0x1a, 0x5b, 0xd7, 0x57, 0xa0, 0x1e, 0xf8, 0x8e, 0xe0, 0x04, 0xe6,
+ 0x71, 0xa4, 0xcd, 0xd0, 0xe1, 0x8c, 0x0d, 0x3d, 0xd9, 0x20, 0x7c, 0x2c, 0x56, 0xde, 0x02, 0xec,
+ 0xdb, 0x3f, 0x4e, 0x4a, 0x77, 0xdf, 0x23, 0xa4, 0xc1, 0x8c, 0x0b, 0x03, 0x46, 0x21, 0x76, 0x4c,
+ 0x85, 0x2c, 0x55, 0xa7, 0x6d, 0x05, 0x2d, 0x0f, 0x91, 0x94, 0xc3, 0x60, 0xfc, 0x1d, 0xd5, 0xd6,
+ 0x94, 0x19, 0x0b, 0x22, 0xb0, 0x5b, 0xc0, 0x94, 0x16, 0x66, 0x2c, 0xe4, 0x7a, 0x5c, 0x11, 0xad,
+ 0x7d, 0x40, 0xb1, 0x84, 0x78, 0x04, 0xb1, 0xa6, 0x1c, 0x73, 0xaa, 0xb5, 0xfa, 0xcd, 0x18, 0xa5,
+ 0x50, 0xfe, 0xb9, 0xab, 0xb0, 0x7d, 0xce, 0x0d, 0x49, 0x46, 0x57, 0x65, 0x53, 0x4c, 0xec, 0x55,
+ 0xe1, 0xc5, 0x05, 0x95, 0xbd, 0x52, 0x7e, 0xf1, 0x0c, 0xad, 0x84, 0x24, 0xd9, 0xce, 0xc8, 0x8e,
+ 0x47, 0x57, 0x00, 0xaf, 0x03, 0x8b, 0x31, 0x28, 0x3e, 0xbc, 0xc4, 0x6c, 0x14, 0x79, 0xc2, 0x87,
+ 0x63, 0xd8, 0x89, 0xdc, 0x35, 0x1f, 0x8f, 0x55, 0x62, 0xf0, 0xa8, 0x8e, 0xdd, 0x82, 0xf0, 0x6b,
+ 0x90, 0x02, 0xc8, 0x8f, 0x80, 0x1a, 0x82, 0xb4, 0x82, 0xd3, 0x4b, 0xf9, 0x02, 0x03, 0x01, 0x00,
+ 0x01, 0x02, 0x82, 0x01, 0x01, 0x00, 0xbf, 0x1a, 0x4e, 0xbd, 0xeb, 0x8f, 0xa4, 0xb0, 0x3f, 0x95,
+ 0x26, 0x28, 0x65, 0xa7, 0x9c, 0x22, 0xf7, 0x0a, 0xfd, 0x08, 0x73, 0xb5, 0x6d, 0x77, 0x1f, 0x3c,
+ 0x08, 0x9a, 0xbf, 0x05, 0xbe, 0x06, 0x6d, 0x93, 0x0b, 0xbf, 0x92, 0x3d, 0x87, 0x6d, 0x9c, 0x23,
+ 0xdb, 0x73, 0xe3, 0x58, 0x3f, 0xc3, 0x0c, 0x73, 0x0f, 0xc4, 0x83, 0xc7, 0xa3, 0xc8, 0x90, 0x1e,
+ 0x5f, 0xe0, 0x8c, 0x7d, 0x62, 0xca, 0xdb, 0x0b, 0x12, 0x11, 0x87, 0xb8, 0x83, 0x24, 0x25, 0xa7,
+ 0x9a, 0x1b, 0x9d, 0xd4, 0xe1, 0xa3, 0xcf, 0x8c, 0xd3, 0x9d, 0x8d, 0xbb, 0x84, 0x32, 0x9a, 0xc9,
+ 0x8e, 0x9f, 0x15, 0x74, 0xf8, 0x11, 0x18, 0x09, 0x27, 0xd5, 0x1a, 0x2d, 0x70, 0x9f, 0x70, 0xc1,
+ 0x17, 0xbf, 0x37, 0x61, 0xc7, 0x1a, 0x6d, 0x08, 0xa3, 0x8c, 0x05, 0xb9, 0xb5, 0x93, 0x28, 0xf9,
+ 0x4d, 0x58, 0x9c, 0x34, 0x4a, 0x3f, 0x2d, 0xab, 0x3c, 0x4d, 0x21, 0x84, 0xa7, 0x5b, 0xf3, 0x90,
+ 0x1d, 0xce, 0x13, 0x63, 0x29, 0x47, 0xdf, 0xfe, 0x8e, 0x9b, 0x95, 0x91, 0x9e, 0x73, 0xb7, 0xf8,
+ 0xf9, 0x18, 0x43, 0x9e, 0x10, 0x21, 0xb3, 0xb3, 0x7c, 0x54, 0x99, 0x30, 0x59, 0xd0, 0x00, 0x37,
+ 0x11, 0x7f, 0x13, 0x2d, 0x0c, 0xec, 0xb6, 0x64, 0x1c, 0xd2, 0x39, 0x75, 0xdb, 0x9b, 0x4a, 0x73,
+ 0xb8, 0x64, 0xaf, 0x01, 0x13, 0x89, 0xb9, 0x69, 0xd4, 0x02, 0x28, 0xaa, 0xae, 0x39, 0xf0, 0x57,
+ 0x85, 0x80, 0x1c, 0x2e, 0xe5, 0xec, 0x79, 0x2d, 0x1c, 0x80, 0x12, 0x2f, 0x6b, 0x43, 0xdf, 0x8c,
+ 0x95, 0xcc, 0xb9, 0x8d, 0x3b, 0x29, 0xee, 0x3b, 0x41, 0xda, 0x6f, 0xb0, 0x51, 0xa0, 0xfb, 0x5d,
+ 0x9a, 0x05, 0xf4, 0x46, 0x1b, 0xb4, 0x65, 0xf6, 0xf6, 0x6f, 0xfa, 0xd3, 0x3d, 0x47, 0x5d, 0xb1,
+ 0x68, 0xd1, 0x04, 0x08, 0x59, 0xa5, 0x02, 0x81, 0x81, 0x00, 0xe7, 0xc9, 0x3d, 0x5c, 0xdb, 0x01,
+ 0x1c, 0xc3, 0x2e, 0x57, 0x07, 0x42, 0xee, 0x26, 0x6f, 0xc6, 0x94, 0xd5, 0xe4, 0x38, 0x3a, 0x23,
+ 0xc6, 0x84, 0x54, 0x30, 0x5b, 0x71, 0x4e, 0xf8, 0x55, 0x85, 0x6d, 0x4d, 0x06, 0x42, 0x38, 0x00,
+ 0xed, 0x0a, 0x5b, 0x63, 0x8f, 0x93, 0x4a, 0x0a, 0x32, 0x56, 0xfd, 0x43, 0x6e, 0x4a, 0xff, 0x7f,
+ 0x19, 0x9a, 0xe1, 0x99, 0xb6, 0x81, 0x9c, 0x53, 0x9a, 0x9b, 0x51, 0x53, 0x90, 0x0d, 0x12, 0xd5,
+ 0x4e, 0xe1, 0x8e, 0x2e, 0x03, 0xd5, 0x04, 0x5e, 0x19, 0xe2, 0x27, 0xbb, 0xa7, 0xb8, 0x44, 0x7d,
+ 0xc8, 0x9b, 0xb5, 0x2b, 0x5d, 0x51, 0x85, 0xcd, 0xcb, 0xb9, 0x4c, 0x3b, 0x49, 0xfa, 0x1d, 0x60,
+ 0x56, 0x2f, 0x4a, 0x94, 0x5c, 0x96, 0xbf, 0xab, 0xc6, 0xcb, 0xeb, 0x87, 0x93, 0x6b, 0x67, 0xe2,
+ 0xd0, 0xc6, 0xa2, 0x2e, 0x86, 0x97, 0x40, 0x60, 0x4e, 0xf7, 0x02, 0x81, 0x81, 0x00, 0xe6, 0x30,
+ 0x11, 0x32, 0x5e, 0x9b, 0xe7, 0xdb, 0xbb, 0xcb, 0x35, 0x4f, 0x37, 0x90, 0xad, 0x48, 0x15, 0xc6,
+ 0x91, 0x40, 0x45, 0x7a, 0xa5, 0x72, 0xca, 0x62, 0x07, 0xb4, 0x00, 0x65, 0xc2, 0xd2, 0x5e, 0x0c,
+ 0xe0, 0x48, 0x00, 0xe4, 0x6f, 0x9c, 0x5b, 0xbd, 0xf1, 0xf4, 0x9b, 0x4f, 0xd1, 0xe6, 0xcc, 0xc3,
+ 0xd9, 0x36, 0x4a, 0x30, 0x1b, 0x4b, 0xbe, 0xf3, 0x24, 0xb8, 0x63, 0x34, 0x08, 0x8d, 0x08, 0x9b,
+ 0xe0, 0x37, 0xf8, 0x3e, 0x1d, 0xc9, 0x45, 0xf7, 0x49, 0x5b, 0x98, 0x0d, 0xa1, 0x77, 0x11, 0x82,
+ 0xab, 0xbf, 0x52, 0xc8, 0x42, 0x00, 0x07, 0xb8, 0x1e, 0xbd, 0xfc, 0xaa, 0x17, 0x7b, 0x1c, 0x29,
+ 0x87, 0x2f, 0xbd, 0x2f, 0x8e, 0xd2, 0x8e, 0xe1, 0xb9, 0x03, 0xe7, 0xb7, 0x1a, 0x50, 0xe2, 0x29,
+ 0xa8, 0xf1, 0xec, 0x39, 0x22, 0xcb, 0xc1, 0x5d, 0x01, 0xa3, 0x45, 0xf6, 0x50, 0x8f, 0x02, 0x81,
+ 0x80, 0x44, 0x27, 0x11, 0xd9, 0xe9, 0xb3, 0x4c, 0x07, 0xbf, 0xea, 0x6b, 0x02, 0x2d, 0x10, 0x34,
+ 0x31, 0x89, 0xb5, 0xd2, 0xa3, 0x0d, 0xc5, 0x53, 0x2b, 0xb9, 0xad, 0x76, 0x55, 0xbc, 0xc8, 0x9c,
+ 0x2c, 0xdd, 0x54, 0x96, 0x90, 0x85, 0xf3, 0x0f, 0xbf, 0xc9, 0xdb, 0x5e, 0x6e, 0x0a, 0x89, 0x31,
+ 0x00, 0x0e, 0xfb, 0xf2, 0xc4, 0x2e, 0x97, 0xea, 0xa9, 0x75, 0xc8, 0x42, 0xb7, 0x9d, 0x85, 0x9f,
+ 0xa2, 0x27, 0xa9, 0x90, 0x63, 0xa7, 0xb3, 0xfc, 0xbb, 0xa9, 0x98, 0xb2, 0x1b, 0xc2, 0x6b, 0x00,
+ 0xe5, 0x54, 0x95, 0x82, 0xdd, 0x55, 0x96, 0x3e, 0x94, 0x3a, 0x13, 0x04, 0x1f, 0x62, 0x5e, 0x7e,
+ 0x96, 0x7f, 0x69, 0xb7, 0x78, 0xc9, 0x86, 0x78, 0x10, 0xf3, 0xb6, 0xe7, 0xfa, 0x93, 0x65, 0x28,
+ 0xd0, 0xf0, 0xf2, 0x2e, 0x50, 0x98, 0x7d, 0x42, 0xb2, 0x05, 0x21, 0xf5, 0x05, 0x28, 0x32, 0xa9,
+ 0x45, 0x02, 0x81, 0x81, 0x00, 0xbb, 0xff, 0x63, 0xfc, 0x24, 0x62, 0xe6, 0xb1, 0x82, 0xa5, 0xcb,
+ 0x8b, 0x40, 0x51, 0x6c, 0x04, 0xa4, 0xac, 0x41, 0x33, 0x21, 0xcb, 0xb2, 0x56, 0x97, 0x4e, 0x0b,
+ 0x06, 0x8b, 0x10, 0x91, 0x56, 0x28, 0xb4, 0x11, 0x75, 0x1d, 0x2d, 0x74, 0xae, 0x5a, 0x0b, 0x3f,
+ 0x12, 0x4c, 0xca, 0x9b, 0x1f, 0x09, 0xfb, 0xa6, 0x6a, 0x7d, 0x9a, 0xde, 0xa0, 0x35, 0x7a, 0xf5,
+ 0x71, 0x96, 0xac, 0x07, 0x93, 0xd0, 0x05, 0x26, 0xd1, 0xef, 0x70, 0x23, 0xf9, 0x9f, 0xa8, 0x00,
+ 0x84, 0xcb, 0x21, 0xce, 0xce, 0xa5, 0x41, 0x78, 0xad, 0xd0, 0x99, 0x77, 0xb5, 0xf8, 0x97, 0xfa,
+ 0x9b, 0xa6, 0x40, 0xf0, 0xde, 0x7e, 0x38, 0xb8, 0x8d, 0x57, 0xd1, 0x00, 0xaf, 0x9d, 0x3c, 0x63,
+ 0x53, 0xfa, 0x2a, 0x84, 0x56, 0xac, 0xef, 0xe3, 0x68, 0x7a, 0x4a, 0x8b, 0xcd, 0xa7, 0xc6, 0x23,
+ 0x31, 0x4b, 0x51, 0x89, 0xa7, 0x02, 0x81, 0x80, 0x38, 0xdc, 0xdb, 0x2e, 0x32, 0x05, 0xf5, 0x81,
+ 0xa7, 0x0a, 0x9d, 0x08, 0x8e, 0x09, 0x0e, 0x33, 0xd2, 0x42, 0xdd, 0x86, 0x13, 0xe5, 0x5f, 0xeb,
+ 0xe5, 0xe9, 0xbd, 0x16, 0x21, 0x6e, 0x30, 0x0e, 0xc4, 0x4c, 0x40, 0xac, 0x88, 0xda, 0x11, 0x1b,
+ 0xd6, 0x16, 0xd3, 0x3a, 0x61, 0x03, 0x43, 0x02, 0x69, 0xf0, 0x0a, 0xa8, 0xa1, 0xa4, 0x66, 0x14,
+ 0xc2, 0x2c, 0x68, 0xc8, 0x43, 0x5d, 0x19, 0x75, 0x4b, 0xee, 0x4f, 0xd3, 0xff, 0xd3, 0x67, 0x47,
+ 0x9d, 0x1a, 0xb1, 0x6b, 0x1d, 0x31, 0xd4, 0xa9, 0x71, 0xec, 0x09, 0x87, 0xc9, 0xf8, 0xe2, 0x3b,
+ 0xef, 0x6e, 0x9b, 0xd2, 0xa3, 0x5d, 0xcb, 0x27, 0x1c, 0xef, 0xcb, 0x25, 0x36, 0x00, 0x05, 0xfe,
+ 0x26, 0xd7, 0xed, 0xa0, 0xb1, 0x7f, 0x1a, 0xdb, 0x4a, 0xd6, 0x0e, 0xb0, 0x06, 0x51, 0xa9, 0x90,
+ 0x2c, 0x5a, 0x71, 0xa1, 0xa9, 0xc0, 0x3f, 0xaf
+};
+unsigned int test_server_key_der_len = 1192;
diff --git a/test/regression/interoperability_test/ecc_certificates/ECCA.crt b/test/regression/interoperability_test/ecc_certificates/ECCA.crt
new file mode 100644
index 00000000..1238bb01
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECCA.crt
@@ -0,0 +1,19 @@
+-----BEGIN CERTIFICATE-----
+MIIDHDCCAgQCCQDT07SfslME9zANBgkqhkiG9w0BAQsFADBQMQswCQYDVQQGEwJD
+TjELMAkGA1UECAwCU0gxCzAJBgNVBAcMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UE
+CwwCRUwxDTALBgNVBAMMBEVDQ0EwHhcNMTgwNTE2MDE0MzI0WhcNMTgwNjE1MDE0
+MzI0WjBQMQswCQYDVQQGEwJDTjELMAkGA1UECAwCU0gxCzAJBgNVBAcMAlNIMQsw
+CQYDVQQKDAJFTDELMAkGA1UECwwCRUwxDTALBgNVBAMMBEVDQ0EwggEiMA0GCSqG
+SIb3DQEBAQUAA4IBDwAwggEKAoIBAQDoWEB9hpWYWrCaKSzVj/PHmijuYKI5rshW
+hNg5vaBoOr9Lz+cK+X+dxXvykRJVOziYeZSOPGyhlLX530zGNQgA1JokuP2t8GO6
++X2D6kSHa5caA6Q+5wFHd38MwrizCm0SNIzzrWkJiqvQ2CNo/4ON6l3FOSFxwIqL
+CNeLAqwViHhj1gcBnbOzVdhbklU3bsO/0jARvLsUyisVGvitIVhryEbqJRaCLVJn
+ROgpqw6vgdmJjmWQh9qL8AtrGEHHV0dOjeqo9W3CIYY6V4i8mu01iVQr9/HUZeWS
+63aT//1N9l9uk6gNH02Aa4VsDMKvHYoG96Zyl4FLCrqFJ83yNYstAgMBAAEwDQYJ
+KoZIhvcNAQELBQADggEBAI62ZR93k2f2zuo7TZpWVASzq34rwcwE2dVTtZLlysik
+cCMVc1+N2rozLEqOXgHxjiQd85kZjtcdPpgiBUoxoQHmeY0rctxficvYVD56TG1v
+QSCfPTGyz8wEXJaipc/5zdhoQzpjIe94NVdI/7JuSa8ucuTmOWaNZXbk67HU6B42
+nsv9gkSrAEducYSPKkUB0Z/d0Ma4XWq9+RUPs6DyErW4Xkg54oTbDcevTotzbehU
+JscYics/y6561S7wR+xO4loAWxqsw06hYbmrjtJoDfHIPT6sqATWAw1AOuqI+hTl
++ewwPfxdxXeOKBfkZ0kNTvJ+3REujt7oG59dFCCRZU0=
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECCA.key b/test/regression/interoperability_test/ecc_certificates/ECCA.key
new file mode 100644
index 00000000..0a7baafa
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECCA.key
@@ -0,0 +1,15 @@
+-----BEGIN RSA PRIVATE KEY-----
+MIICXQIBAAKBgQChKk3fnfx1ysC5xkuk0WUPq8ryCh982bSeBu80RxSOUAYm42CE
+11FT/NBzwPCjML/gH1viLvOUjN1lMRZBtZS01ohoy+IHIdzQ71eRTOP2KUYNLJCs
+djHQ++qYAYVKQDS5HfRph1ve8mfEpmTRKCc6NnbZ+QROXRUPC3+aeZyjPwIDAQAB
+AoGAYPi8XIWJ5zI03lLzJtubTF+YwCPZKF0x8TfI7BKsyqhZ20JKzANmevuOTWfV
+IsvtV6Rmu+R2SXasq/tqIeVo8KX9yqokFjTeRg81C69Bbgfp15ELZiu/e+CLFOP0
+nNDMXJ86wdDjV8JHHex++M6ExrZu4ZMJB1K9/Su9FyOYHwkCQQDPDQODVuyfuMRi
+tdrEl415ZYQ+dwXI+trqboSTWvrYC/rFruvQ2LD5HWCewUcA24yCBpdhpKJDXBg2
+W+hngw3zAkEAx0Q8Mh8c6s1XjhkkGKrYt7hkPpAEzbP5XA1lpSSZQ5NQWmRSRvCA
+RpDi5kU/XmIWZn3NbH1vlVQhcQYz/2UMhQJBAJoyH+alSq2cpay5sEXuc+7vmnAG
+pelKYNRsIBG5lMxnB4hHP9mWNx4fMcCpQh6yYs7G5+BRAoLVyDZbdhX4tN8CQFRY
+2NYqf1YQl3gpwjLC1rtlzOECm1XrUakabqUpycpl6ARrJLysfs/f8nugYkN0Z6D4
+rWS37+yY0RMDmi0IO/UCQQC2gprRhNdgLWDiSmTMpPTMAGVXEQWs6CpkbrjqvsqY
+bC2ybrUfEZ6+3w3rEO97bFBbBbY08ml3S9kUifG95ysN
+-----END RSA PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECCA2.crt b/test/regression/interoperability_test/ecc_certificates/ECCA2.crt
new file mode 100644
index 00000000..8627814e
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECCA2.crt
@@ -0,0 +1,11 @@
+-----BEGIN CERTIFICATE-----
+MIIBkjCCATgCCQCmfYU0kzbVOzAKBggqhkjOPQQDAjBRMQswCQYDVQQGEwJDTjEL
+MAkGA1UECAwCU0gxCzAJBgNVBAcMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UECwwC
+RUwxDjAMBgNVBAMMBUVDQ0EyMB4XDTE4MDUxNzAxNTAzM1oXDTIyMDUxNjAxNTAz
+M1owUTELMAkGA1UEBhMCQ04xCzAJBgNVBAgMAlNIMQswCQYDVQQHDAJTSDELMAkG
+A1UECgwCRUwxCzAJBgNVBAsMAkVMMQ4wDAYDVQQDDAVFQ0NBMjBZMBMGByqGSM49
+AgEGCCqGSM49AwEHA0IABFkiQxrnR9MiHG2AnjcLy9ZC8D7yYfFw1EDXfozzsqaL
+cPkUAmXx/AMZHAryz1DROAA3lhqD/I7gU2YDlxjIX1swCgYIKoZIzj0EAwIDSAAw
+RQIgYtEzmYYrXBELkvFBtdF1f2AIqlNrB9lViOynFVAMvdQCIQCWicuH8hYVNjfg
+Oni5ZYiHwApYBTOnj+iltuquSXO9rw==
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECCA2.key b/test/regression/interoperability_test/ecc_certificates/ECCA2.key
new file mode 100644
index 00000000..4e28f0c1
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECCA2.key
@@ -0,0 +1,8 @@
+-----BEGIN EC PARAMETERS-----
+BggqhkjOPQMBBw==
+-----END EC PARAMETERS-----
+-----BEGIN EC PRIVATE KEY-----
+MHcCAQEEIKklbj875SRcEBDl+HuuOYbkFfed0IJQn1q0pPiLzohGoAoGCCqGSM49
+AwEHoUQDQgAEWSJDGudH0yIcbYCeNwvL1kLwPvJh8XDUQNd+jPOypotw+RQCZfH8
+AxkcCvLPUNE4ADeWGoP8juBTZgOXGMhfWw==
+-----END EC PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECCA3.crt b/test/regression/interoperability_test/ecc_certificates/ECCA3.crt
new file mode 100644
index 00000000..744868a7
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECCA3.crt
@@ -0,0 +1,14 @@
+-----BEGIN CERTIFICATE-----
+MIICGjCCAXsCCQDYQcwIiEK2TTAKBggqhkjOPQQDAjBRMQswCQYDVQQGEwJDTjEL
+MAkGA1UECAwCU0gxCzAJBgNVBAcMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UECwwC
+RUwxDjAMBgNVBAMMBUVDQ0EzMB4XDTE4MDUxNzA1MTQyMloXDTIyMDUxNjA1MTQy
+MlowUTELMAkGA1UEBhMCQ04xCzAJBgNVBAgMAlNIMQswCQYDVQQHDAJTSDELMAkG
+A1UECgwCRUwxCzAJBgNVBAsMAkVMMQ4wDAYDVQQDDAVFQ0NBMzCBmzAQBgcqhkjO
+PQIBBgUrgQQAIwOBhgAEAETlSfYvYlahfVpzRM39VqfBQAniW+xMbUl84FGXOKfr
+23a2BfCuzzGRGp4Oaow47VhHHe+4qAfdWTXOICOLSZLIAYiI+IFlJzdrXS4IJR6v
+8CT5C6xEfnEIJ3Yioi6twq5bZ3xuU4qRenPRv6vZ6zUvvRgJFHmY31vkia0AGC43
+agTLMAoGCCqGSM49BAMCA4GMADCBiAJCARS93V8AoviXHZz2NzxN5M71MqbCWU2X
+Tk8eo1zS7IEniiC2vpD0PbSEp+bmtu7VcY5lYGmDriJ5p4+dUC/HTXP1AkIBVFvF
+P7uOJZ0AprX77FHt6PIm7WZe9hI+hWHsqNzm5yv40IcCcA294mVvva/VeweHiZsY
+vlVPUUe5NKckYqZ2UkY=
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECCA3.key b/test/regression/interoperability_test/ecc_certificates/ECCA3.key
new file mode 100644
index 00000000..adaf6d2c
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECCA3.key
@@ -0,0 +1,10 @@
+-----BEGIN EC PARAMETERS-----
+BgUrgQQAIw==
+-----END EC PARAMETERS-----
+-----BEGIN EC PRIVATE KEY-----
+MIHcAgEBBEIA49gG/BfHTkRLuMIjPyo10EyjUkiKcTL6Vef7t4K0z1EN1YHa/oV7
+DQNJiDcf0eEhFEEL8qClenXedMFGTQ1ow8egBwYFK4EEACOhgYkDgYYABABE5Un2
+L2JWoX1ac0TN/VanwUAJ4lvsTG1JfOBRlzin69t2tgXwrs8xkRqeDmqMOO1YRx3v
+uKgH3Vk1ziAji0mSyAGIiPiBZSc3a10uCCUer/Ak+QusRH5xCCd2IqIurcKuW2d8
+blOKkXpz0b+r2es1L70YCRR5mN9b5ImtABguN2oEyw==
+-----END EC PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECCA4.crl b/test/regression/interoperability_test/ecc_certificates/ECCA4.crl
new file mode 100644
index 00000000..709ffde6
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECCA4.crl
Binary files differ
diff --git a/test/regression/interoperability_test/ecc_certificates/ECCA4.crt b/test/regression/interoperability_test/ecc_certificates/ECCA4.crt
new file mode 100644
index 00000000..d35b4cf6
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECCA4.crt
@@ -0,0 +1,12 @@
+-----BEGIN CERTIFICATE-----
+MIIBzzCCAVUCCQC8ZNn+apEOwjAKBggqhkjOPQQDAjBRMQswCQYDVQQGEwJDTjEL
+MAkGA1UECAwCU0gxCzAJBgNVBAcMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UECwwC
+RUwxDjAMBgNVBAMMBUVDQ0E0MB4XDTE4MDUxNzA3MTYwOFoXDTIyMDUxNjA3MTYw
+OFowUTELMAkGA1UEBhMCQ04xCzAJBgNVBAgMAlNIMQswCQYDVQQHDAJTSDELMAkG
+A1UECgwCRUwxCzAJBgNVBAsMAkVMMQ4wDAYDVQQDDAVFQ0NBNDB2MBAGByqGSM49
+AgEGBSuBBAAiA2IABMywO780VDHb9BO2H3X8xm8lQ8fhmbHfySyjFGCVVdy8b4eZ
+27vIJP47NCP6eWvhqCO/I3KZ04ZlpqapEK4glocmyi5dB26otrzvhUdxWZsWDW2l
+pTrJZcs03/PGkB7XiDAKBggqhkjOPQQDAgNoADBlAjEAoNCOKf2OyhCfAbz0kv1/
+u512bI5IYPBXIgCZV3nhE+6AY1d5PVMjyxFHfpR4CrjtAjBuJBx4/vs+Tjg2uu1C
+yKmhwFE2S18elVkmj0KSA1l0k5NON9WvcdCWPwkDzFuCPmU=
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECCA4.key b/test/regression/interoperability_test/ecc_certificates/ECCA4.key
new file mode 100644
index 00000000..95c26415
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECCA4.key
@@ -0,0 +1,9 @@
+-----BEGIN EC PARAMETERS-----
+BgUrgQQAIg==
+-----END EC PARAMETERS-----
+-----BEGIN EC PRIVATE KEY-----
+MIGkAgEBBDDNNgkwph5+3BInjICWDt2R2El02jAODs885+neTmmNtF0moEu+RwAB
+c778r9yx81ygBwYFK4EEACKhZANiAATMsDu/NFQx2/QTth91/MZvJUPH4Zmx38ks
+oxRglVXcvG+Hmdu7yCT+OzQj+nlr4agjvyNymdOGZaamqRCuIJaHJsouXQduqLa8
+74VHcVmbFg1tpaU6yWXLNN/zxpAe14g=
+-----END EC PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECIntm.crl b/test/regression/interoperability_test/ecc_certificates/ECIntm.crl
new file mode 100644
index 00000000..82a81f09
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECIntm.crl
Binary files differ
diff --git a/test/regression/interoperability_test/ecc_certificates/ECIntm.crt b/test/regression/interoperability_test/ecc_certificates/ECIntm.crt
new file mode 100644
index 00000000..09c65182
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECIntm.crt
@@ -0,0 +1,54 @@
+Certificate:
+ Data:
+ Version: 3 (0x2)
+ Serial Number: 10 (0xa)
+ Signature Algorithm: ecdsa-with-SHA256
+ Issuer: C=CN, ST=SH, L=SH, O=EL, OU=EL, CN=ECCA4
+ Validity
+ Not Before: Jun 8 01:38:45 2018 GMT
+ Not After : Jun 8 01:38:45 2019 GMT
+ Subject: C=CN, ST=SH, O=EL, OU=EL, CN=ECIntm
+ Subject Public Key Info:
+ Public Key Algorithm: id-ecPublicKey
+ Public-Key: (256 bit)
+ pub:
+ 04:2f:17:12:9b:9a:43:d7:f4:9c:06:f9:a6:e0:94:
+ c1:5c:c9:c7:a6:1c:b5:c8:a1:e9:b4:2a:78:ab:eb:
+ 88:84:c5:7b:98:fa:fa:c9:cd:da:e1:72:5a:9b:d5:
+ 99:5c:a8:7a:ae:8e:0d:f9:e7:8c:90:12:60:d4:53:
+ 5e:30:a2:72:5b
+ ASN1 OID: prime256v1
+ NIST CURVE: P-256
+ X509v3 extensions:
+ X509v3 Authority Key Identifier:
+ DirName:/C=CN/ST=SH/L=SH/O=EL/OU=EL/CN=ECCA4
+ serial:BC:64:D9:FE:6A:91:0E:C2
+
+ X509v3 Basic Constraints:
+ CA:FALSE
+ X509v3 Key Usage:
+ Digital Signature, Certificate Sign, CRL Sign
+ X509v3 Extended Key Usage:
+ TLS Web Server Authentication, TLS Web Client Authentication, Code Signing, E-mail Protection, Time Stamping
+ Signature Algorithm: ecdsa-with-SHA256
+ 30:65:02:30:63:92:28:85:04:b9:a2:bf:58:66:ef:05:0c:bc:
+ 4a:f9:5e:d3:75:86:89:7d:4b:3a:a6:32:e9:7f:a5:13:fc:96:
+ 99:4f:d4:ec:21:e5:bc:55:f6:41:d1:61:ff:bd:ea:e1:02:31:
+ 00:8e:20:3b:a3:6e:a3:ef:dc:d9:5e:f4:43:90:d7:3e:eb:fe:
+ 2d:26:22:08:04:5d:e4:1c:fd:d6:f0:a7:f2:ca:29:fa:f6:35:
+ 7c:f1:8c:5e:65:62:b5:d6:38:19:af:1d:02
+-----BEGIN CERTIFICATE-----
+MIICazCCAfGgAwIBAgIBCjAKBggqhkjOPQQDAjBRMQswCQYDVQQGEwJDTjELMAkG
+A1UECAwCU0gxCzAJBgNVBAcMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UECwwCRUwx
+DjAMBgNVBAMMBUVDQ0E0MB4XDTE4MDYwODAxMzg0NVoXDTE5MDYwODAxMzg0NVow
+RTELMAkGA1UEBhMCQ04xCzAJBgNVBAgMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UE
+CwwCRUwxDzANBgNVBAMMBkVDSW50bTBZMBMGByqGSM49AgEGCCqGSM49AwEHA0IA
+BC8XEpuaQ9f0nAb5puCUwVzJx6Yctcih6bQqeKvriITFe5j6+snN2uFyWpvVmVyo
+eq6ODfnnjJASYNRTXjCiclujgcUwgcIwawYDVR0jBGQwYqFVpFMwUTELMAkGA1UE
+BhMCQ04xCzAJBgNVBAgMAlNIMQswCQYDVQQHDAJTSDELMAkGA1UECgwCRUwxCzAJ
+BgNVBAsMAkVMMQ4wDAYDVQQDDAVFQ0NBNIIJALxk2f5qkQ7CMAkGA1UdEwQCMAAw
+CwYDVR0PBAQDAgGGMDsGA1UdJQQ0MDIGCCsGAQUFBwMBBggrBgEFBQcDAgYIKwYB
+BQUHAwMGCCsGAQUFBwMEBggrBgEFBQcDCDAKBggqhkjOPQQDAgNoADBlAjBjkiiF
+BLmiv1hm7wUMvEr5XtN1hol9SzqmMul/pRP8lplP1Owh5bxV9kHRYf+96uECMQCO
+IDujbqPv3Nle9EOQ1z7r/i0mIggEXeQc/dbwp/LKKfr2NXzxjF5lYrXWOBmvHQI=
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECIntm.key b/test/regression/interoperability_test/ecc_certificates/ECIntm.key
new file mode 100644
index 00000000..0ab025d1
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECIntm.key
@@ -0,0 +1,8 @@
+-----BEGIN EC PARAMETERS-----
+BggqhkjOPQMBBw==
+-----END EC PARAMETERS-----
+-----BEGIN EC PRIVATE KEY-----
+MHcCAQEEILGSO/aUnZaUbiqiQHKY9Xit8TRNzKzM3OIVImZivXiooAoGCCqGSM49
+AwEHoUQDQgAELxcSm5pD1/ScBvmm4JTBXMnHphy1yKHptCp4q+uIhMV7mPr6yc3a
+4XJam9WZXKh6ro4N+eeMkBJg1FNeMKJyWw==
+-----END EC PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECRevoked.crt b/test/regression/interoperability_test/ecc_certificates/ECRevoked.crt
new file mode 100644
index 00000000..0d15fbbf
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECRevoked.crt
@@ -0,0 +1,55 @@
+Certificate:
+ Data:
+ Version: 3 (0x2)
+ Serial Number: 9 (0x9)
+ Signature Algorithm: ecdsa-with-SHA256
+ Issuer: C=CN, ST=SH, L=SH, O=EL, OU=EL, CN=ECCA4
+ Validity
+ Not Before: Jun 7 08:44:21 2018 GMT
+ Not After : Jun 7 08:44:21 2019 GMT
+ Subject: C=CN, ST=SH, O=EL, OU=EL, CN=ECRevoked
+ Subject Public Key Info:
+ Public Key Algorithm: id-ecPublicKey
+ Public-Key: (256 bit)
+ pub:
+ 04:2c:24:bc:a3:e7:a3:69:08:fa:d5:43:ca:52:6c:
+ 13:db:06:78:10:7c:a0:93:51:7b:1b:21:67:84:8c:
+ f0:a1:a6:cb:f7:e7:7e:f1:7a:22:00:d0:ea:cf:35:
+ db:f0:82:9e:4a:d4:a8:b1:77:c9:fc:08:d9:18:26:
+ 4a:f6:70:6e:e7
+ ASN1 OID: prime256v1
+ NIST CURVE: P-256
+ X509v3 extensions:
+ X509v3 Authority Key Identifier:
+ DirName:/C=CN/ST=SH/L=SH/O=EL/OU=EL/CN=ECCA4
+ serial:BC:64:D9:FE:6A:91:0E:C2
+
+ X509v3 Basic Constraints:
+ CA:FALSE
+ X509v3 Key Usage:
+ Digital Signature, Non Repudiation, Key Encipherment, Data Encipherment, Key Agreement
+ X509v3 Extended Key Usage:
+ TLS Web Server Authentication, TLS Web Client Authentication, Code Signing, E-mail Protection, Time Stamping
+ Signature Algorithm: ecdsa-with-SHA256
+ 30:65:02:31:00:bf:ce:c7:53:db:05:65:db:95:fb:9b:3b:05:
+ 2e:aa:3a:a1:51:fb:12:42:c4:15:b7:aa:49:07:5b:38:22:b3:
+ 0c:7f:46:93:ad:18:34:90:cc:2b:bb:fd:b9:9b:37:ba:f3:02:
+ 30:70:ed:a2:60:a6:66:bb:b7:3c:59:79:10:89:44:bd:47:b4:
+ 80:ef:f9:eb:70:37:c8:b5:8f:aa:f5:32:54:29:7f:a9:98:94:
+ ba:48:94:35:25:bf:d1:d8:aa:88:f8:ce:d8
+-----BEGIN CERTIFICATE-----
+MIICbjCCAfSgAwIBAgIBCTAKBggqhkjOPQQDAjBRMQswCQYDVQQGEwJDTjELMAkG
+A1UECAwCU0gxCzAJBgNVBAcMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UECwwCRUwx
+DjAMBgNVBAMMBUVDQ0E0MB4XDTE4MDYwNzA4NDQyMVoXDTE5MDYwNzA4NDQyMVow
+SDELMAkGA1UEBhMCQ04xCzAJBgNVBAgMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UE
+CwwCRUwxEjAQBgNVBAMMCUVDUmV2b2tlZDBZMBMGByqGSM49AgEGCCqGSM49AwEH
+A0IABCwkvKPno2kI+tVDylJsE9sGeBB8oJNRexshZ4SM8KGmy/fnfvF6IgDQ6s81
+2/CCnkrUqLF3yfwI2RgmSvZwbuejgcUwgcIwawYDVR0jBGQwYqFVpFMwUTELMAkG
+A1UEBhMCQ04xCzAJBgNVBAgMAlNIMQswCQYDVQQHDAJTSDELMAkGA1UECgwCRUwx
+CzAJBgNVBAsMAkVMMQ4wDAYDVQQDDAVFQ0NBNIIJALxk2f5qkQ7CMAkGA1UdEwQC
+MAAwCwYDVR0PBAQDAgP4MDsGA1UdJQQ0MDIGCCsGAQUFBwMBBggrBgEFBQcDAgYI
+KwYBBQUHAwMGCCsGAQUFBwMEBggrBgEFBQcDCDAKBggqhkjOPQQDAgNoADBlAjEA
+v87HU9sFZduV+5s7BS6qOqFR+xJCxBW3qkkHWzgiswx/RpOtGDSQzCu7/bmbN7rz
+AjBw7aJgpma7tzxZeRCJRL1HtIDv+etwN8i1j6r1MlQpf6mYlLpIlDUlv9HYqoj4
+ztg=
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECRevoked.key b/test/regression/interoperability_test/ecc_certificates/ECRevoked.key
new file mode 100644
index 00000000..00f67e3b
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECRevoked.key
@@ -0,0 +1,8 @@
+-----BEGIN EC PARAMETERS-----
+BggqhkjOPQMBBw==
+-----END EC PARAMETERS-----
+-----BEGIN EC PRIVATE KEY-----
+MHcCAQEEIAFabAXgSbH/MdgC0UTE82653a9AScQO7VuHFYjLCeKNoAoGCCqGSM49
+AwEHoUQDQgAELCS8o+ejaQj61UPKUmwT2wZ4EHygk1F7GyFnhIzwoabL9+d+8Xoi
+ANDqzzXb8IKeStSosXfJ/AjZGCZK9nBu5w==
+-----END EC PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECRevoked2.crt b/test/regression/interoperability_test/ecc_certificates/ECRevoked2.crt
new file mode 100644
index 00000000..abb0dbd4
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECRevoked2.crt
@@ -0,0 +1,51 @@
+Certificate:
+ Data:
+ Version: 3 (0x2)
+ Serial Number: 11 (0xb)
+ Signature Algorithm: ecdsa-with-SHA256
+ Issuer: C=CN, ST=SH, O=EL, OU=EL, CN=ECIntm
+ Validity
+ Not Before: Jun 8 01:55:11 2018 GMT
+ Not After : Jun 8 01:55:11 2019 GMT
+ Subject: C=CN, ST=SH, O=EL, OU=EL, CN=ECRevoked2
+ Subject Public Key Info:
+ Public Key Algorithm: id-ecPublicKey
+ Public-Key: (256 bit)
+ pub:
+ 04:1f:4a:62:3f:e5:c7:98:df:cb:63:57:08:7c:e3:
+ 7d:2f:68:a9:70:94:4d:f7:d4:79:bf:53:b2:98:3b:
+ 96:22:c2:9a:fd:7c:77:10:13:20:d7:4c:33:c5:47:
+ cd:c8:e0:ea:77:5e:f2:fb:ef:db:f5:eb:fc:ed:91:
+ 72:20:c6:f0:c4
+ ASN1 OID: prime256v1
+ NIST CURVE: P-256
+ X509v3 extensions:
+ X509v3 Authority Key Identifier:
+ DirName:/C=CN/ST=SH/L=SH/O=EL/OU=EL/CN=ECCA4
+ serial:0A
+
+ X509v3 Basic Constraints:
+ CA:FALSE
+ X509v3 Key Usage:
+ Digital Signature, Non Repudiation, Key Encipherment, Data Encipherment, Key Agreement
+ X509v3 Extended Key Usage:
+ TLS Web Server Authentication, TLS Web Client Authentication, Code Signing, E-mail Protection, Time Stamping
+ Signature Algorithm: ecdsa-with-SHA256
+ 30:44:02:20:31:be:74:d3:dd:4f:3d:fe:c6:40:9e:20:ce:07:
+ 5b:c6:18:f1:13:60:f5:00:c9:0c:b3:37:98:59:ec:f3:09:e3:
+ 02:20:4e:61:65:97:08:7f:ee:c4:1d:86:31:95:bc:6e:44:fe:
+ 02:70:35:aa:70:28:a3:3f:8b:d8:a5:4b:1c:eb:de:fa
+-----BEGIN CERTIFICATE-----
+MIICOjCCAeGgAwIBAgIBCzAKBggqhkjOPQQDAjBFMQswCQYDVQQGEwJDTjELMAkG
+A1UECAwCU0gxCzAJBgNVBAoMAkVMMQswCQYDVQQLDAJFTDEPMA0GA1UEAwwGRUNJ
+bnRtMB4XDTE4MDYwODAxNTUxMVoXDTE5MDYwODAxNTUxMVowSTELMAkGA1UEBhMC
+Q04xCzAJBgNVBAgMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UECwwCRUwxEzARBgNV
+BAMMCkVDUmV2b2tlZDIwWTATBgcqhkjOPQIBBggqhkjOPQMBBwNCAAQfSmI/5ceY
+38tjVwh8430vaKlwlE331Hm/U7KYO5Yiwpr9fHcQEyDXTDPFR83I4Op3XvL779v1
+6/ztkXIgxvDEo4G9MIG6MGMGA1UdIwRcMFqhVaRTMFExCzAJBgNVBAYTAkNOMQsw
+CQYDVQQIDAJTSDELMAkGA1UEBwwCU0gxCzAJBgNVBAoMAkVMMQswCQYDVQQLDAJF
+TDEOMAwGA1UEAwwFRUNDQTSCAQowCQYDVR0TBAIwADALBgNVHQ8EBAMCA/gwOwYD
+VR0lBDQwMgYIKwYBBQUHAwEGCCsGAQUFBwMCBggrBgEFBQcDAwYIKwYBBQUHAwQG
+CCsGAQUFBwMIMAoGCCqGSM49BAMCA0cAMEQCIDG+dNPdTz3+xkCeIM4HW8YY8RNg
+9QDJDLM3mFns8wnjAiBOYWWXCH/uxB2GMZW8bkT+AnA1qnAooz+L2KVLHOve+g==
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECRevoked2.key b/test/regression/interoperability_test/ecc_certificates/ECRevoked2.key
new file mode 100644
index 00000000..66b4c12f
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECRevoked2.key
@@ -0,0 +1,8 @@
+-----BEGIN EC PARAMETERS-----
+BggqhkjOPQMBBw==
+-----END EC PARAMETERS-----
+-----BEGIN EC PRIVATE KEY-----
+MHcCAQEEIClcnxBOgq59p4B93dG1xdD/AfAdRC3mHNmlrsKfTdCgoAoGCCqGSM49
+AwEHoUQDQgAEH0piP+XHmN/LY1cIfON9L2ipcJRN99R5v1OymDuWIsKa/Xx3EBMg
+10wzxUfNyODqd17y++/b9ev87ZFyIMbwxA==
+-----END EC PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTest.crt b/test/regression/interoperability_test/ecc_certificates/ECTest.crt
new file mode 100644
index 00000000..47642557
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTest.crt
@@ -0,0 +1,15 @@
+-----BEGIN CERTIFICATE-----
+MIICUzCCATsCCQDbR6w8PgJYQjANBgkqhkiG9w0BAQsFADBQMQswCQYDVQQGEwJD
+TjELMAkGA1UECAwCU0gxCzAJBgNVBAcMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UE
+CwwCRUwxDTALBgNVBAMMBEVDQ0EwHhcNMTgwNTE2MDUyMTQzWhcNMTgwNjE1MDUy
+MTQzWjBSMQswCQYDVQQGEwJDTjELMAkGA1UECAwCU0gxCzAJBgNVBAcMAlNIMQsw
+CQYDVQQKDAJFTDELMAkGA1UECwwCRUwxDzANBgNVBAMMBkVDVGVzdDBZMBMGByqG
+SM49AgEGCCqGSM49AwEHA0IABE3OIgIpH/C/OuVxQmKlCQyS9oJLmLBj0MoGcujH
+ZbbBU4AO7xcua2ZHMNnBVm6CpW8psPeN4P7jySw2blOYmDkwDQYJKoZIhvcNAQEL
+BQADggEBALf62Nc4PL8I1gJvhH/70awzI6cnAXaZkKDSrDpW8kyQvYRmMEyeBz30
+50MNQJKfk4nw0/I+RO7pNxa+1F/lnPNxafST11rr1hyu6MoyDKNgKZNN+SC/CfhQ
+sl1P9OkZ7/dSqYTPmo6S6zgQwOCNPBjzhgyajo3FspPIpfI6Vc++kZbOo6PLy3av
+MfochqUZ0prADqIP3TnZXdbOjJvDbqeYu7LmmAUtfCiktmks4gynJpE1AT3QL6AD
+h8lEzxlD2GxhyN0YUc0w0PAJsJb03nhL2b6LWrfmZnPprCvTO1Ervh5YFU01eVZ6
+WnmaZ2AMPO6dZ12FLBvmxKrsd192nsM=
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTest.key b/test/regression/interoperability_test/ecc_certificates/ECTest.key
new file mode 100644
index 00000000..f716af1c
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTest.key
@@ -0,0 +1,5 @@
+-----BEGIN PRIVATE KEY-----
+MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgXSoW/Yx4CXNcAg+u
+yyW7c+U7IUszgcNxoGKolxLLJQ2hRANCAARNziICKR/wvzrlcUJipQkMkvaCS5iw
+Y9DKBnLox2W2wVOADu8XLmtmRzDZwVZugqVvKbD3jeD+48ksNm5TmJg5
+-----END PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTestClient1.crt b/test/regression/interoperability_test/ecc_certificates/ECTestClient1.crt
new file mode 100644
index 00000000..da296431
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTestClient1.crt
@@ -0,0 +1,89 @@
+Certificate:
+ Data:
+ Version: 3 (0x2)
+ Serial Number: 22 (0x16)
+ Signature Algorithm: ecdsa-with-SHA256
+ Issuer: C=CN, ST=SH, L=SH, O=EL, OU=EL, CN=ECCA4
+ Validity
+ Not Before: Apr 20 02:59:42 2023 GMT
+ Not After : Apr 19 02:59:42 2024 GMT
+ Subject: C=CN, ST=SH, O=EL, CN=ECTestClient1
+ Subject Public Key Info:
+ Public Key Algorithm: id-ecPublicKey
+ Public-Key: (256 bit)
+ pub:
+ 04:67:0b:4d:d1:29:7a:f8:29:41:d8:38:b3:ad:60:
+ b5:d0:39:90:6c:4e:36:41:c3:0c:a6:62:2e:f9:c4:
+ fb:e3:0f:1c:77:7e:30:0f:4f:62:bd:88:ff:43:2d:
+ b7:a4:a4:9a:1a:ba:d3:2f:3a:d3:87:c2:cc:80:62:
+ 76:7c:ff:32:39
+ ASN1 OID: prime256v1
+ NIST CURVE: P-256
+ X509v3 extensions:
+ X509v3 Authority Key Identifier:
+ DirName:/C=CN/ST=SH/L=SH/O=EL/OU=EL/CN=ECCA4
+ serial:BC:64:D9:FE:6A:91:0E:C2
+
+ X509v3 Basic Constraints:
+ CA:FALSE
+ X509v3 Key Usage:
+ Digital Signature, Certificate Sign, CRL Sign
+ X509v3 Extended Key Usage:
+ TLS Web Server Authentication, TLS Web Client Authentication, Code Signing, E-mail Protection, Time Stamping
+ Netscape Comment:
+ longlonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglonglongcomment
+ Signature Algorithm: ecdsa-with-SHA256
+ 30:64:02:30:7c:6c:e7:69:a6:dc:a6:80:fd:24:c4:49:50:fa:
+ 67:a5:c3:83:40:7a:8b:42:8b:c5:98:95:ae:cb:0e:43:83:72:
+ f6:c9:51:f1:71:5c:9c:ab:b1:63:93:fb:1b:eb:19:0d:02:30:
+ 0a:6b:15:18:0a:63:ae:9e:8e:2b:d4:59:a2:e6:1f:2c:c3:fc:
+ 4f:1f:8b:99:b1:0f:78:7c:bf:fd:e6:2f:5a:12:12:60:65:bf:
+ f4:c7:fc:5f:d4:c3:bc:ae:d6:53:6a:6b
+-----BEGIN CERTIFICATE-----
+MIIIhDCCCAugAwIBAgIBFjAKBggqhkjOPQQDAjBRMQswCQYDVQQGEwJDTjELMAkG
+A1UECAwCU0gxCzAJBgNVBAcMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UECwwCRUwx
+DjAMBgNVBAMMBUVDQ0E0MB4XDTIzMDQyMDAyNTk0MloXDTI0MDQxOTAyNTk0Mlow
+PzELMAkGA1UEBhMCQ04xCzAJBgNVBAgMAlNIMQswCQYDVQQKDAJFTDEWMBQGA1UE
+AwwNRUNUZXN0Q2xpZW50MTBZMBMGByqGSM49AgEGCCqGSM49AwEHA0IABGcLTdEp
+evgpQdg4s61gtdA5kGxONkHDDKZiLvnE++MPHHd+MA9PYr2I/0Mtt6Skmhq60y86
+04fCzIBidnz/MjmjggbkMIIG4DBrBgNVHSMEZDBioVWkUzBRMQswCQYDVQQGEwJD
+TjELMAkGA1UECAwCU0gxCzAJBgNVBAcMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UE
+CwwCRUwxDjAMBgNVBAMMBUVDQ0E0ggkAvGTZ/mqRDsIwCQYDVR0TBAIwADALBgNV
+HQ8EBAMCAYYwOwYDVR0lBDQwMgYIKwYBBQUHAwEGCCsGAQUFBwMCBggrBgEFBQcD
+AwYIKwYBBQUHAwQGCCsGAQUFBwMIMIIGGgYJYIZIAYb4QgENBIIGCxaCBgdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25n
+bG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdsb25nbG9uZ2xvbmdjb21t
+ZW50MAoGCCqGSM49BAMCA2cAMGQCMHxs52mm3KaA/STESVD6Z6XDg0B6i0KLxZiV
+rssOQ4Ny9slR8XFcnKuxY5P7G+sZDQIwCmsVGApjrp6OK9RZouYfLMP8Tx+LmbEP
+eHy//eYvWhISYGW/9Mf8X9TDvK7WU2pr
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTestClient1.key b/test/regression/interoperability_test/ecc_certificates/ECTestClient1.key
new file mode 100644
index 00000000..198c5f98
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTestClient1.key
@@ -0,0 +1,8 @@
+-----BEGIN EC PARAMETERS-----
+BggqhkjOPQMBBw==
+-----END EC PARAMETERS-----
+-----BEGIN EC PRIVATE KEY-----
+MHcCAQEEIM3hPa1nQZCk/w1WEzrF5fBbJlgH9kcr0juTavdAhEyboAoGCCqGSM49
+AwEHoUQDQgAEZwtN0Sl6+ClB2DizrWC10DmQbE42QcMMpmIu+cT74w8cd34wD09i
+vYj/Qy23pKSaGrrTLzrTh8LMgGJ2fP8yOQ==
+-----END EC PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTestServer10.crt b/test/regression/interoperability_test/ecc_certificates/ECTestServer10.crt
new file mode 100644
index 00000000..bee9a130
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTestServer10.crt
@@ -0,0 +1,52 @@
+Certificate:
+ Data:
+ Version: 3 (0x2)
+ Serial Number: 12 (0xc)
+ Signature Algorithm: ecdsa-with-SHA1
+ Issuer: C=CN, ST=SH, L=SH, O=EL, OU=EL, CN=ECCA2
+ Validity
+ Not Before: Jun 8 07:58:44 2018 GMT
+ Not After : Jun 8 07:58:44 2019 GMT
+ Subject: C=CN, ST=SH, O=EL, OU=EL, CN=ECTestServer10
+ Subject Public Key Info:
+ Public Key Algorithm: id-ecPublicKey
+ Public-Key: (256 bit)
+ pub:
+ 04:f9:1a:1d:20:7d:9a:66:4e:7e:ba:6b:46:32:c5:
+ 9b:cf:1a:e8:d7:39:53:26:86:b9:86:e9:92:d4:0b:
+ 17:89:fa:9c:91:1b:d4:6c:20:96:a5:c2:50:ad:0c:
+ 23:18:1b:a5:33:93:58:41:15:23:01:c4:e4:99:99:
+ 40:5f:1c:85:18
+ ASN1 OID: prime256v1
+ NIST CURVE: P-256
+ X509v3 extensions:
+ X509v3 Authority Key Identifier:
+ DirName:/C=CN/ST=SH/L=SH/O=EL/OU=EL/CN=ECCA2
+ serial:A6:7D:85:34:93:36:D5:3B
+
+ X509v3 Basic Constraints:
+ CA:FALSE
+ X509v3 Key Usage:
+ Digital Signature, Non Repudiation, Key Encipherment, Data Encipherment, Key Agreement
+ X509v3 Extended Key Usage:
+ TLS Web Server Authentication, TLS Web Client Authentication, Code Signing, E-mail Protection, Time Stamping
+ Signature Algorithm: ecdsa-with-SHA1
+ 30:45:02:21:00:df:12:00:97:b8:c2:d2:68:6f:fd:81:a9:e5:
+ e9:01:b5:4d:c2:50:c3:83:11:f1:7c:96:fc:16:71:30:81:9a:
+ c4:02:20:5d:d9:2d:ed:92:bb:c7:55:ee:bd:df:1b:3e:3b:b8:
+ c7:1a:d9:32:e0:0b:05:f0:56:3b:df:17:70:d3:b9:bb:14
+-----BEGIN CERTIFICATE-----
+MIICUTCCAfigAwIBAgIBDDAJBgcqhkjOPQQBMFExCzAJBgNVBAYTAkNOMQswCQYD
+VQQIDAJTSDELMAkGA1UEBwwCU0gxCzAJBgNVBAoMAkVMMQswCQYDVQQLDAJFTDEO
+MAwGA1UEAwwFRUNDQTIwHhcNMTgwNjA4MDc1ODQ0WhcNMTkwNjA4MDc1ODQ0WjBN
+MQswCQYDVQQGEwJDTjELMAkGA1UECAwCU0gxCzAJBgNVBAoMAkVMMQswCQYDVQQL
+DAJFTDEXMBUGA1UEAwwORUNUZXN0U2VydmVyMTAwWTATBgcqhkjOPQIBBggqhkjO
+PQMBBwNCAAT5Gh0gfZpmTn66a0YyxZvPGujXOVMmhrmG6ZLUCxeJ+pyRG9RsIJal
+wlCtDCMYG6Uzk1hBFSMBxOSZmUBfHIUYo4HFMIHCMGsGA1UdIwRkMGKhVaRTMFEx
+CzAJBgNVBAYTAkNOMQswCQYDVQQIDAJTSDELMAkGA1UEBwwCU0gxCzAJBgNVBAoM
+AkVMMQswCQYDVQQLDAJFTDEOMAwGA1UEAwwFRUNDQTKCCQCmfYU0kzbVOzAJBgNV
+HRMEAjAAMAsGA1UdDwQEAwID+DA7BgNVHSUENDAyBggrBgEFBQcDAQYIKwYBBQUH
+AwIGCCsGAQUFBwMDBggrBgEFBQcDBAYIKwYBBQUHAwgwCQYHKoZIzj0EAQNIADBF
+AiEA3xIAl7jC0mhv/YGp5ekBtU3CUMODEfF8lvwWcTCBmsQCIF3ZLe2Su8dV7r3f
+Gz47uMca2TLgCwXwVjvfF3DTubsU
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTestServer10.key b/test/regression/interoperability_test/ecc_certificates/ECTestServer10.key
new file mode 100644
index 00000000..e3016f91
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTestServer10.key
@@ -0,0 +1,8 @@
+-----BEGIN EC PARAMETERS-----
+BggqhkjOPQMBBw==
+-----END EC PARAMETERS-----
+-----BEGIN EC PRIVATE KEY-----
+MHcCAQEEICSrDSw+sGrfBRJql24SaZL8XHB9WxfNGwdRZWgNHunMoAoGCCqGSM49
+AwEHoUQDQgAE+RodIH2aZk5+umtGMsWbzxro1zlTJoa5humS1AsXifqckRvUbCCW
+pcJQrQwjGBulM5NYQRUjAcTkmZlAXxyFGA==
+-----END EC PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTestServer2.crt b/test/regression/interoperability_test/ecc_certificates/ECTestServer2.crt
new file mode 100644
index 00000000..f5c837d5
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTestServer2.crt
@@ -0,0 +1,52 @@
+Certificate:
+ Data:
+ Version: 3 (0x2)
+ Serial Number: 1 (0x1)
+ Signature Algorithm: ecdsa-with-SHA256
+ Issuer: C=CN, ST=SH, L=SH, O=EL, OU=EL, CN=ECCA2
+ Validity
+ Not Before: May 17 01:54:18 2018 GMT
+ Not After : May 17 01:54:18 2019 GMT
+ Subject: C=CN, ST=SH, O=EL, OU=EL, CN=ECTestServer2
+ Subject Public Key Info:
+ Public Key Algorithm: id-ecPublicKey
+ Public-Key: (256 bit)
+ pub:
+ 04:46:5f:dc:06:e4:83:8f:2a:24:4d:ef:fb:81:d4:
+ c7:87:b4:6f:34:98:fe:ce:0d:9e:83:ed:0f:15:5b:
+ 7e:73:65:23:94:e9:d7:b5:05:17:93:02:50:0f:d0:
+ ba:93:ae:45:28:72:fa:88:50:74:bd:b1:d2:ee:47:
+ 26:e8:ba:2c:21
+ ASN1 OID: prime256v1
+ NIST CURVE: P-256
+ X509v3 extensions:
+ X509v3 Authority Key Identifier:
+ DirName:/C=CN/ST=SH/L=SH/O=EL/OU=EL/CN=ECCA2
+ serial:A6:7D:85:34:93:36:D5:3B
+
+ X509v3 Basic Constraints:
+ CA:FALSE
+ X509v3 Key Usage:
+ Digital Signature, Non Repudiation, Key Encipherment, Data Encipherment, Key Agreement
+ X509v3 Extended Key Usage:
+ TLS Web Server Authentication, TLS Web Client Authentication, Code Signing, E-mail Protection, Time Stamping
+ Signature Algorithm: ecdsa-with-SHA256
+ 30:46:02:21:00:f8:ed:34:8e:e7:a5:20:bf:2b:15:97:02:16:
+ 98:8b:0f:2a:f6:ee:5c:e9:f7:64:91:ed:59:7e:5f:51:a1:cf:
+ f3:02:21:00:a1:07:cb:e1:86:6a:01:eb:39:48:e0:55:ed:09:
+ bb:74:8f:d4:59:3c:71:cc:a7:01:77:72:84:7d:a7:f6:0e:64
+-----BEGIN CERTIFICATE-----
+MIICUzCCAfigAwIBAgIBATAKBggqhkjOPQQDAjBRMQswCQYDVQQGEwJDTjELMAkG
+A1UECAwCU0gxCzAJBgNVBAcMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UECwwCRUwx
+DjAMBgNVBAMMBUVDQ0EyMB4XDTE4MDUxNzAxNTQxOFoXDTE5MDUxNzAxNTQxOFow
+TDELMAkGA1UEBhMCQ04xCzAJBgNVBAgMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UE
+CwwCRUwxFjAUBgNVBAMMDUVDVGVzdFNlcnZlcjIwWTATBgcqhkjOPQIBBggqhkjO
+PQMBBwNCAARGX9wG5IOPKiRN7/uB1MeHtG80mP7ODZ6D7Q8VW35zZSOU6de1BReT
+AlAP0LqTrkUocvqIUHS9sdLuRybouiwho4HFMIHCMGsGA1UdIwRkMGKhVaRTMFEx
+CzAJBgNVBAYTAkNOMQswCQYDVQQIDAJTSDELMAkGA1UEBwwCU0gxCzAJBgNVBAoM
+AkVMMQswCQYDVQQLDAJFTDEOMAwGA1UEAwwFRUNDQTKCCQCmfYU0kzbVOzAJBgNV
+HRMEAjAAMAsGA1UdDwQEAwID+DA7BgNVHSUENDAyBggrBgEFBQcDAQYIKwYBBQUH
+AwIGCCsGAQUFBwMDBggrBgEFBQcDBAYIKwYBBQUHAwgwCgYIKoZIzj0EAwIDSQAw
+RgIhAPjtNI7npSC/KxWXAhaYiw8q9u5c6fdkke1Zfl9Roc/zAiEAoQfL4YZqAes5
+SOBV7Qm7dI/UWTxxzKcBd3KEfaf2DmQ=
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTestServer2.key b/test/regression/interoperability_test/ecc_certificates/ECTestServer2.key
new file mode 100644
index 00000000..b8babdb9
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTestServer2.key
@@ -0,0 +1,8 @@
+-----BEGIN EC PARAMETERS-----
+BggqhkjOPQMBBw==
+-----END EC PARAMETERS-----
+-----BEGIN EC PRIVATE KEY-----
+MHcCAQEEIFmLLKjv52EtFwyNkqSuB0ahkZz0Q+258t+34gyodiUooAoGCCqGSM49
+AwEHoUQDQgAERl/cBuSDjyokTe/7gdTHh7RvNJj+zg2eg+0PFVt+c2UjlOnXtQUX
+kwJQD9C6k65FKHL6iFB0vbHS7kcm6LosIQ==
+-----END EC PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTestServer3.crt b/test/regression/interoperability_test/ecc_certificates/ECTestServer3.crt
new file mode 100644
index 00000000..fa85d05a
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTestServer3.crt
@@ -0,0 +1,63 @@
+Certificate:
+ Data:
+ Version: 3 (0x2)
+ Serial Number: 2 (0x2)
+ Signature Algorithm: ecdsa-with-SHA256
+ Issuer: C=CN, ST=SH, L=SH, O=EL, OU=EL, CN=ECCA3
+ Validity
+ Not Before: May 17 05:15:24 2018 GMT
+ Not After : May 17 05:15:24 2019 GMT
+ Subject: C=CN, ST=SH, O=EL, OU=EL, CN=ECTestServer3
+ Subject Public Key Info:
+ Public Key Algorithm: id-ecPublicKey
+ Public-Key: (521 bit)
+ pub:
+ 04:00:30:a5:94:4f:3e:d1:8d:cf:c4:d7:54:fb:62:
+ aa:10:11:95:20:8b:71:6c:a0:88:68:47:c1:f4:0c:
+ 41:1c:21:6c:0c:c4:0c:1b:91:6d:95:ad:84:1a:c3:
+ 1c:fb:f3:a3:6a:b9:13:e0:23:8f:42:0f:1c:75:da:
+ 4d:d8:b0:49:aa:1c:75:00:a7:a4:69:dc:a8:63:41:
+ 85:80:51:cb:2b:c2:29:e3:f9:36:27:93:d8:0a:31:
+ fc:4d:0e:ab:42:64:a5:0f:f5:38:7b:39:9c:99:33:
+ ec:cb:12:90:5d:92:49:9a:06:ff:d7:7c:80:d9:f9:
+ 18:0a:62:97:3e:0f:45:63:d9:73:4c:ef:f2
+ ASN1 OID: secp521r1
+ NIST CURVE: P-521
+ X509v3 extensions:
+ X509v3 Authority Key Identifier:
+ DirName:/C=CN/ST=SH/L=SH/O=EL/OU=EL/CN=ECCA3
+ serial:D8:41:CC:08:88:42:B6:4D
+
+ X509v3 Basic Constraints:
+ CA:FALSE
+ X509v3 Key Usage:
+ Digital Signature, Non Repudiation, Key Encipherment, Data Encipherment, Key Agreement
+ X509v3 Extended Key Usage:
+ TLS Web Server Authentication, TLS Web Client Authentication, Code Signing, E-mail Protection, Time Stamping
+ Signature Algorithm: ecdsa-with-SHA256
+ 30:81:88:02:42:00:df:ad:0f:cb:3d:c6:a3:eb:5b:66:bc:22:
+ 96:de:5d:a4:3e:24:0e:3f:15:78:81:60:78:20:32:56:ef:25:
+ 36:be:16:7d:51:2f:e6:ef:25:39:72:25:65:a7:af:7c:f0:bb:
+ f2:06:e3:61:6e:45:5e:62:41:a5:3e:e1:b4:fd:44:72:5a:02:
+ 42:01:5d:fb:f8:c2:0e:23:72:d8:13:6e:e2:32:96:33:02:22:
+ 5d:5d:0e:76:79:7b:a6:68:e0:e5:1e:b2:d0:d6:4a:14:90:80:
+ 4b:20:16:c1:c3:3d:da:28:e9:52:e6:3f:18:90:b8:82:48:44:
+ 12:99:9d:35:59:37:81:89:ae:89:c4:13:9d
+-----BEGIN CERTIFICATE-----
+MIIC2jCCAjugAwIBAgIBAjAKBggqhkjOPQQDAjBRMQswCQYDVQQGEwJDTjELMAkG
+A1UECAwCU0gxCzAJBgNVBAcMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UECwwCRUwx
+DjAMBgNVBAMMBUVDQ0EzMB4XDTE4MDUxNzA1MTUyNFoXDTE5MDUxNzA1MTUyNFow
+TDELMAkGA1UEBhMCQ04xCzAJBgNVBAgMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UE
+CwwCRUwxFjAUBgNVBAMMDUVDVGVzdFNlcnZlcjMwgZswEAYHKoZIzj0CAQYFK4EE
+ACMDgYYABAAwpZRPPtGNz8TXVPtiqhARlSCLcWygiGhHwfQMQRwhbAzEDBuRbZWt
+hBrDHPvzo2q5E+Ajj0IPHHXaTdiwSaocdQCnpGncqGNBhYBRyyvCKeP5NieT2Aox
+/E0Oq0JkpQ/1OHs5nJkz7MsSkF2SSZoG/9d8gNn5GApilz4PRWPZc0zv8qOBxTCB
+wjBrBgNVHSMEZDBioVWkUzBRMQswCQYDVQQGEwJDTjELMAkGA1UECAwCU0gxCzAJ
+BgNVBAcMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UECwwCRUwxDjAMBgNVBAMMBUVD
+Q0EzggkA2EHMCIhCtk0wCQYDVR0TBAIwADALBgNVHQ8EBAMCA/gwOwYDVR0lBDQw
+MgYIKwYBBQUHAwEGCCsGAQUFBwMCBggrBgEFBQcDAwYIKwYBBQUHAwQGCCsGAQUF
+BwMIMAoGCCqGSM49BAMCA4GMADCBiAJCAN+tD8s9xqPrW2a8IpbeXaQ+JA4/FXiB
+YHggMlbvJTa+Fn1RL+bvJTlyJWWnr3zwu/IG42FuRV5iQaU+4bT9RHJaAkIBXfv4
+wg4jctgTbuIyljMCIl1dDnZ5e6Zo4OUestDWShSQgEsgFsHDPdoo6VLmPxiQuIJI
+RBKZnTVZN4GJronEE50=
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTestServer3.key b/test/regression/interoperability_test/ecc_certificates/ECTestServer3.key
new file mode 100644
index 00000000..0448c243
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTestServer3.key
@@ -0,0 +1,10 @@
+-----BEGIN EC PARAMETERS-----
+BgUrgQQAIw==
+-----END EC PARAMETERS-----
+-----BEGIN EC PRIVATE KEY-----
+MIHcAgEBBEIA7EWokt3EVwS6PST/wYFvZSzT/XgZjEAzE45DhIs9rVC9P0To/2VA
+gjvRouGAD/gE1Bkz9NYW0l+Vmg5y7XT+5yegBwYFK4EEACOhgYkDgYYABAAwpZRP
+PtGNz8TXVPtiqhARlSCLcWygiGhHwfQMQRwhbAzEDBuRbZWthBrDHPvzo2q5E+Aj
+j0IPHHXaTdiwSaocdQCnpGncqGNBhYBRyyvCKeP5NieT2Aox/E0Oq0JkpQ/1OHs5
+nJkz7MsSkF2SSZoG/9d8gNn5GApilz4PRWPZc0zv8g==
+-----END EC PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTestServer4.crt b/test/regression/interoperability_test/ecc_certificates/ECTestServer4.crt
new file mode 100644
index 00000000..61585279
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTestServer4.crt
@@ -0,0 +1,57 @@
+Certificate:
+ Data:
+ Version: 3 (0x2)
+ Serial Number: 3 (0x3)
+ Signature Algorithm: ecdsa-with-SHA256
+ Issuer: C=CN, ST=SH, L=SH, O=EL, OU=EL, CN=ECCA4
+ Validity
+ Not Before: May 17 07:17:03 2018 GMT
+ Not After : May 17 07:17:03 2019 GMT
+ Subject: C=CN, ST=SH, O=EL, OU=EL, CN=ECTestServer4
+ Subject Public Key Info:
+ Public Key Algorithm: id-ecPublicKey
+ Public-Key: (384 bit)
+ pub:
+ 04:cf:d9:16:42:8e:b5:0a:cb:fe:41:07:c9:1f:e3:
+ 87:02:db:23:c2:de:fa:45:7e:65:0b:1c:f7:c5:c0:
+ bd:ad:39:2e:3c:30:0e:ad:b8:c4:9e:a3:8f:90:ee:
+ e7:3d:c6:1f:2d:ff:48:fc:e6:7c:72:35:cc:c9:af:
+ 69:ee:c6:0f:c2:cf:7c:1f:61:d8:b4:94:a9:70:52:
+ d5:6a:38:1c:86:01:72:1e:8d:a5:67:fb:ff:b2:f1:
+ eb:fc:2a:3f:d0:12:78
+ ASN1 OID: secp384r1
+ NIST CURVE: P-384
+ X509v3 extensions:
+ X509v3 Authority Key Identifier:
+ DirName:/C=CN/ST=SH/L=SH/O=EL/OU=EL/CN=ECCA4
+ serial:BC:64:D9:FE:6A:91:0E:C2
+
+ X509v3 Basic Constraints:
+ CA:FALSE
+ X509v3 Key Usage:
+ Digital Signature, Non Repudiation, Key Encipherment, Data Encipherment, Key Agreement
+ X509v3 Extended Key Usage:
+ TLS Web Server Authentication, TLS Web Client Authentication, Code Signing, E-mail Protection, Time Stamping
+ Signature Algorithm: ecdsa-with-SHA256
+ 30:64:02:30:2f:ad:80:53:ef:83:71:0e:d0:d8:2a:96:b9:37:
+ e8:06:b2:49:29:f2:fd:58:e3:1f:00:66:62:4f:97:8f:44:b7:
+ 10:1f:70:88:a8:44:86:89:9d:21:e4:72:6c:6f:d0:92:02:30:
+ 06:53:65:a6:04:fd:20:2f:5b:4d:95:14:a4:fa:97:b9:cf:80:
+ ab:6a:a5:7a:7b:7a:c5:c3:98:1e:5f:fc:49:23:f7:3d:f5:38:
+ 55:25:db:6d:1d:62:36:d2:fa:47:0d:c2
+-----BEGIN CERTIFICATE-----
+MIICjjCCAhWgAwIBAgIBAzAKBggqhkjOPQQDAjBRMQswCQYDVQQGEwJDTjELMAkG
+A1UECAwCU0gxCzAJBgNVBAcMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UECwwCRUwx
+DjAMBgNVBAMMBUVDQ0E0MB4XDTE4MDUxNzA3MTcwM1oXDTE5MDUxNzA3MTcwM1ow
+TDELMAkGA1UEBhMCQ04xCzAJBgNVBAgMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UE
+CwwCRUwxFjAUBgNVBAMMDUVDVGVzdFNlcnZlcjQwdjAQBgcqhkjOPQIBBgUrgQQA
+IgNiAATP2RZCjrUKy/5BB8kf44cC2yPC3vpFfmULHPfFwL2tOS48MA6tuMSeo4+Q
+7uc9xh8t/0j85nxyNczJr2nuxg/Cz3wfYdi0lKlwUtVqOByGAXIejaVn+/+y8ev8
+Kj/QEnijgcUwgcIwawYDVR0jBGQwYqFVpFMwUTELMAkGA1UEBhMCQ04xCzAJBgNV
+BAgMAlNIMQswCQYDVQQHDAJTSDELMAkGA1UECgwCRUwxCzAJBgNVBAsMAkVMMQ4w
+DAYDVQQDDAVFQ0NBNIIJALxk2f5qkQ7CMAkGA1UdEwQCMAAwCwYDVR0PBAQDAgP4
+MDsGA1UdJQQ0MDIGCCsGAQUFBwMBBggrBgEFBQcDAgYIKwYBBQUHAwMGCCsGAQUF
+BwMEBggrBgEFBQcDCDAKBggqhkjOPQQDAgNnADBkAjAvrYBT74NxDtDYKpa5N+gG
+skkp8v1Y4x8AZmJPl49EtxAfcIioRIaJnSHkcmxv0JICMAZTZaYE/SAvW02VFKT6
+l7nPgKtqpXp7esXDmB5f/Ekj9z31OFUl220dYjbS+kcNwg==
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTestServer4.key b/test/regression/interoperability_test/ecc_certificates/ECTestServer4.key
new file mode 100644
index 00000000..ea64011a
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTestServer4.key
@@ -0,0 +1,9 @@
+-----BEGIN EC PARAMETERS-----
+BgUrgQQAIg==
+-----END EC PARAMETERS-----
+-----BEGIN EC PRIVATE KEY-----
+MIGkAgEBBDASF37w5YOouSr4usluQZO2EQqyfPb6nJ2LUzp5MM2S8nff3CR5HzxH
+0fl0LP+RA6KgBwYFK4EEACKhZANiAATP2RZCjrUKy/5BB8kf44cC2yPC3vpFfmUL
+HPfFwL2tOS48MA6tuMSeo4+Q7uc9xh8t/0j85nxyNczJr2nuxg/Cz3wfYdi0lKlw
+UtVqOByGAXIejaVn+/+y8ev8Kj/QEng=
+-----END EC PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTestServer6.crt b/test/regression/interoperability_test/ecc_certificates/ECTestServer6.crt
new file mode 100644
index 00000000..754de3eb
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTestServer6.crt
@@ -0,0 +1,71 @@
+Certificate:
+ Data:
+ Version: 3 (0x2)
+ Serial Number: 5 (0x5)
+ Signature Algorithm: ecdsa-with-SHA256
+ Issuer: C=CN, ST=SH, L=SH, O=EL, OU=EL, CN=ECCA4
+ Validity
+ Not Before: May 24 01:30:14 2018 GMT
+ Not After : May 24 01:30:14 2019 GMT
+ Subject: C=CN, ST=SH, O=EL, OU=EL, CN=ECTestServer6
+ Subject Public Key Info:
+ Public Key Algorithm: rsaEncryption
+ Public-Key: (2048 bit)
+ Modulus:
+ 00:bb:bc:6a:bc:7c:20:77:47:9a:34:9b:0c:06:c5:
+ c4:40:d8:4b:21:89:63:11:a5:69:e6:43:85:e9:fd:
+ 57:4a:20:fc:45:51:2a:72:f0:03:6e:09:23:23:ae:
+ 70:3e:df:f0:83:45:47:e6:47:5f:15:6a:c4:a2:30:
+ aa:1c:be:f8:6e:24:a9:39:03:40:5d:32:6a:a3:8f:
+ 09:31:73:9f:11:b1:94:2d:8f:ee:21:6e:5b:ee:03:
+ a8:a6:31:09:5e:9b:45:1b:6b:19:7e:7c:ef:8a:9e:
+ 04:a1:cb:01:28:12:47:84:3e:8a:4c:eb:62:cc:cc:
+ 2a:f0:2c:1c:03:82:17:91:39:fa:a9:c9:28:4d:78:
+ c3:48:94:6d:fb:25:4b:72:d8:21:37:64:26:31:01:
+ fc:4c:fe:00:83:ee:8b:57:90:53:0d:0c:6f:82:30:
+ f1:0b:ea:4e:5f:9a:47:70:02:37:a2:ef:c4:f9:4c:
+ 00:aa:80:6f:42:c8:45:2a:38:cb:90:43:d1:79:5e:
+ 34:e6:9a:dc:75:3c:68:9e:39:37:56:f1:67:ea:41:
+ 17:4c:fa:2a:dc:ef:ff:3a:a1:c7:f2:46:a6:e3:d4:
+ 24:81:5f:5a:56:13:cf:a0:f8:3b:ee:30:13:4b:17:
+ 47:9a:aa:31:4f:1a:74:e5:bf:d0:7f:d1:d0:10:a2:
+ 4d:81
+ Exponent: 65537 (0x10001)
+ X509v3 extensions:
+ X509v3 Authority Key Identifier:
+ DirName:/C=CN/ST=SH/L=SH/O=EL/OU=EL/CN=ECCA4
+ serial:BC:64:D9:FE:6A:91:0E:C2
+
+ X509v3 Basic Constraints:
+ CA:FALSE
+ X509v3 Key Usage:
+ Digital Signature, Non Repudiation, Key Encipherment, Data Encipherment, Key Agreement
+ X509v3 Extended Key Usage:
+ TLS Web Server Authentication, TLS Web Client Authentication, Code Signing, E-mail Protection, Time Stamping
+ Signature Algorithm: ecdsa-with-SHA256
+ 30:65:02:31:00:9a:02:c1:30:87:e9:86:c7:24:7f:d9:e4:5b:
+ 04:e7:a3:bf:dc:0d:a8:83:03:9d:df:11:ce:29:eb:ed:e0:80:
+ 67:e7:72:5c:f5:af:aa:74:68:11:65:ea:e3:cc:eb:11:bd:02:
+ 30:32:c6:2d:07:22:55:b6:e2:4c:48:7f:8e:88:d6:9a:e9:e6:
+ 5a:71:ed:dd:dd:9d:4b:f1:8a:51:19:a0:9d:af:61:c6:13:0e:
+ d0:c6:7d:62:a9:c8:d0:2b:37:8d:d4:95:d0
+-----BEGIN CERTIFICATE-----
+MIIDPTCCAsOgAwIBAgIBBTAKBggqhkjOPQQDAjBRMQswCQYDVQQGEwJDTjELMAkG
+A1UECAwCU0gxCzAJBgNVBAcMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UECwwCRUwx
+DjAMBgNVBAMMBUVDQ0E0MB4XDTE4MDUyNDAxMzAxNFoXDTE5MDUyNDAxMzAxNFow
+TDELMAkGA1UEBhMCQ04xCzAJBgNVBAgMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UE
+CwwCRUwxFjAUBgNVBAMMDUVDVGVzdFNlcnZlcjYwggEiMA0GCSqGSIb3DQEBAQUA
+A4IBDwAwggEKAoIBAQC7vGq8fCB3R5o0mwwGxcRA2EshiWMRpWnmQ4Xp/VdKIPxF
+USpy8ANuCSMjrnA+3/CDRUfmR18VasSiMKocvvhuJKk5A0BdMmqjjwkxc58RsZQt
+j+4hblvuA6imMQlem0Ubaxl+fO+KngShywEoEkeEPopM62LMzCrwLBwDgheROfqp
+yShNeMNIlG37JUty2CE3ZCYxAfxM/gCD7otXkFMNDG+CMPEL6k5fmkdwAjei78T5
+TACqgG9CyEUqOMuQQ9F5XjTmmtx1PGieOTdW8WfqQRdM+irc7/86ocfyRqbj1CSB
+X1pWE8+g+DvuMBNLF0eaqjFPGnTlv9B/0dAQok2BAgMBAAGjgcUwgcIwawYDVR0j
+BGQwYqFVpFMwUTELMAkGA1UEBhMCQ04xCzAJBgNVBAgMAlNIMQswCQYDVQQHDAJT
+SDELMAkGA1UECgwCRUwxCzAJBgNVBAsMAkVMMQ4wDAYDVQQDDAVFQ0NBNIIJALxk
+2f5qkQ7CMAkGA1UdEwQCMAAwCwYDVR0PBAQDAgP4MDsGA1UdJQQ0MDIGCCsGAQUF
+BwMBBggrBgEFBQcDAgYIKwYBBQUHAwMGCCsGAQUFBwMEBggrBgEFBQcDCDAKBggq
+hkjOPQQDAgNoADBlAjEAmgLBMIfphsckf9nkWwTno7/cDaiDA53fEc4p6+3ggGfn
+clz1r6p0aBFl6uPM6xG9AjAyxi0HIlW24kxIf46I1prp5lpx7d3dnUvxilEZoJ2v
+YcYTDtDGfWKpyNArN43UldA=
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTestServer6.key b/test/regression/interoperability_test/ecc_certificates/ECTestServer6.key
new file mode 100644
index 00000000..d01e4d04
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTestServer6.key
@@ -0,0 +1,27 @@
+-----BEGIN RSA PRIVATE KEY-----
+MIIEpAIBAAKCAQEAu7xqvHwgd0eaNJsMBsXEQNhLIYljEaVp5kOF6f1XSiD8RVEq
+cvADbgkjI65wPt/wg0VH5kdfFWrEojCqHL74biSpOQNAXTJqo48JMXOfEbGULY/u
+IW5b7gOopjEJXptFG2sZfnzvip4EocsBKBJHhD6KTOtizMwq8CwcA4IXkTn6qcko
+TXjDSJRt+yVLctghN2QmMQH8TP4Ag+6LV5BTDQxvgjDxC+pOX5pHcAI3ou/E+UwA
+qoBvQshFKjjLkEPReV405prcdTxonjk3VvFn6kEXTPoq3O//OqHH8kam49QkgV9a
+VhPPoPg77jATSxdHmqoxTxp05b/Qf9HQEKJNgQIDAQABAoIBAQCpWp8uyQrAj2cc
+bYG72kvf8z5TUox8LqwJfIAhRNiplnf8T+vrI3j0mmmIlqPLFFjzElx574hm2Zno
+dd3/cIbLVWcSd0xoxkJMqYuxgIvOelMhhuVaYyOq4sIQqcu5/Heq9EJbSHkOot2q
+1maEr3i0Y3Z/TRgjh0p0vlXHFGQOLKLf7lLyoTTfyz8e0QGX6i6GFKCsbhwFOPe5
+nW3JBpar9p1rzW8d5hU4GoetioSHV47HFggQB/0nioHr0ySRsGsr+qz0yL/pAcu+
+FSLtJ07jzT4qJFpg9TA3sK5GCzFRZwHxNPg0iSYQigoPzA3trwlNZhpdExMcHeF0
+xsr38eUBAoGBAOs8ClvAmSHCHCW2xlPXt7//oXLUMvEf+xm1TNF06jgsU+Od66Zd
+XDgmrMOY6Z30Ji6inmj2CkE3wSQGeOJ/wuD8JBcM1IZtZHcrVfLu/zED2IHmNRGK
+CxokawZz9SXhlZSBqLdGOfGW5aF83I8a/ACxADmJes1smM+6lSe0P2sVAoGBAMxO
++oIi7BHCVGYD3jzrX9CfmhJYPcpQC/2ox/As1PEFGyofh54MnlrR+YB6zUfrxfVD
+DNwzCobL4MZryCdCb1rsVNIyOWT89W/j9Bk7oU8rkcxhSSHkUhRZ5jkvXUAJRnI9
+sQ23Xvumg0fQogYNEAXfIrG2mbHwPscL3qRZEwO9AoGAFAvk0hbitebF4UznL+P1
+S85sIs4EnVndWz6BEmSFRU45w+8EUwQnxL0/Adg5KHXS/yxqlYVKMG6g7gIDMUI0
+CFpUdQZp4h7WbfVqeK53XuT2AXPt19XMxmiOGlmtbZIA3kwCZcP9UiJK5W0vmp5x
+FVoAK+cUaQc1Kpa6+Uw6D1UCgYBTX4dqw8WCGcNHPhzaz1JyWC8PfWL5xGCgStgM
+cr8S+/px3hwBqzST60vd2j8bMmO+CnadBVcuWtSHJESxgLLgb8DNZiF1zKR73JIo
+GeVh4W3F8Y1ef0XfeDAy9dkf4KkWxYYTCtl/6Bt6mvEDdyEqxDvsOY/OxTNZFsbs
+Wk0gIQKBgQCUxnhRiOTyk0LbuUatgnOyToN0j3n+kK5xfxegyDaQxXEOwRItIEBd
+WnPr7/ujaKW0zp2L8JcRsyJtxBbtHHGrvIuPspTrID/RBdVuYaqG7u4hDH2mU3s7
+nMWf8E15FJlx67VPN2zmi5vYEU2qsWzuD0J1+AzDxj0wsB5pkB8sFg==
+-----END RSA PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTestServer7_256.crt b/test/regression/interoperability_test/ecc_certificates/ECTestServer7_256.crt
new file mode 100644
index 00000000..4cb7dd11
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTestServer7_256.crt
@@ -0,0 +1,55 @@
+Certificate:
+ Data:
+ Version: 3 (0x2)
+ Serial Number: 6 (0x6)
+ Signature Algorithm: ecdsa-with-SHA256
+ Issuer: C=CN, ST=SH, L=SH, O=EL, OU=EL, CN=ECCA4
+ Validity
+ Not Before: May 25 04:45:33 2018 GMT
+ Not After : May 25 04:45:33 2019 GMT
+ Subject: C=CN, ST=SH, O=EL, OU=EL, CN=ECTestServer7_256
+ Subject Public Key Info:
+ Public Key Algorithm: id-ecPublicKey
+ Public-Key: (256 bit)
+ pub:
+ 04:ee:e8:6b:81:32:42:79:9e:16:27:71:3b:c6:62:
+ 2c:ea:50:83:13:be:07:20:96:f3:9e:b4:c9:e0:cc:
+ f9:97:3b:be:5c:ef:bc:39:c0:33:06:27:6e:a6:f6:
+ ba:25:8f:40:71:2a:b1:a1:44:4f:37:05:17:46:64:
+ 3b:29:74:62:b0
+ ASN1 OID: prime256v1
+ NIST CURVE: P-256
+ X509v3 extensions:
+ X509v3 Authority Key Identifier:
+ DirName:/C=CN/ST=SH/L=SH/O=EL/OU=EL/CN=ECCA4
+ serial:BC:64:D9:FE:6A:91:0E:C2
+
+ X509v3 Basic Constraints:
+ CA:FALSE
+ X509v3 Key Usage:
+ Digital Signature, Non Repudiation, Key Encipherment, Data Encipherment, Key Agreement
+ X509v3 Extended Key Usage:
+ TLS Web Server Authentication, TLS Web Client Authentication, Code Signing, E-mail Protection, Time Stamping
+ Signature Algorithm: ecdsa-with-SHA256
+ 30:66:02:31:00:8f:cd:27:83:3b:3a:93:a2:1c:1a:8d:be:02:
+ 07:9f:6c:f5:28:83:91:7d:1c:49:f2:83:40:4a:78:11:b0:a0:
+ f4:50:1b:ba:79:59:f6:15:70:37:9f:0c:ae:1b:3e:25:9e:02:
+ 31:00:e3:91:01:6a:26:98:86:7d:90:75:8b:1d:aa:cf:12:e5:
+ 99:96:b4:49:ed:90:dc:45:f3:ee:12:11:45:db:94:69:da:5c:
+ 7d:f8:53:17:05:b3:57:82:06:91:b9:db:a1:09
+-----BEGIN CERTIFICATE-----
+MIICdzCCAfygAwIBAgIBBjAKBggqhkjOPQQDAjBRMQswCQYDVQQGEwJDTjELMAkG
+A1UECAwCU0gxCzAJBgNVBAcMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UECwwCRUwx
+DjAMBgNVBAMMBUVDQ0E0MB4XDTE4MDUyNTA0NDUzM1oXDTE5MDUyNTA0NDUzM1ow
+UDELMAkGA1UEBhMCQ04xCzAJBgNVBAgMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UE
+CwwCRUwxGjAYBgNVBAMMEUVDVGVzdFNlcnZlcjdfMjU2MFkwEwYHKoZIzj0CAQYI
+KoZIzj0DAQcDQgAE7uhrgTJCeZ4WJ3E7xmIs6lCDE74HIJbznrTJ4Mz5lzu+XO+8
+OcAzBidupva6JY9AcSqxoURPNwUXRmQ7KXRisKOBxTCBwjBrBgNVHSMEZDBioVWk
+UzBRMQswCQYDVQQGEwJDTjELMAkGA1UECAwCU0gxCzAJBgNVBAcMAlNIMQswCQYD
+VQQKDAJFTDELMAkGA1UECwwCRUwxDjAMBgNVBAMMBUVDQ0E0ggkAvGTZ/mqRDsIw
+CQYDVR0TBAIwADALBgNVHQ8EBAMCA/gwOwYDVR0lBDQwMgYIKwYBBQUHAwEGCCsG
+AQUFBwMCBggrBgEFBQcDAwYIKwYBBQUHAwQGCCsGAQUFBwMIMAoGCCqGSM49BAMC
+A2kAMGYCMQCPzSeDOzqTohwajb4CB59s9SiDkX0cSfKDQEp4EbCg9FAbunlZ9hVw
+N58Mrhs+JZ4CMQDjkQFqJpiGfZB1ix2qzxLlmZa0Se2Q3EXz7hIRRduUadpcffhT
+FwWzV4IGkbnboQk=
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTestServer7_256.key b/test/regression/interoperability_test/ecc_certificates/ECTestServer7_256.key
new file mode 100644
index 00000000..8314b92f
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTestServer7_256.key
@@ -0,0 +1,8 @@
+-----BEGIN EC PARAMETERS-----
+BggqhkjOPQMBBw==
+-----END EC PARAMETERS-----
+-----BEGIN EC PRIVATE KEY-----
+MHcCAQEEIOEroiYKpuF3yj0t5kqKnXPXqphnKGRBDizcPvJsffWCoAoGCCqGSM49
+AwEHoUQDQgAE7uhrgTJCeZ4WJ3E7xmIs6lCDE74HIJbznrTJ4Mz5lzu+XO+8OcAz
+Bidupva6JY9AcSqxoURPNwUXRmQ7KXRisA==
+-----END EC PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTestServer8_224.crt b/test/regression/interoperability_test/ecc_certificates/ECTestServer8_224.crt
new file mode 100644
index 00000000..2e52180f
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTestServer8_224.crt
@@ -0,0 +1,51 @@
+Certificate:
+ Data:
+ Version: 3 (0x2)
+ Serial Number: 7 (0x7)
+ Signature Algorithm: ecdsa-with-SHA256
+ Issuer: C=CN, ST=SH, L=SH, O=EL, OU=EL, CN=ECCA2
+ Validity
+ Not Before: Jun 7 02:25:27 2018 GMT
+ Not After : Jun 7 02:25:27 2019 GMT
+ Subject: C=CN, ST=SH, O=EL, OU=EL, CN=ECTestServer8
+ Subject Public Key Info:
+ Public Key Algorithm: id-ecPublicKey
+ Public-Key: (224 bit)
+ pub:
+ 04:fa:17:9d:00:cb:26:b5:b8:d5:45:d7:63:e1:db:
+ e9:c4:b5:86:e4:1d:a5:10:f5:da:6c:3a:4d:a3:5d:
+ 77:ef:7c:e4:81:c7:72:52:ba:83:40:41:de:0a:cc:
+ ec:73:b6:0b:e5:15:90:fe:29:90:65:59
+ ASN1 OID: secp224r1
+ NIST CURVE: P-224
+ X509v3 extensions:
+ X509v3 Authority Key Identifier:
+ DirName:/C=CN/ST=SH/L=SH/O=EL/OU=EL/CN=ECCA2
+ serial:A6:7D:85:34:93:36:D5:3B
+
+ X509v3 Basic Constraints:
+ CA:FALSE
+ X509v3 Key Usage:
+ Digital Signature, Non Repudiation, Key Encipherment, Data Encipherment, Key Agreement
+ X509v3 Extended Key Usage:
+ TLS Web Server Authentication, TLS Web Client Authentication, Code Signing, E-mail Protection, Time Stamping
+ Signature Algorithm: ecdsa-with-SHA256
+ 30:44:02:20:71:ad:f5:33:c7:04:6a:28:b0:06:45:04:f3:f1:
+ 4e:60:2f:68:1d:fa:b4:87:f2:af:21:e0:1b:84:84:8f:74:cf:
+ 02:20:15:73:48:84:93:89:7a:c9:b8:b2:97:76:82:d7:62:31:
+ 25:50:46:8b:ff:de:57:f3:bd:02:18:21:ba:d4:fe:b0
+-----BEGIN CERTIFICATE-----
+MIICRjCCAe2gAwIBAgIBBzAKBggqhkjOPQQDAjBRMQswCQYDVQQGEwJDTjELMAkG
+A1UECAwCU0gxCzAJBgNVBAcMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UECwwCRUwx
+DjAMBgNVBAMMBUVDQ0EyMB4XDTE4MDYwNzAyMjUyN1oXDTE5MDYwNzAyMjUyN1ow
+TDELMAkGA1UEBhMCQ04xCzAJBgNVBAgMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UE
+CwwCRUwxFjAUBgNVBAMMDUVDVGVzdFNlcnZlcjgwTjAQBgcqhkjOPQIBBgUrgQQA
+IQM6AAT6F50Ayya1uNVF12Ph2+nEtYbkHaUQ9dpsOk2jXXfvfOSBx3JSuoNAQd4K
+zOxztgvlFZD+KZBlWaOBxTCBwjBrBgNVHSMEZDBioVWkUzBRMQswCQYDVQQGEwJD
+TjELMAkGA1UECAwCU0gxCzAJBgNVBAcMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UE
+CwwCRUwxDjAMBgNVBAMMBUVDQ0EyggkApn2FNJM21TswCQYDVR0TBAIwADALBgNV
+HQ8EBAMCA/gwOwYDVR0lBDQwMgYIKwYBBQUHAwEGCCsGAQUFBwMCBggrBgEFBQcD
+AwYIKwYBBQUHAwQGCCsGAQUFBwMIMAoGCCqGSM49BAMCA0cAMEQCIHGt9TPHBGoo
+sAZFBPPxTmAvaB36tIfyryHgG4SEj3TPAiAVc0iEk4l6ybiyl3aC12IxJVBGi//e
+V/O9AhghutT+sA==
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTestServer8_224.key b/test/regression/interoperability_test/ecc_certificates/ECTestServer8_224.key
new file mode 100644
index 00000000..c8dd1bfb
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTestServer8_224.key
@@ -0,0 +1,8 @@
+-----BEGIN EC PARAMETERS-----
+BgUrgQQAIQ==
+-----END EC PARAMETERS-----
+-----BEGIN EC PRIVATE KEY-----
+MGgCAQEEHL6QyG2cvfMo28Ck7m5t7jCeP3p0nOrArVWO/6KgBwYFK4EEACGhPAM6
+AAT6F50Ayya1uNVF12Ph2+nEtYbkHaUQ9dpsOk2jXXfvfOSBx3JSuoNAQd4KzOxz
+tgvlFZD+KZBlWQ==
+-----END EC PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTestServer9_192.crt b/test/regression/interoperability_test/ecc_certificates/ECTestServer9_192.crt
new file mode 100644
index 00000000..ebe50612
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTestServer9_192.crt
@@ -0,0 +1,51 @@
+Certificate:
+ Data:
+ Version: 3 (0x2)
+ Serial Number: 8 (0x8)
+ Signature Algorithm: ecdsa-with-SHA256
+ Issuer: C=CN, ST=SH, L=SH, O=EL, OU=EL, CN=ECCA2
+ Validity
+ Not Before: Jun 7 02:29:10 2018 GMT
+ Not After : Jun 7 02:29:10 2019 GMT
+ Subject: C=CN, ST=SH, O=EL, OU=EL, CN=ECTestServer9
+ Subject Public Key Info:
+ Public Key Algorithm: id-ecPublicKey
+ Public-Key: (192 bit)
+ pub:
+ 04:44:99:10:2c:49:94:99:00:c7:55:19:d3:63:f9:
+ 23:6a:d4:47:6d:b5:41:a1:3b:45:09:13:e3:7a:42:
+ 2f:91:55:05:e1:64:e9:c5:b9:14:6d:a2:06:bc:54:
+ b3:fb:b3:13
+ ASN1 OID: prime192v1
+ NIST CURVE: P-192
+ X509v3 extensions:
+ X509v3 Authority Key Identifier:
+ DirName:/C=CN/ST=SH/L=SH/O=EL/OU=EL/CN=ECCA2
+ serial:A6:7D:85:34:93:36:D5:3B
+
+ X509v3 Basic Constraints:
+ CA:FALSE
+ X509v3 Key Usage:
+ Digital Signature, Non Repudiation, Key Encipherment, Data Encipherment, Key Agreement
+ X509v3 Extended Key Usage:
+ TLS Web Server Authentication, TLS Web Client Authentication, Code Signing, E-mail Protection, Time Stamping
+ Signature Algorithm: ecdsa-with-SHA256
+ 30:45:02:21:00:b9:64:a3:66:0d:25:df:e2:c7:0f:eb:a3:80:
+ e8:29:7e:7c:8c:0f:b1:65:9e:a7:50:e4:ea:d2:04:91:6e:58:
+ f8:02:20:23:6a:e7:c2:d1:e6:bc:54:6d:01:8d:fa:e7:7e:09:
+ e9:65:e1:82:16:e6:a0:d2:14:bf:56:ec:d2:c7:f2:d5:f7
+-----BEGIN CERTIFICATE-----
+MIICQjCCAeigAwIBAgIBCDAKBggqhkjOPQQDAjBRMQswCQYDVQQGEwJDTjELMAkG
+A1UECAwCU0gxCzAJBgNVBAcMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UECwwCRUwx
+DjAMBgNVBAMMBUVDQ0EyMB4XDTE4MDYwNzAyMjkxMFoXDTE5MDYwNzAyMjkxMFow
+TDELMAkGA1UEBhMCQ04xCzAJBgNVBAgMAlNIMQswCQYDVQQKDAJFTDELMAkGA1UE
+CwwCRUwxFjAUBgNVBAMMDUVDVGVzdFNlcnZlcjkwSTATBgcqhkjOPQIBBggqhkjO
+PQMBAQMyAAREmRAsSZSZAMdVGdNj+SNq1EdttUGhO0UJE+N6Qi+RVQXhZOnFuRRt
+oga8VLP7sxOjgcUwgcIwawYDVR0jBGQwYqFVpFMwUTELMAkGA1UEBhMCQ04xCzAJ
+BgNVBAgMAlNIMQswCQYDVQQHDAJTSDELMAkGA1UECgwCRUwxCzAJBgNVBAsMAkVM
+MQ4wDAYDVQQDDAVFQ0NBMoIJAKZ9hTSTNtU7MAkGA1UdEwQCMAAwCwYDVR0PBAQD
+AgP4MDsGA1UdJQQ0MDIGCCsGAQUFBwMBBggrBgEFBQcDAgYIKwYBBQUHAwMGCCsG
+AQUFBwMEBggrBgEFBQcDCDAKBggqhkjOPQQDAgNIADBFAiEAuWSjZg0l3+LHD+uj
+gOgpfnyMD7FlnqdQ5OrSBJFuWPgCICNq58LR5rxUbQGN+ud+Cell4YIW5qDSFL9W
+7NLH8tX3
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/ecc_certificates/ECTestServer9_192.key b/test/regression/interoperability_test/ecc_certificates/ECTestServer9_192.key
new file mode 100644
index 00000000..f3841582
--- /dev/null
+++ b/test/regression/interoperability_test/ecc_certificates/ECTestServer9_192.key
@@ -0,0 +1,8 @@
+-----BEGIN EC PARAMETERS-----
+BggqhkjOPQMBAQ==
+-----END EC PARAMETERS-----
+-----BEGIN EC PRIVATE KEY-----
+MF8CAQEEGOAPxROexeXNR3wOdYqNDbdZU7JtBlFetqAKBggqhkjOPQMBAaE0AzIA
+BESZECxJlJkAx1UZ02P5I2rUR221QaE7RQkT43pCL5FVBeFk6cW5FG2iBrxUs/uz
+Ew==
+-----END EC PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/nx_pcap_network_driver.c b/test/regression/interoperability_test/nx_pcap_network_driver.c
new file mode 100644
index 00000000..1742c2c7
--- /dev/null
+++ b/test/regression/interoperability_test/nx_pcap_network_driver.c
@@ -0,0 +1,634 @@
+/**************************************************************************/
+/* */
+/* Copyright (c) Microsoft Corporation. All rights reserved. */
+/* */
+/* This software is licensed under the Microsoft Software License */
+/* Terms for Microsoft Azure RTOS. Full text of the license can be */
+/* found in the LICENSE file at https://aka.ms/AzureRTOS_EULA */
+/* and in the root directory of this software. */
+/* */
+/**************************************************************************/
+
+#ifdef WIN32
+#define HAVE_REMOTE
+#define WPCAP
+#endif
+
+#include "pcap.h"
+#include "nx_api.h"
+#include "tx_thread.h"
+#ifndef WIN32
+#include "pthread.h"
+#endif
+#ifdef NX_ENABLE_PPPOE
+#include "nx_pppoe_server.h"
+#endif
+
+#ifdef WIN32
+#pragma comment(lib, "wpcap.lib")
+#pragma comment(lib, "Packet.lib")
+#pragma comment(lib, "ws2_32.lib")
+#endif
+
+/* Define zero-terminated string containing the source name to open. */
+/* In windows, the SOURCE NAME looks like this "rpcap://\\Device\\NPF_{4C8Bxxxx-xxxx-xxxx-xxxx-xxxxxxxx8356}" */
+/* In Linux, the SOURCE NAME looks like this "eth0" */
+#ifndef NX_PCAP_SOURCE_NAME
+#define NX_PCAP_SOURCE_NAME "rpcap://\\Device\\NPF_{4C8Bxxxx-xxxx-xxxx-xxxx-xxxxxxxx8356}"
+
+#endif /* NX_LIBPCAP_SOURCE_NAME */
+
+/* Define the Link MTU. Note this is not the same as the IP MTU. The Link MTU
+ includes the addition of the Physical Network header (usually Ethernet). This
+ should be larger than the IP instance MTU by the size of the physical header. */
+#define NX_LINK_MTU 1514
+#define NX_MAX_PACKET_SIZE 1536
+
+/* Define Ethernet address format. This is prepended to the incoming IP
+ and ARP/RARP messages. The frame beginning is 14 bytes, but for speed
+ purposes, we are going to assume there are 16 bytes free in front of the
+ prepend pointer and that the prepend pointer is 32-bit aligned.
+
+ Byte Offset Size Meaning
+
+ 0 6 Destination Ethernet Address
+ 6 6 Source Ethernet Address
+ 12 2 Ethernet Frame Type, where:
+
+ 0x0800 -> IP Datagram
+ 0x0806 -> ARP Request/Reply
+ 0x0835 -> RARP request reply
+
+ 42 18 Padding on ARP and RARP messages only. */
+
+#define NX_ETHERNET_IP 0x0800
+#define NX_ETHERNET_ARP 0x0806
+#define NX_ETHERNET_RARP 0x8035
+#define NX_ETHERNET_IPV6 0x86DD
+#define NX_ETHERNET_PPPOE_DISCOVERY 0x8863
+#define NX_ETHERNET_PPPOE_SESSION 0x8864
+#define NX_ETHERNET_SIZE 14
+
+/* For the pcap ethernet driver, physical addresses are allocated starting
+ at the preset value and then incremented before the next allocation. */
+
+ULONG nx_pcap_address_msw = 0x0011;
+ULONG nx_pcap_address_lsw = 0x22334457;
+
+static const CHAR *nx_pcap_source_name = NX_PCAP_SOURCE_NAME;
+
+#ifdef WIN32
+/* Define the Windows thread to call pcap_loop. */
+static HANDLE nx_pcap_receive_thread;
+#else
+/* Define the Linux thread to call pcap_loop. */
+static pthread_t nx_pcap_receive_thread;
+#endif
+static NX_IP *nx_pcap_default_ip;
+static pcap_t *nx_pcap_fp;
+
+/* Define the buffer to store data that will be sent by pcap. */
+static UCHAR nx_pcap_send_buff[NX_MAX_PACKET_SIZE];
+
+
+/* Define driver prototypes. */
+
+UINT _nx_pcap_initialize(NX_IP *ip_ptr);
+UINT _nx_pcap_send_packet(NX_PACKET * packet_ptr);
+#ifdef WIN32
+DWORD WINAPI _nx_pcap_receive_thread_entry(LPVOID thread_input);
+#else
+void *_nx_pcap_receive_thread_entry(void *arg);
+#endif
+VOID _nx_lpcap_packet_receive_handler(u_char *param, const struct pcap_pkthdr *header, const u_char *pkt_data);
+VOID _nx_pcap_network_driver_output(NX_PACKET *packet_ptr);
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+VOID nx_pcap_cleanup();
+
+/* Define interface capability. */
+
+#ifdef NX_ENABLE_INTERFACE_CAPABILITY
+#define NX_INTERFACE_CAPABILITY ( NX_INTERFACE_CAPABILITY_IPV4_RX_CHECKSUM | \
+ NX_INTERFACE_CAPABILITY_TCP_RX_CHECKSUM | \
+ NX_INTERFACE_CAPABILITY_UDP_RX_CHECKSUM | \
+ NX_INTERFACE_CAPABILITY_ICMPV4_RX_CHECKSUM | \
+ NX_INTERFACE_CAPABILITY_ICMPV6_RX_CHECKSUM )
+#endif /* NX_ENABLE_INTERFACE_CAPABILITY */
+
+VOID nx_pcap_set_source_name(const CHAR *source_name)
+{
+ nx_pcap_source_name = source_name;
+}
+
+UINT _nx_pcap_send_packet(NX_PACKET * packet_ptr)
+{
+ULONG size = 0;
+
+ /* Make sure the data length is less than MTU. */
+ if(packet_ptr -> nx_packet_length > NX_MAX_PACKET_SIZE)
+ return NX_NOT_SUCCESSFUL;
+
+ if(nx_packet_data_retrieve(packet_ptr, nx_pcap_send_buff, &size))
+ return NX_NOT_SUCCESSFUL;
+
+ if(pcap_sendpacket(nx_pcap_fp, nx_pcap_send_buff, size) != 0)
+ return NX_NOT_SUCCESSFUL;
+
+ return NX_SUCCESS;
+}
+
+
+void nx_pcap_cleanup()
+{
+ pcap_close(nx_pcap_fp);
+}
+
+
+VOID _nx_pcap_packet_receive_handler(u_char *param, const struct pcap_pkthdr *header, const u_char *pkt_data)
+{
+
+NX_PACKET *packet_ptr;
+UINT status;
+UINT packet_type;
+
+#ifndef NX_ENABLE_PCAP_LOCAL_RECEIVE
+ /* Check whether the packet is generated by local. */
+ if((*(pkt_data + 6) == ((nx_pcap_address_msw >> 8) & 0xFF)) &&
+ (*(pkt_data + 7) == (nx_pcap_address_msw & 0xFF)) &&
+ (*(pkt_data + 8) == ((nx_pcap_address_lsw >> 24) & 0xFF)) &&
+ (*(pkt_data + 9) == ((nx_pcap_address_lsw >> 16) & 0xFF)) &&
+ (*(pkt_data + 10) == ((nx_pcap_address_lsw >> 8) & 0xFF)) &&
+ (*(pkt_data + 11) == (nx_pcap_address_lsw & 0xFF)))
+ {
+ return;
+ }
+#endif /* NX_PCAP_LOCAL_RECEIVE */
+
+ _tx_thread_context_save();
+
+ status = nx_packet_allocate(nx_pcap_default_ip -> nx_ip_default_packet_pool, &packet_ptr, NX_RECEIVE_PACKET, NX_NO_WAIT);
+
+ if(status)
+ {
+ _tx_thread_context_restore();
+ return;
+ }
+
+ /* Make sure IP header is 4-byte aligned. */
+ packet_ptr -> nx_packet_prepend_ptr += 2;
+ packet_ptr -> nx_packet_append_ptr += 2;
+
+ status = nx_packet_data_append(packet_ptr, (VOID*)pkt_data, header -> len,
+ nx_pcap_default_ip -> nx_ip_default_packet_pool, NX_NO_WAIT);
+
+ if(status)
+ {
+ nx_packet_release(packet_ptr);
+ _tx_thread_context_restore();
+ return;
+ }
+
+ /* Pickup the packet header to determine where the packet needs to be sent. */
+ packet_type = (((UINT) (*(packet_ptr -> nx_packet_prepend_ptr+12))) << 8) |
+ ((UINT) (*(packet_ptr -> nx_packet_prepend_ptr+13)));
+
+ /* Route the incoming packet according to its ethernet type. */
+ if((packet_type == NX_ETHERNET_IP) || (packet_type == NX_ETHERNET_IPV6))
+ {
+
+ /* Note: The length reported by some Ethernet hardware includes bytes after the packet
+ as well as the Ethernet header. In some cases, the actual packet length after the
+ Ethernet header should be derived from the length in the IP header (lower 16 bits of
+ the first 32-bit word). */
+
+ /* Clean off the Ethernet header. */
+ packet_ptr -> nx_packet_prepend_ptr = packet_ptr -> nx_packet_prepend_ptr + NX_ETHERNET_SIZE;
+
+ /* Adjust the packet length. */
+ packet_ptr -> nx_packet_length = packet_ptr -> nx_packet_length - NX_ETHERNET_SIZE;
+
+
+ _nx_ip_packet_deferred_receive(nx_pcap_default_ip, packet_ptr);
+ }
+ else if(packet_type == NX_ETHERNET_ARP)
+ {
+
+ /* Clean off the Ethernet header. */
+ packet_ptr -> nx_packet_prepend_ptr = packet_ptr -> nx_packet_prepend_ptr + NX_ETHERNET_SIZE;
+
+ /* Adjust the packet length. */
+ packet_ptr -> nx_packet_length = packet_ptr -> nx_packet_length - NX_ETHERNET_SIZE;
+
+ _nx_arp_packet_deferred_receive(nx_pcap_default_ip, packet_ptr);
+
+ }
+ else if(packet_type == NX_ETHERNET_RARP)
+ {
+
+ /* Clean off the Ethernet header. */
+ packet_ptr -> nx_packet_prepend_ptr = packet_ptr -> nx_packet_prepend_ptr + NX_ETHERNET_SIZE;
+
+ /* Adjust the packet length. */
+ packet_ptr -> nx_packet_length = packet_ptr -> nx_packet_length - NX_ETHERNET_SIZE;
+
+ _nx_rarp_packet_deferred_receive(nx_pcap_default_ip, packet_ptr);
+ }
+#ifdef NX_ENABLE_PPPOE
+ else if ((packet_type == NX_ETHERNET_PPPOE_DISCOVERY) ||
+ (packet_type == NX_ETHERNET_PPPOE_SESSION))
+ {
+
+ /* Clean off the Ethernet header. */
+ packet_ptr -> nx_packet_prepend_ptr = packet_ptr -> nx_packet_prepend_ptr + NX_ETHERNET_SIZE;
+
+ /* Adjust the packet length. */
+ packet_ptr -> nx_packet_length = packet_ptr -> nx_packet_length - NX_ETHERNET_SIZE;
+
+ /* Route to the PPPoE receive function. */
+ _nx_pppoe_packet_deferred_receive(packet_ptr);
+ }
+#endif
+ else
+ {
+
+ /* Invalid ethernet header... release the packet. */
+ nx_packet_release(packet_ptr);
+ }
+ _tx_thread_context_restore();
+}
+
+#ifdef WIN32
+DWORD WINAPI _nx_pcap_receive_thread_entry(LPVOID thread_input)
+{
+ /* Loop to capture packets. */
+ pcap_loop(nx_pcap_fp, 0, _nx_pcap_packet_receive_handler, NULL);
+ return 0;
+}
+#else
+void *_nx_pcap_receive_thread_entry(void *arg)
+{
+
+ /* Loop to capture packets. */
+ pcap_loop(nx_pcap_fp, 0, _nx_pcap_packet_receive_handler, NULL);
+ return((void *)0);
+}
+#endif
+
+UINT _nx_pcap_initialize(NX_IP *ip_ptr_in)
+{
+CHAR errbuf[PCAP_ERRBUF_SIZE] = { 0 };
+
+#ifndef WIN32
+struct sched_param sp;
+
+ /* Define the thread's priority. */
+#ifdef TX_LINUX_PRIORITY_ISR
+ sp.sched_priority = TX_LINUX_PRIORITY_ISR;
+#else
+ sp.sched_priority = 2;
+#endif
+#endif
+
+ /* Return if source has been opened. */
+ if(nx_pcap_fp)
+ return 1;
+
+#ifdef WIN32
+ if((nx_pcap_fp = pcap_open(nx_pcap_source_name, 65536, PCAP_OPENFLAG_PROMISCUOUS, 1, NULL, errbuf)) == NULL)
+ {
+ return NX_NOT_CREATED;
+ }
+#else
+ if((nx_pcap_fp = pcap_create(nx_pcap_source_name, NULL)) == NULL)
+ {
+ return NX_NOT_CREATED;
+ }
+
+ if (pcap_set_immediate_mode(nx_pcap_fp, 1) < 0)
+ {
+ nx_pcap_cleanup();
+ return NX_NOT_CREATED;
+ }
+
+ if (pcap_set_promisc(nx_pcap_fp, 1) < 0)
+ {
+ nx_pcap_cleanup();
+ return NX_NOT_CREATED;
+ }
+
+ if (pcap_set_snaplen(nx_pcap_fp, 65536) < 0)
+ {
+ nx_pcap_cleanup();
+ return NX_NOT_CREATED;
+ }
+
+ if (pcap_activate(nx_pcap_fp) < 0)
+ {
+ nx_pcap_cleanup();
+ return NX_NOT_CREATED;
+ }
+#endif
+
+ nx_pcap_default_ip = ip_ptr_in;
+
+#ifdef WIN32
+ nx_pcap_receive_thread = CreateThread(NULL, 0, _nx_pcap_receive_thread_entry, (LPVOID)NULL, CREATE_SUSPENDED, NULL);
+ SetThreadPriority(nx_pcap_receive_thread, THREAD_PRIORITY_BELOW_NORMAL);
+ ResumeThread(nx_pcap_receive_thread);
+#else
+
+ /* Create a Linux thread to loop for capturing packets */
+ pthread_create(&nx_pcap_receive_thread, NULL, _nx_pcap_receive_thread_entry, NULL);
+
+ /* Set the thread's policy and priority */
+ pthread_setschedparam(nx_pcap_receive_thread, SCHED_FIFO, &sp);
+#endif
+
+ return NX_SUCCESS;
+}
+
+
+VOID _nx_pcap_network_driver_output(NX_PACKET *packet_ptr)
+{
+UINT old_threshold = 0;
+
+ /* Disable preemption. */
+ tx_thread_preemption_change(tx_thread_identify(), 0, &old_threshold);
+
+ _nx_pcap_send_packet(packet_ptr);
+
+ /* Remove the Ethernet header. In real hardware environments, this is typically
+ done after a transmit complete interrupt. */
+ packet_ptr -> nx_packet_prepend_ptr = packet_ptr -> nx_packet_prepend_ptr + NX_ETHERNET_SIZE;
+
+ /* Adjust the packet length. */
+ packet_ptr -> nx_packet_length = packet_ptr -> nx_packet_length - NX_ETHERNET_SIZE;
+
+ /* Now that the Ethernet frame has been removed, release the packet. */
+ nx_packet_transmit_release(packet_ptr);
+
+ /* Restore preemption. */
+ tx_thread_preemption_change(tx_thread_identify(), old_threshold, &old_threshold);
+}
+
+
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr)
+{
+NX_IP *ip_ptr;
+NX_PACKET *packet_ptr;
+ULONG *ethernet_frame_ptr;
+NX_INTERFACE *interface_ptr;
+#ifdef __PRODUCT_NETXDUO__
+UINT interface_index;
+#endif
+
+ /* Setup the IP pointer from the driver request. */
+ ip_ptr = driver_req_ptr -> nx_ip_driver_ptr;
+
+ /* Default to successful return. */
+ driver_req_ptr -> nx_ip_driver_status = NX_SUCCESS;
+
+ /* Setup interface pointer. */
+ interface_ptr = driver_req_ptr -> nx_ip_driver_interface;
+
+#ifdef __PRODUCT_NETXDUO__
+ /* Obtain the index number of the network interface. */
+ interface_index = interface_ptr -> nx_interface_index;
+#endif
+
+ /* Process according to the driver request type in the IP control
+ block. */
+ switch (driver_req_ptr -> nx_ip_driver_command)
+ {
+
+ case NX_LINK_INTERFACE_ATTACH:
+ {
+ interface_ptr = (NX_INTERFACE*)(driver_req_ptr -> nx_ip_driver_interface);
+ break;
+ }
+
+ case NX_LINK_INITIALIZE:
+ {
+
+ /* Device driver shall initialize the Ethernet Controller here. */
+
+ /* Once the Ethernet controller is initialized, the driver needs to
+ configure the NetX Interface Control block, as outlined below. */
+
+#ifdef __PRODUCT_NETXDUO__
+ /* The nx_interface_ip_mtu_size should be the MTU for the IP payload.
+ For regular Ethernet, the IP MTU is 1500. */
+ nx_ip_interface_mtu_set(ip_ptr, interface_index, (NX_LINK_MTU - NX_ETHERNET_SIZE));
+
+ /* Set the physical address (MAC address) of this IP instance. */
+ /* For this pcap driver, the MAC address is constructed by
+ incrementing a base lsw value, to simulate multiple nodes hanging on the
+ ethernet. */
+ nx_ip_interface_physical_address_set(ip_ptr, interface_index,
+ nx_pcap_address_msw,
+ nx_pcap_address_lsw,
+ NX_FALSE);
+
+ /* Indicate to the IP software that IP to physical mapping is required. */
+ nx_ip_interface_address_mapping_configure(ip_ptr, interface_index, NX_TRUE);
+#else
+ interface_ptr -> nx_interface_ip_mtu_size = NX_LINK_MTU;
+ interface_ptr -> nx_interface_physical_address_msw = nx_pcap_address_msw;
+ interface_ptr -> nx_interface_physical_address_lsw = nx_pcap_address_lsw;
+ interface_ptr -> nx_interface_address_mapping_needed = NX_TRUE;
+#endif
+
+
+ _nx_pcap_initialize(ip_ptr);
+
+#ifdef NX_ENABLE_INTERFACE_CAPABILITY
+ nx_ip_interface_capability_set(ip_ptr, interface_index, NX_INTERFACE_CAPABILITY);
+#endif /* NX_ENABLE_INTERFACE_CAPABILITY */
+ break;
+ }
+
+ case NX_LINK_ENABLE:
+ {
+
+ /* Process driver link enable. An Ethernet driver shall enable the
+ transmit and reception logic. Once the IP stack issues the
+ LINK_ENABLE command, the stack may start transmitting IP packets. */
+
+
+ /* In the driver, just set the enabled flag. */
+ interface_ptr -> nx_interface_link_up = NX_TRUE;
+
+ break;
+ }
+
+ case NX_LINK_DISABLE:
+ {
+
+ /* Process driver link disable. This command indicates the IP layer
+ is not going to transmit any IP datagrams, nor does it expect any
+ IP datagrams from the interface. Therefore after processing this command,
+ the device driver shall not send any incoming packets to the IP
+ layer. Optionally the device driver may turn off the interface. */
+
+ /* In the pcap driver, just clear the enabled flag. */
+ interface_ptr -> nx_interface_link_up = NX_FALSE;
+
+ break;
+ }
+
+ case NX_LINK_PACKET_SEND:
+ case NX_LINK_PACKET_BROADCAST:
+ case NX_LINK_ARP_SEND:
+ case NX_LINK_ARP_RESPONSE_SEND:
+ case NX_LINK_RARP_SEND:
+#ifdef NX_ENABLE_PPPOE
+ case NX_LINK_PPPOE_DISCOVERY_SEND:
+ case NX_LINK_PPPOE_SESSION_SEND:
+#endif
+ {
+
+ /*
+ The IP stack sends down a data packet for transmission.
+ The device driver needs to prepend a MAC header, and fill in the
+ Ethernet frame type (assuming Ethernet protocol for network transmission)
+ based on the type of packet being transmitted.
+
+ The following sequence illustrates this process.
+ */
+
+ /* Place the ethernet frame at the front of the packet. */
+ packet_ptr = driver_req_ptr -> nx_ip_driver_packet;
+
+ /* Adjust the prepend pointer. */
+ packet_ptr -> nx_packet_prepend_ptr = packet_ptr -> nx_packet_prepend_ptr - NX_ETHERNET_SIZE;
+
+ /* Adjust the packet length. */
+ packet_ptr -> nx_packet_length = packet_ptr -> nx_packet_length + NX_ETHERNET_SIZE;
+
+ /* Setup the ethernet frame pointer to build the ethernet frame. Backup another 2
+ bytes to get 32-bit word alignment. */
+ ethernet_frame_ptr = (ULONG *) (packet_ptr -> nx_packet_prepend_ptr - 2);
+
+ /* Build the ethernet frame. */
+ *ethernet_frame_ptr = driver_req_ptr -> nx_ip_driver_physical_address_msw;
+ *(ethernet_frame_ptr+1) = driver_req_ptr -> nx_ip_driver_physical_address_lsw;
+ *(ethernet_frame_ptr+2) = (interface_ptr -> nx_interface_physical_address_msw << 16) |
+ (interface_ptr -> nx_interface_physical_address_lsw >> 16);
+ *(ethernet_frame_ptr+3) = (interface_ptr -> nx_interface_physical_address_lsw << 16);
+
+ if(driver_req_ptr -> nx_ip_driver_command == NX_LINK_ARP_SEND)
+ *(ethernet_frame_ptr+3) |= NX_ETHERNET_ARP;
+ else if(driver_req_ptr -> nx_ip_driver_command == NX_LINK_ARP_RESPONSE_SEND)
+ *(ethernet_frame_ptr+3) |= NX_ETHERNET_ARP;
+ else if(driver_req_ptr -> nx_ip_driver_command == NX_LINK_RARP_SEND)
+ *(ethernet_frame_ptr+3) |= NX_ETHERNET_RARP;
+#ifdef NX_ENABLE_PPPOE
+ else if(driver_req_ptr -> nx_ip_driver_command == NX_LINK_PPPOE_DISCOVERY_SEND)
+ {
+ *(ethernet_frame_ptr + 3) |= NX_ETHERNET_PPPOE_DISCOVERY;
+ }
+ else if(driver_req_ptr -> nx_ip_driver_command == NX_LINK_PPPOE_SESSION_SEND)
+ {
+ *(ethernet_frame_ptr + 3) |= NX_ETHERNET_PPPOE_SESSION;
+ }
+#endif
+#ifdef __PRODUCT_NETXDUO__
+ else if(packet_ptr -> nx_packet_ip_version == 4)
+ *(ethernet_frame_ptr+3) |= NX_ETHERNET_IP;
+ else
+ *(ethernet_frame_ptr+3) |= NX_ETHERNET_IPV6;
+#else
+ else
+ *(ethernet_frame_ptr+3) |= NX_ETHERNET_IP;
+#endif
+
+
+
+ /* Endian swapping if NX_LITTLE_ENDIAN is defined. */
+ NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr));
+ NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr+1));
+ NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr+2));
+ NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr+3));
+
+ /* At this point, the packet is a complete Ethernet frame, ready to be transmitted.
+ The driver shall call the actual Ethernet transmit routine and put the packet
+ on the wire.
+
+ In this example, the pcap network transmit routine is called. */
+ _nx_pcap_network_driver_output(packet_ptr);
+ break;
+ }
+
+ case NX_LINK_MULTICAST_JOIN:
+ {
+
+ /* The IP layer issues this command to join a multicast group. Note that
+ multicast operation is required for IPv6.
+
+ On a typically Ethernet controller, the driver computes a hash value based
+ on MAC address, and programs the hash table.
+
+ It is likely the driver also needs to maintain an internal MAC address table.
+ Later if a multicast address is removed, the driver needs
+ to reprogram the hash table based on the remaining multicast MAC addresses. */
+
+ break;
+ }
+
+ case NX_LINK_MULTICAST_LEAVE:
+ {
+
+ /* The IP layer issues this command to remove a multicast MAC address from the
+ receiving list. A device driver shall properly remove the multicast address
+ from the hash table, so the hardware does not receive such traffic. Note that
+ in order to reprogram the hash table, the device driver may have to keep track of
+ current active multicast MAC addresses. */
+
+ /* The following procedure only applies to our pcap network driver, which manages
+ multicast MAC addresses by a simple look up table. */
+
+ break;
+ }
+
+ case NX_LINK_GET_STATUS:
+ {
+
+ /* Return the link status in the supplied return pointer. */
+ *(driver_req_ptr -> nx_ip_driver_return_ptr) = ip_ptr-> nx_ip_interface[0].nx_interface_link_up;
+ break;
+ }
+
+ case NX_LINK_DEFERRED_PROCESSING:
+ {
+
+ /* Driver defined deferred processing. This is typically used to defer interrupt
+ processing to the thread level.
+
+ A typical use case of this command is:
+ On receiving an Ethernet frame, the RX ISR does not process the received frame,
+ but instead records such an event in its internal data structure, and issues
+ a notification to the IP stack (the driver sends the notification to the IP
+ helping thread by calling "_nx_ip_driver_deferred_processing()". When the IP stack
+ gets a notification of a pending driver deferred process, it calls the
+ driver with the NX_LINK_DEFERRED_PROCESSING command. The driver shall complete
+ the pending receive process.
+ */
+
+ /* The pcap driver doesn't require a deferred process so it breaks out of
+ the switch case. */
+
+
+ break;
+ }
+
+ default:
+ {
+
+ /* Invalid driver request. */
+ /* Return the unhandled command status. */
+ driver_req_ptr -> nx_ip_driver_status = NX_UNHANDLED_COMMAND;
+ }
+
+ }
+}
+
diff --git a/test/regression/interoperability_test/nx_secure_test/cert.c b/test/regression/interoperability_test/nx_secure_test/cert.c
new file mode 100644
index 00000000..be5d89d7
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/cert.c
@@ -0,0 +1,68 @@
+unsigned char cert_der[] = {
+ 0x30, 0x82, 0x04, 0x07, 0x30, 0x82, 0x02, 0xef, 0xa0, 0x03, 0x02, 0x01, 0x02, 0x02, 0x09, 0x00,
+ 0xfb, 0x9f, 0xac, 0x8a, 0xe9, 0xe9, 0xfc, 0x6f, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86,
+ 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05, 0x00, 0x30, 0x81, 0x99, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03,
+ 0x55, 0x04, 0x06, 0x13, 0x02, 0x43, 0x4e, 0x31, 0x11, 0x30, 0x0f, 0x06, 0x03, 0x55, 0x04, 0x08,
+ 0x0c, 0x08, 0x53, 0x68, 0x61, 0x6e, 0x67, 0x48, 0x61, 0x69, 0x31, 0x11, 0x30, 0x0f, 0x06, 0x03,
+ 0x55, 0x04, 0x07, 0x0c, 0x08, 0x53, 0x68, 0x61, 0x6e, 0x67, 0x48, 0x61, 0x69, 0x31, 0x15, 0x30,
+ 0x13, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x0c, 0x65, 0x78, 0x70, 0x72, 0x65, 0x73, 0x73, 0x6c,
+ 0x6f, 0x67, 0x69, 0x63, 0x31, 0x14, 0x30, 0x12, 0x06, 0x03, 0x55, 0x04, 0x0b, 0x0c, 0x0b, 0x64,
+ 0x65, 0x76, 0x65, 0x6c, 0x6f, 0x70, 0x6d, 0x65, 0x6e, 0x74, 0x31, 0x0f, 0x30, 0x0d, 0x06, 0x03,
+ 0x55, 0x04, 0x03, 0x0c, 0x06, 0x7a, 0x68, 0x75, 0x61, 0x6e, 0x67, 0x31, 0x26, 0x30, 0x24, 0x06,
+ 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x09, 0x01, 0x16, 0x17, 0x7a, 0x68, 0x75, 0x61,
+ 0x6e, 0x67, 0x40, 0x65, 0x78, 0x70, 0x72, 0x65, 0x73, 0x73, 0x6c, 0x6f, 0x67, 0x69, 0x63, 0x2e,
+ 0x63, 0x6f, 0x6d, 0x30, 0x1e, 0x17, 0x0d, 0x31, 0x37, 0x30, 0x37, 0x31, 0x38, 0x30, 0x38, 0x33,
+ 0x39, 0x31, 0x37, 0x5a, 0x17, 0x0d, 0x31, 0x38, 0x30, 0x37, 0x31, 0x38, 0x30, 0x38, 0x33, 0x39,
+ 0x31, 0x37, 0x5a, 0x30, 0x81, 0x99, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13,
+ 0x02, 0x43, 0x4e, 0x31, 0x11, 0x30, 0x0f, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x08, 0x53, 0x68,
+ 0x61, 0x6e, 0x67, 0x48, 0x61, 0x69, 0x31, 0x11, 0x30, 0x0f, 0x06, 0x03, 0x55, 0x04, 0x07, 0x0c,
+ 0x08, 0x53, 0x68, 0x61, 0x6e, 0x67, 0x48, 0x61, 0x69, 0x31, 0x15, 0x30, 0x13, 0x06, 0x03, 0x55,
+ 0x04, 0x0a, 0x0c, 0x0c, 0x65, 0x78, 0x70, 0x72, 0x65, 0x73, 0x73, 0x6c, 0x6f, 0x67, 0x69, 0x63,
+ 0x31, 0x14, 0x30, 0x12, 0x06, 0x03, 0x55, 0x04, 0x0b, 0x0c, 0x0b, 0x64, 0x65, 0x76, 0x65, 0x6c,
+ 0x6f, 0x70, 0x6d, 0x65, 0x6e, 0x74, 0x31, 0x0f, 0x30, 0x0d, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c,
+ 0x06, 0x7a, 0x68, 0x75, 0x61, 0x6e, 0x67, 0x31, 0x26, 0x30, 0x24, 0x06, 0x09, 0x2a, 0x86, 0x48,
+ 0x86, 0xf7, 0x0d, 0x01, 0x09, 0x01, 0x16, 0x17, 0x7a, 0x68, 0x75, 0x61, 0x6e, 0x67, 0x40, 0x65,
+ 0x78, 0x70, 0x72, 0x65, 0x73, 0x73, 0x6c, 0x6f, 0x67, 0x69, 0x63, 0x2e, 0x63, 0x6f, 0x6d, 0x30,
+ 0x82, 0x01, 0x22, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x01,
+ 0x05, 0x00, 0x03, 0x82, 0x01, 0x0f, 0x00, 0x30, 0x82, 0x01, 0x0a, 0x02, 0x82, 0x01, 0x01, 0x00,
+ 0xa7, 0xa3, 0xf4, 0x15, 0xcc, 0xd0, 0xb6, 0x64, 0xb1, 0x2a, 0xf7, 0x63, 0xbf, 0xbc, 0xf1, 0x31,
+ 0xa0, 0xb4, 0x39, 0xd6, 0x62, 0xbe, 0xeb, 0xd8, 0x01, 0x27, 0x10, 0xa7, 0x6d, 0xb8, 0x38, 0x01,
+ 0xaf, 0xa2, 0x87, 0xc3, 0xf2, 0x47, 0x4b, 0x36, 0x68, 0x40, 0x31, 0x03, 0xb1, 0x00, 0x5c, 0xfb,
+ 0x80, 0x20, 0xb6, 0x22, 0xb4, 0x3a, 0x20, 0x10, 0x58, 0xd4, 0x24, 0xdb, 0xf2, 0x36, 0x49, 0xd7,
+ 0x73, 0xda, 0xf7, 0x89, 0xc0, 0x50, 0x19, 0xe4, 0x40, 0x6d, 0x71, 0x77, 0xfd, 0x64, 0xbb, 0x7f,
+ 0x0b, 0xf6, 0xcb, 0x6f, 0x34, 0x33, 0xa8, 0x71, 0xb9, 0x78, 0x74, 0x35, 0xd6, 0x6f, 0x0e, 0x3e,
+ 0x32, 0x5d, 0x59, 0x02, 0xe0, 0xd0, 0x01, 0x68, 0x8b, 0x22, 0xc0, 0x5a, 0x5b, 0xd8, 0xd5, 0x31,
+ 0xdc, 0x90, 0xf0, 0xd3, 0xe2, 0x36, 0x74, 0x07, 0x2b, 0x0c, 0x9e, 0x02, 0xee, 0xea, 0x25, 0xbb,
+ 0x7b, 0xa5, 0x4f, 0x02, 0x56, 0x20, 0x77, 0x83, 0x68, 0xb0, 0x43, 0x5d, 0x19, 0x37, 0x00, 0x72,
+ 0x7e, 0xba, 0xce, 0x1c, 0x67, 0xc2, 0xdc, 0x05, 0x8b, 0xa6, 0xf5, 0xc6, 0xb5, 0xd1, 0x15, 0x40,
+ 0x47, 0x88, 0x0b, 0xda, 0x32, 0xa5, 0x4d, 0x16, 0x68, 0xd1, 0x6c, 0x63, 0xb9, 0x8f, 0x76, 0x13,
+ 0x69, 0x15, 0xc3, 0x6d, 0xc4, 0x5c, 0xe8, 0x2b, 0xe4, 0xc0, 0x99, 0xbd, 0x7a, 0x66, 0x83, 0x34,
+ 0x5b, 0x95, 0xeb, 0x1f, 0x51, 0xbf, 0x7e, 0xfd, 0xea, 0x0c, 0xb7, 0xf7, 0x36, 0xeb, 0xfb, 0xf0,
+ 0x03, 0xf1, 0xe0, 0x15, 0x21, 0x3a, 0xc6, 0xa2, 0xd9, 0xfa, 0x25, 0x58, 0x62, 0xb8, 0x2e, 0x6d,
+ 0xb5, 0xf7, 0x4d, 0x46, 0xcd, 0xec, 0xae, 0x34, 0x16, 0x47, 0xd1, 0x17, 0xcc, 0x78, 0x38, 0x85,
+ 0x6a, 0x22, 0x62, 0x7e, 0xc3, 0x16, 0x2f, 0x5c, 0x6a, 0x99, 0x42, 0x08, 0xc4, 0xaf, 0xe2, 0x5d,
+ 0x02, 0x03, 0x01, 0x00, 0x01, 0xa3, 0x50, 0x30, 0x4e, 0x30, 0x1d, 0x06, 0x03, 0x55, 0x1d, 0x0e,
+ 0x04, 0x16, 0x04, 0x14, 0x17, 0x97, 0x07, 0x1d, 0xdc, 0xee, 0x28, 0x41, 0xcb, 0x30, 0x0c, 0x24,
+ 0x69, 0x6c, 0x8c, 0xcc, 0xfd, 0x34, 0x58, 0x68, 0x30, 0x1f, 0x06, 0x03, 0x55, 0x1d, 0x23, 0x04,
+ 0x18, 0x30, 0x16, 0x80, 0x14, 0x17, 0x97, 0x07, 0x1d, 0xdc, 0xee, 0x28, 0x41, 0xcb, 0x30, 0x0c,
+ 0x24, 0x69, 0x6c, 0x8c, 0xcc, 0xfd, 0x34, 0x58, 0x68, 0x30, 0x0c, 0x06, 0x03, 0x55, 0x1d, 0x13,
+ 0x04, 0x05, 0x30, 0x03, 0x01, 0x01, 0xff, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7,
+ 0x0d, 0x01, 0x01, 0x0b, 0x05, 0x00, 0x03, 0x82, 0x01, 0x01, 0x00, 0x4e, 0xee, 0x44, 0x2e, 0x0f,
+ 0xad, 0xf1, 0x7b, 0x9c, 0x4d, 0x43, 0x0f, 0xc0, 0xd0, 0xc0, 0xdd, 0x21, 0x4d, 0x2c, 0xb1, 0xd8,
+ 0x8e, 0x75, 0x06, 0x10, 0xe6, 0x25, 0x43, 0xe1, 0x7d, 0x06, 0x24, 0x9f, 0x45, 0x86, 0x9b, 0x79,
+ 0xd2, 0xc0, 0x77, 0xc7, 0x37, 0x5e, 0xb9, 0x06, 0x1f, 0x17, 0xd3, 0x2e, 0x03, 0xd9, 0xe7, 0x34,
+ 0x4a, 0x62, 0x92, 0xe8, 0x11, 0xa8, 0xeb, 0xff, 0x2e, 0xc9, 0x09, 0x66, 0x65, 0x21, 0xc5, 0xca,
+ 0x95, 0x55, 0xd8, 0x33, 0x06, 0xed, 0xf0, 0x2d, 0xcc, 0x34, 0x8e, 0x61, 0xa2, 0xf3, 0xdc, 0x3e,
+ 0x70, 0x34, 0x35, 0xef, 0xe4, 0x26, 0xb7, 0xf6, 0x9f, 0xa4, 0x0c, 0x69, 0x9e, 0x27, 0x74, 0x7b,
+ 0x14, 0xd4, 0x6e, 0xfc, 0xee, 0xf6, 0xe1, 0x9d, 0x8f, 0x1c, 0xcb, 0x95, 0xa1, 0xda, 0xf4, 0xec,
+ 0x6b, 0x68, 0x1a, 0xb5, 0x3f, 0x58, 0x86, 0xd8, 0x2a, 0x58, 0x85, 0xc2, 0x6f, 0x6f, 0xe3, 0x96,
+ 0x21, 0xaa, 0x64, 0x1e, 0x7b, 0x69, 0xbd, 0x28, 0xc4, 0x52, 0x23, 0x9f, 0xd0, 0xc6, 0x12, 0xc3,
+ 0xf3, 0x52, 0x80, 0x76, 0x99, 0xa6, 0x95, 0x06, 0xab, 0x24, 0xf3, 0x95, 0x50, 0xde, 0xd7, 0x4f,
+ 0xe8, 0x55, 0x7f, 0xf2, 0x65, 0x40, 0x9f, 0x95, 0xc6, 0x44, 0xac, 0xc0, 0xa0, 0x53, 0xa5, 0xf9,
+ 0x30, 0x2f, 0x39, 0x71, 0xf4, 0xe7, 0x89, 0xb2, 0xd9, 0xb3, 0xca, 0xea, 0x49, 0x43, 0xda, 0xf1,
+ 0x2e, 0x22, 0x6c, 0xed, 0x3d, 0x85, 0x4b, 0x0d, 0x5e, 0x9c, 0xad, 0x09, 0x13, 0xfc, 0xdd, 0x8f,
+ 0xe1, 0x28, 0x16, 0x7c, 0xd5, 0x75, 0x4b, 0x1e, 0x2c, 0xc6, 0x3f, 0x3e, 0xe6, 0xfe, 0xbf, 0xfe,
+ 0x6b, 0x02, 0xdf, 0x81, 0xc8, 0x20, 0xcc, 0x42, 0xb7, 0xec, 0x6f, 0xa4, 0x44, 0x62, 0xa9, 0xd2,
+ 0x6c, 0xbb, 0xd2, 0xe3, 0x9e, 0x4f, 0x03, 0x3d, 0x80, 0xb4, 0xef
+};
+unsigned int cert_der_len = 1035;
diff --git a/test/regression/interoperability_test/nx_secure_test/cert.pem b/test/regression/interoperability_test/nx_secure_test/cert.pem
new file mode 100644
index 00000000..76cbe9bf
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/cert.pem
@@ -0,0 +1,24 @@
+-----BEGIN CERTIFICATE-----
+MIIEBzCCAu+gAwIBAgIJAPufrIrp6fxvMA0GCSqGSIb3DQEBCwUAMIGZMQswCQYD
+VQQGEwJDTjERMA8GA1UECAwIU2hhbmdIYWkxETAPBgNVBAcMCFNoYW5nSGFpMRUw
+EwYDVQQKDAxleHByZXNzbG9naWMxFDASBgNVBAsMC2RldmVsb3BtZW50MQ8wDQYD
+VQQDDAZ6aHVhbmcxJjAkBgkqhkiG9w0BCQEWF3podWFuZ0BleHByZXNzbG9naWMu
+Y29tMB4XDTE3MDcxODA4MzkxN1oXDTE4MDcxODA4MzkxN1owgZkxCzAJBgNVBAYT
+AkNOMREwDwYDVQQIDAhTaGFuZ0hhaTERMA8GA1UEBwwIU2hhbmdIYWkxFTATBgNV
+BAoMDGV4cHJlc3Nsb2dpYzEUMBIGA1UECwwLZGV2ZWxvcG1lbnQxDzANBgNVBAMM
+BnpodWFuZzEmMCQGCSqGSIb3DQEJARYXemh1YW5nQGV4cHJlc3Nsb2dpYy5jb20w
+ggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCno/QVzNC2ZLEq92O/vPEx
+oLQ51mK+69gBJxCnbbg4Aa+ih8PyR0s2aEAxA7EAXPuAILYitDogEFjUJNvyNknX
+c9r3icBQGeRAbXF3/WS7fwv2y280M6hxuXh0NdZvDj4yXVkC4NABaIsiwFpb2NUx
+3JDw0+I2dAcrDJ4C7uolu3ulTwJWIHeDaLBDXRk3AHJ+us4cZ8LcBYum9ca10RVA
+R4gL2jKlTRZo0WxjuY92E2kVw23EXOgr5MCZvXpmgzRblesfUb9+/eoMt/c26/vw
+A/HgFSE6xqLZ+iVYYrgubbX3TUbN7K40FkfRF8x4OIVqImJ+wxYvXGqZQgjEr+Jd
+AgMBAAGjUDBOMB0GA1UdDgQWBBQXlwcd3O4oQcswDCRpbIzM/TRYaDAfBgNVHSME
+GDAWgBQXlwcd3O4oQcswDCRpbIzM/TRYaDAMBgNVHRMEBTADAQH/MA0GCSqGSIb3
+DQEBCwUAA4IBAQBO7kQuD63xe5xNQw/A0MDdIU0ssdiOdQYQ5iVD4X0GJJ9Fhpt5
+0sB3xzdeuQYfF9MuA9nnNEpikugRqOv/LskJZmUhxcqVVdgzBu3wLcw0jmGi89w+
+cDQ17+Qmt/afpAxpnid0exTUbvzu9uGdjxzLlaHa9OxraBq1P1iG2CpYhcJvb+OW
+IapkHntpvSjEUiOf0MYSw/NSgHaZppUGqyTzlVDe10/oVX/yZUCflcZErMCgU6X5
+MC85cfTnibLZs8rqSUPa8S4ibO09hUsNXpytCRP83Y/hKBZ81XVLHizGPz7m/r/+
+awLfgcggzEK37G+kRGKp0my70uOeTwM9gLTv
+-----END CERTIFICATE-----
diff --git a/test/regression/interoperability_test/nx_secure_test/demo_background_test_process_test.c b/test/regression/interoperability_test/nx_secure_test/demo_background_test_process_test.c
new file mode 100644
index 00000000..6c965891
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/demo_background_test_process_test.c
@@ -0,0 +1,83 @@
+#include "tls_test_frame.h"
+
+INT demo_background_test_process_test_entry(TLS_TEST_INSTANCE* instance_ptr);
+
+INT main(INT argc, CHAR* argv[])
+{
+INT status, exit_status;
+UINT offset, length;
+VOID* shared_buffer;
+TLS_TEST_INSTANCE *ins0;
+TLS_TEST_DIRECTOR *director;
+
+ /* Create a test instance. */
+ status = tls_test_instance_create(&ins0, /* test instance ptr */
+ "background_test_process_test_instance", /* instance name */
+ demo_background_test_process_test_entry, /* test entry */
+ 0, /* delay(seconds) */
+ 10, /* timeout(seconds) */
+ 1024, /* shared buffer size */
+ NULL); /* reserved */
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Launch the test instance. */
+ status = tls_test_director_create(&director, NULL);
+ status += tls_test_director_register_test_instance(director, ins0);
+ status += tls_test_director_test_start(director);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check exit status. */
+ status = tls_test_instance_get_exit_status(ins0, &exit_status);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Destroy the test director and registered test instances. */
+ status = tls_test_director_clean_all(director);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ return_value_if_fail(-SIGALRM == exit_status, TLS_TEST_INSTANCE_FAILED);
+ return 0;
+}
+
+INT demo_background_test_process_test_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+INT exit_status, status;
+UINT length;
+TLS_TEST_EXTERNAL_TEST_PROCESS ext_p;
+
+/* Sleep for 10 seconds and then echo "hello". */
+CHAR* external_cmd[] = { "sleep.sh", "10", (CHAR*)NULL};
+
+ /* Launch the test program in background. */
+ status = tls_test_launch_external_test_process_in_background( &ext_p, external_cmd);
+ return_value_if_fail( TLS_TEST_SUCCESS == status, status);
+
+ /* Kill the external test process before termination. */
+ tls_test_sleep(3);
+ status = tls_test_kill_external_test_process( &ext_p);
+ return_value_if_fail( TLS_TEST_SUCCESS == status, status);
+
+ /* Get the exit status of the test process which is kill by SIGTERM. */
+ status = tls_test_wait_external_test_process( &ext_p, &exit_status);
+ return_value_if_fail( TLS_TEST_SUCCESS == status, status);
+ return_value_if_fail( -SIGTERM == exit_status, TLS_TEST_INSTANCE_FAILED);
+
+ /* Sleep for only 1 seconds this time. */
+ external_cmd[1] = "1";
+ status = tls_test_launch_external_test_process_in_background( &ext_p, external_cmd);
+ return_value_if_fail( TLS_TEST_SUCCESS == status, status);
+
+ /* Get the exit status of the test process. */
+ status = tls_test_wait_external_test_process( &ext_p, &exit_status);
+ return_value_if_fail( TLS_TEST_SUCCESS == status, status);
+ return_value_if_fail( 0 == exit_status, TLS_TEST_INSTANCE_FAILED);
+
+ /* The test instance will be killed by SIGALRM this time. */
+ external_cmd[1] = "10";
+ status = tls_test_launch_external_test_process_in_background( &ext_p, external_cmd);
+ return_value_if_fail( TLS_TEST_SUCCESS == status, status);
+
+ status = tls_test_wait_external_test_process( &ext_p, &exit_status);
+ return_value_if_fail( TLS_TEST_SUCCESS == status, status);
+
+ return exit_status;
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/demo_dtls_test.c b/test/regression/interoperability_test/nx_secure_test/demo_dtls_test.c
new file mode 100644
index 00000000..d1d13693
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/demo_dtls_test.c
@@ -0,0 +1,97 @@
+#include "tls_test_frame.h"
+
+INT demo_server_entry(TLS_TEST_INSTANCE* instance_ptr);
+INT demo_client_entry(TLS_TEST_INSTANCE* instance_ptr);
+
+/* Global demo semaphore. */
+TLS_TEST_SEMAPHORE* demo_semaphore;
+
+INT main( INT argc, CHAR* argv[])
+{
+INT status, exit_status[2];
+TLS_TEST_INSTANCE *ins0;
+TLS_TEST_INSTANCE *ins1;
+
+ /* Create two test instances. */
+ status = tls_test_instance_create(&ins0, /* test instance ptr */
+ "demo_server", /* instance name */
+ demo_server_entry, /* test entry */
+ 0, /* delay(seconds) */
+ 20, /* timeout(seconds) */
+ 1024, /* shared buffer size */
+ NULL); /* reserved */
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ status = tls_test_instance_create(&ins1,
+ "demo_client",
+ demo_client_entry,
+ 0,
+ 20,
+ 1024,
+ NULL);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Create a semaphore and set the initial value as 0. */
+ status = tls_test_semaphore_create(&demo_semaphore, 0);
+
+ /* Create the test director. */
+ TLS_TEST_DIRECTOR *director;
+ status = tls_test_director_create(&director, NULL /* reserved */);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Register test instances to the director. */
+ status = tls_test_director_register_test_instance(director, ins0);
+ status += tls_test_director_register_test_instance(director, ins1);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Launch test. */
+ status = tls_test_director_test_start(director);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Collect exit code. */
+ tls_test_instance_get_exit_status(ins0, &(exit_status[0]));
+ tls_test_instance_get_exit_status(ins1, &(exit_status[1]));
+ tls_test_instance_show_exit_status(ins0);
+ tls_test_instance_show_exit_status(ins1);
+
+ /* Destroy registered test instances and the director. */
+ tls_test_director_clean_all(director);
+
+ /* Destroy the semaphore. */
+ tls_test_semaphore_destroy(demo_semaphore);
+
+ /* Is this test point disabled? */
+ if ((TLS_TEST_NOT_AVAILABLE == exit_status[0]) || (TLS_TEST_NOT_AVAILABLE == exit_status[1]))
+ return TLS_TEST_NOT_AVAILABLE;
+
+ return exit_status[0] | exit_status[1];
+}
+
+/* Instance two test entry. */
+INT demo_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+CHAR* external_cmd[] = { "demo_openssl_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING, "-dtls1_2", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ for ( ; i < 1; i++)
+ {
+ print_error_message("Client connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(demo_semaphore);
+ tls_test_sleep(1);
+ print_error_message("Client connection %d: client get semaphore. Launch a external test program.\n", i);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ if (exit_status)
+ {
+ /* Record errors. */
+ instance_status = TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED;
+ }
+ }
+ return instance_status;
+}
+
+/* The definition of demo_server_entry is located at demo_tls_test_server.c */
diff --git a/test/regression/interoperability_test/nx_secure_test/demo_dtls_test_server.c b/test/regression/interoperability_test/nx_secure_test/demo_dtls_test_server.c
new file mode 100644
index 00000000..eef0b79b
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/demo_dtls_test_server.c
@@ -0,0 +1,224 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* demo_semaphore;
+
+/* Define the ThreadX and NetX object control blocks... */
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_SECURE_DTLS_SERVER dtls_server;
+NX_SECURE_X509_CERT certificate;
+
+UCHAR tls_packet_buffer[4000];
+
+/* Session buffer for DTLS server. Must be equal to the size of NX_SECURE_DTLS_SESSION times the
+ number of desired DTLS sessions. */
+static UCHAR session_buffer[sizeof(NX_SECURE_DTLS_SESSION)];
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+void server_thread_entry(ULONG thread_input);
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+CHAR crypto_metadata[30000];
+
+#include "ica_test_device_cert.c"
+#include "ica_test_ica_cert.c"
+
+CHAR *html_data = "HTTP/1.1 200 OK\r\n" \
+ "Date: Fri, 15 Sep 2016 23:59:59 GMT\r\n" \
+ "Content-Type: text/html\r\n" \
+ "Content-Length: 200\r\n\r\n" \
+ "<html>\r\n"\
+ "<body>\r\n"\
+ "<b>Hello NetX Secure User!</b>\r\n"\
+ "This is a simple webpage\r\n"\
+ "served up using NetX Secure!\r\n"\
+ "</body>\r\n"\
+ "</html>\r\n";
+
+/* Define the pointer of current instance control block. */
+static TLS_TEST_INSTANCE* demo_instance_ptr;
+
+/* Define external references. */
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Instance one test entry. */
+INT demo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_DTLS)
+
+ /* Get instance pointer. */
+ demo_instance_ptr = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
+
+/* Define what the initial system looks like. */
+void tx_application_define(void *first_unused_memory)
+{
+ ULONG gateway_ipv4_address;
+ UINT status;
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL, &pool_0, _nx_pcap_network_driver, (UCHAR*)ip_thread_stack, sizeof(ip_thread_stack), 1);
+print_error_message( "ip address number: %lu\n", TLS_TEST_IP_ADDRESS_NUMBER);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ nx_secure_tls_initialize();
+ nx_secure_dtls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", server_thread_entry, 0, demo_thread_stack, sizeof(demo_thread_stack), 16, 16, 4, TX_AUTO_START);
+}
+
+/* Notification flags for DTLS server connect/receive. */
+UINT server_connect_count = 0;
+UINT server_receive_count = 0;
+NX_SECURE_DTLS_SESSION *connect_session;
+NX_SECURE_DTLS_SESSION *receive_session;
+
+/* Connect notify callback for DTLS server - notifies the application thread that
+ a DTLS connection is ready to kickoff a handshake. */
+UINT server_connect_notify(NX_SECURE_DTLS_SESSION *dtls_session, NXD_ADDRESS *ip_address, UINT port)
+{
+ connect_session = dtls_session;
+ server_connect_count++;
+ return(NX_SUCCESS);
+}
+
+/* Receive notify callback for DTLS server - notifies the application thread that
+ we have received a DTLS record over an established DTLS session. */
+UINT server_receive_notify(NX_SECURE_DTLS_SESSION *dtls_session)
+{
+ receive_session = dtls_session;
+ server_receive_count++;
+ return(NX_SUCCESS);
+}
+
+/* TLS Server example application thread. */
+void server_thread_entry(ULONG thread_input)
+{
+ INT i = 0, status = 0;
+ ULONG actual_status;
+ NX_PACKET *receive_packet;
+ NX_PACKET *send_packet;
+ UCHAR receive_buffer[100];
+ ULONG bytes;
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Create a socket. */
+ status = nx_secure_dtls_server_create(&dtls_server, &ip_0, DEVICE_SERVER_PORT, NX_IP_PERIODIC_RATE,
+ session_buffer, sizeof(session_buffer),
+ &nx_crypto_tls_ciphers, crypto_metadata, sizeof(crypto_metadata),
+ tls_packet_buffer, sizeof(tls_packet_buffer),
+ server_connect_notify, server_receive_notify);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ memset(&certificate, 0, sizeof(certificate));
+ status = nx_secure_x509_certificate_initialize(&certificate,
+ test_device_cert_der, test_device_cert_der_len,
+ NX_NULL, 0, test_device_cert_key_der,
+ test_device_cert_key_der_len, NX_SECURE_X509_KEY_TYPE_RSA_PKCS1_DER);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_dtls_server_local_certificate_add(&dtls_server, &certificate, 1);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_dtls_server_start(&dtls_server);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ for ( ; i < 1; i++)
+ {
+ /* Post semaphore before accept sockets. */
+ print_error_message("Server connection %d: server is prepared. Post the semaphore.\n", i);
+ tls_test_semaphore_post(demo_semaphore);
+
+ /* Accept a client socket connection. */
+ print_error_message("Server connection %d: wait for connections.\n", i);
+
+ while (!server_connect_count)
+ {
+ tx_thread_sleep(1);
+ }
+ server_connect_count = 0;
+ print_error_message("Server connection %d: server accept.\n", i);
+
+ /* Start the connected DTLS session. */
+ status = nx_secure_dtls_server_session_start(connect_session, 20 * NX_IP_PERIODIC_RATE);
+ exit_if_fail( NX_SUCCESS == status, 1);
+
+ /* Wait for records to be received. */
+ print_error_message("Server connection %d: wait for records.\n", i);
+ while (!server_receive_count)
+ {
+ tx_thread_sleep(1);
+ }
+ server_receive_count = 0;
+
+ /* Receive the HTTP request, and print it out. */
+ status = nx_secure_dtls_session_receive(receive_session, &receive_packet, 5 * NX_IP_PERIODIC_RATE);
+ exit_if_fail( NX_SUCCESS == status, 2);
+
+ /* Show received data. */
+ nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ receive_buffer[bytes] = 0;
+ print_error_message("Server received data: %s\n", receive_buffer);
+
+ /* Allocate a return packet and send our HTML data back to the client. */
+ status = nx_secure_dtls_packet_allocate(connect_session, &pool_0, &send_packet, NX_NO_WAIT);
+ exit_if_fail( NX_SUCCESS == status, 3);
+
+ /* Send the prepared html page. */
+ status = nx_packet_data_append(send_packet, html_data, strlen(html_data), &pool_0, NX_NO_WAIT);
+ exit_if_fail( NX_SUCCESS == status, 4);
+
+ /* DTLS send the HTML/HTTPS data back to the client. */
+ status = nx_secure_dtls_server_session_send(connect_session, send_packet);
+ exit_if_fail( NX_SUCCESS == status, 5);
+
+ /* End the DTLS session. */
+ nx_secure_dtls_session_end(connect_session, NX_NO_WAIT);
+
+ print_error_message("Server connection %d: server unaccept, sleeping...\n", i);
+ tx_thread_sleep(5 * NX_IP_PERIODIC_RATE);
+ }
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/demo_ping_test.c b/test/regression/interoperability_test/nx_secure_test/demo_ping_test.c
new file mode 100644
index 00000000..54966728
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/demo_ping_test.c
@@ -0,0 +1,194 @@
+#include "tls_test_frame.h"
+
+/* Declare the test entries of two test instances. */
+INT demo_func_entry_0(TLS_TEST_INSTANCE* instance_ptr);
+INT demo_func_entry_1(TLS_TEST_INSTANCE* instance_ptr);
+
+/* Declare global semaphore pointers. */
+TLS_TEST_SEMAPHORE* semaphore_server_prepared;
+TLS_TEST_SEMAPHORE* semaphore_client_terminated;
+
+INT main( INT argc, CHAR* argv[])
+{
+INT status;
+TLS_TEST_INSTANCE* ins0;
+TLS_TEST_INSTANCE* ins1;
+TLS_TEST_DIRECTOR* director;
+INT exit_status[2], i;
+
+ /* Create two test instances. */
+ status = tls_test_instance_create(&ins0, /* test instance ptr */
+ "icmp_server", /* instance name */
+ demo_func_entry_0, /* test entry */
+ 0, /* delay(seconds) */
+ 40000, /* timeout(seconds) */
+ 1024, /* shared buffer size */
+ NULL); /* reserved */
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ status = tls_test_instance_create(&ins1,
+ "icmp_client",
+ demo_func_entry_1,
+ 1,
+ 40000,
+ 1024,
+ NULL);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Create two semaphore and set the initial value as 0. */
+ status = tls_test_semaphore_create(&semaphore_server_prepared, 0/* initial value */);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+ status = tls_test_semaphore_create(&semaphore_client_terminated, 0);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Create the test director. */
+ status = tls_test_director_create(&director, NULL/* description (reserved) */);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Register test instances to the test director. */
+ status = tls_test_director_register_test_instance(director, ins0);
+ status += tls_test_director_register_test_instance(director, ins1);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Launch test. */
+ status = tls_test_director_test_start(director);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Error checking. */
+ tls_test_instance_show_exit_status(ins0);
+ tls_test_instance_show_exit_status(ins1);
+
+ /* Record exit codes. */
+ status = tls_test_instance_get_exit_status(ins0, &(exit_status[0]));
+ status += tls_test_instance_get_exit_status(ins1, &(exit_status[1]));
+ return_value_if_fail(TLS_TEST_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Destroy the director and the registered instances. */
+ status = tls_test_director_clean_all(director);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Destroy semaphores. */
+ tls_test_semaphore_destroy(semaphore_server_prepared);
+ tls_test_semaphore_destroy(semaphore_client_terminated);
+
+ return exit_status[0] | exit_status[1];
+}
+
+/* Call external program as test entry */
+INT demo_func_entry_1(TLS_TEST_INSTANCE* instance_ptr)
+{
+INT exit_status;
+INT status;
+/* Define an array of strings as the arguments of external program. */
+/* Note: the last element of the array must be NULL. */
+CHAR* external_cmd[] = { "ping", TLS_TEST_IP_ADDRESS_STRING, "-c", "4", (CHAR*)NULL};
+
+ /* Wait for server prepared. */
+ tls_test_semaphore_wait(semaphore_server_prepared);
+
+ /* Call external program to ping the icmp server. */
+ /* The exit code of external program will be stored in the contorl block of current instance . */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+ /* Post another semaphore after the icmp test. */
+ tls_test_semaphore_post(semaphore_client_terminated);
+
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+ return TLS_TEST_SUCCESS;
+}
+
+static TLS_TEST_INSTANCE* demo_instance;
+
+/* Create a threax device as an icmp echo server. */
+INT demo_func_entry_0(TLS_TEST_INSTANCE* instance_ptr)
+{
+VOID* shm;
+INT status;
+
+ /* Store the address of current instance control block in static variable for we don't have the method passing parameters to ThreadX kernel. */
+ demo_instance = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+}
+
+/* Define the ThreadX and NetX object control blocks... */
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+UCHAR tls_packet_buffer[4000];
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+/* Pcap network driver. */
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Declare a thread entry. */
+VOID demo_thread_entry(ULONG thread_input);
+
+/* Define what the initial system looks like. */
+void tx_application_define(void *first_unused_memory)
+{
+ULONG gateway_ipv4_address;
+UINT status;
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL, &pool_0, _nx_pcap_network_driver, (UCHAR*)ip_thread_stack, sizeof(ip_thread_stack), 1);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Post the semaphore to enable icmp test. */
+ tls_test_semaphore_post(semaphore_server_prepared);
+
+ /* Create an new thread waiting for the termination of icmp test. */
+ tx_thread_create(&demo_thread, "demo thread", demo_thread_entry, 0, demo_thread_stack, sizeof(demo_thread_stack), 16, 16, 4, TX_AUTO_START);
+}
+
+/* The function entry of the thread created by tx_thread_create. */
+VOID demo_thread_entry(ULONG thread_input)
+{
+ INT status;
+
+ /* Wait fot the termination of icmp test. */
+ /* Wait until success to avoid system call being interrupted by SIGUSR1. */
+ tls_test_semaphore_wait(semaphore_client_terminated);
+
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/demo_semaphore_test.c b/test/regression/interoperability_test/nx_secure_test/demo_semaphore_test.c
new file mode 100644
index 00000000..87e59f8e
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/demo_semaphore_test.c
@@ -0,0 +1,117 @@
+#include "tls_test_frame.h"
+
+/* Declare the test entries of two test instances. */
+INT demo_func_entry_0(TLS_TEST_INSTANCE* instance_ptr);
+INT demo_func_entry_1(TLS_TEST_INSTANCE* instance_ptr);
+
+/* Declare a global variable for demo semaphore. */
+TLS_TEST_SEMAPHORE* demo_semaphore;
+
+INT main( INT argc, CHAR* argv[])
+{
+INT status;
+TLS_TEST_INSTANCE *ins0, *ins1;
+INT exit_status[2];
+TLS_TEST_DIRECTOR *director;
+
+ /* Create two test instances. */
+ status = tls_test_instance_create(&ins0, /* test instance ptr */
+ "semaphore_wait_instance", /* instance name */
+ demo_func_entry_0, /* test entry */
+ 0, /* delay(seconds) */
+ 10, /* timeout(seconds) */
+ 1024, /* shared buffer size */
+ NULL); /* reserved */
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ status = tls_test_instance_create(&ins1,
+ "semaphore_post_instance",
+ demo_func_entry_1,
+ 0,
+ 10,
+ 1024,
+ NULL);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Create a semaphore and set the initial value as 0. */
+ status = tls_test_semaphore_create(&demo_semaphore, 0);
+ print_error_message("semaphore address: %p\n", demo_semaphore);
+
+ /* Create the test director. */
+ status = tls_test_director_create(&director, NULL /* reserved */);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Register test instances to the director. */
+ status = tls_test_director_register_test_instance(director, ins0);
+ status += tls_test_director_register_test_instance(director, ins1);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Launch test. */
+ status = tls_test_director_test_start(director);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Collect exit code. */
+ tls_test_instance_get_exit_status(ins0, &(exit_status[0]));
+ tls_test_instance_get_exit_status(ins1, &(exit_status[1]));
+
+ /* Destroy all created instances. */
+ tls_test_director_clean_all(director);
+
+ /* Destroy the semaphore. */
+ tls_test_semaphore_destroy(demo_semaphore);
+
+ /* Check the exit codes of two instances. */
+ return_value_if_fail((0 == exit_status[0]) && (0 == exit_status[1]), TLS_TEST_UNKNOWN_TYPE_ERROR);
+ return TLS_TEST_SUCCESS;
+}
+
+/* Wait for a semaphore and exit. */
+INT demo_func_entry_0(TLS_TEST_INSTANCE* instance_ptr)
+{
+CHAR* name;
+INT status;
+
+ /* Get the name of the instance. */
+ status = tls_test_instance_get_name(instance_ptr, &name);
+
+ /* Get semaphore address from the shared buffer. */
+ print_error_message("%s: get semaphore address: %p\n", name, demo_semaphore);
+
+ /* Output debug messages to stderr(no buffer). */
+ print_error_message("%s: wait for semaphore...\n", name);
+
+ /* Wait for the semaphore. */
+ status += tls_test_semaphore_wait(demo_semaphore);
+ print_error_message("%s: get semaphore...\n", name);
+
+ /* Error checking. */
+ return_value_if_fail(TLS_TEST_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+ return TLS_TEST_SUCCESS;
+}
+
+/* Sleep for 5 seconds and then post a semaphore. */
+INT demo_func_entry_1( TLS_TEST_INSTANCE* instance_ptr)
+{
+CHAR* name;
+INT status;
+
+ /* Get the name of the instance. */
+ status = tls_test_instance_get_name(instance_ptr, &name);
+
+ /* Get semaphore address from the shared buffer. */
+ print_error_message("%s: get semaphore address: %p\n", name, demo_semaphore);
+
+ /* Sleep for 5 seconds. */
+ /* tls_test_sleep will be woke up by SIGUSR1 immediately in the threads manipulated by ThreadX. */
+ /* Please use tx_thread_sleep after calling tx_kernel_enter */
+ print_error_message("%s: sleeping...\n", name);
+ tls_test_sleep(5);
+
+ /* Post the semaphore. */
+ print_error_message("%s: post semaphore...\n", name);
+ status += tls_test_semaphore_post(demo_semaphore);
+
+ /* Error checking. */
+ return_value_if_fail(TLS_TEST_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/demo_shared_buffer_test.c b/test/regression/interoperability_test/nx_secure_test/demo_shared_buffer_test.c
new file mode 100644
index 00000000..c1146961
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/demo_shared_buffer_test.c
@@ -0,0 +1,105 @@
+#include "tls_test_frame.h"
+
+INT demo_shared_buffer_test_entry(TLS_TEST_INSTANCE* instance_ptr);
+
+INT main(INT argc, CHAR* argv[])
+{
+INT status, exit_status;
+UINT offset, length;
+VOID* shared_buffer;
+TLS_TEST_INSTANCE *ins0;
+TLS_TEST_DIRECTOR *director;
+
+ /* Create a test instance. */
+ status = tls_test_instance_create(&ins0, /* test instance ptr */
+ "shared_buffer_test_instance", /* instance name */
+ demo_shared_buffer_test_entry, /* test entry */
+ 0, /* delay(seconds) */
+ 10, /* timeout(seconds) */
+ 1024, /* shared buffer size */
+ NULL); /* reserved */
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ status = tls_test_instance_get_shared_buffer_offset(ins0, &offset);
+ return_value_if_fail((TLS_TEST_SUCCESS == status) && (0 == offset), TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Get shared buffer. */
+ status = tls_test_instance_get_shared_buffer(ins0, &shared_buffer);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Write some data in the shared buffer. */
+ length = 5;
+ status = tls_test_instance_append_data_to_shared_buffer(ins0, "hello", &length);
+ return_value_if_fail((TLS_TEST_SUCCESS == status) && (5 == length), status);
+
+ /* Get current offset. */
+ status = tls_test_instance_get_shared_buffer_offset(ins0, &offset);
+ return_value_if_fail((TLS_TEST_SUCCESS == status) && (5 == offset), TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Launch the test instance. */
+ status = tls_test_director_create(&director, NULL);
+ status += tls_test_director_register_test_instance(director, ins0);
+ status += tls_test_director_test_start(director);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check exit status. */
+ status = tls_test_instance_get_exit_status(ins0, &(exit_status));
+ return_value_if_fail((0 == exit_status), status);
+
+ /* Get shared buffer. */
+ status = tls_test_instance_get_shared_buffer(ins0, &shared_buffer);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Attempt to get the data written by demo_shared_buffer_test_entry. */
+ return_value_if_fail('h' == ((CHAR*)shared_buffer)[1023], TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Get current offset. */
+ status = tls_test_instance_get_shared_buffer_offset(ins0, &offset);
+ return_value_if_fail((TLS_TEST_SUCCESS == status) && (1024 == offset), TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Destroy the test director and registered test instances. */
+ status = tls_test_director_clean_all(director);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ return 0;
+}
+
+INT demo_shared_buffer_test_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+INT offset, status;
+UINT length;
+
+ /* Get current offset. */
+ status = tls_test_instance_get_shared_buffer_offset(instance_ptr, &offset);
+ return_value_if_fail((TLS_TEST_SUCCESS == status) && (5 == offset), TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Set offset. */
+ status = tls_test_instance_set_shared_buffer_offset(instance_ptr, 10);
+ status += tls_test_instance_get_shared_buffer_offset(instance_ptr, &offset);
+ return_value_if_fail((TLS_TEST_SUCCESS == status) && (10 == offset), TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Exceed the size of shared buffer. */
+ status = tls_test_instance_set_shared_buffer_offset(instance_ptr, 1025);
+ return_value_if_fail(TLS_TEST_ILLEGAL_SHARED_BUFFER_ACCESS == status, status);
+ status = tls_test_instance_get_shared_buffer_offset(instance_ptr, &offset);
+ return_value_if_fail((TLS_TEST_SUCCESS == status) && (10 == offset), status);
+
+ /* Set the offset as the maximum. */
+ status = tls_test_instance_set_shared_buffer_offset(instance_ptr, 1024);
+ status += tls_test_instance_get_shared_buffer_offset(instance_ptr, &offset);
+ return_value_if_fail((TLS_TEST_SUCCESS == status) && (1024 == offset), TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Overflow the shared buffer.. */
+ status = tls_test_instance_set_shared_buffer_offset(instance_ptr, 1023);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+ length = 5;
+ status = tls_test_instance_append_data_to_shared_buffer(instance_ptr, "hello", &length);
+
+ /* The length appended actually will be stored in the variable of length. */
+ return_value_if_fail((1 == length) && (status == TLS_TEST_ILLEGAL_SHARED_BUFFER_ACCESS), status);
+
+ /* Now the offset is equal to the shared buffer size. */
+ status = tls_test_instance_get_shared_buffer_offset(instance_ptr, &offset);
+ return_value_if_fail((offset == 1024) && (status == TLS_TEST_SUCCESS), status);
+ return 0;
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/demo_timeout_test.c b/test/regression/interoperability_test/nx_secure_test/demo_timeout_test.c
new file mode 100644
index 00000000..2c2ebd8d
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/demo_timeout_test.c
@@ -0,0 +1,53 @@
+#include "tls_test_frame.h"
+
+INT demo_timeout_test_entry(TLS_TEST_INSTANCE* instance_ptr);
+
+INT main(INT argc, CHAR* argv[])
+{
+INT status, exit_status;
+UINT offset, length;
+VOID* shared_buffer;
+TLS_TEST_INSTANCE *ins0;
+TLS_TEST_DIRECTOR *director;
+
+ /* Create a test instance. */
+ status = tls_test_instance_create(&ins0, /* test instance ptr */
+ "timeout_test_instance", /* instance name */
+ demo_timeout_test_entry, /* test entry */
+ 0, /* delay(seconds) */
+ 3, /* timeout(seconds) */
+ 1024, /* shared buffer size */
+ NULL); /* reserved */
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Launch the test instance. */
+ status = tls_test_director_create(&director, NULL);
+ status += tls_test_director_register_test_instance(director, ins0);
+ status += tls_test_director_test_start(director);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Get exit status. */
+ status = tls_test_instance_get_exit_status(ins0, &exit_status);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ status = tls_test_instance_show_exit_status(ins0);
+ return_value_if_fail( TLS_TEST_SUCCESS == status, status);
+
+ /* Destroy the test director and registered test instances. */
+ status = tls_test_director_clean_all(director);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check exit status. */
+ return_value_if_fail( -SIGALRM == exit_status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ return 0;
+}
+
+INT demo_timeout_test_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+INT status, exit_status;
+CHAR* external_cmd[] = { "sleep_5_secs_then_echo_hello.sh", NULL};
+
+ status = tls_test_launch_external_test_process( &exit_status, external_cmd);
+ return exit_status;
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/demo_tls_test.c b/test/regression/interoperability_test/nx_secure_test/demo_tls_test.c
new file mode 100644
index 00000000..b651c19f
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/demo_tls_test.c
@@ -0,0 +1,97 @@
+#include "tls_test_frame.h"
+
+INT demo_server_entry(TLS_TEST_INSTANCE* instance_ptr);
+INT demo_client_entry(TLS_TEST_INSTANCE* instance_ptr);
+
+/* Global demo semaphore. */
+TLS_TEST_SEMAPHORE* demo_semaphore;
+
+INT main( INT argc, CHAR* argv[])
+{
+INT status, exit_status[2];
+TLS_TEST_INSTANCE *ins0;
+TLS_TEST_INSTANCE *ins1;
+
+ /* Create two test instances. */
+ status = tls_test_instance_create(&ins0, /* test instance ptr */
+ "demo_server", /* instance name */
+ demo_server_entry, /* test entry */
+ 0, /* delay(seconds) */
+ 20, /* timeout(seconds) */
+ 1024, /* shared buffer size */
+ NULL); /* reserved */
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ status = tls_test_instance_create(&ins1,
+ "demo_client",
+ demo_client_entry,
+ 0,
+ 20,
+ 1024,
+ NULL);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Create a semaphore and set the initial value as 0. */
+ status = tls_test_semaphore_create(&demo_semaphore, 0);
+
+ /* Create the test director. */
+ TLS_TEST_DIRECTOR *director;
+ status = tls_test_director_create(&director, NULL /* reserved */);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Register test instances to the director. */
+ status = tls_test_director_register_test_instance(director, ins0);
+ status += tls_test_director_register_test_instance(director, ins1);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Launch test. */
+ status = tls_test_director_test_start(director);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Collect exit code. */
+ tls_test_instance_get_exit_status(ins0, &(exit_status[0]));
+ tls_test_instance_get_exit_status(ins1, &(exit_status[1]));
+ tls_test_instance_show_exit_status(ins0);
+ tls_test_instance_show_exit_status(ins1);
+
+ /* Destroy registered test instances and the director. */
+ tls_test_director_clean_all(director);
+
+ /* Destroy the semaphore. */
+ tls_test_semaphore_destroy(demo_semaphore);
+
+ /* Is this test point disabled? */
+ if ((TLS_TEST_NOT_AVAILABLE == exit_status[0]) || (TLS_TEST_NOT_AVAILABLE == exit_status[1]))
+ return TLS_TEST_NOT_AVAILABLE;
+
+ return exit_status[0] | exit_status[1];
+}
+
+/* Instance two test entry. */
+INT demo_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+CHAR* external_cmd[] = { "demo_openssl_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING, "-tls1_2", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ for ( ; i < 3; i++)
+ {
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(demo_semaphore);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ if (exit_status)
+ {
+ /* Record errors. */
+ instance_status = TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED;
+ }
+ }
+ return instance_status;
+}
+
+/* The definition of demo_server_entry is located at demo_tls_test_server.c */
diff --git a/test/regression/interoperability_test/nx_secure_test/demo_tls_test_icmp_server.c b/test/regression/interoperability_test/nx_secure_test/demo_tls_test_icmp_server.c
new file mode 100644
index 00000000..ddef1e6e
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/demo_tls_test_icmp_server.c
@@ -0,0 +1,87 @@
+#include "tls_test_frame.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT certificate;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+NX_SECURE_X509_CERT trusted_certificate;
+
+UCHAR tls_packet_buffer[4000];
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+void server_thread_entry(ULONG thread_input);
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+
+/* Define external references. */
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+int demo_func_entry_0( void *ctx)
+{
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+}
+
+/* Define what the initial system looks like. */
+
+void tx_application_define(void *first_unused_memory)
+{
+ULONG gateway_ipv4_address;
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", DEVICE_IP_ADDRESS, 0xFFFFFF00UL, &pool_0, _nx_pcap_network_driver, (UCHAR*)ip_thread_stack, sizeof(ip_thread_stack), 1);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ tx_thread_create(&demo_thread, "demo thread", server_thread_entry, 0, demo_thread_stack, sizeof(demo_thread_stack), 16, 16, 4, TX_AUTO_START);
+}
+
+/* TLS Server example application thread. */
+void server_thread_entry(ULONG thread_input)
+{
+ tx_thread_sleep( 500);
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/demo_tls_test_server.c b/test/regression/interoperability_test/nx_secure_test/demo_tls_test_server.c
new file mode 100644
index 00000000..7d1362bb
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/demo_tls_test_server.c
@@ -0,0 +1,233 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* demo_semaphore;
+
+/* Define the ThreadX and NetX object control blocks... */
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT certificate;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+NX_SECURE_X509_CERT trusted_certificate;
+
+UCHAR tls_packet_buffer[4000];
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+void server_thread_entry(ULONG thread_input);
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+NX_SECURE_X509_CERT device_issuer_certificate;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+CHAR crypto_metadata[30000];
+/*
+ * max_total_metadata_size = 8928 :
+ * max_public_cipher_metasize (sizeof(NX_ECJPAKE)) = 2688
+ * 2 * max_session_cipher_metadata_size (2 * sizeof(NX_AES)) = 2 * 540 = 1080
+ * max_hash_mac_metadata_size (sizeof(NX_CRYPTO_RSA)) = 2608
+ * max_handshake_hash_metadata_size (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)) = 88 + 412 + 360 = 860
+ * max_handshake_hash_scratch_size (sizeof(NX_MD5) + sizeof(NX_SHA1)) = 500
+ * max_tls_prf_metadata_size (sizeof(NX_SECURE_TLS_PRF)) = 1192
+ */
+
+#include "ica_test_device_cert.c"
+#include "ica_test_ica_cert.c"
+
+CHAR *html_data = "HTTP/1.1 200 OK\r\n" \
+ "Date: Fri, 15 Sep 2016 23:59:59 GMT\r\n" \
+ "Content-Type: text/html\r\n" \
+ "Content-Length: 200\r\n\r\n" \
+ "<html>\r\n"\
+ "<body>\r\n"\
+ "<b>Hello NetX Secure User!</b>\r\n"\
+ "This is a simple webpage\r\n"\
+ "served up using NetX Secure!\r\n"\
+ "</body>\r\n"\
+ "</html>\r\n";
+
+/* Define the pointer of current instance control block. */
+static TLS_TEST_INSTANCE* demo_instance_ptr;
+
+/* Define external references. */
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Instance one test entry. */
+INT demo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#ifndef NX_SECURE_TLS_SERVER_DISABLED
+
+ /* Get instance pointer. */
+ demo_instance_ptr = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
+
+/* Define what the initial system looks like. */
+void tx_application_define(void *first_unused_memory)
+{
+ ULONG gateway_ipv4_address;
+ UINT status;
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL, &pool_0, _nx_pcap_network_driver, (UCHAR*)ip_thread_stack, sizeof(ip_thread_stack), 1);
+print_error_message( "ip address number: %lu", TLS_TEST_IP_ADDRESS_NUMBER);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ tx_thread_create(&demo_thread, "demo thread", server_thread_entry, 0, demo_thread_stack, sizeof(demo_thread_stack), 16, 16, 4, TX_AUTO_START);
+}
+
+/* TLS Server example application thread. */
+void server_thread_entry(ULONG thread_input)
+{
+ INT i = 0, status = 0;
+ ULONG actual_status;
+ NX_PACKET *receive_packet;
+ NX_PACKET *send_packet;
+ UCHAR receive_buffer[100];
+ ULONG bytes;
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Server Socket",
+ NX_IP_NORMAL, NX_FRAGMENT_OKAY /*NX_DONT_FRAGMENT*/, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_session_create(&tls_session,
+ &nx_crypto_tls_ciphers,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(&tls_session, tls_packet_buffer, sizeof(tls_packet_buffer));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ // Initialize our certificates
+ nx_secure_tls_remote_certificate_allocate(&tls_session, &remote_certificate, remote_cert_buffer, sizeof(remote_cert_buffer));
+ nx_secure_tls_remote_certificate_allocate(&tls_session, &remote_issuer, remote_issuer_buffer, sizeof(remote_issuer_buffer));
+
+ memset(&certificate, 0, sizeof(certificate));
+ nx_secure_x509_certificate_initialize(&certificate, test_device_cert_der, test_device_cert_der_len, NX_NULL, 0, test_device_cert_key_der, test_device_cert_key_der_len, NX_SECURE_X509_KEY_TYPE_RSA_PKCS1_DER);
+ nx_secure_tls_local_certificate_add(&tls_session, &certificate);
+
+ // Initialize the Intermediate CA certificate - it does not have a private RSA key
+ nx_secure_x509_certificate_initialize(&device_issuer_certificate, ica_cert_der, ica_cert_der_len, NX_NULL, 0, NX_NULL, 0, NX_SECURE_X509_KEY_TYPE_NONE);
+ nx_secure_tls_local_certificate_add(&tls_session, &device_issuer_certificate);
+
+ /* Setup this thread to listen. */
+ status = nx_tcp_server_socket_listen(&ip_0, DEVICE_SERVER_PORT, &tcp_socket, 5, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ for ( ; i < 3; i++)
+ {
+ /* Post semaphore before accept sockets. */
+ print_error_message("Connection %d: server is prepared. Post the semaphore.\n", i);
+ tls_test_semaphore_post(demo_semaphore);
+
+ /* Accept a client socket connection. */
+ print_error_message("Connection %d: wait for connections.\n", i);
+ status = nx_tcp_server_socket_accept(&tcp_socket, NX_WAIT_FOREVER);
+ print_error_message("Connection %d: server accept.\n", i);
+ exit_if_fail( NX_SUCCESS == status, 1);
+
+ /* Start the TLS Session now that we have a connected socket. */
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 2);
+
+ /* Receive the HTTP request, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 3);
+
+ /* Show received data. */
+ nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ receive_buffer[bytes] = 0;
+ print_error_message("Received data: %s\n", receive_buffer);
+
+ /* Allocate a return packet and send our HTML data back to the client. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 4);
+
+ /* Send the prepared html page. */
+ status = nx_packet_data_append(send_packet, html_data, strlen(html_data), &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 5);
+
+ /* TLS send the HTML/HTTPS data back to the client. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ /* Exit the test process directly without release packet. */
+ exit_if_fail( NX_SUCCESS == status, 6);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_IP_PERIODIC_RATE * 3);
+ /*exit_if_fail( NX_SUCCESS == status, 7);*/
+
+ /* Disconnect the TCP socket, closing the connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_IP_PERIODIC_RATE * 3);
+ /*exit_if_fail( NX_SUCCESS == status, 8);*/
+
+ /* Unaccept the server socket. */
+ status = nx_tcp_server_socket_unaccept(&tcp_socket);
+ exit_if_fail( NX_SUCCESS == status, 9);
+
+ print_error_message("Connection %d: server unaccept, sleeping...\n", i);
+ /*tx_thread_sleep( 500);*/
+
+ /* Setup server socket for listening again. */
+ status = nx_tcp_server_socket_relisten(&ip_0, DEVICE_SERVER_PORT, &tcp_socket);
+ exit_if_fail( NX_SUCCESS == status, 10);
+ }
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_aes128_gcm_nx_secure_client_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_aes128_gcm_nx_secure_client_entry.c
new file mode 100644
index 00000000..2366dc34
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_aes128_gcm_nx_secure_client_entry.c
@@ -0,0 +1,236 @@
+#include "tls_test_frame.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_UDP_SOCKET udp_socket;
+NX_SECURE_DTLS_SESSION dtls_session;
+UCHAR cert_buffer[2000];
+NX_SECURE_X509_CERT trusted_certificate;
+NX_SECURE_TLS_CRYPTO tls_ciphers_client;
+
+UCHAR tls_packet_buffer[4000];
+
+#include "cert.c"
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+extern NX_SECURE_TLS_CIPHERSUITE_INFO _nx_crypto_ciphersuite_lookup_table[];
+
+INT dtls_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) && defined(NX_SECURE_ENABLE_AEAD_CIPHER)
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
+
+void tx_application_define(void *first_unused_memory)
+{
+ULONG gateway_ipv4_address;
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+ nx_secure_dtls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+static VOID ciphersuites_setup(NX_SECURE_TLS_CRYPTO *tls_ciphers)
+{
+UINT i;
+UINT status;
+UINT count;
+
+ /* Initialize ciphersuites. */
+ memcpy(tls_ciphers, &nx_crypto_tls_ciphers, sizeof(NX_SECURE_TLS_CRYPTO));
+ i = 0;
+ while (TLS_RSA_WITH_AES_128_GCM_SHA256 !=
+ (UINT)_nx_crypto_ciphersuite_lookup_table[i].nx_secure_tls_ciphersuite)
+ {
+ i++;
+ }
+ tls_ciphers -> nx_secure_tls_ciphersuite_lookup_table = &_nx_crypto_ciphersuite_lookup_table[i];
+ tls_ciphers -> nx_secure_tls_ciphersuite_lookup_table_size = 1;
+}
+
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+NXD_ADDRESS server_address;
+NX_PARAMETER_NOT_USED(thread_input);
+
+
+ /* Address of remote server. */
+ server_address.nxd_ip_version = NX_IP_VERSION_V4;
+ server_address.nxd_ip_address.v4 = REMOTE_IP_ADDRESS_NUMBER;
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_udp_socket_create(&ip_0, &udp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 5);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup this thread to bind to a port. */
+ status = nx_udp_socket_bind(&udp_socket, 0, NX_NO_WAIT);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a DTLS session. */
+ ciphersuites_setup(&tls_ciphers_client);
+ status = nx_secure_dtls_session_create(&dtls_session,
+ &tls_ciphers_client,
+ crypto_metadata,
+ sizeof(crypto_metadata),
+ tls_packet_buffer,
+ sizeof(tls_packet_buffer),
+ 1,
+ cert_buffer,
+ sizeof(cert_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_x509_certificate_initialize(&trusted_certificate, cert_der, cert_der_len,
+ NX_NULL, 0, NULL, 0,
+ NX_SECURE_X509_KEY_TYPE_NONE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_dtls_session_trusted_certificate_add(&dtls_session, &trusted_certificate, 1);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_server_prepared);
+ tx_thread_sleep(100);
+
+ status = nx_icmp_ping(&ip_0, REMOTE_IP_ADDRESS_NUMBER, "abcdefg", 7, &send_packet, 10 * NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, status);
+ nx_packet_release(send_packet);
+
+ /* Attempt to connect the echo server. */
+ print_error_message("DTLS client session starting...\n");
+ status = nx_secure_dtls_client_session_start(&dtls_session, &udp_socket, &server_address, DEVICE_SERVER_PORT, 20 * NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_dtls_packet_allocate(&dtls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 2);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 3);
+
+ /* Send "hello" message. */
+ print_error_message("DTLS client session sending...\n");
+ status = nx_secure_dtls_client_session_send(&dtls_session, send_packet);
+ exit_if_fail(NX_SUCCESS == status, 4);
+
+#if 0
+ /* Receive the echoed and reversed data, and print it out. */
+ print_error_message("DTLS client session receving...\n");
+ status = nx_secure_dtls_session_receive(&dtls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 5);
+
+ /* Extract data received from server. */
+ status = nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ exit_if_fail(NX_SUCCESS == status, 6);
+
+ /* Check the reverse text received from openssl server. */
+ exit_if_fail('o' == ((CHAR*)receive_buffer)[0], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[1], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[2], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('e' == ((CHAR*)receive_buffer)[3], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('h' == ((CHAR*)receive_buffer)[4], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('\n' == ((CHAR*)receive_buffer)[5], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail(6 == bytes, 7);
+#endif
+
+ /* End the DTLS session. This is required to properly shut down the DTLS connection. */
+ print_error_message("DTLS client session end.\n");
+ nx_secure_dtls_session_end(&dtls_session, NX_NO_WAIT);
+
+ /* Delete the DTLS session. */
+ status = nx_secure_dtls_session_delete(&dtls_session);
+ exit_if_fail(NX_SUCCESS == status, 8);
+
+ /* Unbind the UDP socket from our port. */
+ status = nx_udp_socket_unbind(&udp_socket);
+ exit_if_fail(NX_SUCCESS == status, 9);
+
+ /* Delete the UDP socket instance to clean up. */
+ status = nx_udp_socket_delete(&udp_socket);
+ exit_if_fail(NX_SUCCESS == status, 10);
+
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_client_certificate_verify_test_client_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_client_certificate_verify_test_client_entry.c
new file mode 100644
index 00000000..38613f00
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_client_certificate_verify_test_client_entry.c
@@ -0,0 +1,228 @@
+#include "tls_test_frame.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_UDP_SOCKET udp_socket;
+NX_SECURE_DTLS_SESSION dtls_session;
+UCHAR cert_buffer[6000];
+NX_SECURE_X509_CERT certificate, device_issuer_certificate;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+
+UCHAR tls_packet_buffer[4000];
+
+#include "test_client.der.c"
+#include "test_client.key.der.c"
+#include "test.der.c"
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 64)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define an error counter. */
+
+ULONG error_counter;
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS)
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+#else /* !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) */
+
+}
+
+void tx_application_define(void *first_unused_memory)
+{
+ULONG gateway_ipv4_address;
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+ nx_secure_dtls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+NXD_ADDRESS server_address;
+NX_PARAMETER_NOT_USED(thread_input);
+
+
+ /* Address of remote server. */
+ server_address.nxd_ip_version = NX_IP_VERSION_V4;
+ server_address.nxd_ip_address.v4 = REMOTE_IP_ADDRESS_NUMBER;
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_udp_socket_create(&ip_0, &udp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_FRAGMENT_OKAY, NX_IP_TIME_TO_LIVE, 20);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup this thread to bind to a port. */
+ status = nx_udp_socket_bind(&udp_socket, 0, NX_NO_WAIT);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a DTLS session. */
+ status = nx_secure_dtls_session_create(&dtls_session,
+ &nx_crypto_tls_ciphers,
+ crypto_metadata,
+ sizeof(crypto_metadata),
+ tls_packet_buffer,
+ sizeof(tls_packet_buffer),
+ 3,
+ cert_buffer,
+ sizeof(cert_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+
+ /* Added a certificate. */
+ memset(&certificate, 0, sizeof(certificate));
+ status = nx_secure_x509_certificate_initialize(&certificate, test_client_der, test_client_der_len, NX_NULL, 0, test_client_key_der, test_client_key_der_len, NX_SECURE_X509_KEY_TYPE_RSA_PKCS1_DER);
+ show_error_message_if_fail( NX_SUCCESS == status);
+ status = nx_secure_dtls_session_local_certificate_add(&dtls_session, &certificate, 1);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ // Initialize the Intermediate CA certificate - it does not have a private RSA key
+ status = nx_secure_x509_certificate_initialize(&device_issuer_certificate, test_der, test_der_len, NX_NULL, 0, NX_NULL, 0, NX_SECURE_X509_KEY_TYPE_NONE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+ status = nx_secure_dtls_session_trusted_certificate_add(&dtls_session, &device_issuer_certificate, 2);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tx_thread_sleep(100);
+
+ status = nx_icmp_ping(&ip_0, REMOTE_IP_ADDRESS_NUMBER, "abcdefg", 7, &send_packet, 10 * NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, status);
+ nx_packet_release(send_packet);
+
+ /* Attempt to connect the echo server. */
+ print_error_message("DTLS client session starting...\n");
+ status = nx_secure_dtls_client_session_start(&dtls_session, &udp_socket, &server_address, DEVICE_SERVER_PORT, 20 * NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_dtls_packet_allocate(&dtls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send "hello" message. */
+ print_error_message("DTLS client session sending...\n");
+ status = nx_secure_dtls_client_session_send(&dtls_session, send_packet);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+#if 0
+ /* Receive the echoed and reversed data, and print it out. */
+ status = nx_secure_dtls_session_receive(&dtls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Extract data received from server. */
+ status = nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Check the reverse text received from openssl server. */
+ exit_if_fail('h' == ((CHAR*)receive_buffer)[0], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('e' == ((CHAR*)receive_buffer)[1], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[2], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[3], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('o' == ((CHAR*)receive_buffer)[4], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('\n' == ((CHAR*)receive_buffer)[5], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail(6 == bytes, TLS_TEST_UNKNOWN_TYPE_ERROR);
+#endif
+
+ /* End the DTLS session. This is required to properly shut down the DTLS connection. */
+ print_error_message("DTLS client session end.\n");
+ nx_secure_dtls_session_end(&dtls_session, NX_NO_WAIT);
+
+ /* Delete the DTLS session. */
+ status = nx_secure_dtls_session_delete(&dtls_session);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Unbind the UDP socket from our port. */
+ status = nx_udp_socket_unbind(&udp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Delete the UDP socket instance to clean up. */
+ status = nx_udp_socket_delete(&udp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_client_certificate_verify_test_server_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_client_certificate_verify_test_server_entry.c
new file mode 100644
index 00000000..81b9e9b2
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_client_certificate_verify_test_server_entry.c
@@ -0,0 +1,224 @@
+#include "tls_test_frame.h"
+#include "test_server.der.c"
+#include "test_server.key.der.c"
+#include "test.der.c"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_server_prepared;
+
+/* Define the ThreadX and NetX object control blocks... */
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_SECURE_DTLS_SERVER dtls_server;
+
+UCHAR tls_packet_buffer[4000];
+
+/* Session buffer for DTLS server. Must be equal to the size of NX_SECURE_DTLS_SESSION times the
+ number of desired DTLS sessions. */
+static UCHAR session_buffer[sizeof(NX_SECURE_DTLS_SESSION)];
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+void server_thread_entry(ULONG thread_input);
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+UCHAR remote_cert_buffer[6000];
+NX_SECURE_X509_CERT certificate, device_issuer_certificate;
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+
+/* Define the pointer of current instance control block. */
+static TLS_TEST_INSTANCE* demo_instance_ptr;
+
+/* Define external references. */
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Instance one test entry. */
+INT dtls_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_CLIENT_CERTIFICATE_VERIFY) && defined(NX_SECURE_ENABLE_DTLS)
+
+ /* Get instance pointer. */
+ demo_instance_ptr = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+
+#else /* !NX_SECURE_TLS_SERVER_DISABLED && NX_SECURE_ENABLE_CLIENT_CERTIFICATE_VERIFY && NX_SECURE_ENABLE_DTLS */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* !NX_SECURE_TLS_SERVER_DISABLED && NX_SECURE_ENABLE_CLIENT_CERTIFICATE_VERIFY && NX_SECURE_ENABLE_DTLS */
+
+}
+
+/* Define what the initial system looks like. */
+void tx_application_define(void *first_unused_memory)
+{
+ ULONG gateway_ipv4_address;
+ UINT status;
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL, &pool_0, _nx_pcap_network_driver, (UCHAR*)ip_thread_stack, sizeof(ip_thread_stack), 1);
+ print_error_message( "ip address number: %lu\n", TLS_TEST_IP_ADDRESS_NUMBER);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ nx_secure_tls_initialize();
+ nx_secure_dtls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", server_thread_entry, 0, demo_thread_stack, sizeof(demo_thread_stack), 16, 16, 4, TX_AUTO_START);
+}
+
+/* Notification flags for DTLS server connect/receive. */
+UINT server_connect_count = 0;
+UINT server_receive_count = 0;
+NX_SECURE_DTLS_SESSION *connect_session;
+NX_SECURE_DTLS_SESSION *receive_session;
+
+/* Connect notify callback for DTLS server - notifies the application thread that
+ a DTLS connection is ready to kickoff a handshake. */
+UINT server_connect_notify(NX_SECURE_DTLS_SESSION *dtls_session, NXD_ADDRESS *ip_address, UINT port)
+{
+ connect_session = dtls_session;
+ server_connect_count++;
+ return(NX_SUCCESS);
+}
+
+/* Receive notify callback for DTLS server - notifies the application thread that
+ we have received a DTLS record over an established DTLS session. */
+UINT server_receive_notify(NX_SECURE_DTLS_SESSION *dtls_session)
+{
+ receive_session = dtls_session;
+ server_receive_count++;
+ return(NX_SUCCESS);
+}
+
+/* TLS Server example application thread. */
+void server_thread_entry(ULONG thread_input)
+{
+ INT status = 0;
+ ULONG actual_status;
+ NX_PACKET *receive_packet;
+ UCHAR receive_buffer[100];
+ ULONG bytes;
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Create a socket. */
+ status = nx_secure_dtls_server_create(&dtls_server, &ip_0, DEVICE_SERVER_PORT, NX_IP_PERIODIC_RATE,
+ session_buffer, sizeof(session_buffer),
+ &nx_crypto_tls_ciphers, crypto_metadata, sizeof(crypto_metadata),
+ tls_packet_buffer, sizeof(tls_packet_buffer),
+ server_connect_notify, server_receive_notify);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Enable Client Certificate Verification. */
+ nx_secure_dtls_server_x509_client_verify_configure(&dtls_server, 2, remote_cert_buffer, sizeof(remote_cert_buffer));
+
+ memset(&certificate, 0, sizeof(certificate));
+ status = nx_secure_x509_certificate_initialize(&certificate,
+ test_server_der, test_server_der_len,
+ NX_NULL, 0, test_server_key_der,
+ test_server_key_der_len, NX_SECURE_X509_KEY_TYPE_RSA_PKCS1_DER);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_dtls_server_local_certificate_add(&dtls_server, &certificate, 1);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ memset(&device_issuer_certificate, 0, sizeof(device_issuer_certificate));
+ status = nx_secure_x509_certificate_initialize(&device_issuer_certificate,
+ test_der, test_der_len,
+ NX_NULL, 0, NX_NULL,
+ 0, NX_SECURE_X509_KEY_TYPE_NONE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_dtls_server_trusted_certificate_add(&dtls_server, &device_issuer_certificate, 2);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_dtls_server_start(&dtls_server);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Post semaphore before accept sockets. */
+ print_error_message("Server is prepared. Post the semaphore.\n");
+ tls_test_semaphore_post(semaphore_server_prepared);
+
+ /* Accept a client socket connection. */
+ print_error_message("Server wait for connections.\n");
+
+ while (!server_connect_count)
+ {
+ tx_thread_sleep(1);
+ }
+ server_connect_count = 0;
+ print_error_message("Server accept.\n");
+
+ /* Start the DTLS Session now that we have a connected socket. */
+ status = nx_secure_dtls_server_session_start(connect_session, 20 * NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, 1);
+
+ /* Wait for records to be received. */
+ print_error_message("Server wait for records.\n");
+ while (!server_receive_count)
+ {
+ tx_thread_sleep(1);
+ }
+ server_receive_count = 0;
+
+ /* Receive the data, and print it out. */
+ status = nx_secure_dtls_session_receive(receive_session, &receive_packet, 5 * NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, 2);
+
+ /* Show received data. */
+ nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ receive_buffer[bytes] = 0;
+ print_error_message("Server received data: %s\n", receive_buffer);
+
+ /* End the DTLS session. */
+ status = nx_secure_dtls_session_end(connect_session, 5 * NX_IP_PERIODIC_RATE);
+ print_error_message("Server session end status %d.\n", status);
+
+ /* Shutdown DTLS server. */
+ nx_secure_dtls_server_stop(&dtls_server);
+ print_error_message("Server stop.\n");
+
+ /* Delete server. */
+ nx_secure_dtls_server_delete(&dtls_server);
+
+
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_ecc_test_client_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_ecc_test_client_entry.c
new file mode 100644
index 00000000..a92e1b4d
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_ecc_test_client_entry.c
@@ -0,0 +1,231 @@
+#include "tls_test_frame.h"
+#include "../../nx_secure_test/ecc_certs.c"
+#include "../../nx_secure_test/test_ca_cert.c"
+#include "../../nx_secure_test/test_device_cert.c"
+
+/* Define the ThreadX and NetX object control blocks... */
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_UDP_SOCKET udp_socket;
+NX_SECURE_DTLS_SESSION dtls_session;
+UCHAR cert_buffer[6000];
+NX_SECURE_X509_CERT certificate, device_issuer_certificate;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+
+UCHAR tls_packet_buffer[4000];
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 64)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define an error counter. */
+
+ULONG error_counter;
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+#else /* !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) */
+
+}
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+void tx_application_define(void *first_unused_memory)
+{
+ULONG gateway_ipv4_address;
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+ nx_secure_dtls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+NXD_ADDRESS server_address;
+NX_PARAMETER_NOT_USED(thread_input);
+
+
+ /* Address of remote server. */
+ server_address.nxd_ip_version = NX_IP_VERSION_V4;
+ server_address.nxd_ip_address.v4 = REMOTE_IP_ADDRESS_NUMBER;
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_udp_socket_create(&ip_0, &udp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_FRAGMENT_OKAY, NX_IP_TIME_TO_LIVE, 20);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup this thread to bind to a port. */
+ status = nx_udp_socket_bind(&udp_socket, 0, NX_NO_WAIT);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a DTLS session. */
+ status = nx_secure_dtls_session_create(&dtls_session,
+ &nx_crypto_tls_ciphers_ecc,
+ crypto_metadata,
+ sizeof(crypto_metadata),
+ tls_packet_buffer,
+ sizeof(tls_packet_buffer),
+ 3,
+ cert_buffer,
+ sizeof(cert_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_dtls_ecc_initialize(&dtls_session, nx_crypto_ecc_supported_groups,
+ nx_crypto_ecc_supported_groups_size,
+ nx_crypto_ecc_curves);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ // Initialize the CA certificate - it does not have a private RSA key
+ status = nx_secure_x509_certificate_initialize(&device_issuer_certificate, ECCA2_der, ECCA2_der_len, NX_NULL, 0, NX_NULL, 0, NX_SECURE_X509_KEY_TYPE_NONE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+ status = nx_secure_dtls_session_trusted_certificate_add(&dtls_session, &device_issuer_certificate, 2);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tx_thread_sleep(100);
+
+ status = nx_icmp_ping(&ip_0, REMOTE_IP_ADDRESS_NUMBER, "abcdefg", 7, &send_packet, 10 * NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, status);
+ nx_packet_release(send_packet);
+
+ /* Attempt to connect the echo server. */
+ print_error_message("DTLS client session starting...\n");
+ status = nx_secure_dtls_client_session_start(&dtls_session, &udp_socket, &server_address, DEVICE_SERVER_PORT, 20 * NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_dtls_packet_allocate(&dtls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send "hello" message. */
+ print_error_message("DTLS client session sending...\n");
+ status = nx_secure_dtls_client_session_send(&dtls_session, send_packet);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+#if 0
+ /* Receive the echoed and reversed data, and print it out. */
+ status = nx_secure_dtls_session_receive(&dtls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Extract data received from server. */
+ status = nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Check the reverse text received from openssl server. */
+ exit_if_fail('h' == ((CHAR*)receive_buffer)[0], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('e' == ((CHAR*)receive_buffer)[1], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[2], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[3], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('o' == ((CHAR*)receive_buffer)[4], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('\n' == ((CHAR*)receive_buffer)[5], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail(6 == bytes, TLS_TEST_UNKNOWN_TYPE_ERROR);
+#endif
+
+ /* End the DTLS session. This is required to properly shut down the DTLS connection. */
+ print_error_message("DTLS client session end.\n");
+ nx_secure_dtls_session_end(&dtls_session, NX_NO_WAIT);
+
+ /* Delete the DTLS session. */
+ status = nx_secure_dtls_session_delete(&dtls_session);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Unbind the UDP socket from our port. */
+ status = nx_udp_socket_unbind(&udp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Delete the UDP socket instance to clean up. */
+ status = nx_udp_socket_delete(&udp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ exit(0);
+}
+#endif /* !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) */
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_ecc_test_server_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_ecc_test_server_entry.c
new file mode 100644
index 00000000..f04d9e06
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_ecc_test_server_entry.c
@@ -0,0 +1,234 @@
+#include "tls_test_frame.h"
+#include "../../nx_secure_test/ecc_certs.c"
+#include "../../nx_secure_test/test_ca_cert.c"
+#include "../../nx_secure_test/test_device_cert.c"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_server_prepared;
+
+/* Define the ThreadX and NetX object control blocks... */
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_SECURE_DTLS_SERVER dtls_server;
+
+UCHAR tls_packet_buffer[4000];
+
+/* Session buffer for DTLS server. Must be equal to the size of NX_SECURE_DTLS_SESSION times the
+ number of desired DTLS sessions. */
+static UCHAR session_buffer[sizeof(NX_SECURE_DTLS_SESSION)];
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+void server_thread_entry(ULONG thread_input);
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+UCHAR remote_cert_buffer[6000];
+NX_SECURE_X509_CERT certificate, device_issuer_certificate;
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+
+/* Define the pointer of current instance control block. */
+static TLS_TEST_INSTANCE* demo_instance_ptr;
+
+/* Define external references. */
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Instance one test entry. */
+INT dtls_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+ /* Get instance pointer. */
+ demo_instance_ptr = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+
+#else /* !NX_SECURE_TLS_SERVER_DISABLED && NX_SECURE_ENABLE_DTLS && NX_SECURE_ENABLE_ECC_CIPHERSUITE */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* !NX_SECURE_TLS_SERVER_DISABLED && NX_SECURE_ENABLE_DTLS && NX_SECURE_ENABLE_ECC_CIPHERSUITE */
+
+}
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+/* Define what the initial system looks like. */
+void tx_application_define(void *first_unused_memory)
+{
+ ULONG gateway_ipv4_address;
+ UINT status;
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL, &pool_0, _nx_pcap_network_driver, (UCHAR*)ip_thread_stack, sizeof(ip_thread_stack), 1);
+ print_error_message( "ip address number: %lu\n", TLS_TEST_IP_ADDRESS_NUMBER);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ nx_secure_tls_initialize();
+ nx_secure_dtls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", server_thread_entry, 0, demo_thread_stack, sizeof(demo_thread_stack), 16, 16, 4, TX_AUTO_START);
+}
+
+/* Notification flags for DTLS server connect/receive. */
+UINT server_connect_count = 0;
+UINT server_receive_count = 0;
+NX_SECURE_DTLS_SESSION *connect_session;
+NX_SECURE_DTLS_SESSION *receive_session;
+
+/* Connect notify callback for DTLS server - notifies the application thread that
+ a DTLS connection is ready to kickoff a handshake. */
+UINT server_connect_notify(NX_SECURE_DTLS_SESSION *dtls_session, NXD_ADDRESS *ip_address, UINT port)
+{
+ connect_session = dtls_session;
+ server_connect_count++;
+ return(NX_SUCCESS);
+}
+
+/* Receive notify callback for DTLS server - notifies the application thread that
+ we have received a DTLS record over an established DTLS session. */
+UINT server_receive_notify(NX_SECURE_DTLS_SESSION *dtls_session)
+{
+ receive_session = dtls_session;
+ server_receive_count++;
+ return(NX_SUCCESS);
+}
+
+/* TLS Server example application thread. */
+void server_thread_entry(ULONG thread_input)
+{
+ INT status = 0;
+ ULONG actual_status;
+ NX_PACKET *receive_packet;
+ UCHAR receive_buffer[100];
+ ULONG bytes;
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Create a socket. */
+ status = nx_secure_dtls_server_create(&dtls_server, &ip_0, DEVICE_SERVER_PORT, NX_IP_PERIODIC_RATE,
+ session_buffer, sizeof(session_buffer),
+ &nx_crypto_tls_ciphers_ecc, crypto_metadata, sizeof(crypto_metadata),
+ tls_packet_buffer, sizeof(tls_packet_buffer),
+ server_connect_notify, server_receive_notify);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_dtls_server_ecc_initialize(&dtls_server, nx_crypto_ecc_supported_groups,
+ nx_crypto_ecc_supported_groups_size,
+ nx_crypto_ecc_curves);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ memset(&certificate, 0, sizeof(certificate));
+ status = nx_secure_x509_certificate_initialize(&certificate,
+ ECTestServer2_der, ECTestServer2_der_len,
+ NX_NULL, 0, ECTestServer2_key_der,
+ ECTestServer2_key_der_len, NX_SECURE_X509_KEY_TYPE_EC_DER);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_dtls_server_local_certificate_add(&dtls_server, &certificate, 1);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ memset(&device_issuer_certificate, 0, sizeof(device_issuer_certificate));
+ status = nx_secure_x509_certificate_initialize(&device_issuer_certificate,
+ ECCA2_der, ECCA2_der_len,
+ NX_NULL, 0, NX_NULL,
+ 0, NX_SECURE_X509_KEY_TYPE_NONE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_dtls_server_trusted_certificate_add(&dtls_server, &device_issuer_certificate, 2);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_dtls_server_start(&dtls_server);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Post semaphore before accept sockets. */
+ print_error_message("Server is prepared. Post the semaphore.\n");
+ tls_test_semaphore_post(semaphore_server_prepared);
+
+ /* Accept a client socket connection. */
+ print_error_message("Server wait for connections.\n");
+
+ while (!server_connect_count)
+ {
+ tx_thread_sleep(1);
+ }
+ server_connect_count = 0;
+ print_error_message("Server accept.\n");
+
+ /* Start the DTLS Session now that we have a connected socket. */
+ status = nx_secure_dtls_server_session_start(connect_session, 20 * NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, 1);
+
+ /* Wait for records to be received. */
+ print_error_message("Server wait for records.\n");
+ while (!server_receive_count)
+ {
+ tx_thread_sleep(1);
+ }
+ server_receive_count = 0;
+
+ /* Receive the data, and print it out. */
+ status = nx_secure_dtls_session_receive(receive_session, &receive_packet, 5 * NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, 2);
+
+ /* Show received data. */
+ nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ receive_buffer[bytes] = 0;
+ print_error_message("Server received data: %s\n", receive_buffer);
+
+ /* End the DTLS session. */
+ status = nx_secure_dtls_session_end(connect_session, 5 * NX_IP_PERIODIC_RATE);
+ print_error_message("Server session end status %d.\n", status);
+
+ /* Shutdown DTLS server. */
+ nx_secure_dtls_server_stop(&dtls_server);
+ print_error_message("Server stop.\n");
+
+ /* Delete server. */
+ nx_secure_dtls_server_delete(&dtls_server);
+
+
+ exit(0);
+}
+#endif /* !NX_SECURE_TLS_SERVER_DISABLED && NX_SECURE_ENABLE_DTLS && NX_SECURE_ENABLE_ECC_CIPHERSUITE */
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_server_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_server_entry.c
new file mode 100644
index 00000000..17c730ea
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_nx_secure_server_entry.c
@@ -0,0 +1,301 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_server_prepared;
+
+/* Define the ThreadX and NetX object control blocks... */
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_SECURE_DTLS_SERVER dtls_server;
+NX_SECURE_X509_CERT certificate;
+
+UCHAR tls_packet_buffer[4000];
+
+/* Session buffer for DTLS server. Must be equal to the size of NX_SECURE_DTLS_SESSION times the
+ number of desired DTLS sessions. */
+static UCHAR session_buffer[sizeof(NX_SECURE_DTLS_SESSION)];
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+void server_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000];
+
+#if (NX_SECURE_TLS_TLS_1_0_ENABLED) || (NX_SECURE_TLS_TLS_1_1_ENABLED)
+extern NX_CRYPTO_METHOD crypto_method_null;
+extern NX_CRYPTO_METHOD crypto_method_rsa;
+extern NX_CRYPTO_METHOD crypto_method_auth_psk;
+extern NX_CRYPTO_METHOD crypto_method_md5;
+extern NX_CRYPTO_METHOD crypto_method_sha1;
+extern NX_CRYPTO_METHOD crypto_method_sha256;
+extern NX_CRYPTO_METHOD crypto_method_aes_cbc_128;
+extern NX_CRYPTO_METHOD crypto_method_aes_cbc_256;
+extern NX_CRYPTO_METHOD crypto_method_aes_ccm_8;
+extern NX_CRYPTO_METHOD crypto_method_aes_128_gcm_16;
+extern NX_CRYPTO_METHOD crypto_method_hmac_sha1;
+extern NX_CRYPTO_METHOD crypto_method_hmac_sha256;
+extern NX_CRYPTO_METHOD crypto_method_hkdf_sha256;
+extern NX_CRYPTO_METHOD crypto_method_tls_prf_1;
+extern NX_CRYPTO_METHOD crypto_method_tls_prf_sha256;
+extern NX_CRYPTO_METHOD crypto_method_hkdf;
+extern NX_CRYPTO_METHOD crypto_method_hmac;
+extern NX_CRYPTO_METHOD crypto_method_ecdhe;
+
+NX_SECURE_TLS_CIPHERSUITE_INFO _nx_crypto_ciphersuite_lookup_table_1_0_1_1[] =
+{
+ /* Ciphersuite, public cipher, public_auth, session cipher & cipher mode, iv size, key size, hash method, hash size, TLS PRF */
+#ifdef NX_SECURE_ENABLE_AEAD_CIPHER
+ {TLS_RSA_WITH_AES_128_GCM_SHA256, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_128_gcm_16, 16, 16, &crypto_method_null, 0, &crypto_method_tls_prf_sha256},
+#endif /* NX_SECURE_ENABLE_AEAD_CIPHER */
+ {TLS_RSA_WITH_AES_256_CBC_SHA256, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_256, 16, 32, &crypto_method_hmac_sha256, 32, &crypto_method_tls_prf_sha256},
+ {TLS_RSA_WITH_AES_128_CBC_SHA256, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha256, 32, &crypto_method_tls_prf_sha256},
+ {TLS_RSA_WITH_AES_256_CBC_SHA, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_256, 16, 32, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+ {TLS_RSA_WITH_AES_128_CBC_SHA, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+
+#ifdef NX_SECURE_ENABLE_PSK_CIPHERSUITES
+ {TLS_PSK_WITH_AES_128_CBC_SHA256, &crypto_method_null, &crypto_method_auth_psk, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha256, 32, &crypto_method_tls_prf_sha256},
+#ifdef NX_SECURE_ENABLE_AEAD_CIPHER
+ {TLS_PSK_WITH_AES_128_CCM_8, &crypto_method_null, &crypto_method_auth_psk, &crypto_method_aes_ccm_8, 16, 16, &crypto_method_null, 0, &crypto_method_tls_prf_sha256},
+#endif
+#endif /* NX_SECURE_ENABLE_PSK_CIPHERSUITES */
+};
+
+/* Lookup table for X.509 digital certificates - they need a public-key algorithm and a hash routine for verification. */
+NX_SECURE_X509_CRYPTO _nx_crypto_x509_cipher_lookup_table_1_0_1_1[] =
+{
+ /* OID identifier, public cipher, hash method */
+ {NX_SECURE_TLS_X509_TYPE_RSA_SHA_256, &crypto_method_rsa, &crypto_method_sha256},
+ {NX_SECURE_TLS_X509_TYPE_RSA_SHA_1, &crypto_method_rsa, &crypto_method_sha1},
+ {NX_SECURE_TLS_X509_TYPE_RSA_MD5, &crypto_method_rsa, &crypto_method_md5},
+};
+
+/* Define the object we can pass into TLS. */
+NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers =
+{
+ /* Ciphersuite lookup table and size. */
+ _nx_crypto_ciphersuite_lookup_table_1_0_1_1,
+ sizeof(_nx_crypto_ciphersuite_lookup_table_1_0_1_1) / sizeof(NX_SECURE_TLS_CIPHERSUITE_INFO),
+
+#ifndef NX_SECURE_DISABLE_X509
+ /* X.509 certificate cipher table and size. */
+ _nx_crypto_x509_cipher_lookup_table_1_0_1_1,
+ sizeof(_nx_crypto_x509_cipher_lookup_table_1_0_1_1) / sizeof(NX_SECURE_X509_CRYPTO),
+#endif
+
+ /* TLS version-specific methods. */
+#if (NX_SECURE_TLS_TLS_1_0_ENABLED || NX_SECURE_TLS_TLS_1_1_ENABLED)
+ &crypto_method_md5,
+ &crypto_method_sha1,
+ &crypto_method_tls_prf_1,
+#endif
+
+#if (NX_SECURE_TLS_TLS_1_2_ENABLED)
+ &crypto_method_sha256,
+ &crypto_method_tls_prf_sha256,
+#endif
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ &crypto_method_hkdf,
+ &crypto_method_hmac,
+ &crypto_method_ecdhe,
+#endif
+};
+#else
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+#endif
+
+#include "ica_test_device_cert.c"
+#include "ica_test_ica_cert.c"
+
+/* Define the pointer of current instance control block. */
+static TLS_TEST_INSTANCE* demo_instance_ptr;
+
+/* Define external references. */
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Instance one test entry. */
+INT dtls_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_DTLS)
+
+ /* Get instance pointer. */
+ demo_instance_ptr = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
+
+/* Define what the initial system looks like. */
+void tx_application_define(void *first_unused_memory)
+{
+ ULONG gateway_ipv4_address;
+ UINT status;
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL, &pool_0, _nx_pcap_network_driver, (UCHAR*)ip_thread_stack, sizeof(ip_thread_stack), 1);
+print_error_message( "ip address number: %lu\n", TLS_TEST_IP_ADDRESS_NUMBER);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ nx_secure_tls_initialize();
+ nx_secure_dtls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", server_thread_entry, 0, demo_thread_stack, sizeof(demo_thread_stack), 16, 16, 4, TX_AUTO_START);
+}
+
+/* Notification flags for DTLS server connect/receive. */
+UINT server_connect_count = 0;
+UINT server_receive_count = 0;
+NX_SECURE_DTLS_SESSION *connect_session;
+NX_SECURE_DTLS_SESSION *receive_session;
+
+/* Connect notify callback for DTLS server - notifies the application thread that
+ a DTLS connection is ready to kickoff a handshake. */
+UINT server_connect_notify(NX_SECURE_DTLS_SESSION *dtls_session, NXD_ADDRESS *ip_address, UINT port)
+{
+ connect_session = dtls_session;
+ server_connect_count++;
+ return(NX_SUCCESS);
+}
+
+/* Receive notify callback for DTLS server - notifies the application thread that
+ we have received a DTLS record over an established DTLS session. */
+UINT server_receive_notify(NX_SECURE_DTLS_SESSION *dtls_session)
+{
+ receive_session = dtls_session;
+ server_receive_count++;
+ return(NX_SUCCESS);
+}
+
+/* TLS Server example application thread. */
+void server_thread_entry(ULONG thread_input)
+{
+ INT status = 0;
+ ULONG actual_status;
+ NX_PACKET *receive_packet;
+ NX_PACKET *send_packet;
+ UCHAR receive_buffer[100];
+ ULONG bytes;
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Create a socket. */
+ status = nx_secure_dtls_server_create(&dtls_server, &ip_0, DEVICE_SERVER_PORT, NX_IP_PERIODIC_RATE,
+ session_buffer, sizeof(session_buffer),
+ &nx_crypto_tls_ciphers, crypto_metadata, sizeof(crypto_metadata),
+ tls_packet_buffer, sizeof(tls_packet_buffer),
+ server_connect_notify, server_receive_notify);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ memset(&certificate, 0, sizeof(certificate));
+ status = nx_secure_x509_certificate_initialize(&certificate,
+ test_device_cert_der, test_device_cert_der_len,
+ NX_NULL, 0, test_device_cert_key_der,
+ test_device_cert_key_der_len, NX_SECURE_X509_KEY_TYPE_RSA_PKCS1_DER);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_dtls_server_local_certificate_add(&dtls_server, &certificate, 1);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_dtls_server_start(&dtls_server);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Post semaphore before accept sockets. */
+ print_error_message("Server is prepared. Post the semaphore.\n");
+ tls_test_semaphore_post(semaphore_server_prepared);
+
+ /* Accept a client socket connection. */
+ print_error_message("Server wait for connections.\n");
+
+ while (!server_connect_count)
+ {
+ tx_thread_sleep(1);
+ }
+ server_connect_count = 0;
+ print_error_message("Server accept.\n");
+
+ /* Start the DTLS Session now that we have a connected socket. */
+ status = nx_secure_dtls_server_session_start(connect_session, 20 * NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, 1);
+
+ /* Wait for records to be received. */
+ print_error_message("Server wait for records.\n");
+ while (!server_receive_count)
+ {
+ tx_thread_sleep(1);
+ }
+ server_receive_count = 0;
+
+ /* Receive the data, and print it out. */
+ status = nx_secure_dtls_session_receive(receive_session, &receive_packet, 5 * NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, 2);
+
+ /* Show received data. */
+ nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ receive_buffer[bytes] = 0;
+ print_error_message("Server received data: %s\n", receive_buffer);
+
+ /* Allocate a return packet and send received data back to the client. */
+ status = nx_secure_dtls_packet_allocate(connect_session, &pool_0, &send_packet, NX_NO_WAIT);
+ exit_if_fail(NX_SUCCESS == status, 3);
+
+ /* Append the data. */
+ status = nx_packet_data_append(send_packet, receive_buffer, bytes, &pool_0, NX_NO_WAIT);
+ exit_if_fail(NX_SUCCESS == status, 4);
+
+ /* DTLS send the received data back to the client. */
+ status = nx_secure_dtls_server_session_send(connect_session, send_packet);
+ exit_if_fail(NX_SUCCESS == status, 5);
+
+ /* End the DTLS session. */
+ status = nx_secure_dtls_session_end(connect_session, 5 * NX_IP_PERIODIC_RATE);
+ print_error_message("Server session end status %d.\n", status);
+
+ /* Shutdown DTLS server. */
+ nx_secure_dtls_server_stop(&dtls_server);
+ print_error_message("Server stop.\n");
+
+ /* Delete server. */
+ nx_secure_dtls_server_delete(&dtls_server);
+
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_openssl_client_certificate_verify_test_client_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_openssl_client_certificate_verify_test_client_entry.c
new file mode 100644
index 00000000..13672d58
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_openssl_client_certificate_verify_test_client_entry.c
@@ -0,0 +1,43 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_server_prepared;
+
+/* Instance two test entry. */
+INT dtls_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#ifndef NX_SECURE_TLS_SERVER_DISABLED
+
+/* Just use TLSv1.2 */
+CHAR* external_cmd[] = {
+ "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING,
+ "-verify", "10", /* Enabled client certificate verification. */
+ /* This programe must be executed at the directory of cmake_nx_secure_interoperability_test */
+ "-cert", "../../certificates/test_client.crt",
+ "-key", "../../certificates/test_client.key",
+ "-CAfile", "../../certificates/test.crt",
+ "-dtls1_2",
+ (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(semaphore_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_FAILED);
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_openssl_client_certificate_verify_test_server_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_openssl_client_certificate_verify_test_server_entry.c
new file mode 100644
index 00000000..375f792f
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_openssl_client_certificate_verify_test_server_entry.c
@@ -0,0 +1,38 @@
+#include "tls_test_frame.h"
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+/* Openssl echo server entry. */
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS)
+
+INT status, exit_status;
+
+/* Added -rev option to send reverse text received from clients back to the client. Added -naccept 1 to close the server after one tls session. */
+CHAR* external_cmd[] = { "openssl_echo_server.sh", "../../certificates/test_server.key",
+ "../../certificates/test_server.crt", "-dtls1_2",
+ "-port", DEVICE_SERVER_PORT_STRING,
+ "-CAfile", "../../certificates/test.crt",
+ "-Verify", "10", /* Enabled client certificate verification. */
+ (CHAR*)NULL};
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+ return TLS_TEST_SUCCESS;
+
+#else /* !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_openssl_ecc_test_client_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_openssl_ecc_test_client_entry.c
new file mode 100644
index 00000000..6b9c8cfd
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_openssl_ecc_test_client_entry.c
@@ -0,0 +1,40 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_server_prepared;
+
+/* Instance two test entry. */
+INT dtls_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+/* Just use TLSv1.2 */
+CHAR* external_cmd[] = {
+ "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING,
+ /* This programe must be executed at the directory of cmake_nx_secure_interoperability_test */
+ "-CAfile", "../ecc_certificates/ECCA2.crt",
+ "-dtls1_2",
+ (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(semaphore_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_FAILED);
+ return TLS_TEST_SUCCESS;
+
+#else /* if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_openssl_ecc_test_server_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_openssl_ecc_test_server_entry.c
new file mode 100644
index 00000000..f5b38827
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_openssl_ecc_test_server_entry.c
@@ -0,0 +1,38 @@
+#include "tls_test_frame.h"
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+/* Openssl echo server entry. */
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+INT status, exit_status;
+
+/* Added -rev option to send reverse text received from clients back to the client. Added -naccept 1 to close the server after one tls session. */
+CHAR* external_cmd[] = { "openssl_echo_server.sh",
+ "../../ecc_certificates/ECTestServer2.key",
+ "../../ecc_certificates/ECTestServer2.crt", "-dtls1_2",
+ "-port", DEVICE_SERVER_PORT_STRING,
+ "-CAfile", "../../ecc_certificates/ECCA2.crt",
+ (CHAR*)NULL};
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+ return TLS_TEST_SUCCESS;
+
+#else /* !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_openssl_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_openssl_echo_server_entry.c
new file mode 100644
index 00000000..62a84f5c
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_openssl_echo_server_entry.c
@@ -0,0 +1,33 @@
+#include "tls_test_frame.h"
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+/* Openssl echo server entry. */
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS)
+
+INT status, exit_status;
+
+/* Added -rev option to send reverse text received from clients back to the client. Added -naccept 1 to close the server after one tls session. */
+CHAR* external_cmd[] = { "openssl_echo_server.sh", "../key.pem", "../cert.pem", "-port", DEVICE_SERVER_PORT_STRING, "-dtls1_2", (CHAR*)NULL};
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_openssl_server_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_openssl_server_entry.c
new file mode 100644
index 00000000..da0e0754
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_openssl_server_entry.c
@@ -0,0 +1,31 @@
+#include "tls_test_frame.h"
+
+extern TLS_TEST_SEMAPHORE* semaphore_server_prepared;
+/* Openssl echo server entry. */
+INT dtls_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS)
+
+INT status, exit_status;
+CHAR* external_cmd[] = { "openssl_echo_server.sh", "../key.pem", "../cert.pem", "-dtls1_2", "-port", DEVICE_SERVER_PORT_STRING, (CHAR*)NULL};
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_reuse_nx_secure_server_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_reuse_nx_secure_server_entry.c
new file mode 100644
index 00000000..4883e904
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_reuse_nx_secure_server_entry.c
@@ -0,0 +1,218 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_server_prepared;
+
+/* Define the ThreadX and NetX object control blocks... */
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_SECURE_DTLS_SERVER dtls_server;
+NX_SECURE_X509_CERT certificate;
+
+UCHAR tls_packet_buffer[4000];
+
+/* Session buffer for DTLS server. Must be equal to the size of NX_SECURE_DTLS_SESSION times the
+ number of desired DTLS sessions. */
+static UCHAR session_buffer[sizeof(NX_SECURE_DTLS_SESSION)];
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+void server_thread_entry(ULONG thread_input);
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+CHAR crypto_metadata[30000];
+
+#include "ica_test_device_cert.c"
+#include "ica_test_ica_cert.c"
+
+/* Define the pointer of current instance control block. */
+static TLS_TEST_INSTANCE* demo_instance_ptr;
+
+/* Define external references. */
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Instance one test entry. */
+INT dtls_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_DTLS)
+
+ /* Get instance pointer. */
+ demo_instance_ptr = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
+
+/* Define what the initial system looks like. */
+void tx_application_define(void *first_unused_memory)
+{
+ ULONG gateway_ipv4_address;
+ UINT status;
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL, &pool_0, _nx_pcap_network_driver, (UCHAR*)ip_thread_stack, sizeof(ip_thread_stack), 1);
+print_error_message( "ip address number: %lu\n", TLS_TEST_IP_ADDRESS_NUMBER);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ nx_secure_tls_initialize();
+ nx_secure_dtls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", server_thread_entry, 0, demo_thread_stack, sizeof(demo_thread_stack), 16, 16, 4, TX_AUTO_START);
+}
+
+/* Notification flags for DTLS server connect/receive. */
+UINT server_connect_count = 0;
+UINT server_receive_count = 0;
+NX_SECURE_DTLS_SESSION *connect_session;
+NX_SECURE_DTLS_SESSION *receive_session;
+
+/* Connect notify callback for DTLS server - notifies the application thread that
+ a DTLS connection is ready to kickoff a handshake. */
+UINT server_connect_notify(NX_SECURE_DTLS_SESSION *dtls_session, NXD_ADDRESS *ip_address, UINT port)
+{
+ connect_session = dtls_session;
+ server_connect_count++;
+ return(NX_SUCCESS);
+}
+
+/* Receive notify callback for DTLS server - notifies the application thread that
+ we have received a DTLS record over an established DTLS session. */
+UINT server_receive_notify(NX_SECURE_DTLS_SESSION *dtls_session)
+{
+ receive_session = dtls_session;
+ server_receive_count++;
+ return(NX_SUCCESS);
+}
+
+/* TLS Server example application thread. */
+void server_thread_entry(ULONG thread_input)
+{
+ INT i = 0, status = 0;
+ ULONG actual_status;
+ NX_PACKET *receive_packet;
+ NX_PACKET *send_packet;
+ UCHAR receive_buffer[100];
+ ULONG bytes;
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Create a socket. */
+ status = nx_secure_dtls_server_create(&dtls_server, &ip_0, DEVICE_SERVER_PORT, NX_IP_PERIODIC_RATE,
+ session_buffer, sizeof(session_buffer),
+ &nx_crypto_tls_ciphers, crypto_metadata, sizeof(crypto_metadata),
+ tls_packet_buffer, sizeof(tls_packet_buffer),
+ server_connect_notify, server_receive_notify);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ memset(&certificate, 0, sizeof(certificate));
+ status = nx_secure_x509_certificate_initialize(&certificate,
+ test_device_cert_der, test_device_cert_der_len,
+ NX_NULL, 0, test_device_cert_key_der,
+ test_device_cert_key_der_len, NX_SECURE_X509_KEY_TYPE_RSA_PKCS1_DER);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_dtls_server_local_certificate_add(&dtls_server, &certificate, 1);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_dtls_server_start(&dtls_server);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ for (i = 0; i < 3; i++)
+ {
+ /* Post semaphore before accept sockets. */
+ print_error_message("Server connection %d: server is prepared. Post the semaphore.\n", i);
+ tls_test_semaphore_post(semaphore_server_prepared);
+
+ /* Accept a client socket connection. */
+ print_error_message("Server connection %d: wait for connections.\n", i);
+
+ while (!server_connect_count)
+ {
+ tx_thread_sleep(1);
+ }
+ server_connect_count = 0;
+ print_error_message("Server connection %d: server accept.\n", i);
+
+ /* Start the DTLS Session now that we have a connected socket. */
+ status = nx_secure_dtls_server_session_start(connect_session, 20 * NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, 1);
+
+ /* Wait for records to be received. */
+ print_error_message("Server connection %d: wait for records.\n", i);
+ while (!server_receive_count)
+ {
+ tx_thread_sleep(1);
+ }
+ server_receive_count = 0;
+
+ /* Receive the data, and print it out. */
+ status = nx_secure_dtls_session_receive(receive_session, &receive_packet, 5 * NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, 2);
+
+ /* Show received data. */
+ nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ receive_buffer[bytes] = 0;
+ print_error_message("Server received data: %s\n", receive_buffer);
+
+ /* Allocate a return packet and send received data back to the client. */
+ status = nx_secure_dtls_packet_allocate(connect_session, &pool_0, &send_packet, NX_NO_WAIT);
+ exit_if_fail(NX_SUCCESS == status, 3);
+
+ /* Append the data. */
+ status = nx_packet_data_append(send_packet, receive_buffer, bytes, &pool_0, NX_NO_WAIT);
+ exit_if_fail(NX_SUCCESS == status, 4);
+
+ /* DTLS send the received data back to the client. */
+ status = nx_secure_dtls_server_session_send(connect_session, send_packet);
+ exit_if_fail(NX_SUCCESS == status, 5);
+
+ /* End the DTLS session. */
+ status = nx_secure_dtls_session_end(connect_session, 5 * NX_IP_PERIODIC_RATE);
+ print_error_message("Server connection %d: session end status %d.\n", i, status);
+
+ print_error_message("Server connection %d: server unaccept, sleeping...\n", i);
+ tx_thread_sleep(1 * NX_IP_PERIODIC_RATE);
+ }
+
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_reuse_openssl_client_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_reuse_openssl_client_entry.c
new file mode 100644
index 00000000..e2c4360e
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_reuse_openssl_client_entry.c
@@ -0,0 +1,43 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_server_prepared;
+
+/* Instance two test entry. */
+INT dtls_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_DTLS)
+
+/* Just use DTLSv1.2 */
+CHAR* external_cmd[] = { "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING, "-dtls1_2", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ for (i = 0; i < 3; i++)
+ {
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(semaphore_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ if (exit_status)
+ {
+ /* Record errors. */
+ instance_status = TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED;
+ }
+ }
+
+ return instance_status;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_rsa_aes128_gcm_openssl_client_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_rsa_aes128_gcm_openssl_client_entry.c
new file mode 100644
index 00000000..d031e61e
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_rsa_aes128_gcm_openssl_client_entry.c
@@ -0,0 +1,35 @@
+#include "tls_test_frame.h"
+
+/* Global semaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_server_prepared;
+
+/* Instance two test entry. */
+INT dtls_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) && defined(NX_SECURE_ENABLE_AEAD_CIPHER)
+
+/* Just use DTLSv1.2 */
+CHAR* external_cmd[] = { "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING, "-cipher", "AES128-GCM-SHA256", "-dtls1_2", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS;
+
+ print_error_message("Client waiting for semaphore.\n");
+ tls_test_semaphore_wait(semaphore_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Client get semaphore. Launch a external test program.\n");
+
+ /* Call an external program to connect to DTLS server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_FAILED);
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_rsa_aes128_sha_openssl_client_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_rsa_aes128_sha_openssl_client_entry.c
new file mode 100644
index 00000000..5829a965
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_rsa_aes128_sha_openssl_client_entry.c
@@ -0,0 +1,35 @@
+#include "tls_test_frame.h"
+
+/* Global semaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_server_prepared;
+
+/* Instance two test entry. */
+INT dtls_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_DTLS)
+
+/* Just use DTLSv1.2 */
+CHAR* external_cmd[] = { "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING, "-cipher", "AES128-SHA256", "-dtls1_2", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS;
+
+ print_error_message("Client waiting for semaphore.\n");
+ tls_test_semaphore_wait(semaphore_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Client get semaphore. Launch a external test program.\n");
+
+ /* Call an external program to connect to DTLS server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_FAILED);
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_rsa_aes256_sha_openssl_client_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_rsa_aes256_sha_openssl_client_entry.c
new file mode 100644
index 00000000..627ba0ce
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_rsa_aes256_sha_openssl_client_entry.c
@@ -0,0 +1,35 @@
+#include "tls_test_frame.h"
+
+/* Global semaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_server_prepared;
+
+/* Instance two test entry. */
+INT dtls_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_DTLS)
+
+/* Just use DTLSv1.2 */
+CHAR* external_cmd[] = { "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING, "-cipher", "AES256-SHA256", "-dtls1_2", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS;
+
+ print_error_message("Client waiting for semaphore.\n");
+ tls_test_semaphore_wait(semaphore_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Client get semaphore. Launch a external test program.\n");
+
+ /* Call an external program to connect to DTLS server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_FAILED);
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_two_instance_test.c b/test/regression/interoperability_test/nx_secure_test/dtls_two_instance_test.c
new file mode 100644
index 00000000..4c1be6d8
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_two_instance_test.c
@@ -0,0 +1,73 @@
+#include "tls_test_frame.h"
+
+INT dtls_server_entry(TLS_TEST_INSTANCE* instance_ptr);
+INT dtls_client_entry(TLS_TEST_INSTANCE* instance_ptr);
+
+/* Global demo semaphore. */
+TLS_TEST_SEMAPHORE* semaphore_server_prepared;
+
+INT main( INT argc, CHAR* argv[])
+{
+INT status, exit_status[2];
+TLS_TEST_INSTANCE *ins0;
+TLS_TEST_INSTANCE *ins1;
+
+ /* Create two test instances. */
+ status = tls_test_instance_create(&ins0, /* test instance ptr */
+ "dtls_server", /* instance name */
+ dtls_server_entry, /* test entry */
+ 0, /* delay(seconds) */
+ 60, /* timeout(seconds) */
+ 1024, /* shared buffer size */
+ NULL); /* reserved */
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ status = tls_test_instance_create(&ins1,
+ "dtls_client",
+ dtls_client_entry,
+ 0,
+ 60,
+ 1024,
+ NULL);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Create a semaphore and set the initial value as 0. */
+ status = tls_test_semaphore_create(&semaphore_server_prepared, 0);
+
+ /* Create the test director. */
+ TLS_TEST_DIRECTOR *director;
+ status = tls_test_director_create(&director, NULL /* reserved */);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Register test instances to the director. */
+ status = tls_test_director_register_test_instance(director, ins0);
+ status += tls_test_director_register_test_instance(director, ins1);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Launch test. */
+ status = tls_test_director_test_start(director);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Collect exit code. */
+ tls_test_instance_show_exit_status(ins0);
+ tls_test_instance_show_exit_status(ins1);
+
+ /* Call the verify method to determine whether the test is passed. */
+ status = tls_test_instance_get_exit_status(ins0, &exit_status[0]);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+ status = tls_test_instance_get_exit_status(ins1, &exit_status[1]);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Destroy registered test instances and the director. */
+ tls_test_director_clean_all(director);
+
+ /* Destroy the semaphore. */
+ tls_test_semaphore_destroy(semaphore_server_prepared);
+
+ /* Return error if get unexpected test results. */
+ if ((TLS_TEST_NOT_AVAILABLE == exit_status[0]) || (TLS_TEST_NOT_AVAILABLE == exit_status[1]))
+ return TLS_TEST_NOT_AVAILABLE;
+
+ /* Return the result of verification. */
+ return exit_status[0] | exit_status[1];
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_version_1_0_nx_secure_client_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_version_1_0_nx_secure_client_entry.c
new file mode 100644
index 00000000..daa7ba3b
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_version_1_0_nx_secure_client_entry.c
@@ -0,0 +1,298 @@
+#include "tls_test_frame.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_UDP_SOCKET udp_socket;
+NX_SECURE_DTLS_SESSION dtls_session;
+UCHAR cert_buffer[2000];
+NX_SECURE_X509_CERT trusted_certificate;
+
+UCHAR tls_packet_buffer[4000];
+
+#include "cert.c"
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+
+#if (NX_SECURE_TLS_TLS_1_0_ENABLED) || (NX_SECURE_TLS_TLS_1_1_ENABLED)
+extern NX_CRYPTO_METHOD crypto_method_null;
+extern NX_CRYPTO_METHOD crypto_method_rsa;
+extern NX_CRYPTO_METHOD crypto_method_auth_psk;
+extern NX_CRYPTO_METHOD crypto_method_md5;
+extern NX_CRYPTO_METHOD crypto_method_sha1;
+extern NX_CRYPTO_METHOD crypto_method_sha256;
+extern NX_CRYPTO_METHOD crypto_method_aes_cbc_128;
+extern NX_CRYPTO_METHOD crypto_method_aes_cbc_256;
+extern NX_CRYPTO_METHOD crypto_method_aes_ccm_8;
+extern NX_CRYPTO_METHOD crypto_method_aes_128_gcm_16;
+extern NX_CRYPTO_METHOD crypto_method_hmac_sha1;
+extern NX_CRYPTO_METHOD crypto_method_hmac_sha256;
+extern NX_CRYPTO_METHOD crypto_method_hkdf_sha256;
+extern NX_CRYPTO_METHOD crypto_method_tls_prf_1;
+extern NX_CRYPTO_METHOD crypto_method_tls_prf_sha256;
+extern NX_CRYPTO_METHOD crypto_method_hkdf;
+extern NX_CRYPTO_METHOD crypto_method_hmac;
+extern NX_CRYPTO_METHOD crypto_method_ecdhe;
+
+NX_SECURE_TLS_CIPHERSUITE_INFO _nx_crypto_ciphersuite_lookup_table_1_0_1_1[] =
+{
+ /* Ciphersuite, public cipher, public_auth, session cipher & cipher mode, iv size, key size, hash method, hash size, TLS PRF */
+#ifdef NX_SECURE_ENABLE_AEAD_CIPHER
+ {TLS_RSA_WITH_AES_128_GCM_SHA256, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_128_gcm_16, 16, 16, &crypto_method_null, 0, &crypto_method_tls_prf_sha256},
+#endif /* NX_SECURE_ENABLE_AEAD_CIPHER */
+ {TLS_RSA_WITH_AES_256_CBC_SHA256, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_256, 16, 32, &crypto_method_hmac_sha256, 32, &crypto_method_tls_prf_sha256},
+ {TLS_RSA_WITH_AES_128_CBC_SHA256, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha256, 32, &crypto_method_tls_prf_sha256},
+ {TLS_RSA_WITH_AES_256_CBC_SHA, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_256, 16, 32, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+ {TLS_RSA_WITH_AES_128_CBC_SHA, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+
+#ifdef NX_SECURE_ENABLE_PSK_CIPHERSUITES
+ {TLS_PSK_WITH_AES_128_CBC_SHA256, &crypto_method_null, &crypto_method_auth_psk, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha256, 32, &crypto_method_tls_prf_sha256},
+#ifdef NX_SECURE_ENABLE_AEAD_CIPHER
+ {TLS_PSK_WITH_AES_128_CCM_8, &crypto_method_null, &crypto_method_auth_psk, &crypto_method_aes_ccm_8, 16, 16, &crypto_method_null, 0, &crypto_method_tls_prf_sha256},
+#endif
+#endif /* NX_SECURE_ENABLE_PSK_CIPHERSUITES */
+};
+
+/* Lookup table for X.509 digital certificates - they need a public-key algorithm and a hash routine for verification. */
+NX_SECURE_X509_CRYPTO _nx_crypto_x509_cipher_lookup_table_1_0_1_1[] =
+{
+ /* OID identifier, public cipher, hash method */
+ {NX_SECURE_TLS_X509_TYPE_RSA_SHA_256, &crypto_method_rsa, &crypto_method_sha256},
+ {NX_SECURE_TLS_X509_TYPE_RSA_SHA_1, &crypto_method_rsa, &crypto_method_sha1},
+ {NX_SECURE_TLS_X509_TYPE_RSA_MD5, &crypto_method_rsa, &crypto_method_md5},
+};
+
+/* Define the object we can pass into TLS. */
+NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers =
+{
+ /* Ciphersuite lookup table and size. */
+ _nx_crypto_ciphersuite_lookup_table_1_0_1_1,
+ sizeof(_nx_crypto_ciphersuite_lookup_table_1_0_1_1) / sizeof(NX_SECURE_TLS_CIPHERSUITE_INFO),
+
+#ifndef NX_SECURE_DISABLE_X509
+ /* X.509 certificate cipher table and size. */
+ _nx_crypto_x509_cipher_lookup_table_1_0_1_1,
+ sizeof(_nx_crypto_x509_cipher_lookup_table_1_0_1_1) / sizeof(NX_SECURE_X509_CRYPTO),
+#endif
+
+ /* TLS version-specific methods. */
+#if (NX_SECURE_TLS_TLS_1_0_ENABLED || NX_SECURE_TLS_TLS_1_1_ENABLED)
+ & crypto_method_md5,
+ &crypto_method_sha1,
+ &crypto_method_tls_prf_1,
+#endif
+
+#if (NX_SECURE_TLS_TLS_1_2_ENABLED)
+ &crypto_method_sha256,
+ &crypto_method_tls_prf_sha256,
+#endif
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ &crypto_method_hkdf,
+ &crypto_method_hmac,
+ &crypto_method_ecdhe,
+#endif
+};
+#else
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+#endif
+
+INT dtls_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) && (NX_SECURE_TLS_TLS_1_1_ENABLED)
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
+
+void tx_application_define(void *first_unused_memory)
+{
+ULONG gateway_ipv4_address;
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+ nx_secure_dtls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+NXD_ADDRESS server_address;
+NX_PARAMETER_NOT_USED(thread_input);
+
+
+ /* Address of remote server. */
+ server_address.nxd_ip_version = NX_IP_VERSION_V4;
+ server_address.nxd_ip_address.v4 = REMOTE_IP_ADDRESS_NUMBER;
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_udp_socket_create(&ip_0, &udp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 5);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup this thread to bind to a port. */
+ status = nx_udp_socket_bind(&udp_socket, 0, NX_NO_WAIT);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a DTLS session. */
+ status = nx_secure_dtls_session_create(&dtls_session,
+ &nx_crypto_tls_ciphers,
+ crypto_metadata,
+ sizeof(crypto_metadata),
+ tls_packet_buffer,
+ sizeof(tls_packet_buffer),
+ 1,
+ cert_buffer,
+ sizeof(cert_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_x509_certificate_initialize(&trusted_certificate, cert_der, cert_der_len,
+ NX_NULL, 0, NULL, 0, NX_SECURE_X509_KEY_TYPE_NONE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_dtls_session_trusted_certificate_add(&dtls_session, &trusted_certificate, 1);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = _nx_secure_dtls_client_protocol_version_override(&dtls_session, NX_SECURE_DTLS_VERSION_1_0);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_server_prepared);
+ tx_thread_sleep(100);
+
+ status = nx_icmp_ping(&ip_0, REMOTE_IP_ADDRESS_NUMBER, "abcdefg", 7, &send_packet, 10 * NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, status);
+ nx_packet_release(send_packet);
+
+ /* Attempt to connect the echo server. */
+ print_error_message("DTLS client session starting...\n");
+ status = nx_secure_dtls_client_session_start(&dtls_session, &udp_socket, &server_address, DEVICE_SERVER_PORT, 20 * NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_dtls_packet_allocate(&dtls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 2);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 3);
+
+ /* Send "hello" message. */
+ print_error_message("DTLS client session sending...\n");
+ status = nx_secure_dtls_client_session_send(&dtls_session, send_packet);
+ exit_if_fail(NX_SUCCESS == status, 4);
+
+#if 0
+ /* Receive the echoed and reversed data, and print it out. */
+ print_error_message("DTLS client session receving...\n");
+ status = nx_secure_dtls_session_receive(&dtls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 5);
+
+ /* Extract data received from server. */
+ status = nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ exit_if_fail(NX_SUCCESS == status, 6);
+
+ /* Check the reverse text received from openssl server. */
+ exit_if_fail('o' == ((CHAR*)receive_buffer)[0], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[1], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[2], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('e' == ((CHAR*)receive_buffer)[3], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('h' == ((CHAR*)receive_buffer)[4], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('\n' == ((CHAR*)receive_buffer)[5], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail(6 == bytes, 7);
+#endif
+
+ /* End the DTLS session. This is required to properly shut down the DTLS connection. */
+ print_error_message("DTLS client session end.\n");
+ nx_secure_dtls_session_end(&dtls_session, NX_NO_WAIT);
+
+ /* Delete the DTLS session. */
+ status = nx_secure_dtls_session_delete(&dtls_session);
+ exit_if_fail(NX_SUCCESS == status, 8);
+
+ /* Unbind the UDP socket from our port. */
+ status = nx_udp_socket_unbind(&udp_socket);
+ exit_if_fail(NX_SUCCESS == status, 9);
+
+ /* Delete the UDP socket instance to clean up. */
+ status = nx_udp_socket_delete(&udp_socket);
+ exit_if_fail(NX_SUCCESS == status, 10);
+
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_version_1_0_openssl_client_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_version_1_0_openssl_client_entry.c
new file mode 100644
index 00000000..56b5216a
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_version_1_0_openssl_client_entry.c
@@ -0,0 +1,40 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_server_prepared;
+
+/* Instance two test entry. */
+INT dtls_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) && (NX_SECURE_TLS_TLS_1_1_ENABLED)
+
+/* Just use DTLSv1.0 */
+CHAR* external_cmd[] = { "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING, "-dtls1", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(semaphore_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ if (exit_status)
+ {
+ /* Record errors. */
+ instance_status = TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED;
+ }
+
+ return instance_status;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/dtls_version_1_0_openssl_server_entry.c b/test/regression/interoperability_test/nx_secure_test/dtls_version_1_0_openssl_server_entry.c
new file mode 100644
index 00000000..21c61339
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/dtls_version_1_0_openssl_server_entry.c
@@ -0,0 +1,31 @@
+#include "tls_test_frame.h"
+
+extern TLS_TEST_SEMAPHORE* semaphore_server_prepared;
+/* Openssl echo server entry. */
+INT dtls_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS) && (NX_SECURE_TLS_TLS_1_1_ENABLED)
+
+INT status, exit_status;
+CHAR* external_cmd[] = { "openssl_echo_server.sh", "../key.pem", "../cert.pem", "-port", DEVICE_SERVER_PORT_STRING, "-dtls1", (CHAR*)NULL};
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/ecc_tls_1_2_openssl_client_cert_test_server_entry.c b/test/regression/interoperability_test/nx_secure_test/ecc_tls_1_2_openssl_client_cert_test_server_entry.c
new file mode 100644
index 00000000..fa5da41a
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/ecc_tls_1_2_openssl_client_cert_test_server_entry.c
@@ -0,0 +1,53 @@
+#include "tls_test_frame.h"
+
+
+
+CHAR* external_cmd[] = { "openssl", "s_server", "-rev",
+ "-key", "4-key",
+ "-cert", "6-cert",
+ "-CAfile", "8-ca",
+ "-curves", "10-curves",
+ "-naccept", "1", "-tls1_2",
+ "-cipher", "ECDH-ECDSA-AES128-SHA256",
+ "16-Verify", "10",
+ "-port", DEVICE_SERVER_PORT_STRING,
+ (CHAR*)NULL};
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+/* Openssl echo server entry. */
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+INT status, exit_status, i;
+
+/* Added -rev option to send reverse text received from clients back to the client. Added -naccept 1 to close the server after one tls session. */
+CHAR* external_cmd[] = { "openssl", "s_server", "-rev", "-key", "key.pem", "-cert", "cert.pem", "-naccept", "1", "-tls1_2",
+ "-key", "../ecc_certificates/ECTestServer2.key",
+ "-cert", "../ecc_certificates/ECTestServer2.crt",
+ "-CAfile", "../ecc_certificates/ECCA2.crt",
+ "-Verify", "10",
+ "-port", DEVICE_SERVER_PORT_STRING,
+ (CHAR*)NULL};
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+ return TLS_TEST_SUCCESS;
+
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/ecc_tls_1_2_openssl_curves_test_server_entry.c b/test/regression/interoperability_test/nx_secure_test/ecc_tls_1_2_openssl_curves_test_server_entry.c
new file mode 100644
index 00000000..fdc9ce0d
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/ecc_tls_1_2_openssl_curves_test_server_entry.c
@@ -0,0 +1,150 @@
+#include "tls_test_frame.h"
+
+typedef struct
+{
+ UINT curves_index;
+ UINT session_succ;
+ CHAR *key;
+ CHAR *cert;
+ CHAR *ca;
+ UINT verify;
+} OPENSSLTEST;
+
+static CHAR *curves[] =
+{
+ "prime192v1:secp224r1:prime256v1:secp384r1:secp521r1",
+ "prime192v1",
+ "secp224r1",
+ "prime256v1",
+ "secp384r1",
+ "secp521r1",
+ "prime192v1:prime256v1",
+ "secp224r1:prime256v1",
+};
+
+CHAR* external_cmd[] = { "openssl", "s_server", "-rev",
+ "-key", "4-key",
+ "-cert", "6-cert",
+ "-CAfile", "8-ca",
+ "-curves", "10-curves",
+ "-naccept", "1", "-tls1_2",
+ "-cipher", "ECDH-ECDSA-AES128-SHA256",
+ "-port", DEVICE_SERVER_PORT_STRING,
+ "16-Verify", "10",
+ (CHAR*)NULL};
+
+OPENSSLTEST tests[] =
+{
+ /* Select curve by certificate. */
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer9_192.key", "../ecc_certificates/ECTestServer9_192.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer8_224.key", "../ecc_certificates/ECTestServer8_224.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer4.key", "../ecc_certificates/ECTestServer4.crt", "../ecc_certificates/ECCA4.crt", NX_FALSE},
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer3.key", "../ecc_certificates/ECTestServer3.crt", "../ecc_certificates/ECCA3.crt", NX_FALSE},
+
+ /* Specify curve from client. */
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer9_192.key", "../ecc_certificates/ECTestServer9_192.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer8_224.key", "../ecc_certificates/ECTestServer8_224.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer4.key", "../ecc_certificates/ECTestServer4.crt", "../ecc_certificates/ECCA4.crt", NX_FALSE},
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer3.key", "../ecc_certificates/ECTestServer3.crt", "../ecc_certificates/ECCA3.crt", NX_FALSE},
+
+ /* Specify curve from server. */
+ {1, NX_TRUE, "../ecc_certificates/ECTestServer9_192.key", "../ecc_certificates/ECTestServer9_192.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {2, NX_TRUE, "../ecc_certificates/ECTestServer8_224.key", "../ecc_certificates/ECTestServer8_224.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {3, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {4, NX_TRUE, "../ecc_certificates/ECTestServer4.key", "../ecc_certificates/ECTestServer4.crt", "../ecc_certificates/ECCA4.crt", NX_FALSE},
+ {5, NX_TRUE, "../ecc_certificates/ECTestServer3.key", "../ecc_certificates/ECTestServer3.crt", "../ecc_certificates/ECCA3.crt", NX_FALSE},
+
+ /* Configure invalid curves at server side. */
+ {2, NX_FALSE, "../ecc_certificates/ECTestServer9_192.key", "../ecc_certificates/ECTestServer9_192.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {3, NX_FALSE, "../ecc_certificates/ECTestServer9_192.key", "../ecc_certificates/ECTestServer9_192.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {4, NX_FALSE, "../ecc_certificates/ECTestServer9_192.key", "../ecc_certificates/ECTestServer9_192.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {5, NX_FALSE, "../ecc_certificates/ECTestServer9_192.key", "../ecc_certificates/ECTestServer9_192.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+
+ /* Multiple curves used by server and CA cert. */
+ {0, NX_FALSE, "../ecc_certificates/ECTestServer9_192.key", "../ecc_certificates/ECTestServer9_192.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {0, NX_FALSE, "../ecc_certificates/ECTestServer8_224.key", "../ecc_certificates/ECTestServer8_224.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+
+ /* Client curve not supported by server. */
+ {1, NX_FALSE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {2, NX_FALSE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ /* Specify curve from client. */
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer4.key", "../ecc_certificates/ECTestServer4.crt", "../ecc_certificates/ECCA4.crt", NX_FALSE},
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer3.key", "../ecc_certificates/ECTestServer3.crt", "../ecc_certificates/ECCA3.crt", NX_FALSE},
+
+ /* Specify curve from server. */
+ {3, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {4, NX_TRUE, "../ecc_certificates/ECTestServer4.key", "../ecc_certificates/ECTestServer4.crt", "../ecc_certificates/ECCA4.crt", NX_FALSE},
+ {5, NX_TRUE, "../ecc_certificates/ECTestServer3.key", "../ecc_certificates/ECTestServer3.crt", "../ecc_certificates/ECCA3.crt", NX_FALSE},
+
+ /* Client curves not suitable for signature. */
+ {0, NX_FALSE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {0, NX_FALSE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+
+ /* Client curve not supported by server. */
+ {3, NX_FALSE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {4, NX_FALSE, "../ecc_certificates/ECTestServer4.key", "../ecc_certificates/ECTestServer4.crt", "../ecc_certificates/ECCA4.crt", NX_FALSE},
+#endif
+
+};
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+/* Openssl echo server entry. */
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+INT status, exit_status, i;
+
+ for (i = 0; i < sizeof(tests) / sizeof(OPENSSLTEST); i++)
+ {
+ external_cmd[4] = tests[i].key;
+ external_cmd[6] = tests[i].cert;
+ external_cmd[8] = tests[i].ca;
+ external_cmd[10] = curves[tests[i].curves_index];
+ if (tests[i].verify)
+ {
+ external_cmd[18] = "-Verify";
+ }
+ else
+ {
+ external_cmd[18] = NULL;
+ }
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ if (i == 23)
+ {
+ external_cmd[0] = "openssl-1.1";
+ external_cmd[13] = "-tls1_3";
+ external_cmd[14] = "-ciphersuites";
+ external_cmd[15] = "TLS_AES_128_GCM_SHA256";
+ }
+#endif
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+
+ }
+
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/ecc_tls_1_2_openssl_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/ecc_tls_1_2_openssl_echo_server_entry.c
new file mode 100644
index 00000000..e953d2ac
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/ecc_tls_1_2_openssl_echo_server_entry.c
@@ -0,0 +1,193 @@
+#include "tls_test_frame.h"
+
+typedef struct
+{
+ UINT cipher_index;
+ UINT session_succ;
+ CHAR *key;
+ CHAR *cert;
+ CHAR *ca;
+ UINT verify;
+ UCHAR *version;
+} OPENSSLTEST;
+
+static CHAR *ciphers[] =
+{
+ "ALL",
+ "ECDH-ECDSA-AES128-SHA",
+ "ECDH-RSA-AES128-SHA",
+ "ECDHE-ECDSA-AES128-SHA256",
+ "ECDHE-RSA-AES128-SHA256",
+ "ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES128-SHA:ECDH-RSA-AES128-SHA:ECDH-ECDSA-AES128-SHA",
+ "ECDH-ECDSA-AES256-SHA256",
+ "ECDHE-ECDSA-AES256-SHA",
+ "ECDH-RSA-AES256-SHA256",
+ "ECDHE-RSA-AES256-SHA",
+ "ECDHE-ECDSA-AES128-SHA256",
+ "ECDHE-ECDSA-AES256-SHA384",
+ "ECDH-ECDSA-AES128-SHA256",
+ "ECDH-ECDSA-AES256-SHA384",
+ "ECDHE-RSA-AES128-SHA256",
+ "ECDHE-RSA-AES256-SHA384",
+ "ECDH-RSA-AES128-SHA256",
+ "ECDH-RSA-AES256-SHA384",
+ "ECDHE-ECDSA-AES128-GCM-SHA256",
+ "ECDHE-RSA-AES128-GCM-SHA256",
+ "ECDH-ECDSA-AES128-GCM-SHA256",
+ "ECDH-RSA-AES128-GCM-SHA256",
+ "TLS_AES_128_GCM_SHA256",
+ "TLS_AES_256_GCM_SHA384",
+ "TLS_AES_128_CCM_SHA256",
+ "TLS_AES_128_CCM_8_SHA256",
+};
+
+CHAR* external_cmd[] = { "openssl", "s_server", "-rev",
+ "-key", "4-key",
+ "-cert", "6-cert",
+ "-CAfile", "8-ca",
+ "-cipher", "10-cipher",
+ "-naccept", "1", "-tls1_2",
+ "-port", DEVICE_SERVER_PORT_STRING,
+ "14-Verify", "10",
+ (CHAR*)NULL};
+
+OPENSSLTEST tests[] =
+{
+ /* Select ciphersuite according to certificate. */
+ {0, NX_TRUE, "../ecc_certificates/ECTest.key", "../ecc_certificates/ECTest.crt", "../ecc_certificates/ECCA.crt", NX_FALSE, "-tls1_2"},
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"},
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer6.key", "../ecc_certificates/ECTestServer6.crt", "../ecc_certificates/ECCA4.crt", NX_FALSE, "-tls1_2"},
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer10.key", "../ecc_certificates/ECTestServer10.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"},
+
+ /* Select ciphersuite according to certificate.
+ * The order of client ciphersuites are reversed of server. */
+ {0, NX_TRUE, "../ecc_certificates/ECTest.key", "../ecc_certificates/ECTest.crt", "../ecc_certificates/ECCA.crt", NX_FALSE, "-tls1_2"},
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"},
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer6.key", "../ecc_certificates/ECTestServer6.crt", "../ecc_certificates/ECCA4.crt", NX_FALSE, "-tls1_2"},
+
+ /* Specified ciphersuites. */
+ /* {1, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"}, */
+ /* {2, NX_TRUE, "../ecc_certificates/ECTest.key", "../ecc_certificates/ECTest.crt", "../ecc_certificates/ECCA.crt", NX_FALSE, "-tls1_2"}, */
+ {3, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"},
+ {4, NX_TRUE, "../ecc_certificates/ECTestServer6.key", "../ecc_certificates/ECTestServer6.crt", "../ecc_certificates/ECCA4.crt", NX_FALSE, "-tls1_2"},
+
+ /* The Server cert supports ECDH_ECDSA and ECDHE_ECDSA. */
+ /* {0, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"}, */
+ /* {0, NX_FALSE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"}, */
+ {0, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"},
+ {0, NX_FALSE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"},
+
+ /* Let the server pickup supported ciphersuite. */
+ /* {1, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"}, */
+ /* {2, NX_TRUE, "../ecc_certificates/ECTest.key", "../ecc_certificates/ECTest.crt", "../ecc_certificates/ECCA.crt", NX_FALSE, "-tls1_2"}, */
+ {3, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"},
+ {4, NX_TRUE, "../ecc_certificates/ECTestServer6.key", "../ecc_certificates/ECTestServer6.crt", "../ecc_certificates/ECCA4.crt", NX_FALSE, "-tls1_2"},
+
+ /* {6, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"}, */
+ /* {7, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"}, */
+ /* {8, NX_TRUE, "../ecc_certificates/ECTest.key", "../ecc_certificates/ECTest.crt", "../ecc_certificates/ECCA.crt", NX_FALSE, "-tls1_2"}, */
+ /* {9, NX_TRUE, "../ecc_certificates/ECTestServer6.key", "../ecc_certificates/ECTestServer6.crt", "../ecc_certificates/ECCA4.crt", NX_FALSE, "-tls1_2"}, */
+ {10, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"},
+ /*{11, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"},*/
+ /*{12, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"},*/
+ /*{13, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"},*/
+ {14, NX_TRUE, "../ecc_certificates/ECTestServer6.key", "../ecc_certificates/ECTestServer6.crt", "../ecc_certificates/ECCA4.crt", NX_FALSE, "-tls1_2"},
+ /*{15, NX_TRUE, "../ecc_certificates/ECTestServer6.key", "../ecc_certificates/ECTestServer6.crt", "../ecc_certificates/ECCA4.crt", NX_FALSE, "-tls1_2"},*/
+ /*{16, NX_TRUE, "../ecc_certificates/ECTest.key", "../ecc_certificates/ECTest.crt", "../ecc_certificates/ECCA.crt", NX_FALSE, "-tls1_2"},*/
+ /*{17, NX_TRUE, "../ecc_certificates/ECTest.key", "../ecc_certificates/ECTest.crt", "../ecc_certificates/ECCA.crt", NX_FALSE, "-tls1_2"},*/
+
+#ifdef NX_SECURE_TLS_ENABLE_TLS_1_0
+
+ /* Specified ciphersuites. */
+ /*{1, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1"},*/
+ /*{2, NX_TRUE, "../ecc_certificates/ECTest.key", "../ecc_certificates/ECTest.crt", "../ecc_certificates/ECCA.crt", NX_FALSE, "-tls1"},*/
+ {7, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1"},
+ {9, NX_TRUE, "../ecc_certificates/ECTestServer6.key", "../ecc_certificates/ECTestServer6.crt", "../ecc_certificates/ECCA4.crt", NX_FALSE, "-tls1"},
+#endif /* NX_SECURE_TLS_ENABLE_TLS_1_0 */
+
+#ifdef NX_SECURE_TLS_ENABLE_TLS_1_1
+
+ /* Specified ciphersuites. */
+ /*{1, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_1"},*/
+ /*{2, NX_TRUE, "../ecc_certificates/ECTest.key", "../ecc_certificates/ECTest.crt", "../ecc_certificates/ECCA.crt", NX_FALSE, "-tls1_1"},*/
+ {7, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_1"},
+ {9, NX_TRUE, "../ecc_certificates/ECTestServer6.key", "../ecc_certificates/ECTestServer6.crt", "../ecc_certificates/ECCA4.crt", NX_FALSE, "-tls1_1"},
+#endif /* NX_SECURE_TLS_ENABLE_TLS_1_1 */
+
+#ifdef NX_SECURE_ENABLE_AEAD_CIPHER
+ /* AES128-GCM ciphersuites. */
+ {18, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"},
+ {19, NX_TRUE, "../ecc_certificates/ECTestServer6.key", "../ecc_certificates/ECTestServer6.crt", "../ecc_certificates/ECCA4.crt", NX_FALSE, "-tls1_2"},
+ /*{20, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_2"},*/
+ /*{21, NX_TRUE, "../ecc_certificates/ECTest.key", "../ecc_certificates/ECTest.crt", "../ecc_certificates/ECCA.crt", NX_FALSE, "-tls1_2"},*/
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ /* Test TLS 1.3 ciphersuites. */
+ {22, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_3"},
+ {24, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_3"},
+ {25, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_3"},
+
+ /* Client sends ciphersuites not supported by server. */
+ {23, NX_FALSE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE, "-tls1_3"},
+#endif
+#endif
+
+
+};
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+/* Openssl echo server entry. */
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+INT status, exit_status, i;
+
+ for (i = 0; i < sizeof(tests) / sizeof(OPENSSLTEST); i++)
+ {
+ external_cmd[4] = tests[i].key;
+ external_cmd[6] = tests[i].cert;
+ external_cmd[8] = tests[i].ca;
+ external_cmd[10] = ciphers[tests[i].cipher_index];
+ external_cmd[13] = tests[i].version;
+ if (tests[i].verify)
+ {
+ external_cmd[16] = "-Verify";
+ }
+ else
+ {
+ external_cmd[16] = NULL;
+ }
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ if (tests[i].cipher_index == 22)
+ {
+ external_cmd[0] = "openssl-1.1";
+ external_cmd[9] = "-ciphersuites";
+ external_cmd[13] = "-tls1_3";
+ }
+#endif
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+
+ }
+
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/ica_test_device_cert.c b/test/regression/interoperability_test/nx_secure_test/ica_test_device_cert.c
new file mode 100644
index 00000000..9e597f92
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/ica_test_device_cert.c
@@ -0,0 +1,191 @@
+unsigned char test_device_cert_der[] = {
+ 0x30, 0x82, 0x03, 0xdb, 0x30, 0x82, 0x02, 0xc3, 0xa0, 0x03, 0x02, 0x01,
+ 0x02, 0x02, 0x02, 0x10, 0x00, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48,
+ 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05, 0x00, 0x30, 0x6f, 0x31, 0x0b,
+ 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31,
+ 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x02, 0x43, 0x41,
+ 0x31, 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x0d, 0x45,
+ 0x78, 0x70, 0x72, 0x65, 0x73, 0x73, 0x20, 0x4c, 0x6f, 0x67, 0x69, 0x63,
+ 0x31, 0x12, 0x30, 0x10, 0x06, 0x03, 0x55, 0x04, 0x0b, 0x0c, 0x09, 0x4e,
+ 0x58, 0x20, 0x53, 0x65, 0x63, 0x75, 0x72, 0x65, 0x31, 0x27, 0x30, 0x25,
+ 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c, 0x1e, 0x4e, 0x58, 0x20, 0x53, 0x65,
+ 0x63, 0x75, 0x72, 0x65, 0x20, 0x54, 0x65, 0x73, 0x74, 0x20, 0x49, 0x6e,
+ 0x74, 0x65, 0x72, 0x6d, 0x65, 0x64, 0x69, 0x61, 0x74, 0x65, 0x20, 0x43,
+ 0x41, 0x30, 0x1e, 0x17, 0x0d, 0x31, 0x37, 0x30, 0x33, 0x33, 0x31, 0x32,
+ 0x31, 0x30, 0x39, 0x30, 0x39, 0x5a, 0x17, 0x0d, 0x32, 0x37, 0x30, 0x33,
+ 0x32, 0x39, 0x32, 0x31, 0x30, 0x39, 0x30, 0x39, 0x5a, 0x30, 0x75, 0x31,
+ 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53,
+ 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x0a, 0x43,
+ 0x61, 0x6c, 0x69, 0x66, 0x6f, 0x72, 0x6e, 0x69, 0x61, 0x31, 0x16, 0x30,
+ 0x14, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x0d, 0x45, 0x78, 0x70, 0x72,
+ 0x65, 0x73, 0x73, 0x20, 0x4c, 0x6f, 0x67, 0x69, 0x63, 0x31, 0x12, 0x30,
+ 0x10, 0x06, 0x03, 0x55, 0x04, 0x0b, 0x0c, 0x09, 0x4e, 0x58, 0x20, 0x53,
+ 0x65, 0x63, 0x75, 0x72, 0x65, 0x31, 0x25, 0x30, 0x23, 0x06, 0x03, 0x55,
+ 0x04, 0x03, 0x0c, 0x1c, 0x4e, 0x58, 0x20, 0x53, 0x65, 0x63, 0x75, 0x72,
+ 0x65, 0x20, 0x44, 0x65, 0x76, 0x69, 0x63, 0x65, 0x20, 0x43, 0x65, 0x72,
+ 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74, 0x65, 0x30, 0x82, 0x01, 0x22,
+ 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01,
+ 0x01, 0x05, 0x00, 0x03, 0x82, 0x01, 0x0f, 0x00, 0x30, 0x82, 0x01, 0x0a,
+ 0x02, 0x82, 0x01, 0x01, 0x00, 0xc4, 0x7e, 0xd4, 0xe3, 0xa2, 0x0c, 0x78,
+ 0xe6, 0x0f, 0xa5, 0x3c, 0x01, 0x9b, 0x01, 0xdf, 0x96, 0xf6, 0x8e, 0xa0,
+ 0x80, 0x4b, 0xb1, 0xc7, 0x20, 0x3c, 0xca, 0x81, 0x9a, 0xce, 0x08, 0x5f,
+ 0x70, 0x99, 0x8d, 0x44, 0x46, 0xbc, 0xf5, 0xb1, 0x80, 0x3c, 0xe0, 0xc9,
+ 0x09, 0x11, 0xb4, 0x07, 0x89, 0x5f, 0x06, 0x89, 0xec, 0xbe, 0xf8, 0x29,
+ 0x48, 0x40, 0x55, 0x60, 0x1d, 0x59, 0xb3, 0x7b, 0x84, 0x77, 0xc3, 0x34,
+ 0xf4, 0xd3, 0x51, 0x3e, 0x2f, 0x9d, 0x10, 0xbb, 0xaf, 0x47, 0xb2, 0xc5,
+ 0x78, 0x8a, 0x85, 0xea, 0xbb, 0xe5, 0xb3, 0x8a, 0x25, 0xaf, 0xd6, 0xb9,
+ 0xb3, 0x47, 0xf3, 0x5f, 0x7b, 0xc2, 0x69, 0xe3, 0x08, 0xf5, 0x45, 0xae,
+ 0x53, 0xb4, 0x79, 0x6e, 0xdd, 0xcf, 0xc0, 0x53, 0x81, 0x62, 0xd3, 0x2c,
+ 0xc9, 0x19, 0xcb, 0x5d, 0xfc, 0xa9, 0xd8, 0xa7, 0xab, 0x65, 0x52, 0x02,
+ 0x46, 0x56, 0xc0, 0x5b, 0xef, 0xee, 0x0a, 0xf1, 0x35, 0x87, 0xf7, 0x14,
+ 0xec, 0x1b, 0x77, 0x11, 0x81, 0x4d, 0xca, 0xdc, 0x55, 0x66, 0x40, 0xa4,
+ 0x04, 0xdc, 0x2a, 0x9f, 0xfe, 0x9f, 0x99, 0x4d, 0xb2, 0x5a, 0xcb, 0x58,
+ 0x97, 0x1d, 0xd4, 0x74, 0x16, 0xd0, 0x7e, 0x1d, 0x5e, 0x9b, 0xf7, 0xf3,
+ 0x5b, 0xd4, 0xf5, 0xde, 0xa5, 0x71, 0x36, 0x13, 0x7f, 0xea, 0xba, 0x0b,
+ 0x3e, 0xbd, 0xef, 0x7c, 0x34, 0x41, 0xe1, 0xb7, 0x99, 0x46, 0x9f, 0x81,
+ 0xc6, 0xcf, 0x72, 0x94, 0x65, 0x52, 0xf0, 0x88, 0x17, 0xf6, 0x00, 0xf4,
+ 0xd0, 0x9a, 0x66, 0xe7, 0x1e, 0xa5, 0xfd, 0x4b, 0x95, 0xf3, 0x0e, 0x0f,
+ 0x10, 0x60, 0x74, 0x54, 0xda, 0xb0, 0x91, 0x0a, 0x10, 0x07, 0x19, 0x30,
+ 0x71, 0x34, 0x5f, 0xe2, 0x1c, 0x08, 0x77, 0x2e, 0xbc, 0xa3, 0x13, 0x18,
+ 0x22, 0x5e, 0xf9, 0xe0, 0x67, 0x8e, 0xbc, 0xc0, 0x7d, 0x02, 0x03, 0x01,
+ 0x00, 0x01, 0xa3, 0x7b, 0x30, 0x79, 0x30, 0x09, 0x06, 0x03, 0x55, 0x1d,
+ 0x13, 0x04, 0x02, 0x30, 0x00, 0x30, 0x2c, 0x06, 0x09, 0x60, 0x86, 0x48,
+ 0x01, 0x86, 0xf8, 0x42, 0x01, 0x0d, 0x04, 0x1f, 0x16, 0x1d, 0x4f, 0x70,
+ 0x65, 0x6e, 0x53, 0x53, 0x4c, 0x20, 0x47, 0x65, 0x6e, 0x65, 0x72, 0x61,
+ 0x74, 0x65, 0x64, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63,
+ 0x61, 0x74, 0x65, 0x30, 0x1d, 0x06, 0x03, 0x55, 0x1d, 0x0e, 0x04, 0x16,
+ 0x04, 0x14, 0x5c, 0xac, 0x85, 0x36, 0xd2, 0x6c, 0x5b, 0x71, 0xd0, 0x7e,
+ 0x78, 0xe6, 0x4b, 0xc7, 0x9e, 0x0b, 0x06, 0xaa, 0x70, 0x8b, 0x30, 0x1f,
+ 0x06, 0x03, 0x55, 0x1d, 0x23, 0x04, 0x18, 0x30, 0x16, 0x80, 0x14, 0x8e,
+ 0x6a, 0xb0, 0xfe, 0x49, 0xc5, 0x6a, 0x96, 0x9e, 0xba, 0xb8, 0xb6, 0x58,
+ 0xfc, 0x52, 0x7f, 0xab, 0x51, 0xf2, 0x3a, 0x30, 0x0d, 0x06, 0x09, 0x2a,
+ 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05, 0x00, 0x03, 0x82,
+ 0x01, 0x01, 0x00, 0x58, 0x39, 0x3d, 0xc9, 0xcf, 0x4a, 0x8b, 0x15, 0x82,
+ 0xcf, 0xce, 0x12, 0xb8, 0x4f, 0x6e, 0x83, 0x71, 0x9b, 0x52, 0xeb, 0xe9,
+ 0xdc, 0xe4, 0xe1, 0x77, 0x3b, 0x74, 0xd7, 0xc5, 0xd7, 0x50, 0x9a, 0xb9,
+ 0x1f, 0x0a, 0x27, 0x0a, 0x9b, 0x19, 0xf0, 0x2d, 0x86, 0xf7, 0x71, 0xec,
+ 0x7c, 0x87, 0x65, 0x19, 0xd0, 0x86, 0xe2, 0xf1, 0xd5, 0x22, 0x21, 0xe3,
+ 0xbf, 0x0d, 0xcb, 0x42, 0x7f, 0x70, 0xe5, 0x13, 0x96, 0x6d, 0x5b, 0xc1,
+ 0x7e, 0xd0, 0x34, 0x82, 0xaf, 0x29, 0xed, 0x7f, 0x6e, 0xc6, 0x7f, 0x8b,
+ 0xe8, 0x20, 0xc6, 0x39, 0x51, 0x9b, 0xec, 0x15, 0xa8, 0x9a, 0x63, 0xa5,
+ 0x92, 0x4a, 0xbc, 0x45, 0xf0, 0x86, 0xef, 0x09, 0xc0, 0xe4, 0x32, 0x3c,
+ 0x7a, 0x62, 0x51, 0x67, 0x0b, 0x0b, 0x8a, 0x2e, 0x07, 0xd5, 0x7c, 0xd5,
+ 0xd0, 0x4f, 0x93, 0x1d, 0x2d, 0x00, 0x6d, 0x99, 0x89, 0x55, 0xb3, 0x99,
+ 0x98, 0x1b, 0x13, 0x60, 0xb4, 0x80, 0x57, 0xbe, 0xe3, 0x25, 0xb6, 0x9a,
+ 0x75, 0x95, 0x3d, 0xba, 0xe5, 0x48, 0xa6, 0x3b, 0x1c, 0xd7, 0x50, 0x90,
+ 0x19, 0x4c, 0xf5, 0x22, 0x94, 0x7f, 0x79, 0xd5, 0x5e, 0x5a, 0xfb, 0x29,
+ 0x34, 0xf8, 0xd7, 0xf5, 0x2e, 0x95, 0x81, 0xb7, 0x2c, 0x8f, 0x2f, 0xcf,
+ 0xdd, 0xc4, 0xcf, 0x1b, 0x2e, 0x2b, 0xe8, 0x4d, 0x92, 0xf6, 0x8f, 0xba,
+ 0x08, 0x1a, 0x8a, 0x13, 0x2c, 0x2d, 0x38, 0xce, 0xfe, 0xa5, 0x59, 0xc5,
+ 0xea, 0x3a, 0x07, 0x8b, 0xf9, 0x8d, 0x33, 0x25, 0xc0, 0x4e, 0x75, 0x51,
+ 0xfc, 0xd1, 0x12, 0xec, 0x85, 0xb1, 0xb5, 0xf4, 0xc2, 0xb8, 0x05, 0x3c,
+ 0x00, 0x4a, 0x1b, 0xab, 0xb2, 0xab, 0x69, 0x58, 0x33, 0x93, 0xf8, 0x47,
+ 0x12, 0x75, 0xc2, 0x3a, 0x82, 0xe1, 0x2d, 0x95, 0xa9, 0x9c, 0xb9, 0xe3,
+ 0x3d, 0x29, 0x93, 0x65, 0xa1, 0x79, 0xee
+};
+unsigned int test_device_cert_der_len = 991;
+
+unsigned char test_device_cert_key_der[] = {
+ 0x30, 0x82, 0x04, 0xa3, 0x02, 0x01, 0x00, 0x02, 0x82, 0x01, 0x01, 0x00,
+ 0xc4, 0x7e, 0xd4, 0xe3, 0xa2, 0x0c, 0x78, 0xe6, 0x0f, 0xa5, 0x3c, 0x01,
+ 0x9b, 0x01, 0xdf, 0x96, 0xf6, 0x8e, 0xa0, 0x80, 0x4b, 0xb1, 0xc7, 0x20,
+ 0x3c, 0xca, 0x81, 0x9a, 0xce, 0x08, 0x5f, 0x70, 0x99, 0x8d, 0x44, 0x46,
+ 0xbc, 0xf5, 0xb1, 0x80, 0x3c, 0xe0, 0xc9, 0x09, 0x11, 0xb4, 0x07, 0x89,
+ 0x5f, 0x06, 0x89, 0xec, 0xbe, 0xf8, 0x29, 0x48, 0x40, 0x55, 0x60, 0x1d,
+ 0x59, 0xb3, 0x7b, 0x84, 0x77, 0xc3, 0x34, 0xf4, 0xd3, 0x51, 0x3e, 0x2f,
+ 0x9d, 0x10, 0xbb, 0xaf, 0x47, 0xb2, 0xc5, 0x78, 0x8a, 0x85, 0xea, 0xbb,
+ 0xe5, 0xb3, 0x8a, 0x25, 0xaf, 0xd6, 0xb9, 0xb3, 0x47, 0xf3, 0x5f, 0x7b,
+ 0xc2, 0x69, 0xe3, 0x08, 0xf5, 0x45, 0xae, 0x53, 0xb4, 0x79, 0x6e, 0xdd,
+ 0xcf, 0xc0, 0x53, 0x81, 0x62, 0xd3, 0x2c, 0xc9, 0x19, 0xcb, 0x5d, 0xfc,
+ 0xa9, 0xd8, 0xa7, 0xab, 0x65, 0x52, 0x02, 0x46, 0x56, 0xc0, 0x5b, 0xef,
+ 0xee, 0x0a, 0xf1, 0x35, 0x87, 0xf7, 0x14, 0xec, 0x1b, 0x77, 0x11, 0x81,
+ 0x4d, 0xca, 0xdc, 0x55, 0x66, 0x40, 0xa4, 0x04, 0xdc, 0x2a, 0x9f, 0xfe,
+ 0x9f, 0x99, 0x4d, 0xb2, 0x5a, 0xcb, 0x58, 0x97, 0x1d, 0xd4, 0x74, 0x16,
+ 0xd0, 0x7e, 0x1d, 0x5e, 0x9b, 0xf7, 0xf3, 0x5b, 0xd4, 0xf5, 0xde, 0xa5,
+ 0x71, 0x36, 0x13, 0x7f, 0xea, 0xba, 0x0b, 0x3e, 0xbd, 0xef, 0x7c, 0x34,
+ 0x41, 0xe1, 0xb7, 0x99, 0x46, 0x9f, 0x81, 0xc6, 0xcf, 0x72, 0x94, 0x65,
+ 0x52, 0xf0, 0x88, 0x17, 0xf6, 0x00, 0xf4, 0xd0, 0x9a, 0x66, 0xe7, 0x1e,
+ 0xa5, 0xfd, 0x4b, 0x95, 0xf3, 0x0e, 0x0f, 0x10, 0x60, 0x74, 0x54, 0xda,
+ 0xb0, 0x91, 0x0a, 0x10, 0x07, 0x19, 0x30, 0x71, 0x34, 0x5f, 0xe2, 0x1c,
+ 0x08, 0x77, 0x2e, 0xbc, 0xa3, 0x13, 0x18, 0x22, 0x5e, 0xf9, 0xe0, 0x67,
+ 0x8e, 0xbc, 0xc0, 0x7d, 0x02, 0x03, 0x01, 0x00, 0x01, 0x02, 0x82, 0x01,
+ 0x00, 0x20, 0x0c, 0x53, 0xaa, 0xa0, 0xe6, 0x89, 0xdd, 0x74, 0x15, 0xce,
+ 0x18, 0xb0, 0xf0, 0x78, 0x48, 0x46, 0x04, 0x73, 0x37, 0x19, 0xa1, 0x70,
+ 0x49, 0xd8, 0xc0, 0x6a, 0xad, 0x16, 0x07, 0x95, 0x91, 0x66, 0xe9, 0xfc,
+ 0x85, 0xd1, 0x11, 0xfd, 0x96, 0x5d, 0xd7, 0x87, 0xd2, 0x7b, 0xd9, 0xb2,
+ 0x14, 0xfc, 0xb3, 0xb3, 0x51, 0x32, 0xc0, 0x84, 0xf3, 0x2c, 0xd2, 0xff,
+ 0xef, 0x29, 0x8f, 0x35, 0x89, 0x20, 0x83, 0x6d, 0x22, 0xb5, 0x48, 0x9d,
+ 0xec, 0xe4, 0x20, 0x33, 0x8c, 0x5e, 0x14, 0x51, 0x52, 0xdc, 0xbd, 0x04,
+ 0xd1, 0x0a, 0xa0, 0xe2, 0xda, 0x4c, 0xb8, 0xa7, 0xe7, 0x0e, 0xc8, 0x29,
+ 0xfd, 0xa4, 0x72, 0xe2, 0xbd, 0xb6, 0x4b, 0x5c, 0x28, 0x78, 0xda, 0x09,
+ 0x74, 0x12, 0x0b, 0x5b, 0x53, 0x52, 0x0c, 0x01, 0x54, 0xf7, 0x69, 0x0c,
+ 0xf6, 0x45, 0xb9, 0x79, 0x77, 0x61, 0xfa, 0x23, 0x36, 0x8e, 0x54, 0x0f,
+ 0x19, 0x63, 0xd4, 0x84, 0xd7, 0xea, 0xc5, 0x3e, 0x8c, 0x4f, 0x2e, 0x1d,
+ 0x24, 0xd6, 0x53, 0x15, 0x47, 0xcd, 0xb6, 0x43, 0x67, 0x94, 0x85, 0x43,
+ 0xe1, 0x90, 0x8b, 0xef, 0x19, 0x88, 0xcf, 0xa9, 0x1c, 0x50, 0xce, 0x33,
+ 0x11, 0x2c, 0x61, 0x92, 0xf4, 0xc9, 0xa0, 0xa4, 0x34, 0xdc, 0x7e, 0xea,
+ 0xb5, 0x27, 0x0b, 0x35, 0xb0, 0x83, 0x22, 0x85, 0x60, 0x1f, 0xa0, 0xaa,
+ 0x46, 0x01, 0xd7, 0x60, 0x5f, 0x8f, 0x1a, 0x75, 0x8d, 0x65, 0x7e, 0xf2,
+ 0xbc, 0xb0, 0xf4, 0xaa, 0x45, 0x36, 0x09, 0x01, 0x3d, 0x1e, 0x6a, 0x9c,
+ 0x51, 0xcf, 0x71, 0xe6, 0x73, 0x4e, 0x45, 0xe0, 0x36, 0x4c, 0xe0, 0xca,
+ 0x79, 0x6c, 0x62, 0x32, 0xca, 0xfd, 0x61, 0xb2, 0x3b, 0x88, 0xc7, 0x9c,
+ 0x7a, 0x5f, 0x87, 0x66, 0x6e, 0x04, 0xcc, 0x71, 0x50, 0x2e, 0x21, 0x37,
+ 0x2e, 0x33, 0xef, 0x5e, 0x9d, 0x02, 0x81, 0x81, 0x00, 0xf2, 0x58, 0xc2,
+ 0xc5, 0x96, 0xec, 0x49, 0x0c, 0x8b, 0x4f, 0x60, 0x8b, 0x31, 0xd7, 0x66,
+ 0xe3, 0x7e, 0x0e, 0xd1, 0xce, 0x93, 0x89, 0xea, 0x34, 0xd3, 0x93, 0xa2,
+ 0xed, 0xfb, 0x38, 0xa9, 0xc7, 0x99, 0x5b, 0xae, 0x1b, 0x69, 0xd8, 0x9d,
+ 0x70, 0x6b, 0x91, 0x93, 0x42, 0x03, 0x7c, 0xd9, 0x90, 0xa3, 0xec, 0xa5,
+ 0x9a, 0xf1, 0xc4, 0xd6, 0x97, 0x64, 0x08, 0x2b, 0xe8, 0x9c, 0x7b, 0xfa,
+ 0xeb, 0xd3, 0x4c, 0x3c, 0x14, 0x6c, 0xc9, 0x7d, 0x0b, 0x60, 0xe2, 0x9e,
+ 0x08, 0x66, 0xde, 0xd2, 0xc5, 0x41, 0xd8, 0xa7, 0x26, 0x04, 0x78, 0x73,
+ 0x02, 0x58, 0x9f, 0xb6, 0x0c, 0x0e, 0x54, 0x06, 0x50, 0xf3, 0x45, 0xd4,
+ 0xf2, 0x76, 0x50, 0x95, 0xe2, 0x5c, 0xea, 0x50, 0x22, 0xe2, 0x0d, 0xec,
+ 0x68, 0x3f, 0x51, 0xd3, 0x18, 0xe8, 0x29, 0x30, 0x21, 0xf1, 0xfa, 0x12,
+ 0x7a, 0xfa, 0xc4, 0x4b, 0xa7, 0x02, 0x81, 0x81, 0x00, 0xcf, 0x90, 0xc8,
+ 0x24, 0xed, 0xe9, 0x04, 0x5b, 0x4a, 0x76, 0xdc, 0xfb, 0xf8, 0x70, 0x43,
+ 0x0e, 0xf6, 0x9b, 0x68, 0x2c, 0x5d, 0x5b, 0x9e, 0x27, 0x80, 0x0e, 0x2d,
+ 0x66, 0x5f, 0x51, 0x70, 0xcb, 0xfb, 0x70, 0x25, 0x96, 0x06, 0xa5, 0x74,
+ 0x53, 0xaf, 0x45, 0x37, 0xbd, 0x4f, 0x22, 0xd9, 0x79, 0xef, 0xd3, 0x6d,
+ 0x33, 0xbe, 0xd4, 0x34, 0x82, 0x31, 0x50, 0x12, 0xab, 0x64, 0x5f, 0x45,
+ 0x0e, 0x90, 0xfd, 0x9c, 0x7f, 0xdb, 0xa1, 0xbe, 0x83, 0xbf, 0x50, 0x21,
+ 0x62, 0xb3, 0x90, 0x1c, 0x36, 0xf0, 0x44, 0x32, 0xca, 0xa9, 0xac, 0x30,
+ 0xcd, 0x27, 0x50, 0xf0, 0xed, 0x25, 0xf6, 0x35, 0x62, 0xd5, 0x8d, 0x8c,
+ 0x54, 0xfc, 0xbb, 0xd0, 0xb7, 0x53, 0x09, 0x7f, 0xed, 0x1b, 0xda, 0xcd,
+ 0x96, 0x2e, 0xfc, 0x73, 0xdd, 0xe6, 0x1b, 0xb2, 0x00, 0xf7, 0x4c, 0xd7,
+ 0xf9, 0x19, 0xdc, 0x47, 0x3b, 0x02, 0x81, 0x80, 0x2e, 0x37, 0x43, 0x1d,
+ 0x8f, 0x44, 0x8c, 0x41, 0xba, 0x27, 0x6f, 0x0f, 0xdc, 0x77, 0x69, 0x85,
+ 0xa4, 0xba, 0x8a, 0xc4, 0x4c, 0x5a, 0x96, 0xb1, 0x70, 0x4f, 0xcd, 0x58,
+ 0x78, 0xfa, 0x3b, 0x56, 0x77, 0x26, 0x86, 0xb3, 0x6f, 0xa2, 0x01, 0x94,
+ 0x38, 0xcf, 0x50, 0x37, 0xdc, 0x96, 0x68, 0x9f, 0x2e, 0xc3, 0xa8, 0x69,
+ 0x3e, 0x05, 0xfd, 0xae, 0x6d, 0x43, 0x29, 0xac, 0x78, 0x7b, 0x24, 0x44,
+ 0xe8, 0xcc, 0xb7, 0x00, 0x66, 0x26, 0x9e, 0x94, 0x16, 0xeb, 0xe0, 0x9b,
+ 0x55, 0x92, 0xd4, 0xbb, 0x0d, 0x6d, 0x95, 0xa2, 0xa8, 0x63, 0x97, 0xfb,
+ 0x30, 0x8f, 0x74, 0x96, 0x23, 0xfd, 0x5e, 0x1e, 0xfd, 0xe5, 0xa9, 0x50,
+ 0x7b, 0xc3, 0xae, 0x71, 0xb6, 0xaa, 0x70, 0x91, 0xd6, 0x6e, 0x35, 0x51,
+ 0x44, 0x12, 0x04, 0xa1, 0xd1, 0x54, 0x59, 0x7b, 0x7f, 0xbb, 0xe2, 0xde,
+ 0x55, 0x08, 0x2e, 0x2d, 0x02, 0x81, 0x81, 0x00, 0x9c, 0x64, 0xd6, 0xa9,
+ 0x1c, 0xa9, 0x8a, 0x22, 0xcf, 0x04, 0xa8, 0x95, 0x22, 0x28, 0x54, 0x1e,
+ 0x9e, 0x29, 0x92, 0x60, 0x7b, 0x27, 0x61, 0x0f, 0x1a, 0x29, 0x94, 0x83,
+ 0xa2, 0x26, 0x56, 0xfb, 0x1b, 0x44, 0xf0, 0xcd, 0x0d, 0xcc, 0xf4, 0xcd,
+ 0x69, 0x2e, 0x9a, 0x45, 0x05, 0xaf, 0x98, 0x75, 0x8c, 0x02, 0x9e, 0x31,
+ 0x73, 0x03, 0xa9, 0x5c, 0xbf, 0x93, 0x39, 0xbd, 0xf2, 0x2e, 0xe6, 0x75,
+ 0x87, 0x41, 0xcf, 0xfd, 0x76, 0x9b, 0x74, 0x55, 0x08, 0x7d, 0x73, 0xea,
+ 0x4e, 0xa9, 0xb2, 0xd8, 0xa2, 0x48, 0x80, 0x8c, 0xbb, 0x33, 0x86, 0xc1,
+ 0xcd, 0x71, 0xeb, 0x56, 0x84, 0x57, 0xf2, 0xf9, 0xb9, 0x36, 0xa2, 0x1a,
+ 0x17, 0x23, 0xdc, 0xab, 0x84, 0xe1, 0x8f, 0x86, 0x34, 0x8a, 0xb4, 0x85,
+ 0x08, 0x7a, 0x27, 0x43, 0x76, 0xf2, 0x3f, 0x39, 0x03, 0x1c, 0xdf, 0x4e,
+ 0x4d, 0xf1, 0xef, 0xa9, 0x02, 0x81, 0x80, 0x5c, 0x2d, 0x0a, 0x0d, 0x51,
+ 0x48, 0xcd, 0x38, 0x64, 0xf3, 0x7a, 0xfd, 0x1a, 0x19, 0x42, 0x28, 0x68,
+ 0xca, 0xda, 0x98, 0x2b, 0x46, 0xbb, 0x85, 0xdd, 0x55, 0x3d, 0xd8, 0x61,
+ 0x7d, 0xc4, 0x90, 0x9d, 0xee, 0xe8, 0xb2, 0xc8, 0x85, 0xc9, 0x43, 0x14,
+ 0xf7, 0x74, 0x01, 0xeb, 0x03, 0x0b, 0x7f, 0x24, 0x13, 0x99, 0x04, 0xff,
+ 0x95, 0xf0, 0x08, 0x45, 0x76, 0xce, 0x00, 0xe8, 0xc5, 0x76, 0x34, 0xf9,
+ 0x91, 0xa0, 0xc8, 0x83, 0xa9, 0x78, 0x87, 0x1d, 0xac, 0xc9, 0x66, 0x4d,
+ 0x90, 0x46, 0x4e, 0x99, 0xef, 0xdd, 0x16, 0xa9, 0xc9, 0x43, 0xd6, 0xbf,
+ 0xa1, 0x6b, 0x33, 0x8b, 0x68, 0x1d, 0x25, 0xd2, 0x95, 0x0d, 0xd0, 0x4d,
+ 0xe2, 0xd9, 0x1e, 0x9c, 0xe0, 0x4a, 0xad, 0x1e, 0xda, 0xfd, 0x0d, 0xc1,
+ 0xf7, 0x9c, 0xa7, 0x55, 0xb1, 0x70, 0xad, 0x33, 0x15, 0x1e, 0xe5, 0xc0,
+ 0x44, 0x78, 0xd1
+};
+unsigned int test_device_cert_key_der_len = 1191;
+
diff --git a/test/regression/interoperability_test/nx_secure_test/ica_test_ica_cert.c b/test/regression/interoperability_test/nx_secure_test/ica_test_ica_cert.c
new file mode 100644
index 00000000..6f6b9c05
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/ica_test_ica_cert.c
@@ -0,0 +1,86 @@
+unsigned char ica_cert_der[] = {
+ 0x30, 0x82, 0x03, 0xdf, 0x30, 0x82, 0x02, 0xc7, 0xa0, 0x03, 0x02, 0x01,
+ 0x02, 0x02, 0x01, 0x02, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86,
+ 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05, 0x00, 0x30, 0x7a, 0x31, 0x0b, 0x30,
+ 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31, 0x0b,
+ 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x02, 0x43, 0x41, 0x31,
+ 0x12, 0x30, 0x10, 0x06, 0x03, 0x55, 0x04, 0x07, 0x0c, 0x09, 0x53, 0x61,
+ 0x6e, 0x20, 0x44, 0x69, 0x65, 0x67, 0x6f, 0x31, 0x16, 0x30, 0x14, 0x06,
+ 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x0d, 0x45, 0x78, 0x70, 0x72, 0x65, 0x73,
+ 0x73, 0x20, 0x4c, 0x6f, 0x67, 0x69, 0x63, 0x31, 0x14, 0x30, 0x12, 0x06,
+ 0x03, 0x55, 0x04, 0x0b, 0x0c, 0x0b, 0x4e, 0x65, 0x74, 0x58, 0x20, 0x53,
+ 0x65, 0x63, 0x75, 0x72, 0x65, 0x31, 0x1c, 0x30, 0x1a, 0x06, 0x03, 0x55,
+ 0x04, 0x03, 0x0c, 0x13, 0x4e, 0x65, 0x74, 0x58, 0x20, 0x53, 0x65, 0x63,
+ 0x75, 0x72, 0x65, 0x20, 0x54, 0x65, 0x73, 0x74, 0x20, 0x43, 0x41, 0x30,
+ 0x1e, 0x17, 0x0d, 0x31, 0x37, 0x30, 0x33, 0x33, 0x31, 0x32, 0x31, 0x30,
+ 0x30, 0x30, 0x32, 0x5a, 0x17, 0x0d, 0x32, 0x37, 0x30, 0x33, 0x32, 0x39,
+ 0x32, 0x31, 0x30, 0x30, 0x30, 0x32, 0x5a, 0x30, 0x6f, 0x31, 0x0b, 0x30,
+ 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31, 0x0b,
+ 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x02, 0x43, 0x41, 0x31,
+ 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x0d, 0x45, 0x78,
+ 0x70, 0x72, 0x65, 0x73, 0x73, 0x20, 0x4c, 0x6f, 0x67, 0x69, 0x63, 0x31,
+ 0x12, 0x30, 0x10, 0x06, 0x03, 0x55, 0x04, 0x0b, 0x0c, 0x09, 0x4e, 0x58,
+ 0x20, 0x53, 0x65, 0x63, 0x75, 0x72, 0x65, 0x31, 0x27, 0x30, 0x25, 0x06,
+ 0x03, 0x55, 0x04, 0x03, 0x0c, 0x1e, 0x4e, 0x58, 0x20, 0x53, 0x65, 0x63,
+ 0x75, 0x72, 0x65, 0x20, 0x54, 0x65, 0x73, 0x74, 0x20, 0x49, 0x6e, 0x74,
+ 0x65, 0x72, 0x6d, 0x65, 0x64, 0x69, 0x61, 0x74, 0x65, 0x20, 0x43, 0x41,
+ 0x30, 0x82, 0x01, 0x22, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86,
+ 0xf7, 0x0d, 0x01, 0x01, 0x01, 0x05, 0x00, 0x03, 0x82, 0x01, 0x0f, 0x00,
+ 0x30, 0x82, 0x01, 0x0a, 0x02, 0x82, 0x01, 0x01, 0x00, 0xa7, 0xa4, 0xd9,
+ 0xd0, 0x19, 0x84, 0x4e, 0xab, 0x8e, 0x08, 0xad, 0x30, 0xe6, 0x79, 0x46,
+ 0x46, 0xe2, 0xd3, 0x13, 0xc1, 0x69, 0xa9, 0x4a, 0xc9, 0xc8, 0x95, 0x54,
+ 0xa8, 0x76, 0x41, 0x63, 0x10, 0xc4, 0xe4, 0xfd, 0x08, 0x69, 0x7f, 0x89,
+ 0x79, 0x82, 0x62, 0xd7, 0x90, 0x73, 0x55, 0x06, 0x0d, 0x62, 0xec, 0x1b,
+ 0x2d, 0xaf, 0xf2, 0x39, 0x14, 0x47, 0x5b, 0x9d, 0x7a, 0xd2, 0xe3, 0xf9,
+ 0xae, 0x37, 0x49, 0xd0, 0xb8, 0x01, 0xf2, 0x1a, 0x84, 0x9a, 0x50, 0x37,
+ 0x4d, 0xd6, 0xed, 0x7c, 0x44, 0xef, 0xd1, 0xb8, 0x05, 0x4b, 0x3c, 0x05,
+ 0x59, 0x4a, 0xcd, 0xc1, 0xce, 0x6d, 0xb9, 0xbe, 0xb0, 0xc4, 0xe5, 0x44,
+ 0x02, 0xfd, 0xfa, 0x61, 0x3e, 0x59, 0x3e, 0x4b, 0x0f, 0xe6, 0x20, 0xda,
+ 0xf1, 0xca, 0xb5, 0x67, 0x52, 0x2b, 0x2e, 0x1b, 0xfc, 0xf1, 0xc6, 0x55,
+ 0x88, 0xf9, 0x28, 0xaa, 0xd9, 0x55, 0x6a, 0xc7, 0x61, 0x94, 0x24, 0x8d,
+ 0x63, 0xfb, 0xa6, 0x8a, 0x06, 0x21, 0xe2, 0x8e, 0xf7, 0xa8, 0x0b, 0x91,
+ 0x39, 0xff, 0x8d, 0xde, 0xb8, 0x0b, 0x16, 0x8a, 0xc6, 0xac, 0xe0, 0x61,
+ 0x69, 0x98, 0x4a, 0x90, 0xfd, 0x03, 0xe3, 0x38, 0x90, 0xc7, 0xe3, 0x13,
+ 0x40, 0x12, 0xc5, 0x44, 0x07, 0x44, 0x57, 0x43, 0xbb, 0xa4, 0x67, 0x72,
+ 0x20, 0xbb, 0x97, 0xe6, 0xa1, 0x32, 0xb2, 0x73, 0xf2, 0x8d, 0xe3, 0x23,
+ 0xdc, 0x06, 0xc0, 0x1f, 0xfc, 0xe3, 0x3a, 0xcc, 0x9c, 0xf8, 0x00, 0x87,
+ 0x39, 0x0d, 0x1e, 0x4d, 0x59, 0x15, 0x16, 0xe6, 0x63, 0x5b, 0x53, 0x6d,
+ 0x79, 0x2f, 0xb7, 0x5a, 0xcc, 0x37, 0xc9, 0x96, 0xff, 0x46, 0xac, 0xdd,
+ 0x44, 0x9f, 0x3a, 0xc8, 0x83, 0xeb, 0x1b, 0x67, 0xa0, 0x2d, 0xa8, 0x34,
+ 0x19, 0xf0, 0x5b, 0xe8, 0x59, 0xf7, 0xc9, 0x08, 0xab, 0x09, 0x71, 0x78,
+ 0x75, 0x02, 0x03, 0x01, 0x00, 0x01, 0xa3, 0x7b, 0x30, 0x79, 0x30, 0x09,
+ 0x06, 0x03, 0x55, 0x1d, 0x13, 0x04, 0x02, 0x30, 0x00, 0x30, 0x2c, 0x06,
+ 0x09, 0x60, 0x86, 0x48, 0x01, 0x86, 0xf8, 0x42, 0x01, 0x0d, 0x04, 0x1f,
+ 0x16, 0x1d, 0x4f, 0x70, 0x65, 0x6e, 0x53, 0x53, 0x4c, 0x20, 0x47, 0x65,
+ 0x6e, 0x65, 0x72, 0x61, 0x74, 0x65, 0x64, 0x20, 0x43, 0x65, 0x72, 0x74,
+ 0x69, 0x66, 0x69, 0x63, 0x61, 0x74, 0x65, 0x30, 0x1d, 0x06, 0x03, 0x55,
+ 0x1d, 0x0e, 0x04, 0x16, 0x04, 0x14, 0x8e, 0x6a, 0xb0, 0xfe, 0x49, 0xc5,
+ 0x6a, 0x96, 0x9e, 0xba, 0xb8, 0xb6, 0x58, 0xfc, 0x52, 0x7f, 0xab, 0x51,
+ 0xf2, 0x3a, 0x30, 0x1f, 0x06, 0x03, 0x55, 0x1d, 0x23, 0x04, 0x18, 0x30,
+ 0x16, 0x80, 0x14, 0x1b, 0x8d, 0x06, 0xd9, 0x6b, 0xad, 0xee, 0x82, 0x24,
+ 0x26, 0x55, 0x9a, 0x1b, 0x03, 0x44, 0x92, 0x0a, 0x06, 0x92, 0x48, 0x30,
+ 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0b,
+ 0x05, 0x00, 0x03, 0x82, 0x01, 0x01, 0x00, 0x18, 0x5a, 0x50, 0xb6, 0x44,
+ 0xba, 0x68, 0xac, 0x7f, 0x06, 0x0f, 0xbc, 0x1a, 0x58, 0x59, 0xf1, 0xf1,
+ 0xe3, 0xb8, 0x0d, 0x74, 0xdd, 0x74, 0x26, 0x6a, 0xea, 0xfc, 0xfe, 0x06,
+ 0x53, 0xe9, 0x80, 0xe3, 0x07, 0x83, 0x8a, 0xc9, 0xc9, 0xc0, 0x93, 0xb4,
+ 0xc2, 0x59, 0x71, 0xa7, 0x58, 0xac, 0x32, 0x0f, 0x32, 0x9c, 0x5b, 0x4d,
+ 0x53, 0xcb, 0xdc, 0x04, 0x00, 0x04, 0x27, 0x37, 0x2d, 0x11, 0x5b, 0xaa,
+ 0xf6, 0x45, 0x8a, 0xc4, 0x74, 0x2e, 0x47, 0x83, 0xb8, 0x5e, 0x3a, 0xc0,
+ 0x10, 0xaf, 0xc1, 0xd2, 0x61, 0x1c, 0x85, 0x31, 0x16, 0x74, 0x05, 0xf4,
+ 0xc6, 0xd8, 0x35, 0x83, 0x13, 0xca, 0x25, 0x5b, 0x22, 0xc6, 0x2c, 0x32,
+ 0x8d, 0x3a, 0x3f, 0x78, 0x79, 0x57, 0xbe, 0x97, 0x96, 0x90, 0x20, 0x7d,
+ 0xe5, 0xe6, 0xe6, 0x42, 0xde, 0xd3, 0xd4, 0xb4, 0x18, 0x34, 0x9d, 0xc3,
+ 0x95, 0x2d, 0xb2, 0x91, 0x1d, 0xfe, 0x3c, 0xee, 0x5c, 0xda, 0xdd, 0xd7,
+ 0xf5, 0x05, 0xf1, 0xbd, 0xa0, 0x2f, 0x0a, 0x03, 0x2e, 0x45, 0x26, 0x9c,
+ 0xac, 0x16, 0x59, 0x9a, 0x7f, 0xf2, 0x3a, 0x3e, 0xdb, 0x4b, 0x63, 0x58,
+ 0x38, 0x0b, 0x64, 0x5e, 0x24, 0x15, 0x92, 0xb5, 0xcf, 0x33, 0xe9, 0x61,
+ 0x1f, 0xb9, 0x33, 0xa1, 0x09, 0x41, 0x9f, 0x05, 0x11, 0xad, 0x07, 0x0b,
+ 0x60, 0x67, 0x1a, 0x4c, 0x6c, 0x93, 0x36, 0x90, 0x20, 0xac, 0xb3, 0x99,
+ 0x61, 0xa0, 0xda, 0xe5, 0x8d, 0x3f, 0x66, 0xd1, 0xf3, 0x91, 0x40, 0x60,
+ 0xcf, 0x97, 0xbb, 0x15, 0xb1, 0x81, 0x4e, 0xbf, 0xba, 0xef, 0x20, 0x36,
+ 0x6f, 0x00, 0x40, 0xa2, 0xa3, 0x24, 0x5c, 0x61, 0xd5, 0xa5, 0x64, 0xbf,
+ 0xbe, 0x29, 0xdf, 0x47, 0x4b, 0xc8, 0x76, 0x4f, 0x2e, 0x4c, 0x5c, 0xed,
+ 0x99, 0x26, 0xe8, 0xf1, 0x72, 0x5e, 0x9b, 0x86, 0x73, 0xda, 0xfb
+};
+unsigned int ica_cert_der_len = 995;
diff --git a/test/regression/interoperability_test/nx_secure_test/key.pem b/test/regression/interoperability_test/nx_secure_test/key.pem
new file mode 100644
index 00000000..1b8c45c8
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/key.pem
@@ -0,0 +1,28 @@
+-----BEGIN PRIVATE KEY-----
+MIIEvQIBADANBgkqhkiG9w0BAQEFAASCBKcwggSjAgEAAoIBAQCno/QVzNC2ZLEq
+92O/vPExoLQ51mK+69gBJxCnbbg4Aa+ih8PyR0s2aEAxA7EAXPuAILYitDogEFjU
+JNvyNknXc9r3icBQGeRAbXF3/WS7fwv2y280M6hxuXh0NdZvDj4yXVkC4NABaIsi
+wFpb2NUx3JDw0+I2dAcrDJ4C7uolu3ulTwJWIHeDaLBDXRk3AHJ+us4cZ8LcBYum
+9ca10RVAR4gL2jKlTRZo0WxjuY92E2kVw23EXOgr5MCZvXpmgzRblesfUb9+/eoM
+t/c26/vwA/HgFSE6xqLZ+iVYYrgubbX3TUbN7K40FkfRF8x4OIVqImJ+wxYvXGqZ
+QgjEr+JdAgMBAAECggEAcjkGIKxzMTOee7YgYw5sEPJ8mkP2+Dtd7Dsf39SkhpSv
+hUCYREZLewDBbCQlwCeavYyMTU0bpak9vR54NqrC2Wh5M9zKCkn5+eQYQjeHITHJ
+hxjJ5nmkNgi3iAb+2qCLxGlSMuHXGH6Q/tatOpOdf+HXaCAWrB+WmsB4EWuUYqwn
+bbq73n1PuRyRl49wivVCaK56WOYz55/q2L+MeiNUiHfLgyI1tXqZWaDIyzIRfD0l
+8hW2YwKdhkC8NADM78eNZ8Gq3g80XHhPg/4KUKoe4x29SFKKH9mbFKnHeVAKJmLk
+IgHRQ+fg11saiX9bzzBKbti+R9PsYdiS6P8r501HwQKBgQDW9R3V3Dyrf+WrKv7G
+HO6cCPHpHVWzv1Xoqtomocc8V/A6p8J+faK71L8My2IfjH/J7hDh4C/2HebzufDo
+TQ1wDNxiwX7AgWp04HRMbke+RKNgMaXH7IACpkFuFDtkh7+1Naz9+y7pqpJvNlYK
++Ac5PMQeTU77sXAM3ABwtZnLFQKBgQDHpghG68kjLOQEiFmxGOmqKuJXzvHhiTNj
+mOcAR3+q3I1aVKk5fn7HTBCd4NAT7k72bT2Fut6YgC3f1as+y8xli6YJeXrJQ1S3
+V1JLwAFV3fA8KBbutGeP5Vu/0EUqCexCkNDerFLmoToWGreiqmvJmLqA3h4wISKt
+DTgeMjvsKQKBgHtSjzZlrwz5SGtmNFq2uJIec6M5KDUCfagJdTSatfJBxVnxax0k
+uRsn2B/gA0B0W9Ae2+KquvlpeFm2AKdVpXL2fe3OcwjAdrHtH+vFjTV0rYJ/mUvU
+vDBI79rWkqh/VRYCYGgqFmUKbg6NztlmKMbGvQFhewHdb5qBEWOYXE5tAoGBAL3y
+8PMRCGhIIJVTaQp+6mn1rS3f/fAYCmWbJ0Tzwbq9ZltoKy1BdbuGWlTrfO1JkaUR
+oDQo6/nqEjthXjE70zdV214uTy1Hu0VIdksN3fdlVljVx6PKzrFwhY+ExxlNIZTf
+lWoWSDWXdd1sBAVm4XCHuAI90jj2fbhp2FeacbqpAoGAHjjzuvtLU17Mu85dfWY7
+R/xZFhfbWpvzhSc2OBAfBsE9vAUc10l2onz/mO1ralIGJcroJY8lValLhh5tywVT
+diG3dOTqG+OEUlZw3DXXGfwPW/XD/uWK2IRW+w9rbclcbmPjyY/6TnPilB3GrYtJ
+xySPIsMAg/UgEm4KnnBcsMY=
+-----END PRIVATE KEY-----
diff --git a/test/regression/interoperability_test/nx_secure_test/nx_secure_1_0_1_1_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/nx_secure_1_0_1_1_echo_client_entry.c
new file mode 100644
index 00000000..bd79dc8c
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/nx_secure_1_0_1_1_echo_client_entry.c
@@ -0,0 +1,283 @@
+#include "tls_test_frame.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+NX_SECURE_X509_CERT trusted_certificate;
+
+UCHAR tls_packet_buffer[4000];
+#include "cert.c"
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define an error counter. */
+
+ULONG error_counter;
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+
+extern NX_CRYPTO_METHOD crypto_method_rsa;
+extern NX_CRYPTO_METHOD crypto_method_md5;
+extern NX_CRYPTO_METHOD crypto_method_sha1;
+extern NX_CRYPTO_METHOD crypto_method_sha256;
+extern NX_CRYPTO_METHOD crypto_method_aes_cbc_128;
+extern NX_CRYPTO_METHOD crypto_method_aes_cbc_256;
+extern NX_CRYPTO_METHOD crypto_method_hmac_sha1;
+extern NX_CRYPTO_METHOD crypto_method_hkdf_sha256;
+extern NX_CRYPTO_METHOD crypto_method_tls_prf_1;
+extern NX_CRYPTO_METHOD crypto_method_tls_prf_sha256;
+extern NX_CRYPTO_METHOD crypto_method_hkdf;
+extern NX_CRYPTO_METHOD crypto_method_hmac;
+extern NX_CRYPTO_METHOD crypto_method_ecdhe;
+
+NX_SECURE_TLS_CIPHERSUITE_INFO _nx_crypto_ciphersuite_lookup_table_1_0_1_1[] =
+{
+ /* Ciphersuite, public cipher, public_auth, session cipher & cipher mode, iv size, key size, hash method, hash size, TLS PRF */
+ {TLS_RSA_WITH_AES_256_CBC_SHA, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_256, 16, 32, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+ {TLS_RSA_WITH_AES_128_CBC_SHA, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+};
+
+/* Lookup table for X.509 digital certificates - they need a public-key algorithm and a hash routine for verification. */
+NX_SECURE_X509_CRYPTO _nx_crypto_x509_cipher_lookup_table_1_0_1_1[] =
+{
+ /* OID identifier, public cipher, hash method */
+ {NX_SECURE_TLS_X509_TYPE_RSA_SHA_256, &crypto_method_rsa, &crypto_method_sha256},
+ {NX_SECURE_TLS_X509_TYPE_RSA_SHA_1, &crypto_method_rsa, &crypto_method_sha1},
+ {NX_SECURE_TLS_X509_TYPE_RSA_MD5, &crypto_method_rsa, &crypto_method_md5},
+};
+
+/* Define the object we can pass into TLS. */
+NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_1_0_1_1 =
+{
+ /* Ciphersuite lookup table and size. */
+ _nx_crypto_ciphersuite_lookup_table_1_0_1_1,
+ sizeof(_nx_crypto_ciphersuite_lookup_table_1_0_1_1) / sizeof(NX_SECURE_TLS_CIPHERSUITE_INFO),
+
+#ifndef NX_SECURE_DISABLE_X509
+ /* X.509 certificate cipher table and size. */
+ _nx_crypto_x509_cipher_lookup_table_1_0_1_1,
+ sizeof(_nx_crypto_x509_cipher_lookup_table_1_0_1_1) / sizeof(NX_SECURE_X509_CRYPTO),
+#endif
+
+ /* TLS version-specific methods. */
+#if (NX_SECURE_TLS_TLS_1_0_ENABLED || NX_SECURE_TLS_TLS_1_1_ENABLED)
+ &crypto_method_md5,
+ &crypto_method_sha1,
+ &crypto_method_tls_prf_1,
+#endif
+
+#if (NX_SECURE_TLS_TLS_1_2_ENABLED)
+ &crypto_method_sha256,
+ &crypto_method_tls_prf_sha256,
+#endif
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ &crypto_method_hkdf,
+ &crypto_method_hmac,
+ &crypto_method_ecdhe,
+#endif
+};
+
+
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#ifndef NX_SECURE_TLS_CLIENT_DISABLED
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
+
+void tx_application_define(void *first_unused_memory)
+{
+ULONG gateway_ipv4_address;
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+NX_PARAMETER_NOT_USED(thread_input);
+
+ /* Address of remote server. */
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a tls session. */
+ status = nx_secure_tls_session_create(&tls_session,
+ &nx_crypto_tls_ciphers_1_0_1_1,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(&tls_session, tls_packet_buffer, sizeof(tls_packet_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup this thread to bind to a port. */
+ status = nx_tcp_client_socket_bind(&tcp_socket, 0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Need to allocate space for the certificate coming in from the remote host. */
+ nx_secure_tls_remote_certificate_allocate(&tls_session, &remote_certificate, remote_cert_buffer, sizeof(remote_cert_buffer));
+ nx_secure_tls_remote_certificate_allocate(&tls_session, &remote_issuer, remote_issuer_buffer, sizeof(remote_issuer_buffer));
+
+ /* Added trusted certificates. */
+ status = nx_secure_x509_certificate_initialize(&trusted_certificate, cert_der, cert_der_len,
+ NX_NULL, 0, NULL, 0,
+ NX_SECURE_X509_KEY_TYPE_NONE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_trusted_certificate_add(&tls_session,
+ &trusted_certificate);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tx_thread_sleep(100);
+
+ /* Attempt to connect the echo server. */
+ status = nx_tcp_client_socket_connect(&tcp_socket, REMOTE_IP_ADDRESS_NUMBER, DEVICE_SERVER_PORT, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send "hello" message. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Receive the echoed and reversed data, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Extract data received from server. */
+ status = nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Check the reverse text received from openssl server. */
+ exit_if_fail('o' == ((CHAR*)receive_buffer)[0], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[1], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[2], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('e' == ((CHAR*)receive_buffer)[3], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('h' == ((CHAR*)receive_buffer)[4], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('\n' == ((CHAR*)receive_buffer)[5], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail(6 == bytes, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Close the TCP connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Unbind the TCP socket from our port. */
+ status = nx_tcp_client_socket_unbind(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Delete the TCP socket instance to clean up. */
+ status = nx_tcp_socket_delete(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/nx_secure_1_0_1_1_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/nx_secure_1_0_1_1_echo_server_entry.c
new file mode 100644
index 00000000..99c5fa6a
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/nx_secure_1_0_1_1_echo_server_entry.c
@@ -0,0 +1,271 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Define the ThreadX and NetX object control blocks... */
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT certificate;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+NX_SECURE_X509_CERT trusted_certificate;
+
+UCHAR tls_packet_buffer[4000];
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+void server_thread_entry(ULONG thread_input);
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+NX_SECURE_X509_CERT device_issuer_certificate;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+
+
+extern NX_CRYPTO_METHOD crypto_method_rsa;
+extern NX_CRYPTO_METHOD crypto_method_md5;
+extern NX_CRYPTO_METHOD crypto_method_sha1;
+extern NX_CRYPTO_METHOD crypto_method_sha256;
+extern NX_CRYPTO_METHOD crypto_method_aes_cbc_128;
+extern NX_CRYPTO_METHOD crypto_method_aes_cbc_256;
+extern NX_CRYPTO_METHOD crypto_method_hmac_sha1;
+extern NX_CRYPTO_METHOD crypto_method_hkdf_sha256;
+extern NX_CRYPTO_METHOD crypto_method_tls_prf_1;
+extern NX_CRYPTO_METHOD crypto_method_tls_prf_sha256;
+extern NX_CRYPTO_METHOD crypto_method_hkdf;
+extern NX_CRYPTO_METHOD crypto_method_hmac;
+extern NX_CRYPTO_METHOD crypto_method_ecdhe;
+
+NX_SECURE_TLS_CIPHERSUITE_INFO _nx_crypto_ciphersuite_lookup_table_1_0_1_1[] =
+{
+ /* Ciphersuite, public cipher, public_auth, session cipher & cipher mode, iv size, key size, hash method, hash size, TLS PRF */
+ {TLS_RSA_WITH_AES_256_CBC_SHA, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_256, 16, 32, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+ {TLS_RSA_WITH_AES_128_CBC_SHA, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+};
+
+/* Lookup table for X.509 digital certificates - they need a public-key algorithm and a hash routine for verification. */
+NX_SECURE_X509_CRYPTO _nx_crypto_x509_cipher_lookup_table_1_0_1_1[] =
+{
+ /* OID identifier, public cipher, hash method */
+ {NX_SECURE_TLS_X509_TYPE_RSA_SHA_256, &crypto_method_rsa, &crypto_method_sha256},
+ {NX_SECURE_TLS_X509_TYPE_RSA_SHA_1, &crypto_method_rsa, &crypto_method_sha1},
+ {NX_SECURE_TLS_X509_TYPE_RSA_MD5, &crypto_method_rsa, &crypto_method_md5},
+};
+
+/* Define the object we can pass into TLS. */
+NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_1_0_1_1 =
+{
+ /* Ciphersuite lookup table and size. */
+ _nx_crypto_ciphersuite_lookup_table_1_0_1_1,
+ sizeof(_nx_crypto_ciphersuite_lookup_table_1_0_1_1) / sizeof(NX_SECURE_TLS_CIPHERSUITE_INFO),
+
+#ifndef NX_SECURE_DISABLE_X509
+ /* X.509 certificate cipher table and size. */
+ _nx_crypto_x509_cipher_lookup_table_1_0_1_1,
+ sizeof(_nx_crypto_x509_cipher_lookup_table_1_0_1_1) / sizeof(NX_SECURE_X509_CRYPTO),
+#endif
+
+ /* TLS version-specific methods. */
+#if (NX_SECURE_TLS_TLS_1_0_ENABLED || NX_SECURE_TLS_TLS_1_1_ENABLED)
+ & crypto_method_md5,
+ &crypto_method_sha1,
+ &crypto_method_tls_prf_1,
+#endif
+
+#if (NX_SECURE_TLS_TLS_1_2_ENABLED)
+ &crypto_method_sha256,
+ &crypto_method_tls_prf_sha256,
+#endif
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ &crypto_method_hkdf,
+ &crypto_method_hmac,
+ &crypto_method_ecdhe,
+#endif
+};
+
+#include "ica_test_device_cert.c"
+#include "ica_test_ica_cert.c"
+
+/* Define the pointer of current instance control block. */
+static TLS_TEST_INSTANCE* demo_instance_ptr;
+
+/* Define external references. */
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Instance one test entry. */
+INT nx_secure_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#ifndef NX_SECURE_TLS_SERVER_DISABLED
+
+ /* Get instance pointer. */
+ demo_instance_ptr = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
+
+/* Define what the initial system looks like. */
+void tx_application_define(void *first_unused_memory)
+{
+ ULONG gateway_ipv4_address;
+ UINT status;
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL, &pool_0, _nx_pcap_network_driver, (UCHAR*)ip_thread_stack, sizeof(ip_thread_stack), 1);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ tx_thread_create(&demo_thread, "demo thread", server_thread_entry, 0, demo_thread_stack, sizeof(demo_thread_stack), 16, 16, 4, TX_AUTO_START);
+}
+
+/* TLS Server example application thread. */
+void server_thread_entry(ULONG thread_input)
+{
+ INT i = 0, status = 0;
+ ULONG actual_status;
+ NX_PACKET *receive_packet;
+ NX_PACKET *send_packet;
+ UCHAR receive_buffer[100];
+ ULONG bytes;
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Server Socket",
+ NX_IP_NORMAL, NX_FRAGMENT_OKAY /*NX_DONT_FRAGMENT*/, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_session_create(&tls_session,
+ &nx_crypto_tls_ciphers_1_0_1_1,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(&tls_session, tls_packet_buffer, sizeof(tls_packet_buffer));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ // Initialize our certificates
+ nx_secure_tls_remote_certificate_allocate(&tls_session, &remote_certificate, remote_cert_buffer, sizeof(remote_cert_buffer));
+ nx_secure_tls_remote_certificate_allocate(&tls_session, &remote_issuer, remote_issuer_buffer, sizeof(remote_issuer_buffer));
+
+ memset(&certificate, 0, sizeof(certificate));
+ nx_secure_x509_certificate_initialize(&certificate, test_device_cert_der, test_device_cert_der_len, NX_NULL, 0, test_device_cert_key_der, test_device_cert_key_der_len, NX_SECURE_X509_KEY_TYPE_RSA_PKCS1_DER);
+ nx_secure_tls_local_certificate_add(&tls_session, &certificate);
+
+ // Initialize the Intermediate CA certificate - it does not have a private RSA key
+ nx_secure_x509_certificate_initialize(&device_issuer_certificate, ica_cert_der, ica_cert_der_len, NX_NULL, 0, NX_NULL, 0, NX_SECURE_X509_KEY_TYPE_NONE);
+ nx_secure_tls_local_certificate_add(&tls_session, &device_issuer_certificate);
+
+ /* Setup this thread to listen. */
+ status = nx_tcp_server_socket_listen(&ip_0, DEVICE_SERVER_PORT, &tcp_socket, 5, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Post semaphore before accept sockets. */
+ print_error_message("Connection %d: server is prepared. Post the semaphore.\n", i);
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Accept a client socket connection. */
+ print_error_message("Connection %d: wait for connections.\n", i);
+ status = nx_tcp_server_socket_accept(&tcp_socket, NX_WAIT_FOREVER);
+ print_error_message("Connection %d: server accept.\n", i);
+ exit_if_fail( NX_SUCCESS == status, 1);
+
+ /* Start the TLS Session now that we have a connected socket. */
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 2);
+
+ /* Receive the HTTP request, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 3);
+
+ /* Show received data. */
+ nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ receive_buffer[bytes] = 0;
+ print_error_message("Received data: %s\n", receive_buffer);
+
+ /* Allocate a return packet and send our HTML data back to the client. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 4);
+
+ /* Echo the message received. */
+ status = nx_packet_data_append(send_packet, receive_buffer, bytes, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 5);
+
+ /* TLS send the HTML/HTTPS data back to the client. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ /* Exit the test process directly without release packet. */
+ exit_if_fail( NX_SUCCESS == status, 6);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 7);
+
+ /* Disconnect the TCP socket, closing the connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 8);
+
+ /* Unaccept the server socket. */
+ status = nx_tcp_server_socket_unaccept(&tcp_socket);
+ exit_if_fail( NX_SUCCESS == status, 9);
+
+ print_error_message("Connection %d: server unaccept, sleeping...\n", i);
+ tx_thread_sleep( 500);
+
+ /* Setup server socket for listening again. */
+ status = nx_tcp_server_socket_relisten(&ip_0, DEVICE_SERVER_PORT, &tcp_socket);
+ exit_if_fail( NX_SUCCESS == status, 10);
+
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/nx_secure_client_certificate_verify_test_client_entry.c b/test/regression/interoperability_test/nx_secure_test/nx_secure_client_certificate_verify_test_client_entry.c
new file mode 100644
index 00000000..ac632cf6
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/nx_secure_client_certificate_verify_test_client_entry.c
@@ -0,0 +1,226 @@
+#include "tls_test_frame.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+NX_SECURE_X509_CERT certificate, device_issuer_certificate;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+
+UCHAR tls_packet_buffer[4000];
+
+#include "test_client.der.c"
+#include "test_client.key.der.c"
+#include "test.der.c"
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define an error counter. */
+
+ULONG error_counter;
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#ifndef NX_SECURE_TLS_CLIENT_DISABLED
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
+
+void tx_application_define(void *first_unused_memory)
+{
+ULONG gateway_ipv4_address;
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+NX_PARAMETER_NOT_USED(thread_input);
+
+ /* Address of remote server. */
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a tls session. */
+ status = nx_secure_tls_session_create(&tls_session,
+ &nx_crypto_tls_ciphers,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(&tls_session, tls_packet_buffer, sizeof(tls_packet_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup this thread to bind to a port. */
+ status = nx_tcp_client_socket_bind(&tcp_socket, 0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Need to allocate space for the certificate coming in from the remote host. */
+ nx_secure_tls_remote_certificate_allocate(&tls_session, &remote_certificate, remote_cert_buffer, sizeof(remote_cert_buffer));
+ nx_secure_tls_remote_certificate_allocate(&tls_session, &remote_issuer, remote_issuer_buffer, sizeof(remote_issuer_buffer));
+
+ /* Added a certificate. */
+ memset(&certificate, 0, sizeof(certificate));
+ status = nx_secure_x509_certificate_initialize(&certificate, test_client_der, test_client_der_len, NX_NULL, 0, test_client_key_der, test_client_key_der_len, NX_SECURE_X509_KEY_TYPE_RSA_PKCS1_DER);
+ show_error_message_if_fail( NX_SUCCESS == status);
+ status = nx_secure_tls_local_certificate_add(&tls_session, &certificate);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ // Initialize the Intermediate CA certificate - it does not have a private RSA key
+ status = nx_secure_x509_certificate_initialize(&device_issuer_certificate, test_der, test_der_len, NX_NULL, 0, NX_NULL, 0, NX_SECURE_X509_KEY_TYPE_NONE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+ status = nx_secure_tls_trusted_certificate_add(&tls_session, &device_issuer_certificate);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tx_thread_sleep(100);
+
+ /* Attempt to connect the echo server. */
+ status = nx_tcp_client_socket_connect(&tcp_socket, REMOTE_IP_ADDRESS_NUMBER, DEVICE_SERVER_PORT, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send "hello" message. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Receive the echoed and reversed data, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Extract data received from server. */
+ status = nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Check the reverse text received from openssl server. */
+ exit_if_fail('o' == ((CHAR*)receive_buffer)[0], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[1], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[2], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('e' == ((CHAR*)receive_buffer)[3], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('h' == ((CHAR*)receive_buffer)[4], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('\n' == ((CHAR*)receive_buffer)[5], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail(6 == bytes, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Close the TCP connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Unbind the TCP socket from our port. */
+ status = nx_tcp_client_socket_unbind(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Delete the TCP socket instance to clean up. */
+ status = nx_tcp_socket_delete(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/nx_secure_client_certificate_verify_test_server_entry.c b/test/regression/interoperability_test/nx_secure_test/nx_secure_client_certificate_verify_test_server_entry.c
new file mode 100644
index 00000000..97259b5c
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/nx_secure_client_certificate_verify_test_server_entry.c
@@ -0,0 +1,199 @@
+#include "tls_test_frame.h"
+#include "test_server.der.c"
+#include "test_server.key.der.c"
+#include "test.der.c"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Define the ThreadX and NetX object control blocks... */
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+
+UCHAR tls_packet_buffer[4000];
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+void server_thread_entry(ULONG thread_input);
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+NX_SECURE_X509_CERT certificate, device_issuer_certificate;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+
+/* Define the pointer of current instance control block. */
+static TLS_TEST_INSTANCE* demo_instance_ptr;
+
+/* Define external references. */
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Instance one test entry. */
+INT nx_secure_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#ifdef NX_SECURE_ENABLE_CLIENT_CERTIFICATE_VERIFY
+
+ /* Get instance pointer. */
+ demo_instance_ptr = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
+
+/* Define what the initial system looks like. */
+void tx_application_define(void *first_unused_memory)
+{
+ ULONG gateway_ipv4_address;
+ UINT status;
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL, &pool_0, _nx_pcap_network_driver, (UCHAR*)ip_thread_stack, sizeof(ip_thread_stack), 1);
+print_error_message( "ip address number: %lu", TLS_TEST_IP_ADDRESS_NUMBER);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ tx_thread_create(&demo_thread, "demo thread", server_thread_entry, 0, demo_thread_stack, sizeof(demo_thread_stack), 16, 16, 4, TX_AUTO_START);
+}
+
+/* TLS Server example application thread. */
+void server_thread_entry(ULONG thread_input)
+{
+ INT i = 0, status = 0;
+ ULONG actual_status;
+ NX_PACKET *receive_packet;
+ NX_PACKET *send_packet;
+ UCHAR receive_buffer[100];
+ ULONG bytes;
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Server Socket",
+ NX_IP_NORMAL, NX_FRAGMENT_OKAY /*NX_DONT_FRAGMENT*/, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_session_create(&tls_session,
+ &nx_crypto_tls_ciphers,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(&tls_session, tls_packet_buffer, sizeof(tls_packet_buffer));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Enable Client Certificate Verification. */
+ nx_secure_tls_session_client_verify_enable(&tls_session);
+
+ // Initialize our certificates
+ nx_secure_tls_remote_certificate_allocate(&tls_session, &remote_certificate, remote_cert_buffer, sizeof(remote_cert_buffer));
+ nx_secure_tls_remote_certificate_allocate(&tls_session, &remote_issuer, remote_issuer_buffer, sizeof(remote_issuer_buffer));
+
+ /* Added a certificate. */
+ memset(&certificate, 0, sizeof(certificate));
+ status = nx_secure_x509_certificate_initialize(&certificate, test_server_der, test_server_der_len, NX_NULL, 0, test_server_key_der, test_server_key_der_len, NX_SECURE_X509_KEY_TYPE_RSA_PKCS1_DER);
+ show_error_message_if_fail( NX_SUCCESS == status);
+ status = nx_secure_tls_local_certificate_add(&tls_session, &certificate);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ // Initialize the Intermediate CA certificate - it does not have a private RSA key
+ status = nx_secure_x509_certificate_initialize(&device_issuer_certificate, test_der, test_der_len, NX_NULL, 0, NX_NULL, 0, NX_SECURE_X509_KEY_TYPE_NONE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+ status = nx_secure_tls_trusted_certificate_add(&tls_session, &device_issuer_certificate);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Setup this thread to listen. */
+ status = nx_tcp_server_socket_listen(&ip_0, DEVICE_SERVER_PORT, &tcp_socket, 5, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Post semaphore before accept sockets. */
+ print_error_message("Connection %d: server is prepared. Post the semaphore.\n", i);
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Accept a client socket connection. */
+ print_error_message("Connection %d: wait for connections.\n", i);
+ status = nx_tcp_server_socket_accept(&tcp_socket, NX_WAIT_FOREVER);
+ print_error_message("Connection %d: server accept.\n", i);
+ exit_if_fail( NX_SUCCESS == status, 1);
+
+ /* Start the TLS Session now that we have a connected socket. */
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 2);
+
+ /* Receive the HTTP request, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 3);
+
+ /* Show received data. */
+ nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ exit_if_fail( bytes == 6, 4);
+ exit_if_fail( receive_buffer[0] == 'h', 5);
+ exit_if_fail( receive_buffer[1] == 'e', 5);
+ exit_if_fail( receive_buffer[2] == 'l', 5);
+ exit_if_fail( receive_buffer[3] == 'l', 5);
+ exit_if_fail( receive_buffer[4] == 'o', 5);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 7);
+
+ /* Disconnect the TCP socket, closing the connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 8);
+
+ /* Unaccept the server socket. */
+ status = nx_tcp_server_socket_unaccept(&tcp_socket);
+ exit_if_fail( NX_SUCCESS == status, 9);
+
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/nx_secure_dtls_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/nx_secure_dtls_echo_client_entry.c
new file mode 100644
index 00000000..174669ed
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/nx_secure_dtls_echo_client_entry.c
@@ -0,0 +1,213 @@
+#include "tls_test_frame.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_UDP_SOCKET udp_socket;
+NX_SECURE_DTLS_SESSION dtls_session;
+UCHAR cert_buffer[2000];
+NX_SECURE_X509_CERT trusted_certificate;
+
+UCHAR tls_packet_buffer[4000];
+
+#include "cert.c"
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_DTLS)
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
+
+void tx_application_define(void *first_unused_memory)
+{
+ULONG gateway_ipv4_address;
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+ nx_secure_dtls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+NXD_ADDRESS server_address;
+NX_PARAMETER_NOT_USED(thread_input);
+
+
+ /* Address of remote server. */
+ server_address.nxd_ip_version = NX_IP_VERSION_V4;
+ server_address.nxd_ip_address.v4 = REMOTE_IP_ADDRESS_NUMBER;
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_udp_socket_create(&ip_0, &udp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 5);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup this thread to bind to a port. */
+ status = nx_udp_socket_bind(&udp_socket, 0, NX_NO_WAIT);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a DTLS session. */
+ status = nx_secure_dtls_session_create(&dtls_session,
+ &nx_crypto_tls_ciphers,
+ crypto_metadata,
+ sizeof(crypto_metadata),
+ tls_packet_buffer,
+ sizeof(tls_packet_buffer),
+ 1,
+ cert_buffer,
+ sizeof(cert_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_x509_certificate_initialize(&trusted_certificate, cert_der, cert_der_len,
+ NX_NULL, 0, NULL, 0, NX_SECURE_X509_KEY_TYPE_NONE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_dtls_session_trusted_certificate_add(&dtls_session, &trusted_certificate, 1);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tx_thread_sleep(100);
+
+ status = nx_icmp_ping(&ip_0, REMOTE_IP_ADDRESS_NUMBER, "abcdefg", 7, &send_packet, 10 * NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, status);
+ nx_packet_release(send_packet);
+
+ /* Attempt to connect the echo server. */
+ print_error_message("DTLS client session starting...\n");
+ status = nx_secure_dtls_client_session_start(&dtls_session, &udp_socket, &server_address, DEVICE_SERVER_PORT, 20 * NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_dtls_packet_allocate(&dtls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 2);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 3);
+
+ /* Send "hello" message. */
+ print_error_message("DTLS client session sending...\n");
+ status = nx_secure_dtls_client_session_send(&dtls_session, send_packet);
+ exit_if_fail(NX_SUCCESS == status, 4);
+
+#if 0
+ /* Receive the echoed and reversed data, and print it out. */
+ print_error_message("DTLS client session receving...\n");
+ status = nx_secure_dtls_session_receive(&dtls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 5);
+
+ /* Extract data received from server. */
+ status = nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ exit_if_fail(NX_SUCCESS == status, 6);
+
+ /* Check the reverse text received from openssl server. */
+ exit_if_fail('o' == ((CHAR*)receive_buffer)[0], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[1], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[2], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('e' == ((CHAR*)receive_buffer)[3], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('h' == ((CHAR*)receive_buffer)[4], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('\n' == ((CHAR*)receive_buffer)[5], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail(6 == bytes, 7);
+#endif
+
+ /* End the DTLS session. This is required to properly shut down the DTLS connection. */
+ print_error_message("DTLS client session end.\n");
+ nx_secure_dtls_session_end(&dtls_session, NX_NO_WAIT);
+
+ /* Delete the DTLS session. */
+ status = nx_secure_dtls_session_delete(&dtls_session);
+ exit_if_fail(NX_SUCCESS == status, 8);
+
+ /* Unbind the UDP socket from our port. */
+ status = nx_udp_socket_unbind(&udp_socket);
+ exit_if_fail(NX_SUCCESS == status, 9);
+
+ /* Delete the UDP socket instance to clean up. */
+ status = nx_udp_socket_delete(&udp_socket);
+ exit_if_fail(NX_SUCCESS == status, 10);
+
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_1_0_1_1_server_entry.c b/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_1_0_1_1_server_entry.c
new file mode 100644
index 00000000..26571e0d
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_1_0_1_1_server_entry.c
@@ -0,0 +1,493 @@
+/* This test concentrates on TLS ECC ciphersuites negotiation. */
+#include "tls_test_frame.h"
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) && (defined(NX_SECURE_TLS_ENABLE_TLS_1_0) || defined(NX_SECURE_TLS_ENABLE_TLS_1_1))
+#include "nx_crypto_ecdh.h"
+#include "../../nx_secure_test/ecc_certs.c"
+#include "../../nx_secure_test/test_ca_cert.c"
+#include "../../nx_secure_test/test_device_cert.c"
+
+#define NUM_PACKETS 24
+#define PACKET_SIZE 1536
+#define PACKET_POOL_SIZE (NUM_PACKETS * (PACKET_SIZE + sizeof(NX_PACKET)))
+#define THREAD_STACK_SIZE 1024
+#define ARP_CACHE_SIZE 1024
+#define BUFFER_SIZE 64
+#define METADATA_SIZE 16000
+#define CERT_BUFFER_SIZE 2048
+#define CIPHERSUITE_INIT(p, s, c, v) {p, sizeof(p) / sizeof(UINT), s, c, v}
+#define CERTIFICATE_INIT(s, k, c, t) {s, sizeof(s), k, sizeof(k), c, sizeof(c), t}
+
+typedef struct
+{
+ UCHAR *server_cert;
+ UINT server_cert_len;
+ UCHAR *server_key;
+ UINT server_key_len;
+ UCHAR *ca_cert;
+ UINT ca_cert_len;
+ UINT key_type;
+} CERTIFICATE;
+
+typedef struct
+{
+ UINT *list;
+ UINT count;
+ UINT session_succ;
+ CERTIFICATE *cert;
+ USHORT version;
+} CIPHERSUITE;
+
+/* Define the ThreadX and NetX object control blocks... */
+
+static TX_THREAD thread_0;
+static NX_PACKET_POOL pool_0;
+static NX_IP ip_0;
+
+static NX_TCP_SOCKET server_socket_0;
+static NX_SECURE_TLS_SESSION tls_server_session_0;
+static NX_SECURE_X509_CERT server_local_certificate;
+static NX_SECURE_TLS_CRYPTO tls_ciphers_server;
+static NX_SECURE_TLS_CIPHERSUITE_INFO
+ ciphersuite_table_server[10];
+
+static ULONG pool_0_memory[PACKET_POOL_SIZE / sizeof(ULONG)];
+static ULONG thread_0_stack[THREAD_STACK_SIZE / sizeof(ULONG)];
+static ULONG ip_0_stack[THREAD_STACK_SIZE / sizeof(ULONG)];
+static ULONG arp_cache[ARP_CACHE_SIZE];
+static UCHAR server_metadata[METADATA_SIZE];
+
+static UCHAR tls_packet_buffer[4000];
+static UCHAR response_buffer[100];
+
+extern NX_CRYPTO_METHOD crypto_method_ec_secp192;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp224;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp256;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp384;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp521;
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+
+extern NX_CRYPTO_METHOD crypto_method_rsa;
+extern NX_CRYPTO_METHOD crypto_method_md5;
+extern NX_CRYPTO_METHOD crypto_method_sha1;
+extern NX_CRYPTO_METHOD crypto_method_sha224;
+extern NX_CRYPTO_METHOD crypto_method_sha256;
+extern NX_CRYPTO_METHOD crypto_method_sha384;
+extern NX_CRYPTO_METHOD crypto_method_sha512;
+extern NX_CRYPTO_METHOD crypto_method_aes_cbc_128;
+extern NX_CRYPTO_METHOD crypto_method_aes_cbc_256;
+extern NX_CRYPTO_METHOD crypto_method_hmac_sha1;
+extern NX_CRYPTO_METHOD crypto_method_hmac_sha256;
+extern NX_CRYPTO_METHOD crypto_method_hkdf_sha256;
+extern NX_CRYPTO_METHOD crypto_method_tls_prf_1;
+extern NX_CRYPTO_METHOD crypto_method_tls_prf_sha256;
+extern NX_CRYPTO_METHOD crypto_method_hkdf;
+extern NX_CRYPTO_METHOD crypto_method_hmac;
+extern NX_CRYPTO_METHOD crypto_method_ecdhe;
+extern NX_CRYPTO_METHOD crypto_method_ecdsa;
+
+NX_SECURE_X509_CRYPTO _nx_crypto_x509_cipher_lookup_table_ecc[] =
+{
+ /* OID identifier, public cipher, hash method */
+ {NX_SECURE_TLS_X509_TYPE_ECDSA_SHA_256, &crypto_method_ecdsa, &crypto_method_sha256},
+ {NX_SECURE_TLS_X509_TYPE_ECDSA_SHA_384, &crypto_method_ecdsa, &crypto_method_sha384},
+ {NX_SECURE_TLS_X509_TYPE_ECDSA_SHA_512, &crypto_method_ecdsa, &crypto_method_sha512},
+ {NX_SECURE_TLS_X509_TYPE_RSA_SHA_256, &crypto_method_rsa, &crypto_method_sha256},
+ {NX_SECURE_TLS_X509_TYPE_RSA_SHA_384, &crypto_method_rsa, &crypto_method_sha384},
+ {NX_SECURE_TLS_X509_TYPE_RSA_SHA_512, &crypto_method_rsa, &crypto_method_sha512},
+ {NX_SECURE_TLS_X509_TYPE_ECDSA_SHA_224, &crypto_method_ecdsa, &crypto_method_sha224},
+ {NX_SECURE_TLS_X509_TYPE_ECDSA_SHA_1, &crypto_method_ecdsa, &crypto_method_sha1},
+ {NX_SECURE_TLS_X509_TYPE_RSA_SHA_1, &crypto_method_rsa, &crypto_method_sha1},
+ {NX_SECURE_TLS_X509_TYPE_RSA_MD5, &crypto_method_rsa, &crypto_method_md5},
+};
+
+/* Ciphersuite table with ECC. */
+static NX_SECURE_TLS_CIPHERSUITE_INFO _nx_crypto_ciphersuite_lookup_table_ecc[] =
+{
+ /* Ciphersuite, public cipher, public_auth, session cipher & cipher mode, iv size, key size, hash method, hash size, TLS PRF */
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ {TLS_AES_128_GCM_SHA256, &crypto_method_ecdhe, &crypto_method_ecdsa, &crypto_method_aes_128_gcm_16, 96, 16, &crypto_method_sha256, 32, &crypto_method_hkdf},
+ {TLS_AES_128_CCM_SHA256, &crypto_method_ecdhe, &crypto_method_ecdsa, &crypto_method_aes_ccm_16, 96, 16, &crypto_method_sha256, 32, &crypto_method_hkdf},
+ {TLS_AES_128_CCM_8_SHA256, &crypto_method_ecdhe, &crypto_method_ecdsa, &crypto_method_aes_ccm_8, 96, 16, &crypto_method_sha256, 32, &crypto_method_hkdf},
+#endif
+
+#ifdef NX_SECURE_ENABLE_AEAD_CIPHER
+ {TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, &crypto_method_ecdhe, &crypto_method_ecdsa, &crypto_method_aes_128_gcm_16, 16, 16, &crypto_method_null, 0, &crypto_method_tls_prf_sha256},
+ {TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256, &crypto_method_ecdhe, &crypto_method_rsa, &crypto_method_aes_128_gcm_16, 16, 16, &crypto_method_null, 0, &crypto_method_tls_prf_sha256},
+#endif /* NX_SECURE_ENABLE_AEAD_CIPHER */
+
+ {TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256, &crypto_method_ecdhe, &crypto_method_ecdsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha256, 32, &crypto_method_tls_prf_sha256},
+ {TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256, &crypto_method_ecdhe, &crypto_method_rsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha256, 32, &crypto_method_tls_prf_sha256},
+ {TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA, &crypto_method_ecdhe, &crypto_method_ecdsa, &crypto_method_aes_cbc_256, 16, 32, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+ {TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA, &crypto_method_ecdhe, &crypto_method_rsa, &crypto_method_aes_cbc_256, 16, 32, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+ {TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA, &crypto_method_ecdhe, &crypto_method_ecdsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+ {TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA, &crypto_method_ecdhe, &crypto_method_rsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+
+#ifdef NX_SECURE_ENABLE_AEAD_CIPHER
+ {TLS_RSA_WITH_AES_128_GCM_SHA256, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_128_gcm_16, 16, 16, &crypto_method_null, 0, &crypto_method_tls_prf_sha256},
+#endif /* NX_SECURE_ENABLE_AEAD_CIPHER */
+
+ {TLS_RSA_WITH_AES_256_CBC_SHA256, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_256, 16, 32, &crypto_method_hmac_sha256, 32, &crypto_method_tls_prf_sha256},
+ {TLS_RSA_WITH_AES_128_CBC_SHA256, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha256, 32, &crypto_method_tls_prf_sha256},
+ {TLS_RSA_WITH_AES_256_CBC_SHA, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_256, 16, 32, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+ {TLS_RSA_WITH_AES_128_CBC_SHA, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+
+};
+
+static const UINT _nx_crypto_ciphersuite_lookup_table_ecc_size = sizeof(_nx_crypto_ciphersuite_lookup_table_ecc) / sizeof(NX_SECURE_TLS_CIPHERSUITE_INFO);
+
+
+/* Define the object we can pass into TLS. */
+static const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc =
+{
+ /* Ciphersuite lookup table and size. */
+ _nx_crypto_ciphersuite_lookup_table_ecc,
+ sizeof(_nx_crypto_ciphersuite_lookup_table_ecc) / sizeof(NX_SECURE_TLS_CIPHERSUITE_INFO),
+
+#ifndef NX_SECURE_DISABLE_X509
+ /* X.509 certificate cipher table and size. */
+ _nx_crypto_x509_cipher_lookup_table_ecc,
+ sizeof(_nx_crypto_x509_cipher_lookup_table_ecc) / sizeof(NX_SECURE_X509_CRYPTO),
+#endif
+
+ /* TLS version-specific methods. */
+#if (NX_SECURE_TLS_TLS_1_0_ENABLED || NX_SECURE_TLS_TLS_1_1_ENABLED)
+ & crypto_method_md5,
+ &crypto_method_sha1,
+ &crypto_method_tls_prf_1,
+#endif
+
+#if (NX_SECURE_TLS_TLS_1_2_ENABLED)
+ &crypto_method_sha256,
+ &crypto_method_tls_prf_sha256,
+#endif
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ &crypto_method_hkdf,
+ &crypto_method_hmac,
+ &crypto_method_ecdhe,
+#endif
+
+
+};
+
+static CERTIFICATE test_certs[] =
+{
+ CERTIFICATE_INIT(ECTest_der, ECTest_key_der, ECCA_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+ CERTIFICATE_INIT(ECTestServer2_der, ECTestServer2_key_der, ECCA2_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+ CERTIFICATE_INIT(test_device_cert_der, test_device_cert_key_der, test_ca_cert_der, NX_SECURE_X509_KEY_TYPE_RSA_PKCS1_DER),
+ CERTIFICATE_INIT(ECTestServer10_der, ECTestServer10_key_der, ECCA2_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+};
+
+static UINT ciphersuite_list_0[] = {};
+static UINT ciphersuite_list_1[] = {TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA};
+static UINT ciphersuite_list_2[] = {TLS_ECDH_RSA_WITH_AES_128_CBC_SHA};
+static UINT ciphersuite_list_3[] = {TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA};
+static UINT ciphersuite_list_4[] = {TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA};
+static UINT ciphersuite_list_5[] =
+{
+ TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA,
+ TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA,
+ TLS_ECDH_RSA_WITH_AES_128_CBC_SHA,
+ TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA
+};
+static UINT ciphersuite_list_6[] = {TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA};
+static UINT ciphersuite_list_7[] = {TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA};
+static UINT ciphersuite_list_8[] = {TLS_ECDH_RSA_WITH_AES_256_CBC_SHA};
+static UINT ciphersuite_list_9[] = {TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA};
+
+
+static CIPHERSUITE ciphersuites_server[] =
+{
+#ifdef NX_SECURE_TLS_ENABLE_TLS_1_0
+ /* Select ciphersuite according to certificate. */
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[0], NX_SECURE_TLS_VERSION_TLS_1_0),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_0),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[2], NX_SECURE_TLS_VERSION_TLS_1_0),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[3], NX_SECURE_TLS_VERSION_TLS_1_0),
+
+ /* Select ciphersuite according to certificate.
+ * The order of client ciphersuites are reversed of server. */
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[0], NX_SECURE_TLS_VERSION_TLS_1_0),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_0),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[2], NX_SECURE_TLS_VERSION_TLS_1_0),
+
+ /* Specified ciphersuites. */
+ /*CIPHERSUITE_INIT(ciphersuite_list_1, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_0),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_2, NX_TRUE, &test_certs[0], NX_SECURE_TLS_VERSION_TLS_1_0),*/
+ CIPHERSUITE_INIT(ciphersuite_list_3, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_0),
+ CIPHERSUITE_INIT(ciphersuite_list_4, NX_TRUE, &test_certs[2], NX_SECURE_TLS_VERSION_TLS_1_0),
+
+ /* The Server cert supports ECDH_ECDSA and ECDHE_ECDSA. */
+ /*CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_0),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_0, NX_FALSE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_0),*/
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_0),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_FALSE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_0),
+
+ /* Let the server pickup supported ciphersuite. */
+ /*CIPHERSUITE_INIT(ciphersuite_list_1, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_0),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_2, NX_TRUE, &test_certs[0], NX_SECURE_TLS_VERSION_TLS_1_0),*/
+ CIPHERSUITE_INIT(ciphersuite_list_3, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_0),
+ CIPHERSUITE_INIT(ciphersuite_list_4, NX_TRUE, &test_certs[2], NX_SECURE_TLS_VERSION_TLS_1_0),
+
+ /* AES256 ciphersuites. */
+ /*CIPHERSUITE_INIT(ciphersuite_list_6, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_0),*/
+ CIPHERSUITE_INIT(ciphersuite_list_7, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_0),
+ /*CIPHERSUITE_INIT(ciphersuite_list_8, NX_TRUE, &test_certs[0], NX_SECURE_TLS_VERSION_TLS_1_0),*/
+ CIPHERSUITE_INIT(ciphersuite_list_9, NX_TRUE, &test_certs[2], NX_SECURE_TLS_VERSION_TLS_1_0),
+#endif /* NX_SECURE_TLS_ENABLE_TLS_1_0 */
+
+#ifdef NX_SECURE_TLS_ENABLE_TLS_1_1
+ /* Select ciphersuite according to certificate. */
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[0], NX_SECURE_TLS_VERSION_TLS_1_1),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_1),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[2], NX_SECURE_TLS_VERSION_TLS_1_1),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[3], NX_SECURE_TLS_VERSION_TLS_1_1),
+
+ /* Select ciphersuite according to certificate.
+ * The order of client ciphersuites are reversed of server. */
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[0], NX_SECURE_TLS_VERSION_TLS_1_1),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_1),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[2], NX_SECURE_TLS_VERSION_TLS_1_1),
+
+ /* Specified ciphersuites. */
+ /*CIPHERSUITE_INIT(ciphersuite_list_1, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_1),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_2, NX_TRUE, &test_certs[0], NX_SECURE_TLS_VERSION_TLS_1_1),*/
+ CIPHERSUITE_INIT(ciphersuite_list_3, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_1),
+ CIPHERSUITE_INIT(ciphersuite_list_4, NX_TRUE, &test_certs[2], NX_SECURE_TLS_VERSION_TLS_1_1),
+
+ /* The Server cert supports ECDH_ECDSA and ECDHE_ECDSA. */
+ /*CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_1),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_0, NX_FALSE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_1),*/
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_1),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_FALSE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_1),
+
+ /* Let the server pickup supported ciphersuite. */
+ /*CIPHERSUITE_INIT(ciphersuite_list_1, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_1),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_2, NX_TRUE, &test_certs[0], NX_SECURE_TLS_VERSION_TLS_1_1),*/
+ CIPHERSUITE_INIT(ciphersuite_list_3, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_1),
+ CIPHERSUITE_INIT(ciphersuite_list_4, NX_TRUE, &test_certs[2], NX_SECURE_TLS_VERSION_TLS_1_1),
+
+ /* AES256 ciphersuites. */
+ /*CIPHERSUITE_INIT(ciphersuite_list_6, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_1),*/
+ CIPHERSUITE_INIT(ciphersuite_list_7, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_1),
+ /*CIPHERSUITE_INIT(ciphersuite_list_8, NX_TRUE, &test_certs[0], NX_SECURE_TLS_VERSION_TLS_1_1),*/
+ CIPHERSUITE_INIT(ciphersuite_list_9, NX_TRUE, &test_certs[2], NX_SECURE_TLS_VERSION_TLS_1_1),
+#endif /* NX_SECURE_TLS_ENABLE_TLS_1_1 */
+
+};
+
+/* Define thread prototypes. */
+
+static VOID ntest_0_entry(ULONG thread_input);
+extern VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+
+/* Define the pointer of current instance control block. */
+static TLS_TEST_INSTANCE* demo_instance_ptr;
+
+/* Instance one test entry. */
+INT nx_secure_ecc_server_ciphersuites_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+
+ /* Get instance pointer. */
+ demo_instance_ptr = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+}
+
+/* Define what the initial system looks like. */
+
+VOID tx_application_define(void *first_unused_memory)
+{
+UINT status;
+CHAR *pointer;
+
+
+
+ /* Setup the working pointer. */
+ pointer = (CHAR *) first_unused_memory;
+
+ /* Create the server thread. */
+ tx_thread_create(&thread_0, "thread 0", ntest_0_entry, 0,
+ thread_0_stack, sizeof(thread_0_stack),
+ 7, 7, TX_NO_TIME_SLICE, TX_AUTO_START);
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", PACKET_SIZE,
+ pool_0_memory, PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL,
+ &pool_0, _nx_pcap_network_driver,
+ ip_0_stack, sizeof(ip_0_stack), 1);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (VOID *)arp_cache, sizeof(arp_cache));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ nx_secure_tls_initialize();
+}
+
+static VOID ciphersuites_setup(CIPHERSUITE *ciphersuite, NX_SECURE_TLS_CRYPTO *tls_ciphers,
+ NX_SECURE_TLS_CIPHERSUITE_INFO *ciphersuite_table)
+{
+UINT i;
+UINT status;
+UINT count;
+
+ /* Initialize ciphersuites. */
+ memcpy(tls_ciphers, &nx_crypto_tls_ciphers_ecc, sizeof(NX_SECURE_TLS_CRYPTO));
+ if (ciphersuite -> count > 0)
+ {
+ for (count = 0; count < ciphersuite -> count; count++)
+ {
+ i = 0;
+ while (ciphersuite -> list[count] !=
+ (UINT)_nx_crypto_ciphersuite_lookup_table_ecc[i].nx_secure_tls_ciphersuite)
+ {
+ i++;
+ }
+ memcpy(&ciphersuite_table[count],
+ &_nx_crypto_ciphersuite_lookup_table_ecc[i],
+ sizeof(NX_SECURE_TLS_CIPHERSUITE_INFO));
+ }
+ tls_ciphers -> nx_secure_tls_ciphersuite_lookup_table = ciphersuite_table;
+ tls_ciphers -> nx_secure_tls_ciphersuite_lookup_table_size = count;
+ }
+}
+
+static VOID server_tls_setup(NX_SECURE_TLS_SESSION *tls_session_ptr, CERTIFICATE *cert, USHORT version)
+{
+UINT status;
+
+ status = nx_secure_tls_session_create(tls_session_ptr,
+ &tls_ciphers_server,
+ server_metadata,
+ sizeof(server_metadata));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_session_protocol_version_override(tls_session_ptr, version);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_ecc_initialize(tls_session_ptr, nx_crypto_ecc_supported_groups,
+ nx_crypto_ecc_supported_groups_size,
+ nx_crypto_ecc_curves);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ memset(&server_local_certificate, 0, sizeof(server_local_certificate));
+ status = nx_secure_x509_certificate_initialize(&server_local_certificate,
+ cert -> server_cert, cert -> server_cert_len,
+ NX_NULL, 0, cert -> server_key,
+ cert -> server_key_len,
+ cert -> key_type);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_local_certificate_add(tls_session_ptr,
+ &server_local_certificate);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_session_packet_buffer_set(tls_session_ptr, tls_packet_buffer,
+ sizeof(tls_packet_buffer));
+ show_error_message_if_fail( NX_SUCCESS == status);
+}
+
+static void ntest_0_entry(ULONG thread_input)
+{
+UINT i;
+UINT status;
+ULONG actual_status;
+ULONG response_length;
+NX_PACKET *packet_ptr;
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status,
+ NX_IP_PERIODIC_RATE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Create TCP socket. */
+ status = nx_tcp_socket_create(&ip_0, &server_socket_0, "Server socket", NX_IP_NORMAL,
+ NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 8192, NX_NULL, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_tcp_server_socket_listen(&ip_0, DEVICE_SERVER_PORT, &server_socket_0, 5, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ for (i = 0; i < sizeof(ciphersuites_server) / sizeof(CIPHERSUITE); i++)
+ {
+
+ ciphersuites_setup(&ciphersuites_server[i], &tls_ciphers_server, ciphersuite_table_server);
+
+ server_tls_setup(&tls_server_session_0, ciphersuites_server[i].cert, ciphersuites_server[i].version);
+
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ status = nx_tcp_server_socket_accept(&server_socket_0, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 1);
+
+ /* Start TLS session. */
+ status = nx_secure_tls_session_start(&tls_server_session_0, &server_socket_0,
+ NX_WAIT_FOREVER);
+ exit_if_fail (!((status && ciphersuites_server[i].session_succ) ||
+ (!status && !ciphersuites_server[i].session_succ)), 2);
+
+ if (!status)
+ {
+ status = nx_secure_tls_session_receive(&tls_server_session_0, &packet_ptr, NX_WAIT_FOREVER);
+ exit_if_fail ( NX_SUCCESS == status, 3);
+
+ nx_packet_data_retrieve(packet_ptr, response_buffer, &response_length);
+ nx_packet_release(packet_ptr);
+ response_buffer[response_length] = 0;
+ print_error_message("Received data: %s\n", (CHAR *)response_buffer);
+
+ /* Allocate a return packet and send our HTML data back to the client. */
+ status = nx_secure_tls_packet_allocate(&tls_server_session_0, &pool_0, &packet_ptr,
+ NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 4);
+
+ /* Echo the message received. */
+ status = nx_packet_data_append(packet_ptr, response_buffer, response_length, &pool_0,
+ NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 5);
+
+ /* TLS send the HTML/HTTPS data back to the client. */
+ status = nx_secure_tls_session_send(&tls_server_session_0, packet_ptr,
+ NX_IP_PERIODIC_RATE);
+ /* Exit the test process directly without release packet. */
+ exit_if_fail( NX_SUCCESS == status, 6);
+ }
+
+ nx_secure_tls_session_end(&tls_server_session_0, NX_IP_PERIODIC_RATE);
+ nx_secure_tls_session_delete(&tls_server_session_0);
+
+ nx_tcp_socket_disconnect(&server_socket_0, NX_NO_WAIT);
+ nx_tcp_server_socket_unaccept(&server_socket_0);
+ nx_tcp_server_socket_relisten(&ip_0, DEVICE_SERVER_PORT, &server_socket_0);
+ }
+
+ exit(0);
+}
+
+#else
+INT nx_secure_ecc_server_ciphersuites_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+ exit(TLS_TEST_NOT_AVAILABLE);
+}
+#endif
diff --git a/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_client_cert_test_client_entry.c b/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_client_cert_test_client_entry.c
new file mode 100644
index 00000000..cc026440
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_client_cert_test_client_entry.c
@@ -0,0 +1,273 @@
+#include "tls_test_frame.h"
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+#include "nx_crypto_ecdh.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+NX_SECURE_X509_CERT trusted_certificate;
+NX_SECURE_X509_CERT client_local_certificate;
+
+UCHAR tls_packet_buffer[4000];
+
+#include "../../nx_secure_test/ecc_certs.c"
+#include "../../nx_secure_test/test_ca_cert.c"
+#include "../../nx_secure_test/test_device_cert.c"
+
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define an error counter. */
+
+ULONG error_counter;
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+
+
+static VOID client_tls_setup(NX_SECURE_TLS_SESSION *tls_session_ptr)
+{
+UINT status;
+
+ status = nx_secure_tls_session_create(tls_session_ptr,
+ &nx_crypto_tls_ciphers_ecc,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_ecc_initialize(tls_session_ptr, nx_crypto_ecc_supported_groups,
+ nx_crypto_ecc_supported_groups_size,
+ nx_crypto_ecc_curves);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ memset(&remote_cert_buffer, 0, sizeof(remote_cert_buffer));
+ memset(&remote_issuer_buffer, 0, sizeof(remote_issuer_buffer));
+ status = nx_secure_tls_remote_certificate_allocate(tls_session_ptr,
+ &remote_certificate,
+ remote_cert_buffer,
+ sizeof(remote_cert_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_remote_certificate_allocate(tls_session_ptr,
+ &remote_issuer,
+ remote_issuer_buffer,
+ sizeof(remote_issuer_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_x509_certificate_initialize(&trusted_certificate,
+ ECCA2_der,
+ ECCA2_der_len, NX_NULL, 0, NULL, 0, NX_SECURE_X509_KEY_TYPE_NONE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_trusted_certificate_add(tls_session_ptr,
+ &trusted_certificate);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ memset(&client_local_certificate, 0, sizeof(client_local_certificate));
+ status = nx_secure_x509_certificate_initialize(&client_local_certificate,
+ ECTestServer7_256_der, ECTestServer7_256_der_len,
+ NX_NULL, 0, ECTestServer7_256_key_der,
+ ECTestServer7_256_key_der_len,
+ NX_SECURE_X509_KEY_TYPE_EC_DER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_local_certificate_add(tls_session_ptr,
+ &client_local_certificate);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_session_packet_buffer_set(tls_session_ptr, tls_packet_buffer,
+ sizeof(tls_packet_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+}
+
+
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+
+}
+
+void tx_application_define(void *first_unused_memory)
+{
+ULONG gateway_ipv4_address;
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+
+NX_PARAMETER_NOT_USED(thread_input);
+
+ /* Address of remote server. */
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+
+ /* Setup this thread to bind to a port. */
+ status = nx_tcp_client_socket_bind(&tcp_socket, 0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tx_thread_sleep(NX_IP_PERIODIC_RATE);
+
+ client_tls_setup(&tls_session);
+
+ /* Attempt to connect the echo server. */
+ status = nx_tcp_client_socket_connect(&tcp_socket, REMOTE_IP_ADDRESS_NUMBER, DEVICE_SERVER_PORT, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send "hello" message. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Receive the echoed and reversed data, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Extract data received from server. */
+ status = nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Check the reverse text received from openssl server. */
+ exit_if_fail('o' == ((CHAR*)receive_buffer)[0], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[1], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[2], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('e' == ((CHAR*)receive_buffer)[3], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('h' == ((CHAR*)receive_buffer)[4], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('\n' == ((CHAR*)receive_buffer)[5], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail(6 == bytes, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ nx_secure_tls_session_end(&tls_session, NX_NO_WAIT);
+ nx_secure_tls_session_delete(&tls_session);
+
+ /* Close the TCP connection. */
+ nx_tcp_socket_disconnect(&tcp_socket, NX_NO_WAIT);
+
+
+ /* Unbind the TCP socket from our port. */
+ status = nx_tcp_client_socket_unbind(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Delete the TCP socket instance to clean up. */
+ status = nx_tcp_socket_delete(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ exit(0);
+}
+#else
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+
+}
+#endif
diff --git a/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_curves_test_client_entry.c b/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_curves_test_client_entry.c
new file mode 100644
index 00000000..dac4a190
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_curves_test_client_entry.c
@@ -0,0 +1,442 @@
+#include "tls_test_frame.h"
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+#include "nx_crypto_ecdh.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+NX_SECURE_X509_CERT trusted_certificate;
+NX_SECURE_X509_CERT client_local_certificate;
+
+UCHAR tls_packet_buffer[4000];
+#define CERTIFICATE_INIT(s, k, c, t) {s, sizeof(s), k, sizeof(k), c, sizeof(c), t}
+#define TEST_CASE_INIT(g, c, s, t) {g, sizeof(g) / sizeof(USHORT),\
+ c, sizeof(c) / sizeof(NX_CRYPTO_METHOD *), s, t}
+
+typedef struct
+{
+ UCHAR *server_cert;
+ UINT server_cert_len;
+ UCHAR *server_key;
+ UINT server_key_len;
+ UCHAR *ca_cert;
+ UINT ca_cert_len;
+ UINT key_type;
+} CERTIFICATE;
+
+typedef struct
+{
+ USHORT *supported_groups;
+ UINT supported_groups_count;
+ const NX_CRYPTO_METHOD **curves;
+ UINT curve_count;
+ UINT session_succ;
+ CERTIFICATE *cert;
+} TEST_CASE;
+
+#include "../../nx_secure_test/ecc_certs.c"
+#include "../../nx_secure_test/test_ca_cert.c"
+#include "../../nx_secure_test/test_device_cert.c"
+
+extern NX_CRYPTO_METHOD crypto_method_ec_secp192;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp224;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp256;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp384;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp521;
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+
+
+extern NX_CRYPTO_METHOD crypto_method_aes_cbc_128;
+extern NX_CRYPTO_METHOD crypto_method_ecdsa;
+extern NX_CRYPTO_METHOD crypto_method_ecdh;
+extern NX_CRYPTO_METHOD crypto_method_hmac_sha256;
+extern NX_CRYPTO_METHOD crypto_method_tls_prf_sha256;
+extern NX_CRYPTO_METHOD crypto_method_ecdhe;
+extern NX_CRYPTO_METHOD crypto_method_aes_128_gcm_16;
+extern NX_CRYPTO_METHOD crypto_method_sha256;
+extern NX_CRYPTO_METHOD crypto_method_hkdf;
+
+static NX_SECURE_TLS_CIPHERSUITE_INFO ciphersuite_lookup_table[] =
+{
+ /* Ciphersuite, public cipher, public_auth, session cipher & cipher mode, iv size, key size, hash method, hash size, TLS PRF */
+ {TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256, &crypto_method_ecdh, &crypto_method_ecdsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha256, 32, &crypto_method_tls_prf_sha256},
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ {TLS_AES_128_GCM_SHA256, &crypto_method_ecdhe, &crypto_method_ecdsa, &crypto_method_aes_128_gcm_16, 96, 16, &crypto_method_sha256, 32, &crypto_method_hkdf},
+#endif
+};
+static NX_SECURE_TLS_CRYPTO tls_ciphers_ecc;
+
+static USHORT supported_groups_0[] =
+{
+ (USHORT)NX_CRYPTO_EC_SECP192R1,
+ (USHORT)NX_CRYPTO_EC_SECP224R1,
+ (USHORT)NX_CRYPTO_EC_SECP256R1,
+ (USHORT)NX_CRYPTO_EC_SECP384R1,
+ (USHORT)NX_CRYPTO_EC_SECP521R1,
+};
+
+static USHORT supported_groups_1[] = {(USHORT)NX_CRYPTO_EC_SECP192R1};
+static USHORT supported_groups_2[] = {(USHORT)NX_CRYPTO_EC_SECP224R1};
+static USHORT supported_groups_3[] = {(USHORT)NX_CRYPTO_EC_SECP256R1};
+static USHORT supported_groups_4[] = {(USHORT)NX_CRYPTO_EC_SECP384R1};
+static USHORT supported_groups_5[] = {(USHORT)NX_CRYPTO_EC_SECP521R1};
+static USHORT supported_groups_6[] = {(USHORT)NX_CRYPTO_EC_SECP192R1, (USHORT)NX_CRYPTO_EC_SECP256R1};
+static USHORT supported_groups_7[] = {(USHORT)NX_CRYPTO_EC_SECP224R1, (USHORT)NX_CRYPTO_EC_SECP256R1};
+
+
+static const NX_CRYPTO_METHOD *ecc_curves_0[] =
+{
+ &crypto_method_ec_secp192,
+ &crypto_method_ec_secp224,
+ &crypto_method_ec_secp256,
+ &crypto_method_ec_secp384,
+ &crypto_method_ec_secp521,
+};
+
+static const NX_CRYPTO_METHOD *ecc_curves_1[] = {&crypto_method_ec_secp192};
+static const NX_CRYPTO_METHOD *ecc_curves_2[] = {&crypto_method_ec_secp224};
+static const NX_CRYPTO_METHOD *ecc_curves_3[] = {&crypto_method_ec_secp256};
+static const NX_CRYPTO_METHOD *ecc_curves_4[] = {&crypto_method_ec_secp384};
+static const NX_CRYPTO_METHOD *ecc_curves_5[] = {&crypto_method_ec_secp521};
+static const NX_CRYPTO_METHOD *ecc_curves_6[] = {&crypto_method_ec_secp192, &crypto_method_ec_secp256};
+static const NX_CRYPTO_METHOD *ecc_curves_7[] = {&crypto_method_ec_secp224, &crypto_method_ec_secp256};
+
+static CERTIFICATE test_certs[] =
+{
+ CERTIFICATE_INIT(ECTestServer9_192_der, ECTestServer9_192_key_der, ECCA2_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+ CERTIFICATE_INIT(ECTestServer8_224_der, ECTestServer8_224_key_der, ECCA2_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+ CERTIFICATE_INIT(ECTestServer2_der, ECTestServer2_key_der, ECCA2_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+ CERTIFICATE_INIT(ECTestServer4_der, ECTestServer4_key_der, ECCA4_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+ CERTIFICATE_INIT(ECTestServer3_der, ECTestServer3_key_der, ECCA3_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+};
+
+
+static TEST_CASE test_case_client[] =
+{
+
+ /* Select curve by certificate. */
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[0]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[1]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[2]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[3]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[4]),
+
+ /* Specify curve from client. */
+ TEST_CASE_INIT(supported_groups_6, ecc_curves_6, NX_TRUE, &test_certs[0]),
+ TEST_CASE_INIT(supported_groups_7, ecc_curves_7, NX_TRUE, &test_certs[1]),
+ TEST_CASE_INIT(supported_groups_3, ecc_curves_3, NX_TRUE, &test_certs[2]),
+ TEST_CASE_INIT(supported_groups_4, ecc_curves_4, NX_TRUE, &test_certs[3]),
+ TEST_CASE_INIT(supported_groups_5, ecc_curves_5, NX_TRUE, &test_certs[4]),
+
+ /* Specify curve from server. */
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[0]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[1]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[2]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[3]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[4]),
+
+ /* Configure invalid curves at server side. */
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_FALSE, &test_certs[0]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_FALSE, &test_certs[0]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_FALSE, &test_certs[0]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_FALSE, &test_certs[0]),
+
+ /* Multiple curves used by server and CA cert. */
+ TEST_CASE_INIT(supported_groups_1, ecc_curves_1, NX_FALSE, &test_certs[0]), /* ECCA2_der uses P256 which is not supported. */
+ TEST_CASE_INIT(supported_groups_2, ecc_curves_2, NX_FALSE, &test_certs[1]), /* ECCA2_der uses P256 which is not supported. */
+
+ /* Client curve not supported by server. */
+ TEST_CASE_INIT(supported_groups_3, ecc_curves_3, NX_FALSE, &test_certs[2]),
+ TEST_CASE_INIT(supported_groups_3, ecc_curves_3, NX_FALSE, &test_certs[2]),
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ /* Specify curve from client. */
+ TEST_CASE_INIT(supported_groups_3, ecc_curves_3, NX_TRUE, &test_certs[2]),
+ TEST_CASE_INIT(supported_groups_4, ecc_curves_4, NX_TRUE, &test_certs[3]),
+ TEST_CASE_INIT(supported_groups_5, ecc_curves_5, NX_TRUE, &test_certs[4]),
+
+ /* Specify curve from server. */
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[2]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[3]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[4]),
+
+ /* Client curves not suitable for signature. */
+ TEST_CASE_INIT(supported_groups_4, ecc_curves_4, NX_FALSE, &test_certs[3]),
+ TEST_CASE_INIT(supported_groups_5, ecc_curves_5, NX_FALSE, &test_certs[4]),
+
+ /* Client curve not supported by server. */
+ TEST_CASE_INIT(supported_groups_5, ecc_curves_5, NX_FALSE, &test_certs[4]),
+ TEST_CASE_INIT(supported_groups_5, ecc_curves_5, NX_FALSE, &test_certs[4]),
+#endif
+};
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define an error counter. */
+
+ULONG error_counter;
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+
+
+static VOID client_tls_setup(NX_SECURE_TLS_SESSION *tls_session_ptr, TEST_CASE *test_case)
+{
+UINT status;
+
+ status = nx_secure_tls_session_create(tls_session_ptr,
+ &tls_ciphers_ecc,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_ecc_initialize(tls_session_ptr, test_case -> supported_groups,
+ test_case -> supported_groups_count,
+ test_case -> curves);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ memset(&remote_cert_buffer, 0, sizeof(remote_cert_buffer));
+ memset(&remote_issuer_buffer, 0, sizeof(remote_issuer_buffer));
+ status = nx_secure_tls_remote_certificate_allocate(tls_session_ptr,
+ &remote_certificate,
+ remote_cert_buffer,
+ sizeof(remote_cert_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_remote_certificate_allocate(tls_session_ptr,
+ &remote_issuer,
+ remote_issuer_buffer,
+ sizeof(remote_issuer_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_x509_certificate_initialize(&trusted_certificate,
+ test_case -> cert -> ca_cert,
+ test_case -> cert -> ca_cert_len, NX_NULL, 0, NULL, 0, NX_SECURE_X509_KEY_TYPE_NONE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_trusted_certificate_add(tls_session_ptr,
+ &trusted_certificate);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ if (test_case -> cert != NX_NULL)
+ {
+ memset(&client_local_certificate, 0, sizeof(client_local_certificate));
+ status = nx_secure_x509_certificate_initialize(&client_local_certificate,
+ test_case -> cert -> server_cert, test_case -> cert -> server_cert_len,
+ NX_NULL, 0, test_case -> cert -> server_key,
+ test_case -> cert -> server_key_len,
+ test_case -> cert -> key_type);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_local_certificate_add(tls_session_ptr,
+ &client_local_certificate);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+ }
+
+ status = nx_secure_tls_session_packet_buffer_set(tls_session_ptr, tls_packet_buffer,
+ sizeof(tls_packet_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+}
+
+
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+
+}
+
+void tx_application_define(void *first_unused_memory)
+{
+ULONG gateway_ipv4_address;
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+UINT i;
+NX_PARAMETER_NOT_USED(thread_input);
+
+ /* Address of remote server. */
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+
+ /* Setup this thread to bind to a port. */
+ status = nx_tcp_client_socket_bind(&tcp_socket, 0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ memcpy(&tls_ciphers_ecc, &nx_crypto_tls_ciphers_ecc, sizeof(nx_crypto_tls_ciphers_ecc));
+ tls_ciphers_ecc.nx_secure_tls_ciphersuite_lookup_table = ciphersuite_lookup_table;
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ tls_ciphers_ecc.nx_secure_tls_ciphersuite_lookup_table_size = 2;
+#else
+ tls_ciphers_ecc.nx_secure_tls_ciphersuite_lookup_table_size = 1;
+#endif
+
+ for (i = 0; i < sizeof(test_case_client) / sizeof(TEST_CASE); i++)
+ {
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tx_thread_sleep(20 * NX_IP_PERIODIC_RATE);
+
+ client_tls_setup(&tls_session, &test_case_client[i]);
+
+ /* Attempt to connect the echo server. */
+ status = nx_tcp_client_socket_connect(&tcp_socket, REMOTE_IP_ADDRESS_NUMBER, DEVICE_SERVER_PORT, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(!((status && test_case_client[i].session_succ) ||
+ (!status && !test_case_client[i].session_succ)), TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ if (!status)
+ {
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send "hello" message. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Receive the echoed and reversed data, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Extract data received from server. */
+ status = nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ nx_packet_release(receive_packet);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Check the reverse text received from openssl server. */
+ exit_if_fail('o' == ((CHAR*)receive_buffer)[0], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[1], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[2], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('e' == ((CHAR*)receive_buffer)[3], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('h' == ((CHAR*)receive_buffer)[4], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('\n' == ((CHAR*)receive_buffer)[5], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail(6 == bytes, TLS_TEST_UNKNOWN_TYPE_ERROR);
+ }
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ nx_secure_tls_session_end(&tls_session, NX_NO_WAIT);
+ nx_secure_tls_session_delete(&tls_session);
+
+ /* Close the TCP connection. */
+ nx_tcp_socket_disconnect(&tcp_socket, NX_NO_WAIT);
+ }
+
+
+ /* Unbind the TCP socket from our port. */
+ status = nx_tcp_client_socket_unbind(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Delete the TCP socket instance to clean up. */
+ status = nx_tcp_socket_delete(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ exit(0);
+}
+#else
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+
+}
+#endif
diff --git a/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_echo_client_entry.c
new file mode 100644
index 00000000..3afe667e
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_echo_client_entry.c
@@ -0,0 +1,595 @@
+#include "tls_test_frame.h"
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+#include "nx_crypto_ecdh.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+NX_SECURE_X509_CERT trusted_certificate;
+NX_SECURE_X509_CERT client_local_certificate;
+NX_SECURE_TLS_CRYPTO tls_ciphers_client;
+NX_SECURE_TLS_CIPHERSUITE_INFO ciphersuite_table_client[10];
+
+UCHAR tls_packet_buffer[4000];
+
+#define CIPHERSUITE_INIT(p, s, c, v) {p, sizeof(p) / sizeof(UINT), s, c, v}
+#define CERTIFICATE_INIT(s, k, c, t) {s, sizeof(s), k, sizeof(k), c, sizeof(c), t}
+
+typedef struct
+{
+ UCHAR *server_cert;
+ UINT server_cert_len;
+ UCHAR *server_key;
+ UINT server_key_len;
+ UCHAR *ca_cert;
+ UINT ca_cert_len;
+ UINT key_type;
+} CERTIFICATE;
+
+typedef struct
+{
+ UINT *list;
+ UINT count;
+ UINT session_succ;
+ CERTIFICATE *cert;
+ USHORT version;
+} CIPHERSUITE;
+
+#include "../../nx_secure_test/ecc_certs.c"
+#include "../../nx_secure_test/test_ca_cert.c"
+#include "../../nx_secure_test/test_device_cert.c"
+
+extern NX_CRYPTO_METHOD crypto_method_ec_secp192;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp224;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp256;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp384;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp521;
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+
+#if defined(NX_SECURE_TLS_ENABLE_TLS_1_0) || defined(NX_SECURE_TLS_ENABLE_TLS_1_1)
+extern NX_CRYPTO_METHOD crypto_method_rsa;
+extern NX_CRYPTO_METHOD crypto_method_md5;
+extern NX_CRYPTO_METHOD crypto_method_sha1;
+extern NX_CRYPTO_METHOD crypto_method_sha224;
+extern NX_CRYPTO_METHOD crypto_method_sha256;
+extern NX_CRYPTO_METHOD crypto_method_sha384;
+extern NX_CRYPTO_METHOD crypto_method_sha512;
+extern NX_CRYPTO_METHOD crypto_method_aes_cbc_128;
+extern NX_CRYPTO_METHOD crypto_method_aes_cbc_256;
+extern NX_CRYPTO_METHOD crypto_method_hmac_sha1;
+extern NX_CRYPTO_METHOD crypto_method_hmac_sha256;
+extern NX_CRYPTO_METHOD crypto_method_hkdf_sha256;
+extern NX_CRYPTO_METHOD crypto_method_tls_prf_1;
+extern NX_CRYPTO_METHOD crypto_method_tls_prf_sha256;
+extern NX_CRYPTO_METHOD crypto_method_hkdf;
+extern NX_CRYPTO_METHOD crypto_method_hmac;
+extern NX_CRYPTO_METHOD crypto_method_ecdhe;
+extern NX_CRYPTO_METHOD crypto_method_ecdsa;
+
+NX_SECURE_X509_CRYPTO _nx_crypto_x509_cipher_lookup_table_ecc[] =
+{
+ /* OID identifier, public cipher, hash method */
+ {NX_SECURE_TLS_X509_TYPE_ECDSA_SHA_256, &crypto_method_ecdsa, &crypto_method_sha256},
+ {NX_SECURE_TLS_X509_TYPE_ECDSA_SHA_384, &crypto_method_ecdsa, &crypto_method_sha384},
+ {NX_SECURE_TLS_X509_TYPE_ECDSA_SHA_512, &crypto_method_ecdsa, &crypto_method_sha512},
+ {NX_SECURE_TLS_X509_TYPE_RSA_SHA_256, &crypto_method_rsa, &crypto_method_sha256},
+ {NX_SECURE_TLS_X509_TYPE_RSA_SHA_384, &crypto_method_rsa, &crypto_method_sha384},
+ {NX_SECURE_TLS_X509_TYPE_RSA_SHA_512, &crypto_method_rsa, &crypto_method_sha512},
+ {NX_SECURE_TLS_X509_TYPE_ECDSA_SHA_224, &crypto_method_ecdsa, &crypto_method_sha224},
+ {NX_SECURE_TLS_X509_TYPE_ECDSA_SHA_1, &crypto_method_ecdsa, &crypto_method_sha1},
+ {NX_SECURE_TLS_X509_TYPE_RSA_SHA_1, &crypto_method_rsa, &crypto_method_sha1},
+ {NX_SECURE_TLS_X509_TYPE_RSA_MD5, &crypto_method_rsa, &crypto_method_md5},
+};
+
+/* Ciphersuite table with ECC. */
+static NX_SECURE_TLS_CIPHERSUITE_INFO _nx_crypto_ciphersuite_lookup_table_ecc[] =
+{
+ /* Ciphersuite, public cipher, public_auth, session cipher & cipher mode, iv size, key size, hash method, hash size, TLS PRF */
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ {TLS_AES_128_GCM_SHA256, &crypto_method_ecdhe, &crypto_method_ecdsa, &crypto_method_aes_128_gcm_16, 96, 16, &crypto_method_sha256, 32, &crypto_method_hkdf},
+ {TLS_AES_128_CCM_SHA256, &crypto_method_ecdhe, &crypto_method_ecdsa, &crypto_method_aes_ccm_16, 96, 16, &crypto_method_sha256, 32, &crypto_method_hkdf},
+ {TLS_AES_128_CCM_8_SHA256, &crypto_method_ecdhe, &crypto_method_ecdsa, &crypto_method_aes_ccm_8, 96, 16, &crypto_method_sha256, 32, &crypto_method_hkdf},
+#endif
+
+#ifdef NX_SECURE_ENABLE_AEAD_CIPHER
+ {TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, &crypto_method_ecdhe, &crypto_method_ecdsa, &crypto_method_aes_128_gcm_16, 16, 16, &crypto_method_null, 0, &crypto_method_tls_prf_sha256},
+ {TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256, &crypto_method_ecdhe, &crypto_method_rsa, &crypto_method_aes_128_gcm_16, 16, 16, &crypto_method_null, 0, &crypto_method_tls_prf_sha256},
+#endif /* NX_SECURE_ENABLE_AEAD_CIPHER */
+
+ {TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256, &crypto_method_ecdhe, &crypto_method_ecdsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha256, 32, &crypto_method_tls_prf_sha256},
+ {TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256, &crypto_method_ecdhe, &crypto_method_rsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha256, 32, &crypto_method_tls_prf_sha256},
+ {TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA, &crypto_method_ecdhe, &crypto_method_ecdsa, &crypto_method_aes_cbc_256, 16, 32, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+ {TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA, &crypto_method_ecdhe, &crypto_method_rsa, &crypto_method_aes_cbc_256, 16, 32, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+ {TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA, &crypto_method_ecdhe, &crypto_method_ecdsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+ {TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA, &crypto_method_ecdhe, &crypto_method_rsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+
+#ifdef NX_SECURE_ENABLE_AEAD_CIPHER
+ {TLS_RSA_WITH_AES_128_GCM_SHA256, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_128_gcm_16, 16, 16, &crypto_method_null, 0, &crypto_method_tls_prf_sha256},
+#endif /* NX_SECURE_ENABLE_AEAD_CIPHER */
+
+ {TLS_RSA_WITH_AES_256_CBC_SHA256, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_256, 16, 32, &crypto_method_hmac_sha256, 32, &crypto_method_tls_prf_sha256},
+ {TLS_RSA_WITH_AES_128_CBC_SHA256, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha256, 32, &crypto_method_tls_prf_sha256},
+ {TLS_RSA_WITH_AES_256_CBC_SHA, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_256, 16, 32, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+ {TLS_RSA_WITH_AES_128_CBC_SHA, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+
+};
+
+static const UINT _nx_crypto_ciphersuite_lookup_table_ecc_size = sizeof(_nx_crypto_ciphersuite_lookup_table_ecc) / sizeof(NX_SECURE_TLS_CIPHERSUITE_INFO);
+
+
+/* Define the object we can pass into TLS. */
+static const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc =
+{
+ /* Ciphersuite lookup table and size. */
+ _nx_crypto_ciphersuite_lookup_table_ecc,
+ sizeof(_nx_crypto_ciphersuite_lookup_table_ecc) / sizeof(NX_SECURE_TLS_CIPHERSUITE_INFO),
+
+#ifndef NX_SECURE_DISABLE_X509
+ /* X.509 certificate cipher table and size. */
+ _nx_crypto_x509_cipher_lookup_table_ecc,
+ sizeof(_nx_crypto_x509_cipher_lookup_table_ecc) / sizeof(NX_SECURE_X509_CRYPTO),
+#endif
+
+ /* TLS version-specific methods. */
+#if (NX_SECURE_TLS_TLS_1_0_ENABLED || NX_SECURE_TLS_TLS_1_1_ENABLED)
+ &crypto_method_md5,
+ &crypto_method_sha1,
+ &crypto_method_tls_prf_1,
+#endif
+
+#if (NX_SECURE_TLS_TLS_1_2_ENABLED)
+ &crypto_method_sha256,
+ &crypto_method_tls_prf_sha256,
+#endif
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ &crypto_method_hkdf,
+ &crypto_method_hmac,
+ &crypto_method_ecdhe,
+#endif
+
+
+};
+
+#else
+extern NX_SECURE_TLS_CIPHERSUITE_INFO _nx_crypto_ciphersuite_lookup_table_ecc[];
+extern const UINT _nx_crypto_ciphersuite_lookup_table_ecc_size;
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+#endif
+
+static CERTIFICATE test_certs[] =
+{
+ CERTIFICATE_INIT(ECTest_der, ECTest_key_der, ECCA_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+ CERTIFICATE_INIT(ECTestServer2_der, ECTestServer2_key_der, ECCA2_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+ CERTIFICATE_INIT(test_device_cert_der, test_device_cert_key_der, test_ca_cert_der, NX_SECURE_X509_KEY_TYPE_RSA_PKCS1_DER),
+ CERTIFICATE_INIT(ECTestServer10_der, ECTestServer10_key_der, ECCA2_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+ CERTIFICATE_INIT(ECTestServer6_der, ECTestServer6_key_der, ECCA4_der, NX_SECURE_X509_KEY_TYPE_RSA_PKCS1_DER),
+};
+
+static UINT ciphersuite_list_0[] = {};
+static UINT ciphersuite_list_1[] = {TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA};
+static UINT ciphersuite_list_2[] = {TLS_ECDH_RSA_WITH_AES_128_CBC_SHA};
+static UINT ciphersuite_list_3[] = {TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256};
+static UINT ciphersuite_list_4[] = {TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256};
+static UINT ciphersuite_list_5[] =
+{
+ TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256,
+ TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256,
+ // TLS_ECDH_RSA_WITH_AES_128_CBC_SHA,
+ // TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA
+};
+static UINT ciphersuite_list_6[] = {TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA};
+static UINT ciphersuite_list_7[] = {TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA};
+static UINT ciphersuite_list_8[] = {TLS_ECDH_RSA_WITH_AES_256_CBC_SHA};
+static UINT ciphersuite_list_9[] = {TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA};
+static UINT ciphersuite_list_10[] = {TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256};
+static UINT ciphersuite_list_11[] = {TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384};
+static UINT ciphersuite_list_12[] = {TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256};
+static UINT ciphersuite_list_13[] = {TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA384};
+static UINT ciphersuite_list_14[] = {TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256};
+static UINT ciphersuite_list_15[] = {TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384};
+static UINT ciphersuite_list_16[] = {TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256};
+static UINT ciphersuite_list_17[] = {TLS_ECDH_RSA_WITH_AES_256_CBC_SHA384};
+static UINT ciphersuite_list_18[] = {TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256};
+static UINT ciphersuite_list_19[] = {TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256};
+static UINT ciphersuite_list_20[] = {TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256};
+static UINT ciphersuite_list_21[] = {TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256};
+static UINT ciphersuite_list_22[] = {TLS_AES_128_GCM_SHA256};
+static UINT ciphersuite_list_23[] = {TLS_AES_256_GCM_SHA384};
+static UINT ciphersuite_list_24[] = {TLS_AES_128_CCM_SHA256};
+static UINT ciphersuite_list_25[] = {TLS_AES_128_CCM_8_SHA256};
+
+static CIPHERSUITE ciphersuites_client[] =
+{
+
+ /* Select ciphersuite according to certificate. */
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[0], 0),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1], 0),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[4], 0),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[3], 0),
+
+ /* Select ciphersuite according to certificate.
+ * The order of client ciphersuites are reversed of server. */
+ CIPHERSUITE_INIT(ciphersuite_list_5, NX_TRUE, &test_certs[0], 0),
+ CIPHERSUITE_INIT(ciphersuite_list_5, NX_TRUE, &test_certs[1], 0),
+ CIPHERSUITE_INIT(ciphersuite_list_5, NX_TRUE, &test_certs[4], 0),
+
+ /* Specified ciphersuites. */
+ /*CIPHERSUITE_INIT(ciphersuite_list_1, NX_TRUE, &test_certs[1], 0),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_2, NX_TRUE, &test_certs[0], 0),*/
+ CIPHERSUITE_INIT(ciphersuite_list_3, NX_TRUE, &test_certs[1], 0),
+ CIPHERSUITE_INIT(ciphersuite_list_4, NX_TRUE, &test_certs[4], 0),
+
+ /* The Server cert supports ECDH_ECDSA and ECDHE_ECDSA. */
+ /*CIPHERSUITE_INIT(ciphersuite_list_1, NX_TRUE, &test_certs[1], 0),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_2, NX_FALSE, &test_certs[1], 0),*/ /* ECDH_RSA not supported. */
+ CIPHERSUITE_INIT(ciphersuite_list_3, NX_TRUE, &test_certs[1], 0),
+ CIPHERSUITE_INIT(ciphersuite_list_4, NX_FALSE, &test_certs[1], 0), /* ECDHE_RSA not supported. */
+
+ /* Let the server pickup supported ciphersuite. */
+ /*CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1], 0),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[0], 0),*/
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1], 0),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[4], 0),
+
+ /* AES256 or SHA256 or SHA384 ciphersuites. */
+ /*CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1], 0),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1], 0),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[0], 0),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[4], 0),*/
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1], 0),
+ /*CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1], 0),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1], 0),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1], 0),*/
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[4], 0),
+ /*CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[4], 0),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[0], 0),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[0], 0),*/
+
+#ifdef NX_SECURE_TLS_ENABLE_TLS_1_0
+
+ /* Specified ciphersuites. */
+ /*CIPHERSUITE_INIT(ciphersuite_list_1, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_0),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_2, NX_TRUE, &test_certs[0], NX_SECURE_TLS_VERSION_TLS_1_0),*/
+ CIPHERSUITE_INIT(ciphersuite_list_7, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_0),
+ CIPHERSUITE_INIT(ciphersuite_list_9, NX_TRUE, &test_certs[4], NX_SECURE_TLS_VERSION_TLS_1_0),
+
+#endif /* NX_SECURE_TLS_ENABLE_TLS_1_0 */
+
+#ifdef NX_SECURE_TLS_ENABLE_TLS_1_1
+ /* Specified ciphersuites. */
+ /*CIPHERSUITE_INIT(ciphersuite_list_1, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_1),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_2, NX_TRUE, &test_certs[0], NX_SECURE_TLS_VERSION_TLS_1_1),*/
+ CIPHERSUITE_INIT(ciphersuite_list_7, NX_TRUE, &test_certs[1], NX_SECURE_TLS_VERSION_TLS_1_1),
+ CIPHERSUITE_INIT(ciphersuite_list_9, NX_TRUE, &test_certs[4], NX_SECURE_TLS_VERSION_TLS_1_1),
+#endif /* NX_SECURE_TLS_ENABLE_TLS_1_1 */
+
+#ifdef NX_SECURE_ENABLE_AEAD_CIPHER
+ /* AES128-GCM ciphersuites. */
+ CIPHERSUITE_INIT(ciphersuite_list_18, NX_TRUE, &test_certs[1], 0),
+ CIPHERSUITE_INIT(ciphersuite_list_19, NX_TRUE, &test_certs[4], 0),
+ /*CIPHERSUITE_INIT(ciphersuite_list_20, NX_TRUE, &test_certs[1], 0),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_21, NX_TRUE, &test_certs[0], 0),*/
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ /* Test TLS 1.3 ciphersuites. */
+ CIPHERSUITE_INIT(ciphersuite_list_22, NX_TRUE, &test_certs[1], 0),
+ CIPHERSUITE_INIT(ciphersuite_list_24, NX_TRUE, &test_certs[1], 0),
+ CIPHERSUITE_INIT(ciphersuite_list_25, NX_TRUE, &test_certs[1], 0),
+
+ /* Client sends ciphersuites not supported by server. */
+ CIPHERSUITE_INIT(ciphersuite_list_22, NX_FALSE, &test_certs[1], 0),
+#endif
+#endif
+
+
+};
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define an error counter. */
+
+ULONG error_counter;
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+
+static VOID ciphersuites_setup(CIPHERSUITE *ciphersuite, NX_SECURE_TLS_CRYPTO *tls_ciphers,
+ NX_SECURE_TLS_CIPHERSUITE_INFO *ciphersuite_table)
+{
+UINT i;
+UINT status;
+UINT count;
+
+ /* Initialize ciphersuites. */
+ memcpy(tls_ciphers, &nx_crypto_tls_ciphers_ecc, sizeof(NX_SECURE_TLS_CRYPTO));
+ if (ciphersuite -> count > 0)
+ {
+ for (count = 0; count < ciphersuite -> count; count++)
+ {
+ i = 0;
+ while (ciphersuite -> list[count] !=
+ (UINT)_nx_crypto_ciphersuite_lookup_table_ecc[i].nx_secure_tls_ciphersuite)
+ {
+ i++;
+ }
+ memcpy(&ciphersuite_table[count],
+ &_nx_crypto_ciphersuite_lookup_table_ecc[i],
+ sizeof(NX_SECURE_TLS_CIPHERSUITE_INFO));
+ }
+ tls_ciphers -> nx_secure_tls_ciphersuite_lookup_table = ciphersuite_table;
+ tls_ciphers -> nx_secure_tls_ciphersuite_lookup_table_size = count;
+ }
+}
+
+static VOID client_tls_setup(NX_SECURE_TLS_SESSION *tls_session_ptr, CERTIFICATE *cert)
+{
+UINT status;
+
+ status = nx_secure_tls_session_create(tls_session_ptr,
+ &tls_ciphers_client,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_ecc_initialize(tls_session_ptr, nx_crypto_ecc_supported_groups,
+ nx_crypto_ecc_supported_groups_size,
+ nx_crypto_ecc_curves);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ memset(&remote_cert_buffer, 0, sizeof(remote_cert_buffer));
+ memset(&remote_issuer_buffer, 0, sizeof(remote_issuer_buffer));
+ status = nx_secure_tls_remote_certificate_allocate(tls_session_ptr,
+ &remote_certificate,
+ remote_cert_buffer,
+ sizeof(remote_cert_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_remote_certificate_allocate(tls_session_ptr,
+ &remote_issuer,
+ remote_issuer_buffer,
+ sizeof(remote_issuer_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_x509_certificate_initialize(&trusted_certificate,
+ cert -> ca_cert,
+ cert -> ca_cert_len, NX_NULL, 0, NULL, 0, NX_SECURE_X509_KEY_TYPE_NONE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_trusted_certificate_add(tls_session_ptr,
+ &trusted_certificate);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ if (cert != NX_NULL)
+ {
+ memset(&client_local_certificate, 0, sizeof(client_local_certificate));
+ status = nx_secure_x509_certificate_initialize(&client_local_certificate,
+ cert -> server_cert, cert -> server_cert_len,
+ NX_NULL, 0, cert -> server_key,
+ cert -> server_key_len,
+ cert -> key_type);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_local_certificate_add(tls_session_ptr,
+ &client_local_certificate);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+ }
+
+ status = nx_secure_tls_session_packet_buffer_set(tls_session_ptr, tls_packet_buffer,
+ sizeof(tls_packet_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+}
+
+
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+
+}
+
+void tx_application_define(void *first_unused_memory)
+{
+ULONG gateway_ipv4_address;
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+UINT i;
+NX_PARAMETER_NOT_USED(thread_input);
+
+ /* Address of remote server. */
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+
+ /* Setup this thread to bind to a port. */
+ status = nx_tcp_client_socket_bind(&tcp_socket, 0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+
+ for (i = 0; i < sizeof(ciphersuites_client) / sizeof(CIPHERSUITE); i++)
+ {
+
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tx_thread_sleep(20 * NX_IP_PERIODIC_RATE);
+
+ ciphersuites_setup(&ciphersuites_client[i], &tls_ciphers_client, ciphersuite_table_client);
+
+ client_tls_setup(&tls_session, ciphersuites_client[i].cert);
+
+ if (ciphersuites_client[i].version)
+ {
+ status = nx_secure_tls_session_protocol_version_override(&tls_session, ciphersuites_client[i].version);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+ }
+
+ /* Attempt to connect the echo server. */
+ status = nx_tcp_client_socket_connect(&tcp_socket, REMOTE_IP_ADDRESS_NUMBER, DEVICE_SERVER_PORT, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ if (((status && ciphersuites_client[i].session_succ) ||
+ (!status && !ciphersuites_client[i].session_succ)))
+ {
+ printf("SESSION START status = %d\n", status);
+ }
+ exit_if_fail(!((status && ciphersuites_client[i].session_succ) ||
+ (!status && !ciphersuites_client[i].session_succ)), TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ if (!status)
+ {
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send "hello" message. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Receive the echoed and reversed data, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Extract data received from server. */
+ status = nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Release the receive packet. */
+ nx_packet_release(receive_packet);
+
+ /* Check the reverse text received from openssl server. */
+ exit_if_fail('o' == ((CHAR*)receive_buffer)[0], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[1], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[2], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('e' == ((CHAR*)receive_buffer)[3], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('h' == ((CHAR*)receive_buffer)[4], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('\n' == ((CHAR*)receive_buffer)[5], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail(6 == bytes, TLS_TEST_UNKNOWN_TYPE_ERROR);
+ }
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ nx_secure_tls_session_end(&tls_session, NX_NO_WAIT);
+ nx_secure_tls_session_delete(&tls_session);
+
+ /* Close the TCP connection. */
+ nx_tcp_socket_disconnect(&tcp_socket, NX_NO_WAIT);
+ }
+
+
+ /* Unbind the TCP socket from our port. */
+ status = nx_tcp_client_socket_unbind(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Delete the TCP socket instance to clean up. */
+ status = nx_tcp_socket_delete(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ exit(0);
+}
+#else
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+
+}
+#endif
diff --git a/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_echo_server_entry.c
new file mode 100644
index 00000000..fcd0faa8
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_echo_server_entry.c
@@ -0,0 +1,215 @@
+#include "tls_test_frame.h"
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+#include "nx_crypto_ecdh.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Define the ThreadX and NetX object control blocks... */
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT certificate;
+
+UCHAR tls_packet_buffer[4000];
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+void server_thread_entry(ULONG thread_input);
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+
+#include "../../nx_secure_test/ecc_certs.c"
+
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+
+
+/* Define the pointer of current instance control block. */
+static TLS_TEST_INSTANCE* demo_instance_ptr;
+
+/* Define external references. */
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Instance one test entry. */
+INT nx_secure_ecc_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+
+ /* Get instance pointer. */
+ demo_instance_ptr = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+}
+
+/* Define what the initial system looks like. */
+void tx_application_define(void *first_unused_memory)
+{
+ ULONG gateway_ipv4_address;
+ UINT status;
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL, &pool_0, _nx_pcap_network_driver, (UCHAR*)ip_thread_stack, sizeof(ip_thread_stack), 1);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ tx_thread_create(&demo_thread, "demo thread", server_thread_entry, 0, demo_thread_stack, sizeof(demo_thread_stack), 16, 16, 4, TX_AUTO_START);
+}
+
+/* TLS Server example application thread. */
+void server_thread_entry(ULONG thread_input)
+{
+ INT i = 0, status = 0;
+ ULONG actual_status;
+ NX_PACKET *receive_packet;
+ NX_PACKET *send_packet;
+ UCHAR receive_buffer[100];
+ ULONG bytes;
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Server Socket",
+ NX_IP_NORMAL, NX_FRAGMENT_OKAY /*NX_DONT_FRAGMENT*/, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_session_create(&tls_session,
+ &nx_crypto_tls_ciphers_ecc,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Initialize ECC tables. */
+ status = nx_secure_tls_ecc_initialize(&tls_session, nx_crypto_ecc_supported_groups,
+ nx_crypto_ecc_supported_groups_size,
+ nx_crypto_ecc_curves);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(&tls_session, tls_packet_buffer, sizeof(tls_packet_buffer));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ memset(&certificate, 0, sizeof(certificate));
+ nx_secure_x509_certificate_initialize(&certificate,
+ ECTestServer2_der, ECTestServer2_der_len,
+ NX_NULL, 0, ECTestServer2_key_der,
+ ECTestServer2_key_der_len,
+ NX_SECURE_X509_KEY_TYPE_EC_DER);
+ nx_secure_tls_local_certificate_add(&tls_session, &certificate);
+
+ /* Setup this thread to listen. */
+ status = nx_tcp_server_socket_listen(&ip_0, DEVICE_SERVER_PORT, &tcp_socket, 5, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Post semaphore before accept sockets. */
+ print_error_message("Connection %d: server is prepared. Post the semaphore.\n", i);
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Accept a client socket connection. */
+ print_error_message("Connection %d: wait for connections.\n", i);
+ status = nx_tcp_server_socket_accept(&tcp_socket, NX_WAIT_FOREVER);
+ print_error_message("Connection %d: server accept.\n", i);
+ exit_if_fail( NX_SUCCESS == status, 1);
+
+ /* Start the TLS Session now that we have a connected socket. */
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 2);
+
+ /* Receive the HTTP request, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 3);
+
+ /* Show received data. */
+ nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ receive_buffer[bytes] = 0;
+ print_error_message("Received data: %s\n", receive_buffer);
+
+ /* Allocate a return packet and send our HTML data back to the client. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 4);
+
+ /* Echo the message received. */
+ status = nx_packet_data_append(send_packet, receive_buffer, bytes, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 5);
+
+ /* TLS send the HTML/HTTPS data back to the client. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ /* Exit the test process directly without release packet. */
+ exit_if_fail( NX_SUCCESS == status, 6);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 7);
+
+ /* Disconnect the TCP socket, closing the connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 8);
+
+ /* Unaccept the server socket. */
+ status = nx_tcp_server_socket_unaccept(&tcp_socket);
+ exit_if_fail( NX_SUCCESS == status, 9);
+
+ print_error_message("Connection %d: server unaccept, sleeping...\n", i);
+ tx_thread_sleep( 500);
+
+ /* Setup server socket for listening again. */
+ status = nx_tcp_server_socket_relisten(&ip_0, DEVICE_SERVER_PORT, &tcp_socket);
+ exit_if_fail( NX_SUCCESS == status, 10);
+
+ exit(0);
+}
+#else
+
+/* Instance one test entry. */
+INT nx_secure_ecc_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+ exit(TLS_TEST_NOT_AVAILABLE);
+}
+#endif
diff --git a/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_server_cert_entry.c b/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_server_cert_entry.c
new file mode 100644
index 00000000..464b38ed
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_server_cert_entry.c
@@ -0,0 +1,231 @@
+/* This test concentrates on TLS ciphersuite TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA. The client certificate is require. */
+#include "tls_test_frame.h"
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) && defined(NX_SECURE_ENABLE_CLIENT_CERTIFICATE_VERIFY)
+#include "nx_crypto_ecdh.h"
+#include "../../nx_secure_test/ecc_certs.c"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Define the ThreadX and NetX object control blocks... */
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT server_trusted_ca;
+NX_SECURE_X509_CERT server_remote_cert;
+NX_SECURE_X509_CERT server_local_certificate;
+
+UCHAR tls_packet_buffer[4000];
+UCHAR server_cert_buffer[2048];
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+void server_thread_entry(ULONG thread_input);
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+
+/* Define the pointer of current instance control block. */
+static TLS_TEST_INSTANCE* demo_instance_ptr;
+
+/* Define external references. */
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Instance one test entry. */
+INT nx_secure_ecc_server_cert_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+
+ /* Get instance pointer. */
+ demo_instance_ptr = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+}
+
+/* Define what the initial system looks like. */
+void tx_application_define(void *first_unused_memory)
+{
+ ULONG gateway_ipv4_address;
+ UINT status;
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL, &pool_0, _nx_pcap_network_driver, (UCHAR*)ip_thread_stack, sizeof(ip_thread_stack), 1);
+print_error_message( "ip address number: %lu", TLS_TEST_IP_ADDRESS_NUMBER);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ tx_thread_create(&demo_thread, "demo thread", server_thread_entry, 0, demo_thread_stack, sizeof(demo_thread_stack), 16, 16, 4, TX_AUTO_START);
+}
+
+/* TLS Server example application thread. */
+void server_thread_entry(ULONG thread_input)
+{
+ INT status = 0;
+ ULONG actual_status;
+ NX_PACKET *receive_packet;
+ NX_PACKET *send_packet;
+ UCHAR receive_buffer[100];
+ ULONG bytes;
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Server Socket",
+ NX_IP_NORMAL, NX_FRAGMENT_OKAY /*NX_DONT_FRAGMENT*/, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_session_create(&tls_session,
+ &nx_crypto_tls_ciphers_ecc,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Initialize ECC tables. */
+ status = nx_secure_tls_ecc_initialize(&tls_session, nx_crypto_ecc_supported_groups,
+ nx_crypto_ecc_supported_groups_size,
+ nx_crypto_ecc_curves);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Enable Client Certificate Verification. */
+ status = nx_secure_tls_session_client_verify_enable(&tls_session);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(&tls_session, tls_packet_buffer, sizeof(tls_packet_buffer));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ memset(&server_remote_cert, 0, sizeof(server_remote_cert));
+ status = nx_secure_tls_remote_certificate_allocate(&tls_session,
+ &server_remote_cert,
+ server_cert_buffer,
+ sizeof(server_cert_buffer));
+
+ memset(&server_local_certificate, 0, sizeof(server_local_certificate));
+ status = nx_secure_x509_certificate_initialize(&server_local_certificate,
+ ECTestServer2_der, ECTestServer2_der_len,
+ NX_NULL, 0, ECTestServer2_key_der,
+ ECTestServer2_key_der_len,
+ NX_SECURE_X509_KEY_TYPE_EC_DER);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_local_certificate_add(&tls_session,
+ &server_local_certificate);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_x509_certificate_initialize(&server_trusted_ca, ECCA4_der, ECCA4_der_len,
+ NX_NULL, 0, NULL, 0,
+ NX_SECURE_X509_KEY_TYPE_NONE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_trusted_certificate_add(&tls_session,
+ &server_trusted_ca);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Setup this thread to listen. */
+ status = nx_tcp_server_socket_listen(&ip_0, DEVICE_SERVER_PORT, &tcp_socket, 5, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Post semaphore before accept sockets. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Accept a client socket connection. */
+ status = nx_tcp_server_socket_accept(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 1);
+
+ /* Start the TLS Session now that we have a connected socket. */
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 2);
+
+ /* Receive the HTTP request, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 3);
+
+ /* Show received data. */
+ nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ receive_buffer[bytes] = 0;
+ print_error_message("Received data: %s\n", receive_buffer);
+
+ /* Allocate a return packet and send our HTML data back to the client. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 4);
+
+ /* Echo the message received. */
+ status = nx_packet_data_append(send_packet, receive_buffer, bytes, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 5);
+
+ /* TLS send the HTML/HTTPS data back to the client. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ /* Exit the test process directly without release packet. */
+ exit_if_fail( NX_SUCCESS == status, 6);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 7);
+
+ /* Disconnect the TCP socket, closing the connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 8);
+
+ /* Unaccept the server socket. */
+ status = nx_tcp_server_socket_unaccept(&tcp_socket);
+ exit_if_fail( NX_SUCCESS == status, 9);
+
+ exit(0);
+}
+#else
+
+/* Instance one test entry. */
+INT nx_secure_ecc_server_cert_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+ exit(TLS_TEST_NOT_AVAILABLE);
+}
+#endif
diff --git a/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_server_ciphersuites_entry.c b/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_server_ciphersuites_entry.c
new file mode 100644
index 00000000..01b9e0eb
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_server_ciphersuites_entry.c
@@ -0,0 +1,391 @@
+/* This test concentrates on TLS ECC ciphersuites negotiation. */
+#include "tls_test_frame.h"
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+#include "nx_crypto_ecdh.h"
+#include "../../nx_secure_test/ecc_certs.c"
+#include "../../nx_secure_test/test_ca_cert.c"
+#include "../../nx_secure_test/test_device_cert.c"
+
+#define NUM_PACKETS 24
+#define PACKET_SIZE 1536
+#define PACKET_POOL_SIZE (NUM_PACKETS * (PACKET_SIZE + sizeof(NX_PACKET)))
+#define THREAD_STACK_SIZE 1024
+#define ARP_CACHE_SIZE 1024
+#define BUFFER_SIZE 64
+#define METADATA_SIZE 16000
+#define CERT_BUFFER_SIZE 2048
+#define CIPHERSUITE_INIT(p, s, c) {p, sizeof(p) / sizeof(UINT), s, c}
+#define CERTIFICATE_INIT(s, k, c, t) {s, sizeof(s), k, sizeof(k), c, sizeof(c), t}
+
+typedef struct
+{
+ UCHAR *server_cert;
+ UINT server_cert_len;
+ UCHAR *server_key;
+ UINT server_key_len;
+ UCHAR *ca_cert;
+ UINT ca_cert_len;
+ UINT key_type;
+} CERTIFICATE;
+
+typedef struct
+{
+ UINT *list;
+ UINT count;
+ UINT session_succ;
+ CERTIFICATE *cert;
+} CIPHERSUITE;
+
+/* Define the ThreadX and NetX object control blocks... */
+
+static TX_THREAD thread_0;
+static NX_PACKET_POOL pool_0;
+static NX_IP ip_0;
+
+static NX_TCP_SOCKET server_socket_0;
+static NX_SECURE_TLS_SESSION tls_server_session_0;
+static NX_SECURE_X509_CERT server_local_certificate;
+static NX_SECURE_TLS_CRYPTO tls_ciphers_server;
+static NX_SECURE_TLS_CIPHERSUITE_INFO
+ ciphersuite_table_server[10];
+
+static ULONG pool_0_memory[PACKET_POOL_SIZE / sizeof(ULONG)];
+static ULONG thread_0_stack[THREAD_STACK_SIZE / sizeof(ULONG)];
+static ULONG ip_0_stack[THREAD_STACK_SIZE / sizeof(ULONG)];
+static ULONG arp_cache[ARP_CACHE_SIZE];
+static UCHAR server_metadata[METADATA_SIZE];
+
+static UCHAR tls_packet_buffer[4000];
+static UCHAR response_buffer[100];
+
+extern NX_CRYPTO_METHOD crypto_method_ec_secp192;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp224;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp256;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp384;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp521;
+extern NX_SECURE_TLS_CIPHERSUITE_INFO _nx_crypto_ciphersuite_lookup_table_ecc[];
+extern const UINT _nx_crypto_ciphersuite_lookup_table_ecc_size;
+extern NX_SECURE_X509_CRYPTO _nx_crypto_x509_cipher_lookup_table_ecc[];
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+
+static CERTIFICATE test_certs[] =
+{
+ CERTIFICATE_INIT(ECTest_der, ECTest_key_der, ECCA_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+ CERTIFICATE_INIT(ECTestServer2_der, ECTestServer2_key_der, ECCA2_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+ CERTIFICATE_INIT(test_device_cert_der, test_device_cert_key_der, test_ca_cert_der, NX_SECURE_X509_KEY_TYPE_RSA_PKCS1_DER),
+ CERTIFICATE_INIT(ECTestServer10_der, ECTestServer10_key_der, ECCA2_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+};
+
+static UINT ciphersuite_list_0[] = {};
+static UINT ciphersuite_list_1[] = {TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA};
+static UINT ciphersuite_list_2[] = {TLS_ECDH_RSA_WITH_AES_128_CBC_SHA};
+static UINT ciphersuite_list_3[] = {TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256};
+static UINT ciphersuite_list_4[] = {TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256};
+static UINT ciphersuite_list_5[] =
+{
+ TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA,
+ TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA,
+ TLS_ECDH_RSA_WITH_AES_128_CBC_SHA,
+ TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA
+};
+static UINT ciphersuite_list_6[] = {TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA};
+static UINT ciphersuite_list_7[] = {TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA};
+static UINT ciphersuite_list_8[] = {TLS_ECDH_RSA_WITH_AES_256_CBC_SHA};
+static UINT ciphersuite_list_9[] = {TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA};
+static UINT ciphersuite_list_10[] = {TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256};
+static UINT ciphersuite_list_11[] = {TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384};
+static UINT ciphersuite_list_12[] = {TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256};
+static UINT ciphersuite_list_13[] = {TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA384};
+static UINT ciphersuite_list_14[] = {TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256};
+static UINT ciphersuite_list_15[] = {TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384};
+static UINT ciphersuite_list_16[] = {TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256};
+static UINT ciphersuite_list_17[] = {TLS_ECDH_RSA_WITH_AES_256_CBC_SHA384};
+static UINT ciphersuite_list_18[] = {TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256};
+static UINT ciphersuite_list_19[] = {TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256};
+static UINT ciphersuite_list_20[] = {TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256};
+static UINT ciphersuite_list_21[] = {TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256};
+static UINT ciphersuite_list_22[] = {TLS_AES_128_GCM_SHA256};
+static UINT ciphersuite_list_23[] = {TLS_AES_256_GCM_SHA384};
+static UINT ciphersuite_list_24[] = {TLS_AES_128_CCM_SHA256};
+static UINT ciphersuite_list_25[] = {TLS_AES_128_CCM_8_SHA256};
+
+static CIPHERSUITE ciphersuites_server[] =
+{
+
+ /* Select ciphersuite according to certificate. */
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[0]),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1]),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[2]),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[3]),
+
+ /* Select ciphersuite according to certificate.
+ * The order of client ciphersuites are reversed of server. */
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[0]),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1]),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[2]),
+
+ /* Specified ciphersuites. */
+ /* CIPHERSUITE_INIT(ciphersuite_list_1, NX_TRUE, &test_certs[1]), */
+ /* CIPHERSUITE_INIT(ciphersuite_list_2, NX_TRUE, &test_certs[0]), */
+ CIPHERSUITE_INIT(ciphersuite_list_3, NX_TRUE, &test_certs[1]),
+ CIPHERSUITE_INIT(ciphersuite_list_4, NX_TRUE, &test_certs[2]),
+
+ /* The Server cert supports ECDH_ECDSA and ECDHE_ECDSA. */
+ /* CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1]), */
+ /* CIPHERSUITE_INIT(ciphersuite_list_0, NX_FALSE, &test_certs[1]), */
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_TRUE, &test_certs[1]),
+ CIPHERSUITE_INIT(ciphersuite_list_0, NX_FALSE, &test_certs[1]),
+
+ /* Let the server pickup supported ciphersuite. */
+ /* CIPHERSUITE_INIT(ciphersuite_list_1, NX_TRUE, &test_certs[1]),*/
+ /* CIPHERSUITE_INIT(ciphersuite_list_2, NX_TRUE, &test_certs[0]),*/
+ CIPHERSUITE_INIT(ciphersuite_list_3, NX_TRUE, &test_certs[1]),
+ CIPHERSUITE_INIT(ciphersuite_list_4, NX_TRUE, &test_certs[2]),
+
+ /* AES256 or SHA256 or SHA384 ciphersuites. */
+ /* CIPHERSUITE_INIT(ciphersuite_list_6, NX_TRUE, &test_certs[1]), */
+ /* CIPHERSUITE_INIT(ciphersuite_list_7, NX_TRUE, &test_certs[1]), */
+ /* CIPHERSUITE_INIT(ciphersuite_list_8, NX_TRUE, &test_certs[0]), */
+ /* CIPHERSUITE_INIT(ciphersuite_list_9, NX_TRUE, &test_certs[2]), */
+ CIPHERSUITE_INIT(ciphersuite_list_10, NX_TRUE, &test_certs[1]),
+ /*CIPHERSUITE_INIT(ciphersuite_list_11, NX_TRUE, &test_certs[1]),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_12, NX_TRUE, &test_certs[1]),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_13, NX_TRUE, &test_certs[1]),*/
+ CIPHERSUITE_INIT(ciphersuite_list_14, NX_TRUE, &test_certs[2]),
+ /*CIPHERSUITE_INIT(ciphersuite_list_15, NX_TRUE, &test_certs[2]),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_16, NX_TRUE, &test_certs[0]),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_17, NX_TRUE, &test_certs[0]),*/
+
+#ifdef NX_SECURE_ENABLE_AEAD_CIPHER
+ /* AES128-GCM ciphersuites. */
+ CIPHERSUITE_INIT(ciphersuite_list_18, NX_TRUE, &test_certs[1]),
+ CIPHERSUITE_INIT(ciphersuite_list_19, NX_TRUE, &test_certs[2]),
+ /*CIPHERSUITE_INIT(ciphersuite_list_20, NX_TRUE, &test_certs[1]),*/
+ /*CIPHERSUITE_INIT(ciphersuite_list_21, NX_TRUE, &test_certs[0]),*/
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ /* Test TLS 1.3 ciphersuites. */
+ CIPHERSUITE_INIT(ciphersuite_list_22, NX_TRUE, &test_certs[1]),
+ CIPHERSUITE_INIT(ciphersuite_list_24, NX_TRUE, &test_certs[1]),
+ CIPHERSUITE_INIT(ciphersuite_list_25, NX_TRUE, &test_certs[1]),
+
+ /* Client sends ciphersuites not supported by server. */
+ CIPHERSUITE_INIT(ciphersuite_list_22, NX_FALSE, &test_certs[1]),
+#endif
+#endif
+
+};
+
+/* Define thread prototypes. */
+
+static VOID ntest_0_entry(ULONG thread_input);
+extern VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+
+/* Define the pointer of current instance control block. */
+static TLS_TEST_INSTANCE* demo_instance_ptr;
+
+/* Instance one test entry. */
+INT nx_secure_ecc_server_ciphersuites_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+
+ /* Get instance pointer. */
+ demo_instance_ptr = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+}
+
+/* Define what the initial system looks like. */
+
+VOID tx_application_define(void *first_unused_memory)
+{
+UINT status;
+CHAR *pointer;
+
+
+
+ /* Setup the working pointer. */
+ pointer = (CHAR *) first_unused_memory;
+
+ /* Create the server thread. */
+ tx_thread_create(&thread_0, "thread 0", ntest_0_entry, 0,
+ thread_0_stack, sizeof(thread_0_stack),
+ 7, 7, TX_NO_TIME_SLICE, TX_AUTO_START);
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", PACKET_SIZE,
+ pool_0_memory, PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL,
+ &pool_0, _nx_pcap_network_driver,
+ ip_0_stack, sizeof(ip_0_stack), 1);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (VOID *)arp_cache, sizeof(arp_cache));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ nx_secure_tls_initialize();
+}
+
+static VOID ciphersuites_setup(CIPHERSUITE *ciphersuite, NX_SECURE_TLS_CRYPTO *tls_ciphers,
+ NX_SECURE_TLS_CIPHERSUITE_INFO *ciphersuite_table)
+{
+UINT i;
+UINT status;
+UINT count;
+
+ /* Initialize ciphersuites. */
+ memcpy(tls_ciphers, &nx_crypto_tls_ciphers_ecc, sizeof(NX_SECURE_TLS_CRYPTO));
+ if (ciphersuite -> count > 0)
+ {
+ for (count = 0; count < ciphersuite -> count; count++)
+ {
+ i = 0;
+ while (ciphersuite -> list[count] !=
+ (UINT)_nx_crypto_ciphersuite_lookup_table_ecc[i].nx_secure_tls_ciphersuite)
+ {
+ i++;
+ }
+ memcpy(&ciphersuite_table[count],
+ &_nx_crypto_ciphersuite_lookup_table_ecc[i],
+ sizeof(NX_SECURE_TLS_CIPHERSUITE_INFO));
+ }
+ tls_ciphers -> nx_secure_tls_ciphersuite_lookup_table = ciphersuite_table;
+ tls_ciphers -> nx_secure_tls_ciphersuite_lookup_table_size = count;
+ }
+}
+
+static VOID server_tls_setup(NX_SECURE_TLS_SESSION *tls_session_ptr, CERTIFICATE *cert)
+{
+UINT status;
+
+ status = nx_secure_tls_session_create(tls_session_ptr,
+ &tls_ciphers_server,
+ server_metadata,
+ sizeof(server_metadata));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_ecc_initialize(tls_session_ptr, nx_crypto_ecc_supported_groups,
+ nx_crypto_ecc_supported_groups_size,
+ nx_crypto_ecc_curves);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ memset(&server_local_certificate, 0, sizeof(server_local_certificate));
+ status = nx_secure_x509_certificate_initialize(&server_local_certificate,
+ cert -> server_cert, cert -> server_cert_len,
+ NX_NULL, 0, cert -> server_key,
+ cert -> server_key_len,
+ cert -> key_type);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_local_certificate_add(tls_session_ptr,
+ &server_local_certificate);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_session_packet_buffer_set(tls_session_ptr, tls_packet_buffer,
+ sizeof(tls_packet_buffer));
+ show_error_message_if_fail( NX_SUCCESS == status);
+}
+
+static void ntest_0_entry(ULONG thread_input)
+{
+UINT i;
+UINT status;
+ULONG actual_status;
+ULONG response_length;
+NX_PACKET *packet_ptr;
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status,
+ NX_IP_PERIODIC_RATE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Create TCP socket. */
+ status = nx_tcp_socket_create(&ip_0, &server_socket_0, "Server socket", NX_IP_NORMAL,
+ NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 8192, NX_NULL, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_tcp_server_socket_listen(&ip_0, DEVICE_SERVER_PORT, &server_socket_0, 5, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ for (i = 0; i < sizeof(ciphersuites_server) / sizeof(CIPHERSUITE); i++)
+ {
+
+ ciphersuites_setup(&ciphersuites_server[i], &tls_ciphers_server, ciphersuite_table_server);
+
+ server_tls_setup(&tls_server_session_0, ciphersuites_server[i].cert);
+
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ status = nx_tcp_server_socket_accept(&server_socket_0, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 1);
+
+ /* Start TLS session. */
+ status = nx_secure_tls_session_start(&tls_server_session_0, &server_socket_0,
+ NX_WAIT_FOREVER);
+ exit_if_fail (!((status && ciphersuites_server[i].session_succ) ||
+ (!status && !ciphersuites_server[i].session_succ)), 2);
+
+ if (!status)
+ {
+ status = nx_secure_tls_session_receive(&tls_server_session_0, &packet_ptr, NX_WAIT_FOREVER);
+ exit_if_fail ( NX_SUCCESS == status, 3);
+
+ nx_packet_data_retrieve(packet_ptr, response_buffer, &response_length);
+ nx_packet_release(packet_ptr);
+ response_buffer[response_length] = 0;
+ print_error_message("Received data: %s\n", (CHAR *)response_buffer);
+
+ /* Allocate a return packet and send our HTML data back to the client. */
+ status = nx_secure_tls_packet_allocate(&tls_server_session_0, &pool_0, &packet_ptr,
+ NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 4);
+
+ /* Echo the message received. */
+ status = nx_packet_data_append(packet_ptr, response_buffer, response_length, &pool_0,
+ NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 5);
+
+ /* TLS send the HTML/HTTPS data back to the client. */
+ status = nx_secure_tls_session_send(&tls_server_session_0, packet_ptr,
+ NX_IP_PERIODIC_RATE);
+ /* Exit the test process directly without release packet. */
+ exit_if_fail( NX_SUCCESS == status, 6);
+ }
+
+ nx_secure_tls_session_end(&tls_server_session_0, NX_IP_PERIODIC_RATE);
+ nx_secure_tls_session_delete(&tls_server_session_0);
+
+ nx_tcp_socket_disconnect(&server_socket_0, NX_NO_WAIT);
+ nx_tcp_server_socket_unaccept(&server_socket_0);
+ nx_tcp_server_socket_relisten(&ip_0, DEVICE_SERVER_PORT, &server_socket_0);
+ }
+
+ exit(0);
+}
+
+#else
+INT nx_secure_ecc_server_ciphersuites_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+ exit(TLS_TEST_NOT_AVAILABLE);
+}
+#endif
diff --git a/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_server_curves_entry.c b/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_server_curves_entry.c
new file mode 100644
index 00000000..c04d04fd
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/nx_secure_ecc_server_curves_entry.c
@@ -0,0 +1,355 @@
+/* This test concentrates on TLS ECC curve selection. */
+#include "tls_test_frame.h"
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+#include "nx_crypto_ecdh.h"
+#include "../../nx_secure_test/ecc_certs.c"
+
+#define NUM_PACKETS 24
+#define PACKET_SIZE 1536
+#define PACKET_POOL_SIZE (NUM_PACKETS * (PACKET_SIZE + sizeof(NX_PACKET)))
+#define THREAD_STACK_SIZE 1024
+#define ARP_CACHE_SIZE 1024
+#define BUFFER_SIZE 64
+#define METADATA_SIZE 16000
+#define CERT_BUFFER_SIZE 2048
+#define CERTIFICATE_INIT(s, k, c, t) {s, sizeof(s), k, sizeof(k), c, sizeof(c), t}
+#define TEST_CASE_INIT(g, c, s, t) {g, sizeof(g) / sizeof(USHORT),\
+ c, sizeof(c) / sizeof(NX_CRYPTO_METHOD *), s, t}
+
+typedef struct
+{
+ UCHAR *server_cert;
+ UINT server_cert_len;
+ UCHAR *server_key;
+ UINT server_key_len;
+ UCHAR *ca_cert;
+ UINT ca_cert_len;
+ UINT key_type;
+} CERTIFICATE;
+
+typedef struct
+{
+ USHORT *supported_groups;
+ UINT supported_groups_count;
+ const NX_CRYPTO_METHOD **curves;
+ UINT curve_count;
+ UINT session_succ;
+ CERTIFICATE *cert;
+} TEST_CASE;
+
+/* Define the ThreadX and NetX object control blocks... */
+
+static TX_THREAD thread_0;
+static NX_PACKET_POOL pool_0;
+static NX_IP ip_0;
+
+static NX_TCP_SOCKET server_socket_0;
+static NX_SECURE_TLS_SESSION tls_server_session_0;
+static NX_SECURE_X509_CERT server_local_certificate;
+static NX_SECURE_TLS_CRYPTO tls_ciphers_server;
+static NX_SECURE_TLS_CIPHERSUITE_INFO
+ ciphersuite_table_server[10];
+
+static ULONG pool_0_memory[PACKET_POOL_SIZE / sizeof(ULONG)];
+static ULONG thread_0_stack[THREAD_STACK_SIZE / sizeof(ULONG)];
+static ULONG ip_0_stack[THREAD_STACK_SIZE / sizeof(ULONG)];
+static ULONG arp_cache[ARP_CACHE_SIZE];
+static UCHAR server_metadata[METADATA_SIZE];
+
+static UCHAR tls_packet_buffer[4000];
+static UCHAR response_buffer[100];
+
+extern NX_CRYPTO_METHOD crypto_method_ec_secp192;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp224;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp256;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp384;
+extern NX_CRYPTO_METHOD crypto_method_ec_secp521;
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+
+static USHORT supported_groups_0[] =
+{
+ (USHORT)NX_CRYPTO_EC_SECP192R1,
+ (USHORT)NX_CRYPTO_EC_SECP224R1,
+ (USHORT)NX_CRYPTO_EC_SECP256R1,
+ (USHORT)NX_CRYPTO_EC_SECP384R1,
+ (USHORT)NX_CRYPTO_EC_SECP521R1,
+};
+static USHORT supported_groups_1[] = {(USHORT)NX_CRYPTO_EC_SECP192R1};
+static USHORT supported_groups_2[] = {(USHORT)NX_CRYPTO_EC_SECP224R1};
+static USHORT supported_groups_3[] = {(USHORT)NX_CRYPTO_EC_SECP256R1};
+static USHORT supported_groups_4[] = {(USHORT)NX_CRYPTO_EC_SECP384R1};
+static USHORT supported_groups_5[] = {(USHORT)NX_CRYPTO_EC_SECP521R1};
+static USHORT supported_groups_6[] = {(USHORT)NX_CRYPTO_EC_SECP192R1, (USHORT)NX_CRYPTO_EC_SECP256R1};
+static USHORT supported_groups_7[] = {(USHORT)NX_CRYPTO_EC_SECP224R1, (USHORT)NX_CRYPTO_EC_SECP256R1};
+
+static const NX_CRYPTO_METHOD *ecc_curves_0[] =
+{
+ &crypto_method_ec_secp192,
+ &crypto_method_ec_secp224,
+ &crypto_method_ec_secp256,
+ &crypto_method_ec_secp384,
+ &crypto_method_ec_secp521,
+};
+static const NX_CRYPTO_METHOD *ecc_curves_1[] = {&crypto_method_ec_secp192};
+static const NX_CRYPTO_METHOD *ecc_curves_2[] = {&crypto_method_ec_secp224};
+static const NX_CRYPTO_METHOD *ecc_curves_3[] = {&crypto_method_ec_secp256};
+static const NX_CRYPTO_METHOD *ecc_curves_4[] = {&crypto_method_ec_secp384};
+static const NX_CRYPTO_METHOD *ecc_curves_5[] = {&crypto_method_ec_secp521};
+static const NX_CRYPTO_METHOD *ecc_curves_6[] = {&crypto_method_ec_secp192, &crypto_method_ec_secp256};
+static const NX_CRYPTO_METHOD *ecc_curves_7[] = {&crypto_method_ec_secp224, &crypto_method_ec_secp256};
+
+static CERTIFICATE test_certs[] =
+{
+ CERTIFICATE_INIT(ECTestServer9_192_der, ECTestServer9_192_key_der, ECCA2_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+ CERTIFICATE_INIT(ECTestServer8_224_der, ECTestServer8_224_key_der, ECCA2_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+ CERTIFICATE_INIT(ECTestServer2_der, ECTestServer2_key_der, ECCA2_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+ CERTIFICATE_INIT(ECTestServer4_der, ECTestServer4_key_der, ECCA4_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+ CERTIFICATE_INIT(ECTestServer3_der, ECTestServer3_key_der, ECCA3_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+};
+
+static TEST_CASE test_case_server[] =
+{
+
+ /* Select curve by certificate. */
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[0]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[1]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[2]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[3]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[4]),
+
+ /* Specify curve from client. */
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[0]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[1]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[2]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[3]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[4]),
+
+ /* Specify curve from server. */
+ TEST_CASE_INIT(supported_groups_1, ecc_curves_1, NX_TRUE, &test_certs[0]),
+ TEST_CASE_INIT(supported_groups_2, ecc_curves_2, NX_TRUE, &test_certs[1]),
+ TEST_CASE_INIT(supported_groups_3, ecc_curves_3, NX_TRUE, &test_certs[2]),
+ TEST_CASE_INIT(supported_groups_4, ecc_curves_4, NX_TRUE, &test_certs[3]),
+ TEST_CASE_INIT(supported_groups_5, ecc_curves_5, NX_TRUE, &test_certs[4]),
+
+ /* Configure invalid curves at server side. */
+ TEST_CASE_INIT(supported_groups_2, ecc_curves_2, NX_FALSE, &test_certs[0]),
+ TEST_CASE_INIT(supported_groups_3, ecc_curves_3, NX_FALSE, &test_certs[0]),
+ TEST_CASE_INIT(supported_groups_4, ecc_curves_4, NX_FALSE, &test_certs[0]),
+ TEST_CASE_INIT(supported_groups_5, ecc_curves_5, NX_FALSE, &test_certs[0]),
+
+#if 0
+ /* Though the P256 is not in supported list, openssl is still able to verify the issuer. */
+ /* Multiple curves used by server and CA cert. */
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_FALSE, &test_certs[0]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_FALSE, &test_certs[1]),
+#endif
+
+ /* Client curve not supported by server. */
+ TEST_CASE_INIT(supported_groups_1, ecc_curves_1, NX_FALSE, &test_certs[0]),
+ TEST_CASE_INIT(supported_groups_2, ecc_curves_2, NX_FALSE, &test_certs[1]),
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ /* Specify curve from client. */
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[2]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[3]),
+ TEST_CASE_INIT(supported_groups_0, ecc_curves_0, NX_TRUE, &test_certs[4]),
+
+ /* Specify curve from server. */
+ TEST_CASE_INIT(supported_groups_3, ecc_curves_3, NX_TRUE, &test_certs[2]),
+ TEST_CASE_INIT(supported_groups_4, ecc_curves_4, NX_TRUE, &test_certs[3]),
+ TEST_CASE_INIT(supported_groups_5, ecc_curves_5, NX_TRUE, &test_certs[4]),
+
+ /* Configure invalid curves at server side. */
+ TEST_CASE_INIT(supported_groups_4, ecc_curves_4, NX_FALSE, &test_certs[2]),
+ TEST_CASE_INIT(supported_groups_5, ecc_curves_5, NX_FALSE, &test_certs[2]),
+
+ /* Client curve not supported by server. */
+ TEST_CASE_INIT(supported_groups_3, ecc_curves_3, NX_FALSE, &test_certs[2]),
+ TEST_CASE_INIT(supported_groups_4, ecc_curves_4, NX_FALSE, &test_certs[3]),
+#endif
+};
+
+/* Define thread prototypes. */
+
+static VOID ntest_0_entry(ULONG thread_input);
+extern VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+
+/* Define the pointer of current instance control block. */
+static TLS_TEST_INSTANCE* demo_instance_ptr;
+
+/* Instance one test entry. */
+INT nx_secure_ecc_server_curves_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+
+ /* Get instance pointer. */
+ demo_instance_ptr = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+}
+
+/* Define what the initial system looks like. */
+
+VOID tx_application_define(void *first_unused_memory)
+{
+UINT status;
+CHAR *pointer;
+
+
+
+ /* Setup the working pointer. */
+ pointer = (CHAR *) first_unused_memory;
+
+ /* Create the server thread. */
+ tx_thread_create(&thread_0, "thread 0", ntest_0_entry, 0,
+ thread_0_stack, sizeof(thread_0_stack),
+ 7, 7, TX_NO_TIME_SLICE, TX_AUTO_START);
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", PACKET_SIZE,
+ pool_0_memory, PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL,
+ &pool_0, _nx_pcap_network_driver,
+ ip_0_stack, sizeof(ip_0_stack), 1);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (VOID *)arp_cache, sizeof(arp_cache));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ nx_secure_tls_initialize();
+}
+
+static VOID server_tls_setup(NX_SECURE_TLS_SESSION *tls_session_ptr, TEST_CASE *test_case)
+{
+UINT status;
+
+ status = nx_secure_tls_session_create(tls_session_ptr,
+ &nx_crypto_tls_ciphers_ecc,
+ server_metadata,
+ sizeof(server_metadata));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_ecc_initialize(tls_session_ptr, test_case -> supported_groups,
+ test_case -> supported_groups_count,
+ test_case -> curves);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ memset(&server_local_certificate, 0, sizeof(server_local_certificate));
+ status = nx_secure_x509_certificate_initialize(&server_local_certificate,
+ test_case -> cert -> server_cert,
+ test_case -> cert -> server_cert_len,
+ NX_NULL, 0, test_case -> cert -> server_key,
+ test_case -> cert -> server_key_len,
+ test_case -> cert -> key_type);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_local_certificate_add(tls_session_ptr,
+ &server_local_certificate);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_session_packet_buffer_set(tls_session_ptr, tls_packet_buffer,
+ sizeof(tls_packet_buffer));
+ show_error_message_if_fail( NX_SUCCESS == status);
+}
+
+static void ntest_0_entry(ULONG thread_input)
+{
+UINT i;
+UINT status;
+ULONG actual_status;
+ULONG response_length;
+NX_PACKET *packet_ptr;
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status,
+ NX_IP_PERIODIC_RATE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Create TCP socket. */
+ status = nx_tcp_socket_create(&ip_0, &server_socket_0, "Server socket", NX_IP_NORMAL,
+ NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 8192, NX_NULL, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_tcp_server_socket_listen(&ip_0, DEVICE_SERVER_PORT, &server_socket_0, 5, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ for (i = 0; i < sizeof(test_case_server) / sizeof(TEST_CASE); i++)
+ {
+
+ server_tls_setup(&tls_server_session_0, &test_case_server[i]);
+
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ status = nx_tcp_server_socket_accept(&server_socket_0, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 1);
+
+ /* Start TLS session. */
+ status = nx_secure_tls_session_start(&tls_server_session_0, &server_socket_0,
+ NX_WAIT_FOREVER);
+ exit_if_fail (!((status && test_case_server[i].session_succ) ||
+ (!status && !test_case_server[i].session_succ)), 2);
+
+ if (!status)
+ {
+ status = nx_secure_tls_session_receive(&tls_server_session_0, &packet_ptr, NX_WAIT_FOREVER);
+ exit_if_fail ( NX_SUCCESS == status, 3);
+
+ nx_packet_data_retrieve(packet_ptr, response_buffer, &response_length);
+ nx_packet_release(packet_ptr);
+ response_buffer[response_length] = 0;
+ print_error_message("Received data: %s\n", (CHAR *)response_buffer);
+
+ /* Allocate a return packet and send our HTML data back to the client. */
+ status = nx_secure_tls_packet_allocate(&tls_server_session_0, &pool_0, &packet_ptr,
+ NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 4);
+
+ /* Echo the message received. */
+ status = nx_packet_data_append(packet_ptr, response_buffer, response_length, &pool_0,
+ NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 5);
+
+ /* TLS send the HTML/HTTPS data back to the client. */
+ status = nx_secure_tls_session_send(&tls_server_session_0, packet_ptr,
+ NX_IP_PERIODIC_RATE);
+ /* Exit the test process directly without release packet. */
+ exit_if_fail( NX_SUCCESS == status, 6);
+ }
+
+ nx_secure_tls_session_end(&tls_server_session_0, NX_IP_PERIODIC_RATE);
+ nx_secure_tls_session_delete(&tls_server_session_0);
+
+ nx_tcp_socket_disconnect(&server_socket_0, NX_NO_WAIT);
+ nx_tcp_server_socket_unaccept(&server_socket_0);
+ nx_tcp_server_socket_relisten(&ip_0, DEVICE_SERVER_PORT, &server_socket_0);
+ }
+
+ exit(0);
+}
+
+#else
+INT nx_secure_ecc_server_curves_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+ exit(TLS_TEST_NOT_AVAILABLE);
+}
+#endif
diff --git a/test/regression/interoperability_test/nx_secure_test/nx_secure_echo_client_aes128_gcm_entry.c b/test/regression/interoperability_test/nx_secure_test/nx_secure_echo_client_aes128_gcm_entry.c
new file mode 100644
index 00000000..8961dbc6
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/nx_secure_echo_client_aes128_gcm_entry.c
@@ -0,0 +1,242 @@
+#include "tls_test_frame.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+NX_SECURE_X509_CERT trusted_certificate;
+NX_SECURE_TLS_CRYPTO tls_ciphers_client;
+
+UCHAR tls_packet_buffer[4000];
+#include "cert.c"
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define an error counter. */
+
+ULONG error_counter;
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+extern NX_SECURE_TLS_CIPHERSUITE_INFO _nx_crypto_ciphersuite_lookup_table[];
+
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_AEAD_CIPHER)
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
+
+void tx_application_define(void *first_unused_memory)
+{
+ULONG gateway_ipv4_address;
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+static VOID ciphersuites_setup(NX_SECURE_TLS_CRYPTO *tls_ciphers)
+{
+UINT i;
+UINT status;
+UINT count;
+
+ /* Initialize ciphersuites. */
+ memcpy(tls_ciphers, &nx_crypto_tls_ciphers, sizeof(NX_SECURE_TLS_CRYPTO));
+ i = 0;
+ while (TLS_RSA_WITH_AES_128_GCM_SHA256 !=
+ (UINT)_nx_crypto_ciphersuite_lookup_table[i].nx_secure_tls_ciphersuite)
+ {
+ i++;
+ }
+ tls_ciphers -> nx_secure_tls_ciphersuite_lookup_table = &_nx_crypto_ciphersuite_lookup_table[i];
+ tls_ciphers -> nx_secure_tls_ciphersuite_lookup_table_size = 1;
+}
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+NX_PARAMETER_NOT_USED(thread_input);
+
+ /* Address of remote server. */
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a tls session. */
+ ciphersuites_setup(&tls_ciphers_client);
+ status = nx_secure_tls_session_create(&tls_session,
+ &tls_ciphers_client,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(&tls_session, tls_packet_buffer, sizeof(tls_packet_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup this thread to bind to a port. */
+ status = nx_tcp_client_socket_bind(&tcp_socket, 0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Need to allocate space for the certificate coming in from the remote host. */
+ nx_secure_tls_remote_certificate_allocate(&tls_session, &remote_certificate, remote_cert_buffer, sizeof(remote_cert_buffer));
+ nx_secure_tls_remote_certificate_allocate(&tls_session, &remote_issuer, remote_issuer_buffer, sizeof(remote_issuer_buffer));
+
+ /* Added trusted certificates. */
+ status = nx_secure_x509_certificate_initialize(&trusted_certificate, cert_der, cert_der_len,
+ NX_NULL, 0, NULL, 0,
+ NX_SECURE_X509_KEY_TYPE_NONE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_trusted_certificate_add(&tls_session,
+ &trusted_certificate);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tx_thread_sleep(100);
+
+ /* Attempt to connect the echo server. */
+ status = nx_tcp_client_socket_connect(&tcp_socket, REMOTE_IP_ADDRESS_NUMBER, DEVICE_SERVER_PORT, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send "hello" message. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Receive the echoed and reversed data, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Extract data received from server. */
+ status = nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Check the reverse text received from openssl server. */
+ exit_if_fail('o' == ((CHAR*)receive_buffer)[0], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[1], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[2], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('e' == ((CHAR*)receive_buffer)[3], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('h' == ((CHAR*)receive_buffer)[4], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('\n' == ((CHAR*)receive_buffer)[5], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail(6 == bytes, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Close the TCP connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Unbind the TCP socket from our port. */
+ status = nx_tcp_client_socket_unbind(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Delete the TCP socket instance to clean up. */
+ status = nx_tcp_socket_delete(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/nx_secure_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/nx_secure_echo_client_entry.c
new file mode 100644
index 00000000..ca8a8e80
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/nx_secure_echo_client_entry.c
@@ -0,0 +1,221 @@
+#include "tls_test_frame.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+NX_SECURE_X509_CERT trusted_certificate;
+
+UCHAR tls_packet_buffer[4000];
+#include "cert.c"
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define an error counter. */
+
+ULONG error_counter;
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#ifndef NX_SECURE_TLS_CLIENT_DISABLED
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
+
+void tx_application_define(void *first_unused_memory)
+{
+ULONG gateway_ipv4_address;
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+NX_PARAMETER_NOT_USED(thread_input);
+
+ /* Address of remote server. */
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a tls session. */
+ status = nx_secure_tls_session_create(&tls_session,
+ &nx_crypto_tls_ciphers,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(&tls_session, tls_packet_buffer, sizeof(tls_packet_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup this thread to bind to a port. */
+ status = nx_tcp_client_socket_bind(&tcp_socket, 0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Need to allocate space for the certificate coming in from the remote host. */
+ nx_secure_tls_remote_certificate_allocate(&tls_session, &remote_certificate, remote_cert_buffer, sizeof(remote_cert_buffer));
+ nx_secure_tls_remote_certificate_allocate(&tls_session, &remote_issuer, remote_issuer_buffer, sizeof(remote_issuer_buffer));
+
+ /* Added trusted certificates. */
+ status = nx_secure_x509_certificate_initialize(&trusted_certificate, cert_der, cert_der_len,
+ NX_NULL, 0, NULL, 0,
+ NX_SECURE_X509_KEY_TYPE_NONE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_trusted_certificate_add(&tls_session,
+ &trusted_certificate);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tx_thread_sleep(100);
+
+ /* Attempt to connect the echo server. */
+ status = nx_tcp_client_socket_connect(&tcp_socket, REMOTE_IP_ADDRESS_NUMBER, DEVICE_SERVER_PORT, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send "hello" message. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Receive the echoed and reversed data, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Extract data received from server. */
+ status = nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Check the reverse text received from openssl server. */
+ exit_if_fail('o' == ((CHAR*)receive_buffer)[0], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[1], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[2], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('e' == ((CHAR*)receive_buffer)[3], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('h' == ((CHAR*)receive_buffer)[4], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('\n' == ((CHAR*)receive_buffer)[5], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail(6 == bytes, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Close the TCP connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Unbind the TCP socket from our port. */
+ status = nx_tcp_client_socket_unbind(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Delete the TCP socket instance to clean up. */
+ status = nx_tcp_socket_delete(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/nx_secure_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/nx_secure_echo_server_entry.c
new file mode 100644
index 00000000..02728690
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/nx_secure_echo_server_entry.c
@@ -0,0 +1,209 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Define the ThreadX and NetX object control blocks... */
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT certificate;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+NX_SECURE_X509_CERT trusted_certificate;
+
+UCHAR tls_packet_buffer[4000];
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+void server_thread_entry(ULONG thread_input);
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+NX_SECURE_X509_CERT device_issuer_certificate;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+
+#include "ica_test_device_cert.c"
+#include "ica_test_ica_cert.c"
+
+/* Define the pointer of current instance control block. */
+static TLS_TEST_INSTANCE* demo_instance_ptr;
+
+/* Define external references. */
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Instance one test entry. */
+INT nx_secure_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#ifndef NX_SECURE_TLS_SERVER_DISABLED
+
+ /* Get instance pointer. */
+ demo_instance_ptr = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
+
+/* Define what the initial system looks like. */
+void tx_application_define(void *first_unused_memory)
+{
+ ULONG gateway_ipv4_address;
+ UINT status;
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL, &pool_0, _nx_pcap_network_driver, (UCHAR*)ip_thread_stack, sizeof(ip_thread_stack), 1);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ tx_thread_create(&demo_thread, "demo thread", server_thread_entry, 0, demo_thread_stack, sizeof(demo_thread_stack), 16, 16, 4, TX_AUTO_START);
+}
+
+/* TLS Server example application thread. */
+void server_thread_entry(ULONG thread_input)
+{
+ INT i = 0, status = 0;
+ ULONG actual_status;
+ NX_PACKET *receive_packet;
+ NX_PACKET *send_packet;
+ UCHAR receive_buffer[100];
+ ULONG bytes;
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Server Socket",
+ NX_IP_NORMAL, NX_FRAGMENT_OKAY /*NX_DONT_FRAGMENT*/, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_session_create(&tls_session,
+ &nx_crypto_tls_ciphers,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(&tls_session, tls_packet_buffer, sizeof(tls_packet_buffer));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ // Initialize our certificates
+ nx_secure_tls_remote_certificate_allocate(&tls_session, &remote_certificate, remote_cert_buffer, sizeof(remote_cert_buffer));
+ nx_secure_tls_remote_certificate_allocate(&tls_session, &remote_issuer, remote_issuer_buffer, sizeof(remote_issuer_buffer));
+
+ memset(&certificate, 0, sizeof(certificate));
+ nx_secure_x509_certificate_initialize(&certificate, test_device_cert_der, test_device_cert_der_len, NX_NULL, 0, test_device_cert_key_der, test_device_cert_key_der_len, NX_SECURE_X509_KEY_TYPE_RSA_PKCS1_DER);
+ nx_secure_tls_local_certificate_add(&tls_session, &certificate);
+
+ // Initialize the Intermediate CA certificate - it does not have a private RSA key
+ nx_secure_x509_certificate_initialize(&device_issuer_certificate, ica_cert_der, ica_cert_der_len, NX_NULL, 0, NX_NULL, 0, NX_SECURE_X509_KEY_TYPE_NONE);
+ nx_secure_tls_local_certificate_add(&tls_session, &device_issuer_certificate);
+
+ /* Setup this thread to listen. */
+ status = nx_tcp_server_socket_listen(&ip_0, DEVICE_SERVER_PORT, &tcp_socket, 5, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Post semaphore before accept sockets. */
+ print_error_message("Connection %d: server is prepared. Post the semaphore.\n", i);
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Accept a client socket connection. */
+ print_error_message("Connection %d: wait for connections.\n", i);
+ status = nx_tcp_server_socket_accept(&tcp_socket, NX_WAIT_FOREVER);
+ print_error_message("Connection %d: server accept.\n", i);
+ exit_if_fail( NX_SUCCESS == status, 1);
+
+ /* Start the TLS Session now that we have a connected socket. */
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 2);
+
+ /* Receive the HTTP request, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 3);
+
+ /* Show received data. */
+ nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ receive_buffer[bytes] = 0;
+ print_error_message("Received data: %s\n", receive_buffer);
+
+ /* Allocate a return packet and send our HTML data back to the client. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 4);
+
+ /* Echo the message received. */
+ status = nx_packet_data_append(send_packet, receive_buffer, bytes, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 5);
+
+ /* TLS send the HTML/HTTPS data back to the client. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ /* Exit the test process directly without release packet. */
+ exit_if_fail( NX_SUCCESS == status, 6);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 7);
+
+ /* Disconnect the TCP socket, closing the connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 8);
+
+ /* Unaccept the server socket. */
+ status = nx_tcp_server_socket_unaccept(&tcp_socket);
+ exit_if_fail( NX_SUCCESS == status, 9);
+
+ print_error_message("Connection %d: server unaccept, sleeping...\n", i);
+ tx_thread_sleep( 500);
+
+ /* Setup server socket for listening again. */
+ status = nx_tcp_server_socket_relisten(&ip_0, DEVICE_SERVER_PORT, &tcp_socket);
+ exit_if_fail( NX_SUCCESS == status, 10);
+
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/nx_secure_override_tls_1_1_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/nx_secure_override_tls_1_1_echo_client_entry.c
new file mode 100644
index 00000000..d29f7267
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/nx_secure_override_tls_1_1_echo_client_entry.c
@@ -0,0 +1,285 @@
+#include "tls_test_frame.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+NX_SECURE_X509_CERT trusted_certificate;
+
+UCHAR tls_packet_buffer[4000];
+#include "cert.c"
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define an error counter. */
+
+ULONG error_counter;
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+
+
+extern NX_CRYPTO_METHOD crypto_method_rsa;
+extern NX_CRYPTO_METHOD crypto_method_md5;
+extern NX_CRYPTO_METHOD crypto_method_sha1;
+extern NX_CRYPTO_METHOD crypto_method_sha256;
+extern NX_CRYPTO_METHOD crypto_method_aes_cbc_128;
+extern NX_CRYPTO_METHOD crypto_method_aes_cbc_256;
+extern NX_CRYPTO_METHOD crypto_method_hmac_sha1;
+extern NX_CRYPTO_METHOD crypto_method_hkdf_sha256;
+extern NX_CRYPTO_METHOD crypto_method_tls_prf_1;
+extern NX_CRYPTO_METHOD crypto_method_tls_prf_sha256;
+extern NX_CRYPTO_METHOD crypto_method_hkdf;
+extern NX_CRYPTO_METHOD crypto_method_hmac;
+extern NX_CRYPTO_METHOD crypto_method_ecdhe;
+
+NX_SECURE_TLS_CIPHERSUITE_INFO _nx_crypto_ciphersuite_lookup_table_1_0_1_1[] =
+{
+ /* Ciphersuite, public cipher, public_auth, session cipher & cipher mode, iv size, key size, hash method, hash size, TLS PRF */
+ {TLS_RSA_WITH_AES_256_CBC_SHA, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_256, 16, 32, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+ {TLS_RSA_WITH_AES_128_CBC_SHA, &crypto_method_rsa, &crypto_method_rsa, &crypto_method_aes_cbc_128, 16, 16, &crypto_method_hmac_sha1, 20, &crypto_method_tls_prf_sha256},
+};
+
+/* Lookup table for X.509 digital certificates - they need a public-key algorithm and a hash routine for verification. */
+NX_SECURE_X509_CRYPTO _nx_crypto_x509_cipher_lookup_table_1_0_1_1[] =
+{
+ /* OID identifier, public cipher, hash method */
+ {NX_SECURE_TLS_X509_TYPE_RSA_SHA_256, &crypto_method_rsa, &crypto_method_sha256},
+ {NX_SECURE_TLS_X509_TYPE_RSA_SHA_1, &crypto_method_rsa, &crypto_method_sha1},
+ {NX_SECURE_TLS_X509_TYPE_RSA_MD5, &crypto_method_rsa, &crypto_method_md5},
+};
+
+/* Define the object we can pass into TLS. */
+NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_1_0_1_1 =
+{
+ /* Ciphersuite lookup table and size. */
+ _nx_crypto_ciphersuite_lookup_table_1_0_1_1,
+ sizeof(_nx_crypto_ciphersuite_lookup_table_1_0_1_1) / sizeof(NX_SECURE_TLS_CIPHERSUITE_INFO),
+
+#ifndef NX_SECURE_DISABLE_X509
+ /* X.509 certificate cipher table and size. */
+ _nx_crypto_x509_cipher_lookup_table_1_0_1_1,
+ sizeof(_nx_crypto_x509_cipher_lookup_table_1_0_1_1) / sizeof(NX_SECURE_X509_CRYPTO),
+#endif
+
+ /* TLS version-specific methods. */
+#if (NX_SECURE_TLS_TLS_1_0_ENABLED || NX_SECURE_TLS_TLS_1_1_ENABLED)
+ & crypto_method_md5,
+ &crypto_method_sha1,
+ &crypto_method_tls_prf_1,
+#endif
+
+#if (NX_SECURE_TLS_TLS_1_2_ENABLED)
+ &crypto_method_sha256,
+ &crypto_method_tls_prf_sha256,
+#endif
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ &crypto_method_hkdf,
+ &crypto_method_hmac,
+ &crypto_method_ecdhe,
+#endif
+};
+
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#ifndef NX_SECURE_TLS_CLIENT_DISABLED
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
+
+void tx_application_define(void *first_unused_memory)
+{
+ULONG gateway_ipv4_address;
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+NX_PARAMETER_NOT_USED(thread_input);
+
+ /* Address of remote server. */
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a tls session. */
+ status = nx_secure_tls_session_create(&tls_session,
+ &nx_crypto_tls_ciphers_1_0_1_1,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ nx_secure_tls_session_protocol_version_override(&tls_session, NX_SECURE_TLS_VERSION_TLS_1_1);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(&tls_session, tls_packet_buffer, sizeof(tls_packet_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup this thread to bind to a port. */
+ status = nx_tcp_client_socket_bind(&tcp_socket, 0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Need to allocate space for the certificate coming in from the remote host. */
+ nx_secure_tls_remote_certificate_allocate(&tls_session, &remote_certificate, remote_cert_buffer, sizeof(remote_cert_buffer));
+ nx_secure_tls_remote_certificate_allocate(&tls_session, &remote_issuer, remote_issuer_buffer, sizeof(remote_issuer_buffer));
+
+ /* Added trusted certificates. */
+ status = nx_secure_x509_certificate_initialize(&trusted_certificate, cert_der, cert_der_len,
+ NX_NULL, 0, NULL, 0,
+ NX_SECURE_X509_KEY_TYPE_NONE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_trusted_certificate_add(&tls_session,
+ &trusted_certificate);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tx_thread_sleep(100);
+
+ /* Attempt to connect the echo server. */
+ status = nx_tcp_client_socket_connect(&tcp_socket, REMOTE_IP_ADDRESS_NUMBER, DEVICE_SERVER_PORT, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send "hello" message. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Receive the echoed and reversed data, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Extract data received from server. */
+ status = nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Check the reverse text received from openssl server. */
+ exit_if_fail('o' == ((CHAR*)receive_buffer)[0], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[1], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[2], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('e' == ((CHAR*)receive_buffer)[3], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('h' == ((CHAR*)receive_buffer)[4], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('\n' == ((CHAR*)receive_buffer)[5], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail(6 == bytes, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Close the TCP connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Unbind the TCP socket from our port. */
+ status = nx_tcp_client_socket_unbind(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Delete the TCP socket instance to clean up. */
+ status = nx_tcp_socket_delete(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ exit(0);
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/openssl_client_certificate_verify_test_client_entry.c b/test/regression/interoperability_test/nx_secure_test/openssl_client_certificate_verify_test_client_entry.c
new file mode 100644
index 00000000..adc95a56
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/openssl_client_certificate_verify_test_client_entry.c
@@ -0,0 +1,42 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Instance two test entry. */
+INT openssl_echo_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#ifndef NX_SECURE_TLS_SERVER_DISABLED
+
+/* Just use TLSv1.2 */
+CHAR* external_cmd[] = {
+ "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING,
+ "-verify", "10", /* Enabled client certificate verification. */
+ /* This programe must be executed at the directory of cmake_nx_secure_interoperability_test */
+ "-cert", "../../certificates/test_client.crt",
+ "-key", "../../certificates/test_client.key",
+ "-CAfile", "../../certificates/test.crt",
+ (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_FAILED);
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/openssl_client_certificate_verify_test_server_entry.c b/test/regression/interoperability_test/nx_secure_test/openssl_client_certificate_verify_test_server_entry.c
new file mode 100644
index 00000000..6fa7e076
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/openssl_client_certificate_verify_test_server_entry.c
@@ -0,0 +1,42 @@
+#include "tls_test_frame.h"
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+/* Openssl echo server entry. */
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#ifndef NX_SECURE_TLS_CLIENT_DISABLED
+
+INT status, exit_status;
+
+/* Added -rev option to send reverse text received from clients back to the client. Added -naccept 1 to close the server after one tls session. */
+CHAR* external_cmd[] = {
+ "openssl", "s_server", "-rev",
+ "-port", DEVICE_SERVER_PORT_STRING,
+ "-Verify", "10", /* Enabled client certificate verification. */
+ /* This programe must be executed at the directory of cmake_nx_secure_interoperability_test */
+ "-cert", "../certificates/test_server.crt",
+ "-key", "../certificates/test_server.key",
+ "-CAfile", "../certificates/test.crt",
+ "-naccept", "1",
+ (CHAR*)NULL};
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/openssl_echo_server_nx_secure_echo_client_long_time_test.c b/test/regression/interoperability_test/nx_secure_test/openssl_echo_server_nx_secure_echo_client_long_time_test.c
new file mode 100644
index 00000000..8315a4a0
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/openssl_echo_server_nx_secure_echo_client_long_time_test.c
@@ -0,0 +1,75 @@
+#include "tls_test_frame.h"
+
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr);
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr);
+
+/* Global demo semaphore. */
+TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+INT main( INT argc, CHAR* argv[])
+{
+INT status, exit_status[2], i;
+TLS_TEST_INSTANCE *ins0;
+TLS_TEST_INSTANCE *ins1;
+
+ /* Create two test instances. */
+ status = tls_test_instance_create(&ins0, /* test instance ptr */
+ "openssl_echo_server", /* instance name */
+ openssl_echo_server_entry, /* test entry */
+ 0, /* delay(seconds) */
+ 1200, /* timeout(seconds) */
+ 1024, /* shared buffer size */
+ NULL); /* reserved */
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ status = tls_test_instance_create(&ins1,
+ "nx_secure_echo_client",
+ nx_secure_echo_client_entry,
+ 0,
+ 1200,
+ 1024,
+ NULL);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Create a semaphore and set the initial value as 0. */
+ status = tls_test_semaphore_create(&semaphore_echo_server_prepared, 0);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Create the test director. */
+ TLS_TEST_DIRECTOR *director;
+ status = tls_test_director_create(&director, NULL /* reserved */);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Register test instances to the director. */
+ status = tls_test_director_register_test_instance(director, ins0);
+ status += tls_test_director_register_test_instance(director, ins1);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Launch test. */
+ status = tls_test_director_test_start(director);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Error checking. */
+ status = tls_test_instance_show_exit_status(ins0);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+ status = tls_test_instance_show_exit_status(ins1);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Verify the exit status of the test instance of nx_secure echo client. */
+ status = tls_test_instance_get_exit_status(ins0, &exit_status[0]);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+ status = tls_test_instance_get_exit_status(ins1, &exit_status[1]);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Destroy registered test instances and the director. */
+ tls_test_director_clean_all(director);
+
+ /* Destroy the semaphore. */
+ tls_test_semaphore_destroy(semaphore_echo_server_prepared);
+
+ /* Return error if get unexpected test results. */
+ if ((TLS_TEST_NOT_AVAILABLE == exit_status[0]) || (TLS_TEST_NOT_AVAILABLE == exit_status[1]))
+ return TLS_TEST_NOT_AVAILABLE;
+
+ return exit_status[0] | exit_status[1];
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/openssl_echo_server_nx_secure_echo_client_test.c b/test/regression/interoperability_test/nx_secure_test/openssl_echo_server_nx_secure_echo_client_test.c
new file mode 100644
index 00000000..29fd745f
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/openssl_echo_server_nx_secure_echo_client_test.c
@@ -0,0 +1,75 @@
+#include "tls_test_frame.h"
+
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr);
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr);
+
+/* Global demo semaphore. */
+TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+INT main( INT argc, CHAR* argv[])
+{
+INT status, exit_status[2], i;
+TLS_TEST_INSTANCE *ins0;
+TLS_TEST_INSTANCE *ins1;
+
+ /* Create two test instances. */
+ status = tls_test_instance_create(&ins0, /* test instance ptr */
+ "openssl_echo_server", /* instance name */
+ openssl_echo_server_entry, /* test entry */
+ 0, /* delay(seconds) */
+ 60, /* timeout(seconds) */
+ 1024, /* shared buffer size */
+ NULL); /* reserved */
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ status = tls_test_instance_create(&ins1,
+ "nx_secure_echo_client",
+ nx_secure_echo_client_entry,
+ 0,
+ 60,
+ 1024,
+ NULL);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Create a semaphore and set the initial value as 0. */
+ status = tls_test_semaphore_create(&semaphore_echo_server_prepared, 0);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Create the test director. */
+ TLS_TEST_DIRECTOR *director;
+ status = tls_test_director_create(&director, NULL /* reserved */);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Register test instances to the director. */
+ status = tls_test_director_register_test_instance(director, ins0);
+ status += tls_test_director_register_test_instance(director, ins1);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Launch test. */
+ status = tls_test_director_test_start(director);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Error checking. */
+ status = tls_test_instance_show_exit_status(ins0);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+ status = tls_test_instance_show_exit_status(ins1);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Verify the exit status of the test instance of nx_secure echo client. */
+ status = tls_test_instance_get_exit_status(ins0, &exit_status[0]);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+ status = tls_test_instance_get_exit_status(ins1, &exit_status[1]);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Destroy registered test instances and the director. */
+ tls_test_director_clean_all(director);
+
+ /* Destroy the semaphore. */
+ tls_test_semaphore_destroy(semaphore_echo_server_prepared);
+
+ /* Return error if get unexpected test results. */
+ if ((TLS_TEST_NOT_AVAILABLE == exit_status[0]) || (TLS_TEST_NOT_AVAILABLE == exit_status[1]))
+ return TLS_TEST_NOT_AVAILABLE;
+
+ return exit_status[0] | exit_status[1];
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/rsa_aes128_gcm_openssl_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/rsa_aes128_gcm_openssl_echo_client_entry.c
new file mode 100644
index 00000000..ec68f8bf
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/rsa_aes128_gcm_openssl_echo_client_entry.c
@@ -0,0 +1,35 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Instance two test entry. */
+INT openssl_echo_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_AEAD_CIPHER)
+
+/* Just use TLSv1.2 */
+CHAR* external_cmd[] = { "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING, "-cipher", "AES128-GCM-SHA256", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_FAILED);
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/rsa_aes128_sha_openssl_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/rsa_aes128_sha_openssl_echo_client_entry.c
new file mode 100644
index 00000000..026e9e12
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/rsa_aes128_sha_openssl_echo_client_entry.c
@@ -0,0 +1,35 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Instance two test entry. */
+INT openssl_echo_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#ifndef NX_SECURE_TLS_SERVER_DISABLED
+
+/* Just use TLSv1.2 */
+CHAR* external_cmd[] = { "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING, "-cipher", "AES128-SHA256", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_FAILED);
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/rsa_aes256_sha_openssl_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/rsa_aes256_sha_openssl_echo_client_entry.c
new file mode 100644
index 00000000..e234fa12
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/rsa_aes256_sha_openssl_echo_client_entry.c
@@ -0,0 +1,35 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Instance two test entry. */
+INT openssl_echo_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#ifndef NX_SECURE_TLS_SERVER_DISABLED
+
+/* Just use TLSv1.2 */
+CHAR* external_cmd[] = { "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING, "-cipher", "AES256-SHA256", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_FAILED);
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/signature_algorithm_test_nx_secure_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/signature_algorithm_test_nx_secure_echo_client_entry.c
new file mode 100644
index 00000000..c24afd47
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/signature_algorithm_test_nx_secure_echo_client_entry.c
@@ -0,0 +1,376 @@
+#include "tls_test_frame.h"
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+#include "nx_crypto_ecdh.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+NX_SECURE_X509_CERT trusted_certificate;
+NX_SECURE_X509_CERT client_local_certificate;
+NX_SECURE_TLS_CRYPTO tls_ciphers_client;
+NX_SECURE_X509_CRYPTO x509_cipher_table_client[10];
+
+UCHAR tls_packet_buffer[4000];
+#define CERTIFICATE_INIT(s, k, c, t) {s, sizeof(s), k, sizeof(k), c, sizeof(c), t}
+#define SIGALGS_INIT(p, s, c) {p, sizeof(p) / sizeof(UINT), s, c}
+
+typedef struct
+{
+ UCHAR *cert;
+ UINT cert_len;
+ UCHAR *key;
+ UINT key_len;
+ UCHAR *ca_cert;
+ UINT ca_cert_len;
+ UINT key_type;
+} CERTIFICATE;
+
+typedef struct
+{
+ UINT *list;
+ UINT count;
+ UINT session_succ;
+ CERTIFICATE *cert;
+} SIGALGS;
+
+#include "../../nx_secure_test/ecc_certs.c"
+#include "test_client.der.c"
+#include "test_client.key.der.c"
+#include "test.der.c"
+
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+extern NX_SECURE_X509_CRYPTO _nx_crypto_x509_cipher_lookup_table_ecc[];
+extern const UINT _nx_crypto_x509_cipher_lookup_table_ecc_size;
+
+
+static CERTIFICATE test_certs[] =
+{
+ CERTIFICATE_INIT(test_client_der, test_client_key_der, test_der, NX_SECURE_X509_KEY_TYPE_RSA_PKCS1_DER),
+ CERTIFICATE_INIT(ECTestServer2_der, ECTestServer2_key_der, ECCA2_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+};
+
+
+static UINT sigalgs_list_0[] = {};
+static UINT sigalgs_list_1[] = {NX_SECURE_TLS_X509_TYPE_ECDSA_SHA_256};
+
+static SIGALGS sigalgs_client[] =
+{
+
+ /* Test RSA. */
+ SIGALGS_INIT(sigalgs_list_0, NX_TRUE, &test_certs[0]),
+ SIGALGS_INIT(sigalgs_list_0, NX_TRUE, &test_certs[0]),
+ SIGALGS_INIT(sigalgs_list_0, NX_TRUE, &test_certs[0]),
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ SIGALGS_INIT(sigalgs_list_0, NX_FALSE, &test_certs[0]),
+#else
+ SIGALGS_INIT(sigalgs_list_0, NX_TRUE, &test_certs[0]),
+#endif
+
+ /* Test ECDSA. */
+ SIGALGS_INIT(sigalgs_list_0, NX_TRUE, &test_certs[1]),
+ SIGALGS_INIT(sigalgs_list_0, NX_TRUE, &test_certs[1]),
+ SIGALGS_INIT(sigalgs_list_0, NX_TRUE, &test_certs[1]),
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ SIGALGS_INIT(sigalgs_list_0, NX_FALSE, &test_certs[1]),
+#else
+ SIGALGS_INIT(sigalgs_list_0, NX_TRUE, &test_certs[1]),
+#endif
+
+ /* No shared signature algorithms. */
+ SIGALGS_INIT(sigalgs_list_1, NX_FALSE, &test_certs[1]),
+};
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define an error counter. */
+
+ULONG error_counter;
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+
+static VOID sigalgs_setup(SIGALGS *sigalgs, NX_SECURE_TLS_CRYPTO *tls_ciphers,
+ NX_SECURE_X509_CRYPTO *x509_cipher_table)
+{
+UINT i;
+UINT status;
+UINT count;
+
+ /* Initialize ciphersuites. */
+ memcpy(tls_ciphers, &nx_crypto_tls_ciphers_ecc, sizeof(NX_SECURE_TLS_CRYPTO));
+ if (sigalgs -> count > 0)
+ {
+ for (count = 0; count < sigalgs -> count; count++)
+ {
+ i = 0;
+ while (sigalgs -> list[count] !=
+ (UINT)_nx_crypto_x509_cipher_lookup_table_ecc[i].nx_secure_x509_crypto_identifier)
+ {
+ i++;
+ }
+ memcpy(&x509_cipher_table[count],
+ &_nx_crypto_x509_cipher_lookup_table_ecc[i],
+ sizeof(NX_SECURE_TLS_CIPHERSUITE_INFO));
+ }
+ tls_ciphers -> nx_secure_tls_x509_cipher_table = x509_cipher_table;
+ tls_ciphers -> nx_secure_tls_x509_cipher_table_size = count;
+ }
+}
+
+static VOID client_tls_setup(NX_SECURE_TLS_SESSION *tls_session_ptr, CERTIFICATE *cert)
+{
+UINT status;
+
+ status = nx_secure_tls_session_create(tls_session_ptr,
+ &tls_ciphers_client,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_ecc_initialize(tls_session_ptr, nx_crypto_ecc_supported_groups,
+ nx_crypto_ecc_supported_groups_size,
+ nx_crypto_ecc_curves);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ memset(&remote_cert_buffer, 0, sizeof(remote_cert_buffer));
+ memset(&remote_issuer_buffer, 0, sizeof(remote_issuer_buffer));
+ status = nx_secure_tls_remote_certificate_allocate(tls_session_ptr,
+ &remote_certificate,
+ remote_cert_buffer,
+ sizeof(remote_cert_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_remote_certificate_allocate(tls_session_ptr,
+ &remote_issuer,
+ remote_issuer_buffer,
+ sizeof(remote_issuer_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_x509_certificate_initialize(&trusted_certificate,
+ cert -> ca_cert,
+ cert -> ca_cert_len, NX_NULL, 0, NULL, 0, NX_SECURE_X509_KEY_TYPE_NONE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_trusted_certificate_add(tls_session_ptr,
+ &trusted_certificate);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ if (cert != NX_NULL)
+ {
+ memset(&client_local_certificate, 0, sizeof(client_local_certificate));
+ status = nx_secure_x509_certificate_initialize(&client_local_certificate,
+ cert -> cert, cert -> cert_len,
+ NX_NULL, 0, cert -> key,
+ cert -> key_len,
+ cert -> key_type);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_local_certificate_add(tls_session_ptr,
+ &client_local_certificate);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+ }
+
+ status = nx_secure_tls_session_packet_buffer_set(tls_session_ptr, tls_packet_buffer,
+ sizeof(tls_packet_buffer));
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+}
+
+
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+
+}
+
+void tx_application_define(void *first_unused_memory)
+{
+ULONG gateway_ipv4_address;
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+UINT i;
+NX_PARAMETER_NOT_USED(thread_input);
+
+ /* Address of remote server. */
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+
+ /* Setup this thread to bind to a port. */
+ status = nx_tcp_client_socket_bind(&tcp_socket, 0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+
+ for (i = 0; i < sizeof(sigalgs_client) / sizeof(SIGALGS); i++)
+ {
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tx_thread_sleep(20 * NX_IP_PERIODIC_RATE);
+
+ sigalgs_setup(&sigalgs_client[i], &tls_ciphers_client, x509_cipher_table_client);
+ client_tls_setup(&tls_session, sigalgs_client[i].cert);
+
+ /* Attempt to connect the echo server. */
+ status = nx_tcp_client_socket_connect(&tcp_socket, REMOTE_IP_ADDRESS_NUMBER, DEVICE_SERVER_PORT, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(!((status && sigalgs_client[i].session_succ) ||
+ (!status && !sigalgs_client[i].session_succ)), TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ if (!status)
+ {
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send "hello" message. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Receive the echoed and reversed data, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Extract data received from server. */
+ status = nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ nx_packet_release(receive_packet);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Check the reverse text received from openssl server. */
+ exit_if_fail('o' == ((CHAR*)receive_buffer)[0], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[1], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[2], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('e' == ((CHAR*)receive_buffer)[3], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('h' == ((CHAR*)receive_buffer)[4], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('\n' == ((CHAR*)receive_buffer)[5], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail(6 == bytes, TLS_TEST_UNKNOWN_TYPE_ERROR);
+ }
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ nx_secure_tls_session_end(&tls_session, NX_NO_WAIT);
+ nx_secure_tls_session_delete(&tls_session);
+
+ /* Close the TCP connection. */
+ nx_tcp_socket_disconnect(&tcp_socket, NX_NO_WAIT);
+ }
+
+
+ /* Unbind the TCP socket from our port. */
+ status = nx_tcp_client_socket_unbind(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Delete the TCP socket instance to clean up. */
+ status = nx_tcp_socket_delete(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ exit(0);
+}
+#else
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+
+}
+#endif
diff --git a/test/regression/interoperability_test/nx_secure_test/signature_algorithm_test_nx_secure_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/signature_algorithm_test_nx_secure_echo_server_entry.c
new file mode 100644
index 00000000..b3e90dc7
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/signature_algorithm_test_nx_secure_echo_server_entry.c
@@ -0,0 +1,305 @@
+/* This test concentrates on TLS ECC ciphersuites negotiation. */
+#include "tls_test_frame.h"
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+#include "nx_crypto_ecdh.h"
+#include "../../nx_secure_test/ecc_certs.c"
+#include "../../nx_secure_test/test_ca_cert.c"
+#include "../../nx_secure_test/test_device_cert.c"
+
+#define NUM_PACKETS 24
+#define PACKET_SIZE 1536
+#define PACKET_POOL_SIZE (NUM_PACKETS * (PACKET_SIZE + sizeof(NX_PACKET)))
+#define THREAD_STACK_SIZE 1024
+#define ARP_CACHE_SIZE 1024
+#define BUFFER_SIZE 64
+#define METADATA_SIZE 16000
+#define CERT_BUFFER_SIZE 2048
+#define SIGALGS_INIT(p, s, c) {p, sizeof(p) / sizeof(UINT), s, c}
+#define CERTIFICATE_INIT(s, k, c, t) {s, sizeof(s), k, sizeof(k), c, sizeof(c), t}
+
+typedef struct
+{
+ UCHAR *server_cert;
+ UINT server_cert_len;
+ UCHAR *server_key;
+ UINT server_key_len;
+ UCHAR *ca_cert;
+ UINT ca_cert_len;
+ UINT key_type;
+} CERTIFICATE;
+
+typedef struct
+{
+ UINT *list;
+ UINT count;
+ UINT session_succ;
+ CERTIFICATE *cert;
+} SIGALGS;
+
+/* Define the ThreadX and NetX object control blocks... */
+
+static TX_THREAD thread_0;
+static NX_PACKET_POOL pool_0;
+static NX_IP ip_0;
+
+static NX_TCP_SOCKET server_socket_0;
+static NX_SECURE_TLS_SESSION tls_server_session_0;
+static NX_SECURE_X509_CERT server_local_certificate;
+static NX_SECURE_TLS_CRYPTO tls_ciphers_server;
+NX_SECURE_X509_CRYPTO x509_cipher_table_server[10];
+
+static ULONG pool_0_memory[PACKET_POOL_SIZE / sizeof(ULONG)];
+static ULONG thread_0_stack[THREAD_STACK_SIZE / sizeof(ULONG)];
+static ULONG ip_0_stack[THREAD_STACK_SIZE / sizeof(ULONG)];
+static ULONG arp_cache[ARP_CACHE_SIZE];
+static UCHAR server_metadata[METADATA_SIZE];
+
+static UCHAR tls_packet_buffer[4000];
+static UCHAR response_buffer[100];
+
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+extern NX_SECURE_X509_CRYPTO _nx_crypto_x509_cipher_lookup_table_ecc[];
+extern const UINT _nx_crypto_x509_cipher_lookup_table_ecc_size;
+
+static CERTIFICATE test_certs[] =
+{
+ CERTIFICATE_INIT(test_device_cert_der, test_device_cert_key_der, test_ca_cert_der, NX_SECURE_X509_KEY_TYPE_RSA_PKCS1_DER),
+ CERTIFICATE_INIT(ECTestServer2_der, ECTestServer2_key_der, ECCA2_der, NX_SECURE_X509_KEY_TYPE_EC_DER),
+};
+
+static UINT sigalgs_list_0[] = {};
+static UINT sigalgs_list_1[] = {NX_SECURE_TLS_X509_TYPE_ECDSA_SHA_256};
+
+static SIGALGS sigalgs_server[] =
+{
+
+ /* Test RSA. */
+ SIGALGS_INIT(sigalgs_list_0, NX_TRUE, &test_certs[0]),
+ SIGALGS_INIT(sigalgs_list_0, NX_TRUE, &test_certs[0]),
+ SIGALGS_INIT(sigalgs_list_0, NX_TRUE, &test_certs[0]),
+ SIGALGS_INIT(sigalgs_list_0, NX_TRUE, &test_certs[0]),
+
+ /* Test ECDSA. */
+ SIGALGS_INIT(sigalgs_list_0, NX_TRUE, &test_certs[1]),
+ SIGALGS_INIT(sigalgs_list_0, NX_TRUE, &test_certs[1]),
+ SIGALGS_INIT(sigalgs_list_0, NX_TRUE, &test_certs[1]),
+ SIGALGS_INIT(sigalgs_list_0, NX_TRUE, &test_certs[1]),
+
+ /* No shared signature algorithms. */
+ SIGALGS_INIT(sigalgs_list_1, NX_FALSE, &test_certs[1]),
+
+};
+
+/* Define thread prototypes. */
+
+static VOID ntest_0_entry(ULONG thread_input);
+extern VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+
+/* Define the pointer of current instance control block. */
+static TLS_TEST_INSTANCE* demo_instance_ptr;
+
+/* Instance one test entry. */
+INT nx_secure_ecc_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+
+ /* Get instance pointer. */
+ demo_instance_ptr = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+}
+
+/* Define what the initial system looks like. */
+
+VOID tx_application_define(void *first_unused_memory)
+{
+UINT status;
+CHAR *pointer;
+
+
+
+ /* Setup the working pointer. */
+ pointer = (CHAR *) first_unused_memory;
+
+ /* Create the server thread. */
+ tx_thread_create(&thread_0, "thread 0", ntest_0_entry, 0,
+ thread_0_stack, sizeof(thread_0_stack),
+ 7, 7, TX_NO_TIME_SLICE, TX_AUTO_START);
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", PACKET_SIZE,
+ pool_0_memory, PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL,
+ &pool_0, _nx_pcap_network_driver,
+ ip_0_stack, sizeof(ip_0_stack), 1);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (VOID *)arp_cache, sizeof(arp_cache));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ nx_secure_tls_initialize();
+}
+
+static VOID sigalgs_setup(SIGALGS *siglags, NX_SECURE_TLS_CRYPTO *tls_ciphers,
+ NX_SECURE_X509_CRYPTO *x509_cipher_table)
+{
+UINT i;
+UINT status;
+UINT count;
+
+ /* Initialize ciphersuites. */
+ memcpy(tls_ciphers, &nx_crypto_tls_ciphers_ecc, sizeof(NX_SECURE_TLS_CRYPTO));
+ if (siglags -> count > 0)
+ {
+ for (count = 0; count < siglags -> count; count++)
+ {
+ i = 0;
+ while (siglags -> list[count] !=
+ (UINT)_nx_crypto_x509_cipher_lookup_table_ecc[i].nx_secure_x509_crypto_identifier)
+ {
+ i++;
+ }
+ memcpy(&x509_cipher_table[count],
+ &_nx_crypto_x509_cipher_lookup_table_ecc[i],
+ sizeof(NX_SECURE_TLS_CIPHERSUITE_INFO));
+ }
+ tls_ciphers -> nx_secure_tls_x509_cipher_table = x509_cipher_table;
+ tls_ciphers -> nx_secure_tls_x509_cipher_table_size = count;
+ }
+}
+
+static VOID server_tls_setup(NX_SECURE_TLS_SESSION *tls_session_ptr, CERTIFICATE *cert)
+{
+UINT status;
+
+ status = nx_secure_tls_session_create(tls_session_ptr,
+ &tls_ciphers_server,
+ server_metadata,
+ sizeof(server_metadata));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_ecc_initialize(tls_session_ptr, nx_crypto_ecc_supported_groups,
+ nx_crypto_ecc_supported_groups_size,
+ nx_crypto_ecc_curves);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ memset(&server_local_certificate, 0, sizeof(server_local_certificate));
+ status = nx_secure_x509_certificate_initialize(&server_local_certificate,
+ cert -> server_cert, cert -> server_cert_len,
+ NX_NULL, 0, cert -> server_key,
+ cert -> server_key_len,
+ cert -> key_type);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_local_certificate_add(tls_session_ptr,
+ &server_local_certificate);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_session_packet_buffer_set(tls_session_ptr, tls_packet_buffer,
+ sizeof(tls_packet_buffer));
+ show_error_message_if_fail( NX_SUCCESS == status);
+}
+
+static void ntest_0_entry(ULONG thread_input)
+{
+UINT i;
+UINT status;
+ULONG actual_status;
+ULONG response_length;
+NX_PACKET *packet_ptr;
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status,
+ NX_IP_PERIODIC_RATE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Create TCP socket. */
+ status = nx_tcp_socket_create(&ip_0, &server_socket_0, "Server socket", NX_IP_NORMAL,
+ NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 8192, NX_NULL, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_tcp_server_socket_listen(&ip_0, DEVICE_SERVER_PORT, &server_socket_0, 5, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ for (i = 0; i < sizeof(sigalgs_server) / sizeof(SIGALGS); i++)
+ {
+
+ sigalgs_setup(&sigalgs_server[i], &tls_ciphers_server, x509_cipher_table_server);
+
+ server_tls_setup(&tls_server_session_0, sigalgs_server[i].cert);
+
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ status = nx_tcp_server_socket_accept(&server_socket_0, NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 1);
+
+ /* Start TLS session. */
+ status = nx_secure_tls_session_start(&tls_server_session_0, &server_socket_0,
+ NX_WAIT_FOREVER);
+ exit_if_fail (!((status && sigalgs_server[i].session_succ) ||
+ (!status && !sigalgs_server[i].session_succ)), 2);
+
+ if (!status)
+ {
+ status = nx_secure_tls_session_receive(&tls_server_session_0, &packet_ptr, NX_WAIT_FOREVER);
+ exit_if_fail ( NX_SUCCESS == status, 3);
+
+ nx_packet_data_retrieve(packet_ptr, response_buffer, &response_length);
+ nx_packet_release(packet_ptr);
+ response_buffer[response_length] = 0;
+ print_error_message("Received data: %s\n", (CHAR *)response_buffer);
+
+ /* Allocate a return packet and send our HTML data back to the client. */
+ status = nx_secure_tls_packet_allocate(&tls_server_session_0, &pool_0, &packet_ptr,
+ NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 4);
+
+ /* Echo the message received. */
+ status = nx_packet_data_append(packet_ptr, response_buffer, response_length, &pool_0,
+ NX_WAIT_FOREVER);
+ exit_if_fail( NX_SUCCESS == status, 5);
+
+ /* TLS send the HTML/HTTPS data back to the client. */
+ status = nx_secure_tls_session_send(&tls_server_session_0, packet_ptr,
+ NX_IP_PERIODIC_RATE);
+ /* Exit the test process directly without release packet. */
+ exit_if_fail( NX_SUCCESS == status, 6);
+ }
+
+ nx_secure_tls_session_end(&tls_server_session_0, NX_IP_PERIODIC_RATE);
+ nx_secure_tls_session_delete(&tls_server_session_0);
+
+ nx_tcp_socket_disconnect(&server_socket_0, NX_NO_WAIT);
+ nx_tcp_server_socket_unaccept(&server_socket_0);
+ nx_tcp_server_socket_relisten(&ip_0, DEVICE_SERVER_PORT, &server_socket_0);
+ }
+
+ exit(0);
+}
+
+#else
+INT nx_secure_ecc_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+ exit(TLS_TEST_NOT_AVAILABLE);
+}
+#endif
diff --git a/test/regression/interoperability_test/nx_secure_test/signature_algorithm_test_openssl_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/signature_algorithm_test_openssl_echo_client_entry.c
new file mode 100644
index 00000000..e286dc50
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/signature_algorithm_test_openssl_echo_client_entry.c
@@ -0,0 +1,82 @@
+#include "tls_test_frame.h"
+
+typedef struct
+{
+ UINT sig_alg_index;
+ UINT session_succ;
+} OPENSSLTEST;
+
+static CHAR *signature_algorithms[] =
+{
+ "RSA+SHA256",
+ "RSA+SHA384",
+ "RSA+SHA512",
+ "RSA+SHA1",
+ "ECDSA+SHA256",
+ "ECDSA+SHA384",
+ "ECDSA+SHA512",
+ "ECDSA+SHA1",
+};
+
+OPENSSLTEST tests[] =
+{
+
+ /* Test RSA. */
+ {0, NX_TRUE},
+ {1, NX_TRUE},
+ {2, NX_TRUE},
+ {3, NX_TRUE},
+
+ /* Test ECDSA. */
+ {4, NX_TRUE},
+ {5, NX_TRUE},
+ {6, NX_TRUE},
+ {7, NX_TRUE},
+
+ /* Noa shared signature algorithms. */
+ {5, NX_FALSE},
+};
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+INT openssl_echo_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+/* Just use TLSv1.2 */
+CHAR* external_cmd[] = { "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING,
+ "-sigalgs", "", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ for ( ; i < sizeof(tests) / sizeof(OPENSSLTEST); i++)
+ {
+
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+
+ /* Call an external program to connect to tls server. */
+ external_cmd[4] = signature_algorithms[tests[i].sig_alg_index];
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ if ((exit_status && tests[i].session_succ) ||
+ (!exit_status && !tests[i].session_succ))
+ {
+
+ /* Record errors. */
+ instance_status = TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED;
+ }
+ }
+ return instance_status;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/signature_algorithm_test_openssl_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/signature_algorithm_test_openssl_echo_server_entry.c
new file mode 100644
index 00000000..b0755f0c
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/signature_algorithm_test_openssl_echo_server_entry.c
@@ -0,0 +1,107 @@
+#include "tls_test_frame.h"
+
+typedef struct
+{
+ UINT sig_alg_index;
+ UINT session_succ;
+ CHAR *key;
+ CHAR *cert;
+ CHAR *ca;
+ UINT verify;
+} OPENSSLTEST;
+
+static CHAR *signature_algorithms[] =
+{
+ "RSA+SHA256",
+ "RSA+SHA384",
+ "RSA+SHA512",
+ "RSA+SHA1",
+ "ECDSA+SHA256",
+ "ECDSA+SHA384",
+ "ECDSA+SHA512",
+ "ECDSA+SHA1",
+};
+
+CHAR* external_cmd[] = { "openssl", "s_server", "-rev",
+ "-key", "4-key",
+ "-cert", "6-cert",
+ "-CAfile", "8-ca",
+ "-sigalgs", "10-sigalg",
+ "-naccept", "1", "-tls1_2",
+ "-port", DEVICE_SERVER_PORT_STRING,
+ "14-Verify", "10",
+ (CHAR*)NULL};
+
+OPENSSLTEST tests[] =
+{
+
+ /* Test RSA. */
+ {0, NX_TRUE, "../certificates/test_server.key", "../certificates/test_server.crt", "../certificates/test.crt", NX_FALSE},
+ {1, NX_TRUE, "../certificates/test_server.key", "../certificates/test_server.crt", "../certificates/test.crt", NX_FALSE},
+ {2, NX_TRUE, "../certificates/test_server.key", "../certificates/test_server.crt", "../certificates/test.crt", NX_FALSE},
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ {3, NX_FALSE, "../certificates/test_server.key", "../certificates/test_server.crt", "../certificates/test.crt", NX_FALSE},
+#else
+ {3, NX_TRUE, "../certificates/test_server.key", "../certificates/test_server.crt", "../certificates/test.crt", NX_FALSE},
+#endif
+
+ /* Test ECDSA. */
+ {4, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {5, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+ {6, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ {7, NX_FALSE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+#else
+ {7, NX_TRUE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+#endif
+
+ /* No shared signature algorithms. */
+ {5, NX_FALSE, "../ecc_certificates/ECTestServer2.key", "../ecc_certificates/ECTestServer2.crt", "../ecc_certificates/ECCA2.crt", NX_FALSE},
+};
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+/* Openssl echo server entry. */
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+INT status, exit_status, i;
+
+ for (i = 0; i < sizeof(tests) / sizeof(OPENSSLTEST); i++)
+ {
+ external_cmd[4] = tests[i].key;
+ external_cmd[6] = tests[i].cert;
+ external_cmd[8] = tests[i].ca;
+ external_cmd[10] = signature_algorithms[tests[i].sig_alg_index];
+ if (tests[i].verify)
+ {
+ external_cmd[16] = "-Verify";
+ }
+ else
+ {
+ external_cmd[16] = NULL;
+ }
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+
+ }
+
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/test.der.c b/test/regression/interoperability_test/nx_secure_test/test.der.c
new file mode 100644
index 00000000..b2f8f8be
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/test.der.c
@@ -0,0 +1,99 @@
+unsigned char test_der[] = {
+ 0x30, 0x82, 0x05, 0xf2, 0x30, 0x82, 0x03, 0xda, 0xa0, 0x03, 0x02, 0x01, 0x02, 0x02, 0x01, 0x01,
+ 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05, 0x00, 0x30,
+ 0x81, 0x89, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31,
+ 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x0a, 0x43, 0x61, 0x6c, 0x69, 0x66, 0x6f,
+ 0x72, 0x6e, 0x69, 0x61, 0x31, 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x07, 0x0c, 0x0d, 0x53,
+ 0x61, 0x6e, 0x20, 0x46, 0x72, 0x61, 0x6e, 0x63, 0x69, 0x73, 0x63, 0x6f, 0x31, 0x10, 0x30, 0x0e,
+ 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x07, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x31, 0x13,
+ 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x0b, 0x0c, 0x0a, 0x4f, 0x70, 0x65, 0x72, 0x61, 0x74, 0x69,
+ 0x6f, 0x6e, 0x73, 0x31, 0x26, 0x30, 0x24, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c, 0x1d, 0x45, 0x4c,
+ 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74,
+ 0x65, 0x20, 0x41, 0x75, 0x74, 0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x30, 0x1e, 0x17, 0x0d, 0x31,
+ 0x37, 0x30, 0x33, 0x30, 0x39, 0x30, 0x38, 0x30, 0x30, 0x35, 0x33, 0x5a, 0x17, 0x0d, 0x32, 0x37,
+ 0x30, 0x33, 0x30, 0x39, 0x30, 0x38, 0x30, 0x30, 0x35, 0x33, 0x5a, 0x30, 0x81, 0x89, 0x31, 0x0b,
+ 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31, 0x13, 0x30, 0x11, 0x06,
+ 0x03, 0x55, 0x04, 0x08, 0x0c, 0x0a, 0x43, 0x61, 0x6c, 0x69, 0x66, 0x6f, 0x72, 0x6e, 0x69, 0x61,
+ 0x31, 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x07, 0x0c, 0x0d, 0x53, 0x61, 0x6e, 0x20, 0x46,
+ 0x72, 0x61, 0x6e, 0x63, 0x69, 0x73, 0x63, 0x6f, 0x31, 0x10, 0x30, 0x0e, 0x06, 0x03, 0x55, 0x04,
+ 0x0a, 0x0c, 0x07, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03,
+ 0x55, 0x04, 0x0b, 0x0c, 0x0a, 0x4f, 0x70, 0x65, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x31,
+ 0x26, 0x30, 0x24, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c, 0x1d, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63,
+ 0x2e, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74, 0x65, 0x20, 0x41, 0x75,
+ 0x74, 0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x30, 0x82, 0x02, 0x22, 0x30, 0x0d, 0x06, 0x09, 0x2a,
+ 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x01, 0x05, 0x00, 0x03, 0x82, 0x02, 0x0f, 0x00, 0x30,
+ 0x82, 0x02, 0x0a, 0x02, 0x82, 0x02, 0x01, 0x00, 0xcb, 0xd9, 0xfd, 0x82, 0x2f, 0xd9, 0x42, 0x72,
+ 0x9b, 0xd1, 0x7d, 0x54, 0xb2, 0x7a, 0x7d, 0x37, 0x0b, 0xf9, 0xf9, 0xd7, 0xec, 0x1c, 0xce, 0xc7,
+ 0x6a, 0x59, 0x88, 0x09, 0x6d, 0x83, 0xd7, 0xe9, 0xd0, 0xa6, 0xc3, 0xdc, 0xc9, 0xa5, 0xe5, 0xff,
+ 0x59, 0x93, 0x33, 0x9e, 0x94, 0x05, 0x9f, 0x0e, 0x52, 0x52, 0x9b, 0x06, 0x2b, 0xec, 0xa9, 0x12,
+ 0x71, 0xe8, 0x9d, 0xb3, 0x47, 0x08, 0xa5, 0x95, 0x0d, 0x67, 0x16, 0x4b, 0x08, 0x7e, 0x86, 0x0e,
+ 0xef, 0x93, 0x41, 0xba, 0xe6, 0x43, 0xc0, 0x4e, 0xb1, 0x22, 0xe5, 0x3f, 0x4e, 0xe1, 0xab, 0x5f,
+ 0x82, 0xa2, 0x84, 0x9d, 0x2b, 0x87, 0x83, 0x49, 0x07, 0x0a, 0x82, 0xc7, 0x8b, 0x63, 0xc8, 0xa0,
+ 0xcb, 0x8e, 0xc5, 0x36, 0x81, 0xce, 0xc2, 0x61, 0xb6, 0xf7, 0xee, 0x3e, 0x9b, 0xcd, 0x58, 0xb9,
+ 0x8d, 0x5c, 0x74, 0x6c, 0x6c, 0x35, 0xea, 0xae, 0xb2, 0x2e, 0xcb, 0x4d, 0x5f, 0xc9, 0x7f, 0x52,
+ 0xde, 0x8d, 0xc0, 0x14, 0x05, 0x87, 0x04, 0x9a, 0x1e, 0x70, 0xa1, 0xad, 0x7d, 0xba, 0x3d, 0x8b,
+ 0xb3, 0xa7, 0x6f, 0x32, 0x9c, 0xa1, 0xd5, 0x61, 0xa7, 0xbe, 0x11, 0x3c, 0x82, 0x33, 0x5b, 0x6e,
+ 0xaf, 0xc9, 0x47, 0x07, 0x23, 0xec, 0x58, 0xf0, 0xc2, 0xc5, 0x3b, 0xa8, 0x54, 0x77, 0x7d, 0xde,
+ 0x71, 0x8e, 0xa5, 0x7d, 0x08, 0x7b, 0x09, 0xee, 0x55, 0xda, 0xb1, 0xc6, 0xe2, 0xa8, 0x7f, 0x20,
+ 0xd3, 0xd0, 0x72, 0x85, 0x2b, 0x8e, 0x06, 0xe9, 0xc2, 0x10, 0x1c, 0x49, 0x61, 0x7e, 0x1e, 0x31,
+ 0x89, 0x7f, 0xfa, 0x12, 0x03, 0xdb, 0x49, 0xb4, 0x02, 0x5e, 0xe5, 0x64, 0x9e, 0x39, 0x23, 0x15,
+ 0xde, 0xbc, 0x8a, 0x5f, 0xb9, 0xd8, 0xf6, 0x96, 0x47, 0x39, 0x93, 0xc4, 0xb2, 0x85, 0x9b, 0xa3,
+ 0x17, 0x67, 0x9a, 0xb6, 0x27, 0x79, 0xc8, 0x55, 0x4f, 0x08, 0x27, 0x93, 0xa2, 0x19, 0xd9, 0x84,
+ 0xef, 0x3e, 0x6f, 0xbb, 0xe6, 0x87, 0xdc, 0x5a, 0x58, 0xed, 0xc2, 0xaf, 0x3e, 0x6e, 0xf5, 0x58,
+ 0x43, 0xc6, 0x47, 0x49, 0xc5, 0x02, 0x96, 0xff, 0x0e, 0xb6, 0x1b, 0x91, 0xb8, 0x32, 0x9c, 0x36,
+ 0xdc, 0x09, 0x0a, 0xf6, 0x2f, 0xcc, 0x44, 0x1d, 0xd3, 0xb3, 0x0e, 0x87, 0x0c, 0xe3, 0xbb, 0xd6,
+ 0x96, 0x37, 0xd3, 0x9b, 0x21, 0xeb, 0x1d, 0x2d, 0x48, 0x79, 0x46, 0x94, 0x10, 0xa7, 0x83, 0xf2,
+ 0x71, 0xb8, 0xc5, 0xc5, 0x50, 0xd7, 0x01, 0x41, 0xc5, 0xe2, 0x0d, 0x4b, 0x43, 0x4e, 0x09, 0xa5,
+ 0x03, 0x14, 0x5f, 0xc7, 0x81, 0xa1, 0xe7, 0xa8, 0x03, 0x35, 0x2b, 0x73, 0x24, 0x9c, 0x99, 0x8f,
+ 0x95, 0xc8, 0xe0, 0x24, 0x55, 0xcc, 0x67, 0x3c, 0xa0, 0x85, 0x14, 0xc6, 0x09, 0x63, 0x85, 0xcc,
+ 0x68, 0xed, 0x1d, 0xd3, 0x52, 0x3c, 0x06, 0x2d, 0x77, 0xc3, 0x17, 0xc5, 0x57, 0xd4, 0xe1, 0xbf,
+ 0x39, 0xce, 0xda, 0x67, 0x75, 0x10, 0x87, 0x21, 0xca, 0x56, 0x34, 0x5a, 0x9c, 0x2b, 0xcd, 0x0f,
+ 0x25, 0xa9, 0xcd, 0xd1, 0x5c, 0xbe, 0xbd, 0xba, 0x06, 0xc8, 0x4d, 0x90, 0x26, 0x48, 0x11, 0x2b,
+ 0x96, 0x78, 0x51, 0x1a, 0x09, 0xd0, 0xfb, 0xb8, 0x3c, 0xc7, 0xd8, 0xdf, 0x5d, 0x85, 0xc0, 0xfd,
+ 0x1e, 0x67, 0x0d, 0x20, 0xe3, 0x8a, 0x8c, 0x05, 0x0c, 0x43, 0x69, 0xfc, 0xc9, 0x43, 0xce, 0x43,
+ 0x29, 0xad, 0xc5, 0xa7, 0x92, 0xba, 0x1d, 0x8f, 0xd3, 0x75, 0xdf, 0x30, 0x44, 0x1c, 0x66, 0xab,
+ 0x67, 0xc5, 0x44, 0x8c, 0x51, 0xb0, 0x13, 0x16, 0x10, 0x7f, 0x69, 0x47, 0x7b, 0xc1, 0xfb, 0x60,
+ 0x47, 0xd2, 0x4b, 0xb3, 0x05, 0xbc, 0xea, 0xd9, 0x4e, 0xce, 0xd9, 0x8a, 0xda, 0xc3, 0xd5, 0x51,
+ 0x07, 0x8d, 0x2e, 0x07, 0x00, 0x3d, 0xf6, 0x11, 0x02, 0x03, 0x01, 0x00, 0x01, 0xa3, 0x63, 0x30,
+ 0x61, 0x30, 0x0e, 0x06, 0x03, 0x55, 0x1d, 0x0f, 0x01, 0x01, 0xff, 0x04, 0x04, 0x03, 0x02, 0x01,
+ 0x06, 0x30, 0x0f, 0x06, 0x03, 0x55, 0x1d, 0x13, 0x01, 0x01, 0xff, 0x04, 0x05, 0x30, 0x03, 0x01,
+ 0x01, 0xff, 0x30, 0x1d, 0x06, 0x03, 0x55, 0x1d, 0x0e, 0x04, 0x16, 0x04, 0x14, 0x2d, 0x7c, 0x48,
+ 0x9c, 0x8b, 0x54, 0x14, 0x21, 0x3f, 0xe2, 0x75, 0xa5, 0x99, 0x8a, 0x77, 0x64, 0xdf, 0x2b, 0xd6,
+ 0x88, 0x30, 0x1f, 0x06, 0x03, 0x55, 0x1d, 0x23, 0x04, 0x18, 0x30, 0x16, 0x80, 0x14, 0x2d, 0x7c,
+ 0x48, 0x9c, 0x8b, 0x54, 0x14, 0x21, 0x3f, 0xe2, 0x75, 0xa5, 0x99, 0x8a, 0x77, 0x64, 0xdf, 0x2b,
+ 0xd6, 0x88, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05,
+ 0x00, 0x03, 0x82, 0x02, 0x01, 0x00, 0x1b, 0xd7, 0xb6, 0xc1, 0x2d, 0x88, 0x9e, 0xf5, 0xe5, 0xa3,
+ 0xf0, 0x58, 0x79, 0xf9, 0x31, 0x18, 0xf0, 0xb7, 0x2e, 0xe5, 0x0a, 0x83, 0xcb, 0x9e, 0x22, 0x45,
+ 0x7b, 0x63, 0x68, 0xbb, 0x39, 0xf0, 0x8c, 0xc5, 0x3f, 0xbe, 0x87, 0x50, 0x40, 0x6c, 0x79, 0x6d,
+ 0x89, 0x16, 0x74, 0xf5, 0xa1, 0x8c, 0xb9, 0xad, 0xd8, 0xe7, 0xe0, 0x41, 0x6e, 0x1d, 0x7d, 0xcb,
+ 0x89, 0x84, 0xce, 0x19, 0x1b, 0xa7, 0xe4, 0xd8, 0x30, 0x9a, 0xcc, 0x31, 0x6e, 0xaf, 0x15, 0xd3,
+ 0xf6, 0x5b, 0x6d, 0x49, 0xb9, 0x5f, 0x7b, 0x55, 0xad, 0x46, 0xcb, 0x41, 0x64, 0x07, 0x1d, 0xb3,
+ 0x14, 0xe3, 0xa3, 0x16, 0xbe, 0x5c, 0xcf, 0xa1, 0x1d, 0x2e, 0xf0, 0x8d, 0xbc, 0x69, 0x53, 0x32,
+ 0x8c, 0xee, 0x16, 0x53, 0x66, 0x7e, 0x61, 0x75, 0xfd, 0xa4, 0x67, 0x04, 0x55, 0x29, 0xb1, 0x38,
+ 0x76, 0x85, 0x93, 0x04, 0x49, 0xa7, 0xbf, 0x88, 0x88, 0x94, 0xad, 0x71, 0x46, 0x7c, 0x82, 0xeb,
+ 0xaa, 0xae, 0xc6, 0xd3, 0x6b, 0x62, 0xd6, 0x8c, 0xad, 0x0d, 0x95, 0x9e, 0xce, 0x10, 0xfa, 0x4c,
+ 0x75, 0xc8, 0xf4, 0x82, 0xda, 0x97, 0x6c, 0xf7, 0xe5, 0x7b, 0x36, 0xb3, 0x13, 0xd5, 0x5c, 0xc3,
+ 0x27, 0x7c, 0x85, 0xfe, 0x9c, 0x18, 0xaa, 0xb5, 0xa2, 0xba, 0xaa, 0xec, 0x7a, 0xeb, 0xa5, 0xd8,
+ 0xef, 0xa7, 0x38, 0x80, 0x71, 0x74, 0x87, 0x70, 0x94, 0x4d, 0x03, 0x4b, 0xc6, 0xc2, 0x61, 0x8d,
+ 0xc3, 0x24, 0xdd, 0x77, 0x86, 0xcd, 0x25, 0x14, 0xd2, 0x8e, 0x20, 0x52, 0xa9, 0xed, 0x68, 0xf0,
+ 0x27, 0x85, 0x4e, 0x22, 0x1c, 0xe9, 0x52, 0x92, 0x67, 0xb6, 0xe1, 0x2a, 0x5c, 0x5f, 0x4b, 0x4a,
+ 0xa7, 0x5f, 0xf1, 0x94, 0x60, 0xe9, 0xd5, 0x96, 0x01, 0x43, 0xdb, 0x39, 0x88, 0x70, 0xad, 0x34,
+ 0x69, 0x36, 0x49, 0x27, 0xf9, 0x92, 0x33, 0x2c, 0xd6, 0x03, 0xaf, 0x22, 0x37, 0x72, 0x16, 0x86,
+ 0xa3, 0x01, 0xca, 0x8c, 0x90, 0xdc, 0x1d, 0x23, 0xca, 0x0f, 0x50, 0xc3, 0x27, 0x9d, 0x70, 0xb7,
+ 0x0f, 0x49, 0xb0, 0x42, 0x5a, 0xfa, 0xe4, 0x51, 0x8c, 0xc0, 0xd0, 0x3c, 0xed, 0x63, 0xda, 0x40,
+ 0x89, 0x80, 0xc4, 0x82, 0x65, 0x5f, 0x82, 0x85, 0x6d, 0xcd, 0xc1, 0x4e, 0x74, 0xb4, 0x15, 0xe1,
+ 0x7e, 0x51, 0xe0, 0x8a, 0x69, 0xa3, 0xb1, 0x22, 0xb8, 0x0e, 0x3c, 0xf6, 0x65, 0x50, 0x70, 0x2d,
+ 0xb2, 0x17, 0x92, 0x7b, 0x0a, 0xf2, 0xde, 0xf9, 0xcf, 0xcc, 0x2c, 0xd8, 0xd0, 0x50, 0xa0, 0x51,
+ 0x31, 0x53, 0xc4, 0xf7, 0x6b, 0xb8, 0x57, 0xda, 0x04, 0x46, 0xbf, 0xba, 0x3c, 0x27, 0xef, 0x2b,
+ 0xab, 0x28, 0x0c, 0x27, 0x55, 0x16, 0xc2, 0x0d, 0x42, 0x53, 0x26, 0xc6, 0x63, 0x7f, 0x4a, 0xbf,
+ 0xda, 0x58, 0xd1, 0xb3, 0xbc, 0x51, 0x9a, 0xbf, 0x4d, 0x66, 0xbb, 0x97, 0xc2, 0x87, 0x25, 0x96,
+ 0xc3, 0xe4, 0x91, 0x6f, 0x3c, 0xc3, 0x0e, 0x63, 0x4d, 0x1b, 0xec, 0xda, 0x47, 0x7e, 0x8c, 0x57,
+ 0x2e, 0x1c, 0xf1, 0x45, 0x1f, 0xe8, 0x73, 0x2c, 0xf3, 0xc1, 0x9a, 0x6c, 0x59, 0xd4, 0xca, 0x29,
+ 0x7f, 0x60, 0x54, 0xfe, 0x52, 0xf8, 0xb7, 0x99, 0x9f, 0xd7, 0x38, 0x1d, 0xd1, 0x4d, 0x34, 0xc5,
+ 0xea, 0x7a, 0x2f, 0x90, 0x5e, 0x61, 0xe5, 0xfc, 0x1f, 0x89, 0xfd, 0x92, 0x13, 0x07, 0x12, 0x0f,
+ 0xf6, 0xe9, 0xc3, 0x17, 0x26, 0x6c, 0x4f, 0xc0, 0xe4, 0x6c, 0x3f, 0xc4, 0x3b, 0xed, 0x90, 0xef,
+ 0x3a, 0xad, 0xd1, 0x52, 0xfb, 0x72, 0xaf, 0xb7, 0xc2, 0x84, 0x0e, 0xef, 0xa1, 0x09, 0x16, 0xd1,
+ 0x08, 0xde, 0xa3, 0x00, 0xca, 0x94, 0x38, 0x19, 0xf8, 0x79, 0xc6, 0x92, 0x69, 0xd5, 0x5b, 0x05,
+ 0xb5, 0xa3, 0x8a, 0x1f, 0x5e, 0x67
+};
+unsigned int test_der_len = 1526;
diff --git a/test/regression/interoperability_test/nx_secure_test/test_client.der.c b/test/regression/interoperability_test/nx_secure_test/test_client.der.c
new file mode 100644
index 00000000..1f54b400
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/test_client.der.c
@@ -0,0 +1,96 @@
+unsigned char test_client_der[] = {
+ 0x30, 0x82, 0x05, 0xc6, 0x30, 0x82, 0x03, 0xae, 0xa0, 0x03, 0x02, 0x01, 0x02, 0x02, 0x01, 0x08,
+ 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05, 0x00, 0x30,
+ 0x81, 0x89, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31,
+ 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x0a, 0x43, 0x61, 0x6c, 0x69, 0x66, 0x6f,
+ 0x72, 0x6e, 0x69, 0x61, 0x31, 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x07, 0x0c, 0x0d, 0x53,
+ 0x61, 0x6e, 0x20, 0x46, 0x72, 0x61, 0x6e, 0x63, 0x69, 0x73, 0x63, 0x6f, 0x31, 0x10, 0x30, 0x0e,
+ 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x07, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x31, 0x13,
+ 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x0b, 0x0c, 0x0a, 0x4f, 0x70, 0x65, 0x72, 0x61, 0x74, 0x69,
+ 0x6f, 0x6e, 0x73, 0x31, 0x26, 0x30, 0x24, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c, 0x1d, 0x45, 0x4c,
+ 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74,
+ 0x65, 0x20, 0x41, 0x75, 0x74, 0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x30, 0x1e, 0x17, 0x0d, 0x31,
+ 0x38, 0x30, 0x36, 0x30, 0x35, 0x30, 0x37, 0x31, 0x37, 0x34, 0x31, 0x5a, 0x17, 0x0d, 0x32, 0x38,
+ 0x30, 0x36, 0x30, 0x32, 0x30, 0x37, 0x31, 0x37, 0x34, 0x31, 0x5a, 0x30, 0x81, 0x82, 0x31, 0x0b,
+ 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31, 0x13, 0x30, 0x11, 0x06,
+ 0x03, 0x55, 0x04, 0x08, 0x13, 0x0a, 0x43, 0x61, 0x6c, 0x69, 0x66, 0x6f, 0x72, 0x6e, 0x69, 0x61,
+ 0x31, 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x07, 0x13, 0x0d, 0x53, 0x61, 0x6e, 0x20, 0x46,
+ 0x72, 0x61, 0x6e, 0x63, 0x69, 0x73, 0x63, 0x6f, 0x31, 0x0f, 0x30, 0x0d, 0x06, 0x03, 0x55, 0x04,
+ 0x0a, 0x13, 0x06, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63, 0x31, 0x19, 0x30, 0x17, 0x06, 0x09, 0x2a,
+ 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x09, 0x01, 0x16, 0x0a, 0x4f, 0x70, 0x65, 0x72, 0x61, 0x74,
+ 0x69, 0x6f, 0x6e, 0x73, 0x31, 0x1a, 0x30, 0x18, 0x06, 0x03, 0x55, 0x04, 0x03, 0x14, 0x11, 0x74,
+ 0x65, 0x73, 0x74, 0x5f, 0x63, 0x6c, 0x69, 0x65, 0x6e, 0x74, 0x2e, 0x6c, 0x6f, 0x63, 0x61, 0x6c,
+ 0x30, 0x82, 0x01, 0x22, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01,
+ 0x01, 0x05, 0x00, 0x03, 0x82, 0x01, 0x0f, 0x00, 0x30, 0x82, 0x01, 0x0a, 0x02, 0x82, 0x01, 0x01,
+ 0x00, 0xa1, 0x38, 0x47, 0x6a, 0xac, 0x77, 0xbf, 0x80, 0x5d, 0xab, 0xcd, 0x84, 0x6b, 0x6f, 0xfd,
+ 0x94, 0x1e, 0x28, 0x4d, 0x2b, 0x4b, 0xb6, 0xf2, 0xe5, 0x4a, 0x9f, 0x59, 0xe5, 0x94, 0x12, 0x00,
+ 0xab, 0xdc, 0x4c, 0xdc, 0xde, 0xa6, 0x32, 0x72, 0x94, 0x5d, 0xd1, 0xc5, 0x4d, 0x9d, 0x35, 0x50,
+ 0x13, 0xf9, 0x64, 0x84, 0x68, 0xae, 0xee, 0xf2, 0x39, 0x32, 0xc5, 0x46, 0xe7, 0x75, 0xbf, 0x99,
+ 0xc6, 0x6d, 0x5b, 0x62, 0xdb, 0x35, 0xa4, 0x72, 0xea, 0xe1, 0x0e, 0xb4, 0xeb, 0x48, 0x08, 0xd0,
+ 0x4e, 0x1c, 0x1c, 0xc2, 0xed, 0xe7, 0x4f, 0x91, 0xe1, 0xa9, 0x07, 0x74, 0x69, 0xa0, 0x7f, 0x14,
+ 0xb7, 0xc4, 0x37, 0x30, 0xbb, 0x65, 0xef, 0xe9, 0x7f, 0x0a, 0x90, 0xf3, 0x06, 0xec, 0xd6, 0x48,
+ 0xc8, 0x1d, 0xe0, 0x8e, 0xad, 0xbe, 0x98, 0xc3, 0x9c, 0x60, 0x30, 0x63, 0xe8, 0xa4, 0x50, 0x6c,
+ 0xd7, 0x50, 0xe2, 0x1f, 0x00, 0xfb, 0x67, 0x34, 0xfd, 0x72, 0xb8, 0x63, 0x49, 0xc3, 0xc6, 0x7a,
+ 0x8c, 0x73, 0x09, 0x27, 0x8f, 0xed, 0x81, 0x56, 0x5a, 0x50, 0x57, 0xde, 0xeb, 0x96, 0xb6, 0x60,
+ 0x37, 0x37, 0xf2, 0x70, 0xfb, 0x16, 0x9b, 0x88, 0x10, 0xb0, 0x83, 0x2b, 0x02, 0x64, 0xf5, 0x42,
+ 0xf3, 0x43, 0x55, 0xf3, 0xdb, 0x5f, 0xf0, 0x40, 0x75, 0x2c, 0x74, 0x1e, 0xb4, 0x52, 0x63, 0x75,
+ 0x8b, 0x76, 0x49, 0xa4, 0xd3, 0x5c, 0x7c, 0x27, 0x81, 0xea, 0x84, 0x78, 0xa7, 0xe2, 0xee, 0x9b,
+ 0xf6, 0xf0, 0xdc, 0x6b, 0x14, 0x02, 0x4b, 0x03, 0x97, 0xa7, 0x2e, 0x43, 0x6a, 0x60, 0xc4, 0xcf,
+ 0x3f, 0xb5, 0x93, 0x88, 0xe9, 0x22, 0x1a, 0xcd, 0xdf, 0x97, 0xa7, 0x74, 0xf4, 0x0d, 0xe2, 0x97,
+ 0xe0, 0x12, 0x83, 0x3d, 0x3e, 0x89, 0xbf, 0xd4, 0xaf, 0x5e, 0xb6, 0xc8, 0xb4, 0x78, 0xac, 0x37,
+ 0xf1, 0x02, 0x03, 0x01, 0x00, 0x01, 0xa3, 0x82, 0x01, 0x3c, 0x30, 0x82, 0x01, 0x38, 0x30, 0x09,
+ 0x06, 0x03, 0x55, 0x1d, 0x13, 0x04, 0x02, 0x30, 0x00, 0x30, 0x0b, 0x06, 0x03, 0x55, 0x1d, 0x0f,
+ 0x04, 0x04, 0x03, 0x02, 0x05, 0xe0, 0x30, 0x31, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01, 0x86, 0xf8,
+ 0x42, 0x01, 0x0d, 0x04, 0x24, 0x16, 0x22, 0x4f, 0x70, 0x65, 0x6e, 0x53, 0x53, 0x4c, 0x20, 0x47,
+ 0x65, 0x6e, 0x65, 0x72, 0x61, 0x74, 0x65, 0x64, 0x20, 0x55, 0x73, 0x65, 0x72, 0x20, 0x43, 0x65,
+ 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74, 0x65, 0x30, 0x1d, 0x06, 0x03, 0x55, 0x1d, 0x0e,
+ 0x04, 0x16, 0x04, 0x14, 0x14, 0x39, 0x5b, 0xa8, 0xdd, 0x0e, 0xe4, 0xfc, 0xdf, 0x65, 0xad, 0xac,
+ 0x35, 0xf3, 0x04, 0xbc, 0xce, 0xb8, 0xee, 0xa8, 0x30, 0x81, 0xb6, 0x06, 0x03, 0x55, 0x1d, 0x23,
+ 0x04, 0x81, 0xae, 0x30, 0x81, 0xab, 0x80, 0x14, 0x2d, 0x7c, 0x48, 0x9c, 0x8b, 0x54, 0x14, 0x21,
+ 0x3f, 0xe2, 0x75, 0xa5, 0x99, 0x8a, 0x77, 0x64, 0xdf, 0x2b, 0xd6, 0x88, 0xa1, 0x81, 0x8f, 0xa4,
+ 0x81, 0x8c, 0x30, 0x81, 0x89, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02,
+ 0x55, 0x53, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x0a, 0x43, 0x61, 0x6c,
+ 0x69, 0x66, 0x6f, 0x72, 0x6e, 0x69, 0x61, 0x31, 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x07,
+ 0x0c, 0x0d, 0x53, 0x61, 0x6e, 0x20, 0x46, 0x72, 0x61, 0x6e, 0x63, 0x69, 0x73, 0x63, 0x6f, 0x31,
+ 0x10, 0x30, 0x0e, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x07, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63,
+ 0x2e, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x0b, 0x0c, 0x0a, 0x4f, 0x70, 0x65, 0x72,
+ 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x31, 0x26, 0x30, 0x24, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c,
+ 0x1d, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69,
+ 0x63, 0x61, 0x74, 0x65, 0x20, 0x41, 0x75, 0x74, 0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x82, 0x01,
+ 0x01, 0x30, 0x13, 0x06, 0x03, 0x55, 0x1d, 0x25, 0x04, 0x0c, 0x30, 0x0a, 0x06, 0x08, 0x2b, 0x06,
+ 0x01, 0x05, 0x05, 0x07, 0x03, 0x02, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d,
+ 0x01, 0x01, 0x0b, 0x05, 0x00, 0x03, 0x82, 0x02, 0x01, 0x00, 0x75, 0x12, 0x06, 0x74, 0x6d, 0x28,
+ 0x81, 0xf0, 0x17, 0xec, 0x8f, 0x05, 0x01, 0xeb, 0x98, 0x9b, 0xf0, 0x3c, 0x12, 0x56, 0x0a, 0xe0,
+ 0xa0, 0x1d, 0x7e, 0xbd, 0x75, 0x86, 0x75, 0xba, 0x2a, 0xc8, 0x2a, 0x04, 0x8c, 0x1e, 0x56, 0x1c,
+ 0x45, 0x28, 0xec, 0x9e, 0x3a, 0x95, 0xb4, 0x30, 0x6f, 0xbe, 0x0d, 0x8c, 0x1d, 0x26, 0x53, 0x95,
+ 0x92, 0xa0, 0xde, 0x01, 0xcb, 0xc6, 0x52, 0x32, 0x01, 0xf3, 0xde, 0xbf, 0x7b, 0xf2, 0x8b, 0xc8,
+ 0x86, 0x3b, 0xa2, 0x23, 0xd5, 0x98, 0xa4, 0x49, 0x71, 0xcf, 0x91, 0x5e, 0x5f, 0xf7, 0x27, 0xa0,
+ 0xfd, 0xd1, 0xb1, 0x9a, 0x70, 0x89, 0x14, 0x49, 0x52, 0x47, 0xf8, 0x68, 0xe3, 0x69, 0xc3, 0x8b,
+ 0x79, 0x47, 0x35, 0xb1, 0x8c, 0x89, 0x48, 0x7a, 0xb3, 0x71, 0xa3, 0xf7, 0xe4, 0x1a, 0x49, 0x39,
+ 0x32, 0x92, 0x35, 0x7a, 0x88, 0x10, 0xcc, 0xae, 0x2c, 0x36, 0xa2, 0xb7, 0x20, 0x21, 0x59, 0x1e,
+ 0x7d, 0xd8, 0x34, 0x23, 0x15, 0x8b, 0x14, 0x77, 0xa0, 0xab, 0x1f, 0xc0, 0x25, 0x00, 0xa5, 0xda,
+ 0x10, 0xe9, 0x83, 0x92, 0x96, 0x78, 0xf5, 0x69, 0x8e, 0x1b, 0x80, 0xb2, 0x4e, 0xf5, 0x97, 0x38,
+ 0x73, 0xe8, 0xd0, 0xcb, 0xec, 0x98, 0x1b, 0x1e, 0x84, 0x6c, 0xce, 0x65, 0x61, 0xdc, 0x37, 0xe7,
+ 0xeb, 0xba, 0x8e, 0xe7, 0xa8, 0xe3, 0xaa, 0x71, 0x1e, 0x85, 0xb9, 0x78, 0x56, 0x8a, 0x40, 0xe9,
+ 0x87, 0x72, 0xcd, 0x89, 0x49, 0x79, 0xab, 0x2a, 0x9d, 0x05, 0x33, 0xf6, 0x8b, 0x64, 0xc3, 0xbe,
+ 0x16, 0xe6, 0x61, 0x95, 0x14, 0x8d, 0x91, 0x76, 0x7e, 0x4d, 0xa6, 0xe0, 0xba, 0x7f, 0x9c, 0x25,
+ 0x42, 0x85, 0x93, 0x24, 0x52, 0x72, 0x43, 0x28, 0x37, 0x38, 0x49, 0x31, 0x17, 0x7a, 0x27, 0x3e,
+ 0x9f, 0x94, 0x5e, 0xc7, 0xfe, 0x6c, 0x13, 0x40, 0x93, 0x4f, 0x46, 0x91, 0xb6, 0x2d, 0xd8, 0xa1,
+ 0x56, 0x1c, 0x36, 0xf9, 0xd3, 0x5f, 0xb4, 0xc2, 0x29, 0xac, 0xeb, 0xe9, 0x5d, 0x05, 0x26, 0x78,
+ 0x84, 0x23, 0x99, 0x5b, 0xc5, 0x9f, 0xf0, 0x44, 0x21, 0xe8, 0x1c, 0x30, 0xd2, 0xbb, 0xc1, 0xc9,
+ 0xaa, 0x39, 0xe9, 0x12, 0x70, 0x7d, 0x26, 0x48, 0x81, 0xf7, 0x75, 0xc5, 0x8e, 0x9a, 0x8b, 0xea,
+ 0x15, 0xa8, 0xff, 0x57, 0xb9, 0xc0, 0xf2, 0x09, 0x7e, 0xd2, 0xb8, 0xdc, 0xa1, 0x81, 0x27, 0x15,
+ 0xa3, 0xfc, 0x81, 0x4d, 0xd9, 0x95, 0xb1, 0x61, 0xd7, 0x86, 0x15, 0x67, 0x6d, 0xdc, 0x8e, 0xb9,
+ 0xcd, 0x9d, 0x64, 0x8e, 0x5e, 0x34, 0x4c, 0x23, 0x86, 0xfa, 0xa2, 0x5a, 0x3d, 0x4e, 0x0a, 0x5f,
+ 0x5a, 0x27, 0x8e, 0x18, 0xf0, 0x5e, 0xdf, 0x90, 0x22, 0xc4, 0x88, 0xba, 0xb2, 0xec, 0x4f, 0x2e,
+ 0x80, 0x7d, 0xdd, 0x03, 0x63, 0xca, 0x77, 0xee, 0xeb, 0xbf, 0xe2, 0x06, 0xa3, 0xd8, 0x19, 0xbc,
+ 0xaa, 0x20, 0xbf, 0xe4, 0xea, 0x48, 0x9e, 0x6c, 0xbc, 0x25, 0x0f, 0x5a, 0xc5, 0x04, 0x82, 0x73,
+ 0x81, 0x3e, 0xcf, 0x62, 0xa6, 0xe9, 0x1d, 0xdc, 0x0d, 0x1c, 0x45, 0x08, 0x8b, 0xef, 0x33, 0x81,
+ 0x98, 0x6c, 0x34, 0x74, 0x2a, 0xf9, 0x5a, 0x3a, 0x13, 0x98, 0x6f, 0xe5, 0x4b, 0x10, 0x7d, 0xdd,
+ 0x97, 0x87, 0x92, 0x67, 0xa3, 0x58, 0x56, 0xc5, 0x86, 0x64, 0x0f, 0x3a, 0xa6, 0x3f, 0x64, 0xc5,
+ 0xba, 0xf7, 0x91, 0xc2, 0xf6, 0x81, 0x1a, 0xcc, 0xe7, 0x67, 0x1d, 0x21, 0x9e, 0x23, 0x18, 0x38,
+ 0x95, 0x1f, 0xb7, 0xc8, 0x77, 0x44, 0xae, 0xfb, 0xbb, 0x32, 0x1b, 0x4a, 0x09, 0x0e, 0xde, 0xdc,
+ 0x43, 0xc6, 0x67, 0xbd, 0xa7, 0xe4, 0xa9, 0x5c, 0xce, 0xd0, 0x2e, 0xf2, 0x7b, 0xca, 0x2c, 0x71,
+ 0xdb, 0x1f, 0x84, 0xb0, 0x93, 0xa9, 0xed, 0xf1, 0x53, 0x73
+};
+unsigned int test_client_der_len = 1482;
diff --git a/test/regression/interoperability_test/nx_secure_test/test_client.key.der.c b/test/regression/interoperability_test/nx_secure_test/test_client.key.der.c
new file mode 100644
index 00000000..49e80e3c
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/test_client.key.der.c
@@ -0,0 +1,78 @@
+unsigned char test_client_key_der[] = {
+ 0x30, 0x82, 0x04, 0xa5, 0x02, 0x01, 0x00, 0x02, 0x82, 0x01, 0x01, 0x00, 0xa1, 0x38, 0x47, 0x6a,
+ 0xac, 0x77, 0xbf, 0x80, 0x5d, 0xab, 0xcd, 0x84, 0x6b, 0x6f, 0xfd, 0x94, 0x1e, 0x28, 0x4d, 0x2b,
+ 0x4b, 0xb6, 0xf2, 0xe5, 0x4a, 0x9f, 0x59, 0xe5, 0x94, 0x12, 0x00, 0xab, 0xdc, 0x4c, 0xdc, 0xde,
+ 0xa6, 0x32, 0x72, 0x94, 0x5d, 0xd1, 0xc5, 0x4d, 0x9d, 0x35, 0x50, 0x13, 0xf9, 0x64, 0x84, 0x68,
+ 0xae, 0xee, 0xf2, 0x39, 0x32, 0xc5, 0x46, 0xe7, 0x75, 0xbf, 0x99, 0xc6, 0x6d, 0x5b, 0x62, 0xdb,
+ 0x35, 0xa4, 0x72, 0xea, 0xe1, 0x0e, 0xb4, 0xeb, 0x48, 0x08, 0xd0, 0x4e, 0x1c, 0x1c, 0xc2, 0xed,
+ 0xe7, 0x4f, 0x91, 0xe1, 0xa9, 0x07, 0x74, 0x69, 0xa0, 0x7f, 0x14, 0xb7, 0xc4, 0x37, 0x30, 0xbb,
+ 0x65, 0xef, 0xe9, 0x7f, 0x0a, 0x90, 0xf3, 0x06, 0xec, 0xd6, 0x48, 0xc8, 0x1d, 0xe0, 0x8e, 0xad,
+ 0xbe, 0x98, 0xc3, 0x9c, 0x60, 0x30, 0x63, 0xe8, 0xa4, 0x50, 0x6c, 0xd7, 0x50, 0xe2, 0x1f, 0x00,
+ 0xfb, 0x67, 0x34, 0xfd, 0x72, 0xb8, 0x63, 0x49, 0xc3, 0xc6, 0x7a, 0x8c, 0x73, 0x09, 0x27, 0x8f,
+ 0xed, 0x81, 0x56, 0x5a, 0x50, 0x57, 0xde, 0xeb, 0x96, 0xb6, 0x60, 0x37, 0x37, 0xf2, 0x70, 0xfb,
+ 0x16, 0x9b, 0x88, 0x10, 0xb0, 0x83, 0x2b, 0x02, 0x64, 0xf5, 0x42, 0xf3, 0x43, 0x55, 0xf3, 0xdb,
+ 0x5f, 0xf0, 0x40, 0x75, 0x2c, 0x74, 0x1e, 0xb4, 0x52, 0x63, 0x75, 0x8b, 0x76, 0x49, 0xa4, 0xd3,
+ 0x5c, 0x7c, 0x27, 0x81, 0xea, 0x84, 0x78, 0xa7, 0xe2, 0xee, 0x9b, 0xf6, 0xf0, 0xdc, 0x6b, 0x14,
+ 0x02, 0x4b, 0x03, 0x97, 0xa7, 0x2e, 0x43, 0x6a, 0x60, 0xc4, 0xcf, 0x3f, 0xb5, 0x93, 0x88, 0xe9,
+ 0x22, 0x1a, 0xcd, 0xdf, 0x97, 0xa7, 0x74, 0xf4, 0x0d, 0xe2, 0x97, 0xe0, 0x12, 0x83, 0x3d, 0x3e,
+ 0x89, 0xbf, 0xd4, 0xaf, 0x5e, 0xb6, 0xc8, 0xb4, 0x78, 0xac, 0x37, 0xf1, 0x02, 0x03, 0x01, 0x00,
+ 0x01, 0x02, 0x82, 0x01, 0x01, 0x00, 0x9f, 0xf7, 0x1a, 0x8d, 0x92, 0xd1, 0x42, 0x97, 0x58, 0xda,
+ 0x36, 0x12, 0x95, 0x13, 0xca, 0xd5, 0x23, 0xd3, 0x33, 0x36, 0xa9, 0x6a, 0xbe, 0xb9, 0x9a, 0x00,
+ 0x61, 0x0f, 0x75, 0x8b, 0x23, 0x55, 0x63, 0x42, 0x74, 0xc9, 0x0a, 0xb8, 0xf5, 0x8d, 0x97, 0x45,
+ 0xa3, 0xf2, 0xad, 0xf1, 0x0f, 0x22, 0xb2, 0x8a, 0xf5, 0x02, 0x75, 0xc8, 0xab, 0x58, 0xeb, 0xb2,
+ 0x68, 0xf7, 0x12, 0x93, 0x69, 0x3e, 0x44, 0x95, 0xaf, 0x91, 0xf8, 0x38, 0xd2, 0xb9, 0x91, 0x53,
+ 0xa9, 0x59, 0xe6, 0xe0, 0xaf, 0xe7, 0x40, 0xe7, 0x9c, 0xd6, 0xb7, 0x73, 0xf1, 0x38, 0xaa, 0x21,
+ 0xb6, 0x75, 0x74, 0x05, 0x84, 0x06, 0x0e, 0xd0, 0x00, 0x2f, 0x81, 0x26, 0xba, 0x55, 0x0e, 0xa3,
+ 0xe2, 0x2f, 0xd5, 0xe1, 0x8c, 0xd7, 0xdb, 0x25, 0x4c, 0x0c, 0xc3, 0x18, 0x0a, 0xc7, 0x67, 0x7d,
+ 0xbc, 0x34, 0x42, 0x8d, 0x76, 0x5f, 0xde, 0x9c, 0xda, 0x2c, 0x02, 0xd9, 0x07, 0x02, 0xe9, 0x0c,
+ 0x04, 0x47, 0xee, 0x7f, 0x1c, 0x51, 0x01, 0xcb, 0xc3, 0x53, 0xd0, 0xbf, 0x17, 0x88, 0xae, 0x3d,
+ 0xf6, 0x16, 0xde, 0xaf, 0x22, 0x22, 0x89, 0xeb, 0x96, 0x45, 0xcf, 0x72, 0x44, 0xbf, 0x02, 0x02,
+ 0xd6, 0x53, 0xaf, 0x14, 0xf9, 0xfb, 0xb0, 0xa5, 0xf8, 0xb6, 0x93, 0x47, 0x7e, 0x2d, 0x70, 0x50,
+ 0xd6, 0x4d, 0xe5, 0x61, 0xf2, 0x30, 0x6b, 0x84, 0x40, 0x58, 0x63, 0x71, 0x04, 0x94, 0xe4, 0x75,
+ 0x2a, 0x1d, 0xab, 0x32, 0x3d, 0xc9, 0x23, 0x0c, 0x1a, 0xc3, 0xbe, 0xf0, 0x10, 0xb7, 0x6c, 0x52,
+ 0xcf, 0x01, 0xe6, 0x8b, 0xe2, 0x7b, 0x7d, 0xbb, 0x71, 0xdc, 0x48, 0xe5, 0xfb, 0x8c, 0x0a, 0xd0,
+ 0x00, 0x80, 0x7d, 0xbc, 0xd6, 0x07, 0xf6, 0x0c, 0xa5, 0x84, 0x92, 0x13, 0xb5, 0x3f, 0x2e, 0xce,
+ 0x35, 0x9e, 0x16, 0xdc, 0x47, 0xed, 0x02, 0x81, 0x81, 0x00, 0xd6, 0xd9, 0x85, 0x4b, 0x45, 0x90,
+ 0xab, 0x4b, 0xff, 0x77, 0x0f, 0x04, 0xe7, 0xd6, 0x71, 0xff, 0xc9, 0xd1, 0xe0, 0x64, 0x47, 0x5c,
+ 0xb4, 0x22, 0x28, 0xe6, 0xe4, 0x65, 0x0f, 0x30, 0x35, 0xef, 0xcc, 0xcc, 0xdc, 0x14, 0xbc, 0xab,
+ 0x10, 0x43, 0x4e, 0x34, 0x96, 0x57, 0x60, 0xf3, 0xba, 0xf5, 0x0e, 0x8d, 0x6b, 0xbd, 0x5e, 0x48,
+ 0x4f, 0x0f, 0x47, 0xdb, 0x3e, 0x74, 0x5d, 0x75, 0xb3, 0x61, 0xd4, 0x44, 0xbb, 0x40, 0x7d, 0xf7,
+ 0x86, 0xa7, 0x11, 0x87, 0x67, 0xe6, 0x92, 0x8e, 0x52, 0xa3, 0xaa, 0x4b, 0x47, 0xd8, 0x0f, 0xf0,
+ 0xfb, 0xe8, 0x93, 0xea, 0xb1, 0x2b, 0x66, 0x6c, 0xb3, 0x57, 0x2b, 0x3b, 0xdb, 0x30, 0x60, 0x7c,
+ 0x7d, 0x40, 0x38, 0x4d, 0x00, 0x23, 0x77, 0x81, 0x2e, 0xfd, 0xca, 0x91, 0x13, 0x01, 0x98, 0xc2,
+ 0xb4, 0x14, 0x8c, 0x22, 0xad, 0x60, 0xcd, 0x80, 0x7b, 0xf7, 0x02, 0x81, 0x81, 0x00, 0xc0, 0x19,
+ 0x2f, 0xe7, 0x79, 0xc4, 0x0f, 0x17, 0xbf, 0x98, 0x2f, 0xa3, 0x13, 0x7d, 0x71, 0xe7, 0x03, 0xc0,
+ 0x84, 0xeb, 0xd9, 0x37, 0x46, 0x00, 0x06, 0x0f, 0xf8, 0x50, 0x4c, 0xed, 0xa8, 0x3b, 0x2c, 0xbf,
+ 0x63, 0x84, 0xc5, 0x33, 0xa8, 0x33, 0x56, 0x42, 0xc8, 0xe0, 0x4c, 0x8a, 0x16, 0x70, 0xc3, 0xed,
+ 0x7b, 0x38, 0xd1, 0xfa, 0x13, 0x3e, 0x41, 0x4a, 0xe7, 0x99, 0xd6, 0xf4, 0x51, 0xa2, 0x87, 0xb0,
+ 0xe4, 0xa8, 0x74, 0xa6, 0xba, 0xa2, 0x31, 0x4d, 0x9a, 0x4f, 0xfb, 0xbb, 0x13, 0xdc, 0x98, 0xc4,
+ 0x55, 0x36, 0x77, 0xc1, 0x76, 0xaf, 0x49, 0xa5, 0x77, 0x8f, 0x35, 0x4f, 0x90, 0xe4, 0xc3, 0x9e,
+ 0xa0, 0x31, 0x20, 0x30, 0x13, 0xfe, 0xcd, 0xbc, 0xe3, 0x35, 0x96, 0xf6, 0x3d, 0x07, 0x49, 0x71,
+ 0x88, 0xea, 0xf9, 0x6b, 0x9c, 0xf5, 0x2e, 0x2e, 0xd9, 0x93, 0xa3, 0xe2, 0xe1, 0x57, 0x02, 0x81,
+ 0x80, 0x23, 0x1b, 0x76, 0x39, 0x7f, 0x8b, 0x8d, 0x42, 0x24, 0xe3, 0x7a, 0x93, 0xcd, 0xa2, 0x70,
+ 0x0c, 0x61, 0x19, 0x27, 0x76, 0x9b, 0x66, 0x9d, 0x94, 0xbb, 0x64, 0x47, 0x4b, 0xf0, 0x38, 0x6b,
+ 0x87, 0xdc, 0xca, 0x58, 0xe8, 0x16, 0x90, 0x49, 0x5f, 0x06, 0x27, 0x77, 0xad, 0x9d, 0x8d, 0x16,
+ 0x2e, 0xb7, 0x0b, 0x0a, 0xe0, 0xed, 0xc8, 0x19, 0x0b, 0x21, 0x2d, 0xc5, 0x3d, 0xd4, 0x8b, 0xc8,
+ 0x1d, 0x23, 0x47, 0x7b, 0xe5, 0xa4, 0xef, 0xce, 0x93, 0xfc, 0x3c, 0x49, 0x11, 0x17, 0x3f, 0xa4,
+ 0x67, 0x54, 0x0b, 0x6b, 0x18, 0xf6, 0x39, 0xe5, 0x9f, 0xf2, 0x93, 0xb6, 0x11, 0xa6, 0x71, 0xfa,
+ 0xb8, 0x32, 0xbb, 0x5c, 0x2c, 0xc2, 0x87, 0x75, 0x1c, 0x0a, 0x57, 0x22, 0xbf, 0xa8, 0xe6, 0x76,
+ 0x1c, 0x48, 0x7e, 0x7e, 0x41, 0x93, 0x89, 0xb5, 0x4d, 0x6a, 0x3c, 0xbc, 0x62, 0x06, 0x12, 0x89,
+ 0xaf, 0x02, 0x81, 0x81, 0x00, 0x90, 0xc7, 0x2a, 0xdc, 0x89, 0x60, 0x23, 0x83, 0xe1, 0x89, 0xa0,
+ 0x75, 0x86, 0xad, 0xe7, 0xd7, 0x95, 0x73, 0x56, 0x7a, 0xae, 0x76, 0x43, 0x12, 0xa7, 0x7f, 0x07,
+ 0xc5, 0xf5, 0x84, 0xb4, 0x63, 0x0c, 0xe1, 0x9d, 0xee, 0xa5, 0xf5, 0xbd, 0xd2, 0x1b, 0x34, 0x30,
+ 0x53, 0x24, 0x3c, 0x7a, 0x97, 0x38, 0x83, 0x56, 0x78, 0x47, 0x80, 0xf3, 0x59, 0xdb, 0x39, 0xc9,
+ 0xfd, 0x9f, 0x0c, 0xfa, 0x2d, 0xc5, 0x98, 0xa3, 0x6c, 0xf6, 0xa5, 0xe6, 0x49, 0x71, 0x61, 0x2c,
+ 0x69, 0x15, 0xaf, 0x34, 0x53, 0xf0, 0xeb, 0x1f, 0xd1, 0xf2, 0x45, 0xe3, 0xde, 0x4e, 0x62, 0x20,
+ 0x0e, 0xd5, 0xbe, 0x06, 0xd4, 0xf3, 0x3e, 0x2d, 0x3b, 0x79, 0x27, 0xe3, 0x1a, 0x0a, 0x13, 0x4f,
+ 0x26, 0xc7, 0x85, 0x04, 0x0f, 0xe6, 0xe1, 0x63, 0xb0, 0xbc, 0x94, 0xc7, 0x71, 0xde, 0x01, 0xbf,
+ 0x47, 0xcf, 0x9f, 0xa1, 0xf7, 0x02, 0x81, 0x81, 0x00, 0x94, 0xbb, 0x72, 0xb9, 0xff, 0xa3, 0x90,
+ 0x71, 0x63, 0xb2, 0xa5, 0xdc, 0x91, 0x2d, 0x91, 0xc9, 0x89, 0x3f, 0xf8, 0x20, 0xe9, 0x09, 0xbb,
+ 0x99, 0x99, 0x30, 0xbd, 0x42, 0xe4, 0xa8, 0xb2, 0x52, 0xf6, 0xb1, 0xc5, 0xa3, 0x8f, 0x45, 0xd3,
+ 0x74, 0x86, 0xd8, 0xa5, 0x14, 0x81, 0x81, 0xbc, 0xd9, 0x02, 0x4e, 0x65, 0xbf, 0x49, 0x84, 0xe3,
+ 0xf2, 0xe1, 0x19, 0x75, 0x1e, 0x5e, 0x87, 0x1a, 0x8b, 0xbf, 0x44, 0x77, 0xa0, 0xb9, 0x00, 0x47,
+ 0x24, 0xc6, 0x8a, 0x23, 0xa3, 0x82, 0xef, 0x43, 0xcb, 0xa5, 0x9f, 0xc7, 0x51, 0x99, 0x95, 0x02,
+ 0x99, 0x5b, 0xa5, 0x22, 0x13, 0x3f, 0xfc, 0x07, 0xcd, 0x75, 0x9a, 0xa3, 0x31, 0x4d, 0x92, 0x7b,
+ 0xcd, 0x2a, 0x99, 0x7b, 0xe5, 0x3d, 0x6b, 0xc6, 0x72, 0xb6, 0x93, 0x16, 0x2c, 0x7f, 0x21, 0x80,
+ 0x6f, 0x5f, 0xf9, 0x20, 0x53, 0x2f, 0x41, 0x03, 0x55
+};
+unsigned int test_client_key_der_len = 1193;
diff --git a/test/regression/interoperability_test/nx_secure_test/test_device_cert.c b/test/regression/interoperability_test/nx_secure_test/test_device_cert.c
new file mode 100644
index 00000000..d706868b
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/test_device_cert.c
@@ -0,0 +1,188 @@
+static unsigned char test_device_cert_der[] = {
+ 0x30, 0x82, 0x03, 0xd2, 0x30, 0x82, 0x02, 0xba, 0xa0, 0x03, 0x02, 0x01,
+ 0x02, 0x02, 0x01, 0x01, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86,
+ 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05, 0x00, 0x30, 0x7a, 0x31, 0x0b, 0x30,
+ 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31, 0x0b,
+ 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x02, 0x43, 0x41, 0x31,
+ 0x12, 0x30, 0x10, 0x06, 0x03, 0x55, 0x04, 0x07, 0x0c, 0x09, 0x53, 0x61,
+ 0x6e, 0x20, 0x44, 0x69, 0x65, 0x67, 0x6f, 0x31, 0x16, 0x30, 0x14, 0x06,
+ 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x0d, 0x45, 0x78, 0x70, 0x72, 0x65, 0x73,
+ 0x73, 0x20, 0x4c, 0x6f, 0x67, 0x69, 0x63, 0x31, 0x14, 0x30, 0x12, 0x06,
+ 0x03, 0x55, 0x04, 0x0b, 0x0c, 0x0b, 0x4e, 0x65, 0x74, 0x58, 0x20, 0x53,
+ 0x65, 0x63, 0x75, 0x72, 0x65, 0x31, 0x1c, 0x30, 0x1a, 0x06, 0x03, 0x55,
+ 0x04, 0x03, 0x0c, 0x13, 0x4e, 0x65, 0x74, 0x58, 0x20, 0x53, 0x65, 0x63,
+ 0x75, 0x72, 0x65, 0x20, 0x54, 0x65, 0x73, 0x74, 0x20, 0x43, 0x41, 0x30,
+ 0x1e, 0x17, 0x0d, 0x31, 0x36, 0x31, 0x31, 0x31, 0x31, 0x31, 0x39, 0x35,
+ 0x31, 0x30, 0x30, 0x5a, 0x17, 0x0d, 0x32, 0x36, 0x31, 0x31, 0x30, 0x39,
+ 0x31, 0x39, 0x35, 0x31, 0x30, 0x30, 0x5a, 0x30, 0x62, 0x31, 0x0b, 0x30,
+ 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31, 0x0b,
+ 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x02, 0x43, 0x41, 0x31,
+ 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x0d, 0x45, 0x78,
+ 0x70, 0x72, 0x65, 0x73, 0x73, 0x20, 0x4c, 0x6f, 0x67, 0x69, 0x63, 0x31,
+ 0x14, 0x30, 0x12, 0x06, 0x03, 0x55, 0x04, 0x0b, 0x0c, 0x0b, 0x4e, 0x65,
+ 0x74, 0x58, 0x20, 0x53, 0x65, 0x63, 0x75, 0x72, 0x65, 0x31, 0x18, 0x30,
+ 0x16, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c, 0x0f, 0x77, 0x77, 0x77, 0x2e,
+ 0x65, 0x78, 0x61, 0x6d, 0x70, 0x6c, 0x65, 0x2e, 0x63, 0x6f, 0x6d, 0x30,
+ 0x82, 0x01, 0x22, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7,
+ 0x0d, 0x01, 0x01, 0x01, 0x05, 0x00, 0x03, 0x82, 0x01, 0x0f, 0x00, 0x30,
+ 0x82, 0x01, 0x0a, 0x02, 0x82, 0x01, 0x01, 0x00, 0xae, 0x03, 0x2c, 0xec,
+ 0xa2, 0x79, 0xd1, 0x15, 0x20, 0x88, 0x4d, 0xcd, 0xa2, 0x1b, 0x05, 0xe3,
+ 0xbd, 0x55, 0xad, 0xc6, 0x1f, 0x64, 0xe8, 0xb5, 0xc5, 0x0d, 0x67, 0xfc,
+ 0x7e, 0xda, 0xfb, 0x70, 0xf6, 0xc9, 0x47, 0x87, 0x3a, 0xaa, 0x88, 0x00,
+ 0xf1, 0xa7, 0xf7, 0xe1, 0xf5, 0x2c, 0x54, 0x0e, 0x33, 0xda, 0xbe, 0x9c,
+ 0x66, 0x30, 0xd9, 0x40, 0xeb, 0x1d, 0xce, 0xe1, 0x55, 0x15, 0x2b, 0x11,
+ 0x47, 0x6c, 0x7e, 0x88, 0xc6, 0x24, 0xcf, 0x87, 0x1b, 0xb5, 0x1f, 0x47,
+ 0xb9, 0xef, 0xad, 0x29, 0xd3, 0x2e, 0x43, 0xee, 0x39, 0xdd, 0x09, 0x54,
+ 0xba, 0xfc, 0xed, 0xbc, 0x2e, 0x0e, 0x53, 0x15, 0x37, 0xcb, 0xc5, 0xf5,
+ 0xee, 0x70, 0x2a, 0xe8, 0x01, 0x6d, 0xb1, 0x39, 0x94, 0x5a, 0xc2, 0x8a,
+ 0x00, 0x04, 0xa9, 0xff, 0xea, 0x56, 0xf7, 0xd7, 0xa8, 0x1b, 0xa4, 0x26,
+ 0xcd, 0x28, 0xaf, 0xfa, 0x52, 0x85, 0x1c, 0x26, 0x3e, 0x5e, 0x01, 0xf7,
+ 0xe1, 0x66, 0xff, 0xac, 0xad, 0x9c, 0x98, 0x2f, 0xe0, 0x7e, 0x9f, 0xf1,
+ 0x33, 0x31, 0xc3, 0x7f, 0xe6, 0x58, 0x5d, 0xd8, 0x5f, 0x7d, 0x2b, 0x5a,
+ 0x55, 0xcf, 0xb1, 0x91, 0x53, 0x41, 0x04, 0xac, 0x86, 0x5e, 0x01, 0x35,
+ 0x2b, 0x74, 0x8d, 0x46, 0x4d, 0x48, 0xc0, 0x5f, 0x83, 0x67, 0xb5, 0x6d,
+ 0x52, 0x3f, 0x3e, 0xe6, 0xec, 0xf8, 0x2e, 0x10, 0x28, 0xdb, 0x69, 0xa6,
+ 0x9d, 0x4b, 0xde, 0x19, 0x2e, 0xd2, 0x5f, 0xc8, 0xa9, 0x3b, 0x52, 0xe9,
+ 0xb2, 0xcd, 0x6e, 0x19, 0x22, 0xf9, 0x99, 0xa6, 0xcc, 0xf5, 0xd3, 0xec,
+ 0xff, 0x0c, 0x77, 0x6f, 0x25, 0x92, 0x07, 0x4c, 0x64, 0x7d, 0x34, 0x49,
+ 0x6f, 0xff, 0x0a, 0xa8, 0x15, 0x64, 0x72, 0x2d, 0x4f, 0x42, 0x05, 0xe8,
+ 0x2b, 0x01, 0xf1, 0xe3, 0x65, 0x94, 0x23, 0xd9, 0xdf, 0x5e, 0x3b, 0xb5,
+ 0x02, 0x03, 0x01, 0x00, 0x01, 0xa3, 0x7b, 0x30, 0x79, 0x30, 0x09, 0x06,
+ 0x03, 0x55, 0x1d, 0x13, 0x04, 0x02, 0x30, 0x00, 0x30, 0x2c, 0x06, 0x09,
+ 0x60, 0x86, 0x48, 0x01, 0x86, 0xf8, 0x42, 0x01, 0x0d, 0x04, 0x1f, 0x16,
+ 0x1d, 0x4f, 0x70, 0x65, 0x6e, 0x53, 0x53, 0x4c, 0x20, 0x47, 0x65, 0x6e,
+ 0x65, 0x72, 0x61, 0x74, 0x65, 0x64, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69,
+ 0x66, 0x69, 0x63, 0x61, 0x74, 0x65, 0x30, 0x1d, 0x06, 0x03, 0x55, 0x1d,
+ 0x0e, 0x04, 0x16, 0x04, 0x14, 0x8d, 0xb0, 0xee, 0x8f, 0x6b, 0x43, 0x52,
+ 0x29, 0xf4, 0x25, 0xff, 0x3c, 0xda, 0x5f, 0xb3, 0xce, 0x9b, 0x7b, 0x75,
+ 0xe1, 0x30, 0x1f, 0x06, 0x03, 0x55, 0x1d, 0x23, 0x04, 0x18, 0x30, 0x16,
+ 0x80, 0x14, 0x1b, 0x8d, 0x06, 0xd9, 0x6b, 0xad, 0xee, 0x82, 0x24, 0x26,
+ 0x55, 0x9a, 0x1b, 0x03, 0x44, 0x92, 0x0a, 0x06, 0x92, 0x48, 0x30, 0x0d,
+ 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05,
+ 0x00, 0x03, 0x82, 0x01, 0x01, 0x00, 0x75, 0x83, 0x89, 0xab, 0x84, 0x52,
+ 0x5f, 0xa4, 0x9e, 0x98, 0xca, 0xa3, 0xf9, 0xab, 0xd4, 0x04, 0x32, 0xa4,
+ 0x8c, 0x96, 0x90, 0x39, 0x88, 0x92, 0xc3, 0xcd, 0x51, 0xc3, 0x01, 0x35,
+ 0x03, 0x78, 0xfa, 0x0d, 0x1e, 0x7b, 0x79, 0xe9, 0x7d, 0xd8, 0x68, 0x7a,
+ 0x65, 0xc6, 0x00, 0x7c, 0xa1, 0x7a, 0x52, 0xc9, 0xa3, 0xf4, 0x0b, 0xbd,
+ 0x76, 0x24, 0xdf, 0xde, 0x22, 0x2d, 0x95, 0xc5, 0xb6, 0x54, 0xb1, 0xac,
+ 0xb6, 0x9a, 0xe4, 0x68, 0x0f, 0x97, 0x4a, 0x44, 0xa2, 0x87, 0x01, 0x82,
+ 0xd4, 0x25, 0xbd, 0x01, 0xbc, 0x35, 0x8a, 0x6d, 0xb7, 0x7c, 0x48, 0xaa,
+ 0x92, 0xd7, 0x57, 0x76, 0x6a, 0xb0, 0xc9, 0x46, 0xa6, 0xbe, 0xbf, 0x0f,
+ 0xf0, 0xea, 0x62, 0x57, 0x71, 0x42, 0xf6, 0x67, 0xa7, 0xa1, 0x50, 0x87,
+ 0x14, 0x8e, 0x32, 0xd0, 0x5e, 0xc9, 0x7b, 0x79, 0x7e, 0xfa, 0x17, 0xc7,
+ 0xad, 0xbd, 0xc3, 0x98, 0x79, 0x45, 0xfb, 0x7f, 0xf7, 0xe6, 0x9f, 0x77,
+ 0xb3, 0x44, 0xc3, 0xaf, 0x6b, 0x61, 0x6a, 0x04, 0x68, 0x24, 0x2d, 0x31,
+ 0xf1, 0x28, 0x2c, 0xf4, 0xf0, 0x07, 0xfe, 0xfd, 0x66, 0x98, 0x77, 0x37,
+ 0x7b, 0x80, 0x1f, 0xb2, 0x49, 0xe4, 0xa6, 0x24, 0x72, 0x42, 0xf4, 0xca,
+ 0x91, 0x80, 0xa1, 0xb2, 0x0a, 0xc9, 0xc0, 0x93, 0xa7, 0x22, 0x0b, 0x13,
+ 0x8a, 0xb2, 0x75, 0x4b, 0x66, 0xf9, 0x87, 0x3a, 0x51, 0x97, 0xc7, 0x1e,
+ 0x2b, 0x61, 0x81, 0x5c, 0xf0, 0xf8, 0x4c, 0xdb, 0x36, 0xc7, 0xba, 0x49,
+ 0xd9, 0x04, 0x6a, 0x95, 0xb0, 0x7f, 0xfc, 0xce, 0xca, 0x23, 0xad, 0xf9,
+ 0xaf, 0x8a, 0x72, 0x8e, 0xab, 0xb8, 0x8b, 0x7e, 0xf7, 0x39, 0xa6, 0x22,
+ 0x56, 0x03, 0x72, 0x06, 0xc3, 0x57, 0x1f, 0x32, 0xaa, 0xb5, 0xa6, 0x00,
+ 0x67, 0x88, 0x4b, 0x40, 0xe9, 0x5e, 0x4a, 0x6f, 0x76, 0xe8
+};
+static unsigned int test_device_cert_der_len = 982;
+static unsigned char test_device_cert_key_der[] = {
+ 0x30, 0x82, 0x04, 0xa4, 0x02, 0x01, 0x00, 0x02, 0x82, 0x01, 0x01, 0x00,
+ 0xae, 0x03, 0x2c, 0xec, 0xa2, 0x79, 0xd1, 0x15, 0x20, 0x88, 0x4d, 0xcd,
+ 0xa2, 0x1b, 0x05, 0xe3, 0xbd, 0x55, 0xad, 0xc6, 0x1f, 0x64, 0xe8, 0xb5,
+ 0xc5, 0x0d, 0x67, 0xfc, 0x7e, 0xda, 0xfb, 0x70, 0xf6, 0xc9, 0x47, 0x87,
+ 0x3a, 0xaa, 0x88, 0x00, 0xf1, 0xa7, 0xf7, 0xe1, 0xf5, 0x2c, 0x54, 0x0e,
+ 0x33, 0xda, 0xbe, 0x9c, 0x66, 0x30, 0xd9, 0x40, 0xeb, 0x1d, 0xce, 0xe1,
+ 0x55, 0x15, 0x2b, 0x11, 0x47, 0x6c, 0x7e, 0x88, 0xc6, 0x24, 0xcf, 0x87,
+ 0x1b, 0xb5, 0x1f, 0x47, 0xb9, 0xef, 0xad, 0x29, 0xd3, 0x2e, 0x43, 0xee,
+ 0x39, 0xdd, 0x09, 0x54, 0xba, 0xfc, 0xed, 0xbc, 0x2e, 0x0e, 0x53, 0x15,
+ 0x37, 0xcb, 0xc5, 0xf5, 0xee, 0x70, 0x2a, 0xe8, 0x01, 0x6d, 0xb1, 0x39,
+ 0x94, 0x5a, 0xc2, 0x8a, 0x00, 0x04, 0xa9, 0xff, 0xea, 0x56, 0xf7, 0xd7,
+ 0xa8, 0x1b, 0xa4, 0x26, 0xcd, 0x28, 0xaf, 0xfa, 0x52, 0x85, 0x1c, 0x26,
+ 0x3e, 0x5e, 0x01, 0xf7, 0xe1, 0x66, 0xff, 0xac, 0xad, 0x9c, 0x98, 0x2f,
+ 0xe0, 0x7e, 0x9f, 0xf1, 0x33, 0x31, 0xc3, 0x7f, 0xe6, 0x58, 0x5d, 0xd8,
+ 0x5f, 0x7d, 0x2b, 0x5a, 0x55, 0xcf, 0xb1, 0x91, 0x53, 0x41, 0x04, 0xac,
+ 0x86, 0x5e, 0x01, 0x35, 0x2b, 0x74, 0x8d, 0x46, 0x4d, 0x48, 0xc0, 0x5f,
+ 0x83, 0x67, 0xb5, 0x6d, 0x52, 0x3f, 0x3e, 0xe6, 0xec, 0xf8, 0x2e, 0x10,
+ 0x28, 0xdb, 0x69, 0xa6, 0x9d, 0x4b, 0xde, 0x19, 0x2e, 0xd2, 0x5f, 0xc8,
+ 0xa9, 0x3b, 0x52, 0xe9, 0xb2, 0xcd, 0x6e, 0x19, 0x22, 0xf9, 0x99, 0xa6,
+ 0xcc, 0xf5, 0xd3, 0xec, 0xff, 0x0c, 0x77, 0x6f, 0x25, 0x92, 0x07, 0x4c,
+ 0x64, 0x7d, 0x34, 0x49, 0x6f, 0xff, 0x0a, 0xa8, 0x15, 0x64, 0x72, 0x2d,
+ 0x4f, 0x42, 0x05, 0xe8, 0x2b, 0x01, 0xf1, 0xe3, 0x65, 0x94, 0x23, 0xd9,
+ 0xdf, 0x5e, 0x3b, 0xb5, 0x02, 0x03, 0x01, 0x00, 0x01, 0x02, 0x82, 0x01,
+ 0x01, 0x00, 0xa5, 0x22, 0x2c, 0x52, 0xd0, 0x09, 0x4c, 0x4a, 0x81, 0x59,
+ 0xf8, 0x83, 0xa9, 0x4f, 0x7d, 0xb2, 0x56, 0xad, 0xe5, 0x3f, 0xfb, 0xf0,
+ 0xf6, 0x09, 0xf1, 0x5b, 0x3c, 0x90, 0x58, 0x0e, 0x15, 0xc9, 0x68, 0xd9,
+ 0x30, 0x40, 0xfb, 0x82, 0x73, 0x98, 0x79, 0xbb, 0xcd, 0xb8, 0x27, 0xc3,
+ 0x8e, 0x6c, 0xff, 0xf6, 0x99, 0x26, 0xb0, 0xaf, 0xb0, 0xac, 0x33, 0xb3,
+ 0x50, 0xed, 0x73, 0xa1, 0xa8, 0x02, 0x38, 0xc6, 0x93, 0xf9, 0xd6, 0x17,
+ 0x7e, 0xbd, 0x97, 0xa4, 0xb5, 0x6f, 0x8a, 0xdb, 0x11, 0x78, 0x7c, 0x89,
+ 0x0e, 0x3c, 0x17, 0xbb, 0x54, 0x2c, 0x8d, 0x5a, 0x93, 0x7d, 0x1e, 0x33,
+ 0xc7, 0xd2, 0x7d, 0xe5, 0xaa, 0x12, 0x2d, 0xd9, 0x52, 0x4e, 0x63, 0x74,
+ 0xa6, 0x57, 0x9f, 0x1a, 0xd6, 0x3c, 0xc1, 0xb1, 0xab, 0x66, 0x4a, 0x0b,
+ 0x88, 0x1d, 0xa6, 0xd1, 0xbc, 0x60, 0x7a, 0x17, 0x1f, 0x8f, 0x9b, 0x35,
+ 0x57, 0xf8, 0xd0, 0x1c, 0xd3, 0xa6, 0x56, 0xc8, 0x03, 0x9c, 0x08, 0x3b,
+ 0x1b, 0x5b, 0xc2, 0x03, 0x3b, 0x3a, 0xa4, 0xe8, 0xed, 0x75, 0x66, 0xb0,
+ 0x85, 0x56, 0x40, 0xfe, 0xae, 0x97, 0x7e, 0xc0, 0x79, 0x49, 0x13, 0x8b,
+ 0x01, 0x0c, 0xae, 0x4c, 0x3d, 0x54, 0x47, 0xc5, 0x51, 0x40, 0x3d, 0xcc,
+ 0x4d, 0x17, 0xb3, 0x4e, 0x1d, 0x85, 0x1c, 0x41, 0x07, 0x03, 0x5e, 0xf9,
+ 0xfa, 0x17, 0x81, 0x24, 0x34, 0xaa, 0xbf, 0x67, 0x73, 0xb6, 0x9c, 0x67,
+ 0x36, 0xd9, 0xee, 0xf7, 0x86, 0x4c, 0x4d, 0x79, 0xca, 0xd7, 0xfd, 0x72,
+ 0xf9, 0xb3, 0x73, 0xc3, 0x57, 0xe5, 0x39, 0x72, 0x93, 0x56, 0xc2, 0xec,
+ 0xf8, 0x25, 0xe4, 0x8f, 0xba, 0xd0, 0x6f, 0x23, 0x8c, 0x39, 0x9e, 0x05,
+ 0x1a, 0x4e, 0xdc, 0x5e, 0xcd, 0x17, 0x59, 0x94, 0x37, 0x22, 0xb7, 0x39,
+ 0x50, 0x65, 0xdc, 0x91, 0x3c, 0xe1, 0x02, 0x81, 0x81, 0x00, 0xe4, 0xc6,
+ 0x42, 0xe5, 0xea, 0xe5, 0x32, 0xf3, 0x51, 0x36, 0x7b, 0x8c, 0x5b, 0x72,
+ 0x24, 0x1a, 0x4a, 0x44, 0x4f, 0x64, 0xe5, 0xa7, 0x74, 0xd9, 0xb2, 0x29,
+ 0x8a, 0x08, 0xcf, 0x9b, 0xd2, 0x9d, 0xc4, 0x20, 0x4c, 0xd3, 0x60, 0x4d,
+ 0xf7, 0xb7, 0xac, 0x92, 0x6b, 0x2b, 0x95, 0x73, 0x6e, 0x57, 0x00, 0x20,
+ 0x9d, 0xb2, 0xf6, 0xbd, 0x0b, 0xbb, 0xaa, 0x7e, 0x7e, 0x3e, 0x53, 0xfb,
+ 0x79, 0x7e, 0x45, 0xd5, 0x2e, 0xab, 0x5e, 0xff, 0x5c, 0x0a, 0x45, 0x2d,
+ 0x27, 0x19, 0xb0, 0x59, 0x0a, 0x39, 0x89, 0xf6, 0xae, 0xc6, 0xe2, 0xd1,
+ 0x07, 0x58, 0xbe, 0x95, 0x27, 0xaf, 0xf7, 0xa6, 0x2f, 0xaa, 0x37, 0x25,
+ 0x7c, 0x7b, 0xd3, 0xda, 0x13, 0x76, 0x0a, 0xb6, 0x6c, 0x99, 0x53, 0x5d,
+ 0xa5, 0x75, 0xfa, 0x10, 0x9b, 0x7f, 0xfe, 0xd7, 0xb4, 0x18, 0x95, 0xa8,
+ 0x65, 0x85, 0x07, 0xc5, 0xc4, 0xad, 0x02, 0x81, 0x81, 0x00, 0xc2, 0xb8,
+ 0x8e, 0xed, 0x9d, 0x4a, 0x1f, 0x9c, 0xda, 0x73, 0xf0, 0x2c, 0x35, 0x91,
+ 0xe4, 0x40, 0x78, 0xe1, 0x12, 0xf3, 0x08, 0xef, 0xdf, 0x97, 0xa0, 0xb0,
+ 0xdd, 0xea, 0xc2, 0xb9, 0x5b, 0xf8, 0xa1, 0xac, 0x32, 0xfd, 0xb8, 0xe9,
+ 0x0f, 0xed, 0xfd, 0xe0, 0xdc, 0x38, 0x90, 0x5e, 0xf5, 0x4c, 0x02, 0xc3,
+ 0x1a, 0x72, 0x18, 0xf7, 0xfe, 0xb7, 0xb8, 0x2a, 0xf8, 0x72, 0xbb, 0x99,
+ 0x56, 0xec, 0x85, 0x58, 0x31, 0x7e, 0x64, 0xdf, 0x02, 0x05, 0xe3, 0xb2,
+ 0xbb, 0xe2, 0x1b, 0xd6, 0x43, 0x73, 0xf8, 0x0f, 0xaf, 0x89, 0x57, 0x44,
+ 0x5f, 0x30, 0x1c, 0xe5, 0x78, 0xbf, 0x0b, 0xe7, 0x4b, 0xbe, 0x80, 0x2f,
+ 0x3d, 0x35, 0x44, 0xfc, 0x9e, 0x0d, 0x85, 0x5d, 0x94, 0x6e, 0xe9, 0x6a,
+ 0x72, 0xa7, 0x46, 0xd8, 0x64, 0x6c, 0xe9, 0x61, 0x92, 0xa0, 0xb6, 0xd1,
+ 0xee, 0xa6, 0xa6, 0xf4, 0x2c, 0x29, 0x02, 0x81, 0x81, 0x00, 0xb4, 0xa7,
+ 0x7b, 0x1c, 0x64, 0x29, 0x29, 0xda, 0xca, 0x3e, 0xe3, 0xc1, 0x2a, 0x55,
+ 0x2f, 0xfd, 0x32, 0xb8, 0x4e, 0x99, 0xb6, 0x60, 0x4d, 0xfd, 0xba, 0x9a,
+ 0xe2, 0xcd, 0xa2, 0x63, 0xc2, 0x25, 0xa3, 0x42, 0x7e, 0x68, 0x4c, 0x9c,
+ 0x45, 0x09, 0x5d, 0xd5, 0x21, 0x9c, 0x01, 0x20, 0x6d, 0xf9, 0x75, 0xb8,
+ 0x4b, 0xcf, 0x8e, 0xd8, 0x29, 0xf3, 0xbf, 0xe6, 0xb3, 0x7a, 0x34, 0x87,
+ 0x58, 0xa1, 0x46, 0x33, 0xd9, 0xee, 0xa9, 0xcd, 0xac, 0xb8, 0xcf, 0x77,
+ 0xa0, 0x70, 0xc0, 0xb9, 0x0f, 0x41, 0xf0, 0x98, 0x43, 0xdb, 0xfa, 0x30,
+ 0x66, 0x44, 0xc5, 0xfa, 0xb2, 0xa4, 0x5a, 0x43, 0x79, 0x50, 0x48, 0xcb,
+ 0xe9, 0x49, 0x3f, 0x39, 0xee, 0x34, 0x40, 0xb1, 0x5d, 0x80, 0x96, 0x3c,
+ 0x54, 0xf4, 0x9c, 0xcb, 0x90, 0x7f, 0xba, 0x96, 0x4b, 0x39, 0x3e, 0xb5,
+ 0x03, 0xb5, 0xd1, 0x35, 0x72, 0xe1, 0x02, 0x81, 0x80, 0x60, 0x14, 0xd5,
+ 0x61, 0xe6, 0x24, 0xf7, 0x28, 0x5c, 0x9a, 0xac, 0xbe, 0x03, 0xc8, 0xf3,
+ 0x49, 0xe4, 0xdb, 0x9a, 0x90, 0x15, 0xae, 0xd7, 0x33, 0x68, 0x75, 0x1d,
+ 0x6b, 0x83, 0x9e, 0x17, 0x05, 0xbe, 0x30, 0xcc, 0x10, 0x6a, 0x37, 0x86,
+ 0x46, 0xb6, 0xe9, 0x47, 0x81, 0x19, 0xab, 0xe1, 0x7a, 0x1a, 0x3a, 0xcf,
+ 0x47, 0xd1, 0x8e, 0x3d, 0x3f, 0xc6, 0x3e, 0x5d, 0xcd, 0xaf, 0x47, 0xe0,
+ 0x9e, 0x60, 0xc5, 0xbd, 0xd6, 0x52, 0x4b, 0xc0, 0x21, 0xcb, 0xd3, 0x1b,
+ 0xe6, 0x5c, 0x3a, 0x03, 0x9a, 0xab, 0xa2, 0x81, 0xc9, 0x51, 0x28, 0x49,
+ 0x97, 0xe2, 0x0a, 0x50, 0xe4, 0x64, 0x29, 0x43, 0x34, 0xc2, 0xe7, 0x8c,
+ 0x5a, 0x46, 0xaa, 0x28, 0x0b, 0x1f, 0xed, 0xa7, 0x1a, 0x7b, 0x4e, 0xad,
+ 0x38, 0x61, 0x3a, 0xd1, 0x82, 0xf4, 0x3d, 0xd3, 0x2e, 0x3e, 0x47, 0xa4,
+ 0x6c, 0xd3, 0x20, 0xd4, 0xd1, 0x02, 0x81, 0x80, 0x68, 0x1a, 0x8d, 0x3c,
+ 0x18, 0x3f, 0x42, 0x5e, 0x38, 0x6d, 0x0a, 0x1e, 0x52, 0xd5, 0x8f, 0xd6,
+ 0x32, 0xff, 0x7c, 0x1c, 0xf3, 0x20, 0x8b, 0x92, 0xa5, 0x44, 0xff, 0x08,
+ 0x21, 0xa1, 0xce, 0x68, 0x8b, 0x03, 0xe0, 0x90, 0xeb, 0x01, 0x4e, 0x85,
+ 0xf9, 0xc5, 0xb7, 0x86, 0xee, 0xd0, 0x59, 0x10, 0x73, 0x98, 0x2a, 0xcb,
+ 0xf6, 0xfe, 0x0d, 0xba, 0x07, 0x91, 0x18, 0xf6, 0xbc, 0x93, 0x8a, 0x91,
+ 0xdd, 0x80, 0x16, 0x37, 0xdf, 0x75, 0x46, 0x87, 0x68, 0xee, 0xf4, 0x76,
+ 0x0c, 0xc5, 0x87, 0x38, 0xf5, 0xb6, 0xda, 0x8a, 0xee, 0x62, 0xc8, 0xc0,
+ 0xa2, 0x8d, 0xbf, 0xd5, 0xf8, 0xba, 0xb5, 0x74, 0xf0, 0x07, 0xa6, 0x1c,
+ 0xcf, 0x76, 0x61, 0xbe, 0xa4, 0x88, 0x4a, 0x95, 0xb0, 0xa3, 0x70, 0x73,
+ 0xa1, 0x6f, 0x73, 0xf0, 0xe8, 0x38, 0x8d, 0xe8, 0xd0, 0x7e, 0x2c, 0x0c,
+ 0xdc, 0x21, 0xfa, 0xc1
+};
+static unsigned int test_device_cert_key_der_len = 1192;
diff --git a/test/regression/interoperability_test/nx_secure_test/test_scripts/demo_openssl_client.sh b/test/regression/interoperability_test/nx_secure_test/test_scripts/demo_openssl_client.sh
new file mode 100755
index 00000000..18de9a85
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/test_scripts/demo_openssl_client.sh
@@ -0,0 +1,8 @@
+#!/bin/bash
+
+date
+echo $0
+echo $1
+echo $2
+echo $3
+echo "GET / HTTP/1.1" | openssl s_client -connect "$1":"$2" "$3" -ign_eof
diff --git a/test/regression/interoperability_test/nx_secure_test/test_scripts/openssl_1_1_echo_client.sh b/test/regression/interoperability_test/nx_secure_test/test_scripts/openssl_1_1_echo_client.sh
new file mode 100755
index 00000000..62782bc1
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/test_scripts/openssl_1_1_echo_client.sh
@@ -0,0 +1,12 @@
+#!/bin/bash
+
+date
+#Show script name.
+echo $0 $@
+
+arg1=$1
+arg2=$2
+shift 2
+
+cd "$( dirname "$0" )"
+echo "hello" | openssl-1.1 s_client -connect "$arg1":"$arg2" -ign_eof $@
diff --git a/test/regression/interoperability_test/nx_secure_test/test_scripts/openssl_1_1_echo_server.sh b/test/regression/interoperability_test/nx_secure_test/test_scripts/openssl_1_1_echo_server.sh
new file mode 100755
index 00000000..f37bc537
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/test_scripts/openssl_1_1_echo_server.sh
@@ -0,0 +1,12 @@
+#!/bin/bash
+
+date
+#Show script name.
+echo $0 $@
+
+arg1=$1
+arg2=$2
+shift 2
+
+cd "$( dirname "$0" )"
+(sleep 4;echo "hello") | openssl-1.1 s_server -key "$arg1" -cert "$arg2" -naccept 1 $@
diff --git a/test/regression/interoperability_test/nx_secure_test/test_scripts/openssl_echo_client.sh b/test/regression/interoperability_test/nx_secure_test/test_scripts/openssl_echo_client.sh
new file mode 100755
index 00000000..12ac5654
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/test_scripts/openssl_echo_client.sh
@@ -0,0 +1,12 @@
+#!/bin/bash
+
+date
+#Show script name.
+echo $0 $@
+
+arg1=$1
+arg2=$2
+shift 2
+
+cd "$( dirname "$0" )"
+echo "hello" | openssl s_client -connect "$arg1":"$arg2" -ign_eof $@
diff --git a/test/regression/interoperability_test/nx_secure_test/test_scripts/openssl_echo_server.sh b/test/regression/interoperability_test/nx_secure_test/test_scripts/openssl_echo_server.sh
new file mode 100755
index 00000000..806fdb99
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/test_scripts/openssl_echo_server.sh
@@ -0,0 +1,12 @@
+#!/bin/bash
+
+date
+#Show script name.
+echo $0 $@
+
+arg1=$1
+arg2=$2
+shift 2
+
+cd "$( dirname "$0" )"
+echo "hello" | openssl s_server -key "$arg1" -cert "$arg2" -naccept 1 $@
diff --git a/test/regression/interoperability_test/nx_secure_test/test_scripts/sleep.sh b/test/regression/interoperability_test/nx_secure_test/test_scripts/sleep.sh
new file mode 100755
index 00000000..f5986bc0
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/test_scripts/sleep.sh
@@ -0,0 +1,5 @@
+#! /bin/bash
+
+echo $0 is called.
+sleep $1
+echo hello
diff --git a/test/regression/interoperability_test/nx_secure_test/test_scripts/sleep_5_secs_then_echo_hello.sh b/test/regression/interoperability_test/nx_secure_test/test_scripts/sleep_5_secs_then_echo_hello.sh
new file mode 100755
index 00000000..46226c71
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/test_scripts/sleep_5_secs_then_echo_hello.sh
@@ -0,0 +1,4 @@
+#!/bin/bash
+
+sleep 5
+echo hello
diff --git a/test/regression/interoperability_test/nx_secure_test/test_scripts/tcp_test.py b/test/regression/interoperability_test/nx_secure_test/test_scripts/tcp_test.py
new file mode 100755
index 00000000..82b88691
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/test_scripts/tcp_test.py
@@ -0,0 +1,7 @@
+#!/usr/bin/python
+
+import socket
+
+sock = socket.socket( socket.AF_INET, socket.SOCK_STREAM)
+conn = sock.connect( ("10.0.0.1", 8888))
+sock.close()
diff --git a/test/regression/interoperability_test/nx_secure_test/test_scripts/test.sh b/test/regression/interoperability_test/nx_secure_test/test_scripts/test.sh
new file mode 100755
index 00000000..78583180
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/test_scripts/test.sh
@@ -0,0 +1,6 @@
+#!/bin/bash
+
+IFS=:
+for i in "a:b";do
+ echo "$i\n"
+done
diff --git a/test/regression/interoperability_test/nx_secure_test/test_server.der.c b/test/regression/interoperability_test/nx_secure_test/test_server.der.c
new file mode 100644
index 00000000..0cbd741b
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/test_server.der.c
@@ -0,0 +1,98 @@
+unsigned char test_server_der[] = {
+ 0x30, 0x82, 0x05, 0xe5, 0x30, 0x82, 0x03, 0xcd, 0xa0, 0x03, 0x02, 0x01, 0x02, 0x02, 0x01, 0x07,
+ 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0b, 0x05, 0x00, 0x30,
+ 0x81, 0x89, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31,
+ 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x0a, 0x43, 0x61, 0x6c, 0x69, 0x66, 0x6f,
+ 0x72, 0x6e, 0x69, 0x61, 0x31, 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x07, 0x0c, 0x0d, 0x53,
+ 0x61, 0x6e, 0x20, 0x46, 0x72, 0x61, 0x6e, 0x63, 0x69, 0x73, 0x63, 0x6f, 0x31, 0x10, 0x30, 0x0e,
+ 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x07, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x31, 0x13,
+ 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x0b, 0x0c, 0x0a, 0x4f, 0x70, 0x65, 0x72, 0x61, 0x74, 0x69,
+ 0x6f, 0x6e, 0x73, 0x31, 0x26, 0x30, 0x24, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c, 0x1d, 0x45, 0x4c,
+ 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74,
+ 0x65, 0x20, 0x41, 0x75, 0x74, 0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x30, 0x1e, 0x17, 0x0d, 0x31,
+ 0x38, 0x30, 0x36, 0x30, 0x35, 0x30, 0x37, 0x31, 0x37, 0x31, 0x38, 0x5a, 0x17, 0x0d, 0x32, 0x38,
+ 0x30, 0x36, 0x30, 0x32, 0x30, 0x37, 0x31, 0x37, 0x31, 0x38, 0x5a, 0x30, 0x81, 0x82, 0x31, 0x0b,
+ 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31, 0x13, 0x30, 0x11, 0x06,
+ 0x03, 0x55, 0x04, 0x08, 0x13, 0x0a, 0x43, 0x61, 0x6c, 0x69, 0x66, 0x6f, 0x72, 0x6e, 0x69, 0x61,
+ 0x31, 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x07, 0x13, 0x0d, 0x53, 0x61, 0x6e, 0x20, 0x46,
+ 0x72, 0x61, 0x6e, 0x63, 0x69, 0x73, 0x63, 0x6f, 0x31, 0x0f, 0x30, 0x0d, 0x06, 0x03, 0x55, 0x04,
+ 0x0a, 0x13, 0x06, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63, 0x31, 0x19, 0x30, 0x17, 0x06, 0x09, 0x2a,
+ 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x09, 0x01, 0x16, 0x0a, 0x4f, 0x70, 0x65, 0x72, 0x61, 0x74,
+ 0x69, 0x6f, 0x6e, 0x73, 0x31, 0x1a, 0x30, 0x18, 0x06, 0x03, 0x55, 0x04, 0x03, 0x14, 0x11, 0x74,
+ 0x65, 0x73, 0x74, 0x5f, 0x73, 0x65, 0x72, 0x76, 0x65, 0x72, 0x2e, 0x6c, 0x6f, 0x63, 0x61, 0x6c,
+ 0x30, 0x82, 0x01, 0x22, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01,
+ 0x01, 0x05, 0x00, 0x03, 0x82, 0x01, 0x0f, 0x00, 0x30, 0x82, 0x01, 0x0a, 0x02, 0x82, 0x01, 0x01,
+ 0x00, 0xd0, 0x6a, 0x52, 0x6e, 0xe6, 0x36, 0x44, 0x08, 0x62, 0x8c, 0xbb, 0xfe, 0xa2, 0xcf, 0xa6,
+ 0xd2, 0x80, 0xd7, 0x56, 0x88, 0x43, 0xfb, 0x48, 0xeb, 0xfe, 0x53, 0x92, 0xbf, 0xee, 0x6a, 0xa2,
+ 0x44, 0x3c, 0x69, 0xfa, 0x9e, 0x2f, 0x44, 0x0d, 0x98, 0x2e, 0x2f, 0x72, 0x64, 0xf7, 0x86, 0xfe,
+ 0x4c, 0x18, 0x1a, 0x99, 0xcb, 0x85, 0xc9, 0xb7, 0x66, 0x9e, 0xc8, 0xfb, 0x33, 0xed, 0x6f, 0x32,
+ 0x87, 0x96, 0xae, 0xb1, 0x62, 0x11, 0xed, 0x30, 0xf4, 0x87, 0xf2, 0x32, 0x46, 0x21, 0x00, 0x25,
+ 0x97, 0xff, 0xf7, 0xf8, 0x71, 0xbb, 0x7e, 0x84, 0xf2, 0xd6, 0x1a, 0x5b, 0xd7, 0x57, 0xa0, 0x1e,
+ 0xf8, 0x8e, 0xe0, 0x04, 0xe6, 0x71, 0xa4, 0xcd, 0xd0, 0xe1, 0x8c, 0x0d, 0x3d, 0xd9, 0x20, 0x7c,
+ 0x2c, 0x56, 0xde, 0x02, 0xec, 0xdb, 0x3f, 0x4e, 0x4a, 0x77, 0xdf, 0x23, 0xa4, 0xc1, 0x8c, 0x0b,
+ 0x03, 0x46, 0x21, 0x76, 0x4c, 0x85, 0x2c, 0x55, 0xa7, 0x6d, 0x05, 0x2d, 0x0f, 0x91, 0x94, 0xc3,
+ 0x60, 0xfc, 0x1d, 0xd5, 0xd6, 0x94, 0x19, 0x0b, 0x22, 0xb0, 0x5b, 0xc0, 0x94, 0x16, 0x66, 0x2c,
+ 0xe4, 0x7a, 0x5c, 0x11, 0xad, 0x7d, 0x40, 0xb1, 0x84, 0x78, 0x04, 0xb1, 0xa6, 0x1c, 0x73, 0xaa,
+ 0xb5, 0xfa, 0xcd, 0x18, 0xa5, 0x50, 0xfe, 0xb9, 0xab, 0xb0, 0x7d, 0xce, 0x0d, 0x49, 0x46, 0x57,
+ 0x65, 0x53, 0x4c, 0xec, 0x55, 0xe1, 0xc5, 0x05, 0x95, 0xbd, 0x52, 0x7e, 0xf1, 0x0c, 0xad, 0x84,
+ 0x24, 0xd9, 0xce, 0xc8, 0x8e, 0x47, 0x57, 0x00, 0xaf, 0x03, 0x8b, 0x31, 0x28, 0x3e, 0xbc, 0xc4,
+ 0x6c, 0x14, 0x79, 0xc2, 0x87, 0x63, 0xd8, 0x89, 0xdc, 0x35, 0x1f, 0x8f, 0x55, 0x62, 0xf0, 0xa8,
+ 0x8e, 0xdd, 0x82, 0xf0, 0x6b, 0x90, 0x02, 0xc8, 0x8f, 0x80, 0x1a, 0x82, 0xb4, 0x82, 0xd3, 0x4b,
+ 0xf9, 0x02, 0x03, 0x01, 0x00, 0x01, 0xa3, 0x82, 0x01, 0x5b, 0x30, 0x82, 0x01, 0x57, 0x30, 0x09,
+ 0x06, 0x03, 0x55, 0x1d, 0x13, 0x04, 0x02, 0x30, 0x00, 0x30, 0x11, 0x06, 0x09, 0x60, 0x86, 0x48,
+ 0x01, 0x86, 0xf8, 0x42, 0x01, 0x01, 0x04, 0x04, 0x03, 0x02, 0x06, 0x40, 0x30, 0x33, 0x06, 0x09,
+ 0x60, 0x86, 0x48, 0x01, 0x86, 0xf8, 0x42, 0x01, 0x0d, 0x04, 0x26, 0x16, 0x24, 0x4f, 0x70, 0x65,
+ 0x6e, 0x53, 0x53, 0x4c, 0x20, 0x47, 0x65, 0x6e, 0x65, 0x72, 0x61, 0x74, 0x65, 0x64, 0x20, 0x53,
+ 0x65, 0x72, 0x76, 0x65, 0x72, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74,
+ 0x65, 0x30, 0x1d, 0x06, 0x03, 0x55, 0x1d, 0x0e, 0x04, 0x16, 0x04, 0x14, 0x36, 0x20, 0xd3, 0x52,
+ 0xa2, 0x16, 0x07, 0x94, 0x04, 0xb5, 0x37, 0xb6, 0xab, 0x53, 0xa5, 0xf3, 0xe9, 0x25, 0xcb, 0x3a,
+ 0x30, 0x81, 0xb6, 0x06, 0x03, 0x55, 0x1d, 0x23, 0x04, 0x81, 0xae, 0x30, 0x81, 0xab, 0x80, 0x14,
+ 0x2d, 0x7c, 0x48, 0x9c, 0x8b, 0x54, 0x14, 0x21, 0x3f, 0xe2, 0x75, 0xa5, 0x99, 0x8a, 0x77, 0x64,
+ 0xdf, 0x2b, 0xd6, 0x88, 0xa1, 0x81, 0x8f, 0xa4, 0x81, 0x8c, 0x30, 0x81, 0x89, 0x31, 0x0b, 0x30,
+ 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03,
+ 0x55, 0x04, 0x08, 0x0c, 0x0a, 0x43, 0x61, 0x6c, 0x69, 0x66, 0x6f, 0x72, 0x6e, 0x69, 0x61, 0x31,
+ 0x16, 0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x07, 0x0c, 0x0d, 0x53, 0x61, 0x6e, 0x20, 0x46, 0x72,
+ 0x61, 0x6e, 0x63, 0x69, 0x73, 0x63, 0x6f, 0x31, 0x10, 0x30, 0x0e, 0x06, 0x03, 0x55, 0x04, 0x0a,
+ 0x0c, 0x07, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55,
+ 0x04, 0x0b, 0x0c, 0x0a, 0x4f, 0x70, 0x65, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x31, 0x26,
+ 0x30, 0x24, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c, 0x1d, 0x45, 0x4c, 0x20, 0x49, 0x6e, 0x63, 0x2e,
+ 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74, 0x65, 0x20, 0x41, 0x75, 0x74,
+ 0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x82, 0x01, 0x01, 0x30, 0x1d, 0x06, 0x03, 0x55, 0x1d, 0x25,
+ 0x04, 0x16, 0x30, 0x14, 0x06, 0x08, 0x2b, 0x06, 0x01, 0x05, 0x05, 0x07, 0x03, 0x01, 0x06, 0x08,
+ 0x2b, 0x06, 0x01, 0x05, 0x05, 0x08, 0x02, 0x02, 0x30, 0x0b, 0x06, 0x03, 0x55, 0x1d, 0x0f, 0x04,
+ 0x04, 0x03, 0x02, 0x05, 0xa0, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01,
+ 0x01, 0x0b, 0x05, 0x00, 0x03, 0x82, 0x02, 0x01, 0x00, 0xbe, 0x9f, 0x3c, 0x88, 0xdc, 0x8a, 0xc3,
+ 0xdc, 0x5a, 0xbe, 0x68, 0x5b, 0xea, 0xac, 0x2a, 0x83, 0x6d, 0xb9, 0xd0, 0xb0, 0x7b, 0x19, 0x5a,
+ 0xef, 0x09, 0x46, 0x3b, 0x6e, 0x58, 0xeb, 0xec, 0x08, 0x0b, 0xc8, 0x7b, 0x94, 0x5d, 0xab, 0x67,
+ 0x03, 0x6c, 0x8a, 0x35, 0x18, 0x4d, 0x2a, 0x1f, 0x8d, 0xa2, 0x78, 0xae, 0x89, 0x90, 0x78, 0x49,
+ 0x9a, 0xeb, 0xac, 0xba, 0x44, 0x4c, 0xea, 0xe0, 0x67, 0xb7, 0xfb, 0xbc, 0x43, 0xd7, 0xbe, 0x1c,
+ 0xe3, 0xa8, 0x43, 0x2b, 0x1e, 0xc0, 0xc9, 0x88, 0xa9, 0x2b, 0x5c, 0x10, 0xe8, 0x4f, 0x23, 0x96,
+ 0x40, 0x7a, 0x41, 0x1f, 0xa0, 0x71, 0x6f, 0x5c, 0xaf, 0x65, 0xf1, 0x9f, 0x61, 0xc5, 0x21, 0xbb,
+ 0x05, 0x7f, 0x89, 0x72, 0x55, 0x9a, 0x71, 0x37, 0x45, 0x36, 0xe4, 0x75, 0x67, 0xf8, 0x5b, 0x3c,
+ 0x6c, 0x7b, 0xf0, 0x5d, 0x23, 0xc6, 0x46, 0x2d, 0x64, 0x27, 0x58, 0x26, 0xc5, 0x54, 0xc9, 0x86,
+ 0x75, 0x76, 0x95, 0xf4, 0xf7, 0x64, 0xe1, 0x1b, 0x7a, 0x6b, 0xf5, 0x52, 0x8e, 0x05, 0x93, 0xf9,
+ 0x9d, 0x50, 0x95, 0xd1, 0xaf, 0x7d, 0xfd, 0x89, 0x7d, 0x30, 0xbe, 0xd7, 0x16, 0xb7, 0xb0, 0x3b,
+ 0x03, 0xe3, 0xfe, 0x64, 0x57, 0x1e, 0x70, 0x9f, 0x54, 0xa4, 0xd5, 0x75, 0x45, 0xad, 0x34, 0x5f,
+ 0x86, 0xbb, 0xb9, 0x20, 0x01, 0x9a, 0xd7, 0xc8, 0x9d, 0xb4, 0xc2, 0x70, 0xd3, 0x7e, 0x06, 0xd4,
+ 0x60, 0xfd, 0x3e, 0x67, 0xd6, 0x91, 0x25, 0xc8, 0x1f, 0x43, 0x0a, 0xcc, 0x3f, 0x68, 0xfc, 0x68,
+ 0xe2, 0xf8, 0xf8, 0xe8, 0xc3, 0xae, 0xcb, 0x9a, 0xbb, 0x68, 0x65, 0xf1, 0x93, 0x89, 0x4a, 0x23,
+ 0x86, 0x46, 0xe7, 0xe1, 0x4b, 0x85, 0xf9, 0xb6, 0x49, 0x00, 0x0d, 0x00, 0xe8, 0x66, 0x92, 0x38,
+ 0x75, 0xc0, 0xf6, 0x9a, 0x61, 0xae, 0x26, 0xe0, 0x4f, 0x5c, 0x4b, 0x2c, 0x05, 0x54, 0x83, 0xb4,
+ 0x12, 0xc4, 0xc1, 0x3f, 0xde, 0x48, 0x54, 0xa9, 0x74, 0x5b, 0x77, 0x15, 0x0f, 0x1b, 0xf2, 0x21,
+ 0xe3, 0x29, 0x0b, 0xb6, 0x3b, 0xc9, 0x66, 0x6e, 0x76, 0x32, 0xd1, 0x86, 0x8b, 0xe7, 0x1f, 0xb5,
+ 0xc3, 0xc6, 0x57, 0x35, 0xdd, 0x28, 0x7c, 0x49, 0x40, 0x3a, 0x45, 0xc6, 0xfd, 0xfe, 0x15, 0x57,
+ 0x69, 0x74, 0x11, 0x09, 0xd0, 0x5c, 0x55, 0x60, 0x23, 0xd3, 0xa0, 0x64, 0xd0, 0xb8, 0x11, 0xd2,
+ 0x6b, 0xc5, 0x9b, 0x1b, 0x40, 0x37, 0x0f, 0x05, 0x6b, 0xdf, 0xde, 0xb1, 0x88, 0xdb, 0x1e, 0x8a,
+ 0xb2, 0x36, 0x9e, 0x28, 0x51, 0x34, 0xf9, 0x1c, 0xe2, 0xe3, 0xb0, 0xf9, 0xdf, 0x12, 0x1a, 0x3a,
+ 0x5e, 0x8e, 0xb5, 0x45, 0x4c, 0x64, 0xdc, 0x70, 0xf6, 0x27, 0xd1, 0x03, 0xc2, 0x55, 0xab, 0x9d,
+ 0x25, 0x49, 0x13, 0xec, 0xd0, 0xee, 0xac, 0x2b, 0x46, 0xe8, 0xcc, 0x51, 0x11, 0x50, 0x25, 0x94,
+ 0xa2, 0xd1, 0x5e, 0xed, 0xfb, 0x47, 0x4e, 0xbd, 0xba, 0xb6, 0x0a, 0x72, 0xac, 0x4e, 0x60, 0xd4,
+ 0x38, 0xb0, 0x58, 0x25, 0x46, 0xff, 0x1f, 0xb2, 0x04, 0x2b, 0xd2, 0x3f, 0xb5, 0xcb, 0xfe, 0x9f,
+ 0x3f, 0xc2, 0x6b, 0x68, 0x12, 0x36, 0x0a, 0xbe, 0x66, 0xde, 0xc9, 0x80, 0xab, 0x14, 0x55, 0x92,
+ 0x0a, 0x2f, 0xc1, 0x1e, 0x5b, 0xbb, 0xa9, 0x71, 0xda, 0x92, 0xca, 0xfc, 0xed, 0x59, 0x73, 0x70,
+ 0x6a, 0x9d, 0xaa, 0xff, 0x46, 0x12, 0xed, 0xa0, 0xdb, 0xb1, 0xfd, 0xf4, 0x04, 0xc4, 0xd6, 0xaa,
+ 0x61, 0x4c, 0xdc, 0xd7, 0xd5, 0xfa, 0x26, 0x06, 0x93, 0x06, 0x5c, 0x3b, 0x44, 0x55, 0x5c, 0x32,
+ 0x6b, 0xe9, 0x21, 0x10, 0x1c, 0xc6, 0xbd, 0x9a, 0xd9, 0x63, 0x7e, 0xae, 0xb7, 0x66, 0x86, 0x34,
+ 0x6b, 0x3f, 0xbb, 0x63, 0xed, 0x39, 0x0e, 0x9e, 0x04
+};
+unsigned int test_server_der_len = 1513;
diff --git a/test/regression/interoperability_test/nx_secure_test/test_server.key.der.c b/test/regression/interoperability_test/nx_secure_test/test_server.key.der.c
new file mode 100644
index 00000000..b8cb7f6d
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/test_server.key.der.c
@@ -0,0 +1,78 @@
+unsigned char test_server_key_der[] = {
+ 0x30, 0x82, 0x04, 0xa4, 0x02, 0x01, 0x00, 0x02, 0x82, 0x01, 0x01, 0x00, 0xd0, 0x6a, 0x52, 0x6e,
+ 0xe6, 0x36, 0x44, 0x08, 0x62, 0x8c, 0xbb, 0xfe, 0xa2, 0xcf, 0xa6, 0xd2, 0x80, 0xd7, 0x56, 0x88,
+ 0x43, 0xfb, 0x48, 0xeb, 0xfe, 0x53, 0x92, 0xbf, 0xee, 0x6a, 0xa2, 0x44, 0x3c, 0x69, 0xfa, 0x9e,
+ 0x2f, 0x44, 0x0d, 0x98, 0x2e, 0x2f, 0x72, 0x64, 0xf7, 0x86, 0xfe, 0x4c, 0x18, 0x1a, 0x99, 0xcb,
+ 0x85, 0xc9, 0xb7, 0x66, 0x9e, 0xc8, 0xfb, 0x33, 0xed, 0x6f, 0x32, 0x87, 0x96, 0xae, 0xb1, 0x62,
+ 0x11, 0xed, 0x30, 0xf4, 0x87, 0xf2, 0x32, 0x46, 0x21, 0x00, 0x25, 0x97, 0xff, 0xf7, 0xf8, 0x71,
+ 0xbb, 0x7e, 0x84, 0xf2, 0xd6, 0x1a, 0x5b, 0xd7, 0x57, 0xa0, 0x1e, 0xf8, 0x8e, 0xe0, 0x04, 0xe6,
+ 0x71, 0xa4, 0xcd, 0xd0, 0xe1, 0x8c, 0x0d, 0x3d, 0xd9, 0x20, 0x7c, 0x2c, 0x56, 0xde, 0x02, 0xec,
+ 0xdb, 0x3f, 0x4e, 0x4a, 0x77, 0xdf, 0x23, 0xa4, 0xc1, 0x8c, 0x0b, 0x03, 0x46, 0x21, 0x76, 0x4c,
+ 0x85, 0x2c, 0x55, 0xa7, 0x6d, 0x05, 0x2d, 0x0f, 0x91, 0x94, 0xc3, 0x60, 0xfc, 0x1d, 0xd5, 0xd6,
+ 0x94, 0x19, 0x0b, 0x22, 0xb0, 0x5b, 0xc0, 0x94, 0x16, 0x66, 0x2c, 0xe4, 0x7a, 0x5c, 0x11, 0xad,
+ 0x7d, 0x40, 0xb1, 0x84, 0x78, 0x04, 0xb1, 0xa6, 0x1c, 0x73, 0xaa, 0xb5, 0xfa, 0xcd, 0x18, 0xa5,
+ 0x50, 0xfe, 0xb9, 0xab, 0xb0, 0x7d, 0xce, 0x0d, 0x49, 0x46, 0x57, 0x65, 0x53, 0x4c, 0xec, 0x55,
+ 0xe1, 0xc5, 0x05, 0x95, 0xbd, 0x52, 0x7e, 0xf1, 0x0c, 0xad, 0x84, 0x24, 0xd9, 0xce, 0xc8, 0x8e,
+ 0x47, 0x57, 0x00, 0xaf, 0x03, 0x8b, 0x31, 0x28, 0x3e, 0xbc, 0xc4, 0x6c, 0x14, 0x79, 0xc2, 0x87,
+ 0x63, 0xd8, 0x89, 0xdc, 0x35, 0x1f, 0x8f, 0x55, 0x62, 0xf0, 0xa8, 0x8e, 0xdd, 0x82, 0xf0, 0x6b,
+ 0x90, 0x02, 0xc8, 0x8f, 0x80, 0x1a, 0x82, 0xb4, 0x82, 0xd3, 0x4b, 0xf9, 0x02, 0x03, 0x01, 0x00,
+ 0x01, 0x02, 0x82, 0x01, 0x01, 0x00, 0xbf, 0x1a, 0x4e, 0xbd, 0xeb, 0x8f, 0xa4, 0xb0, 0x3f, 0x95,
+ 0x26, 0x28, 0x65, 0xa7, 0x9c, 0x22, 0xf7, 0x0a, 0xfd, 0x08, 0x73, 0xb5, 0x6d, 0x77, 0x1f, 0x3c,
+ 0x08, 0x9a, 0xbf, 0x05, 0xbe, 0x06, 0x6d, 0x93, 0x0b, 0xbf, 0x92, 0x3d, 0x87, 0x6d, 0x9c, 0x23,
+ 0xdb, 0x73, 0xe3, 0x58, 0x3f, 0xc3, 0x0c, 0x73, 0x0f, 0xc4, 0x83, 0xc7, 0xa3, 0xc8, 0x90, 0x1e,
+ 0x5f, 0xe0, 0x8c, 0x7d, 0x62, 0xca, 0xdb, 0x0b, 0x12, 0x11, 0x87, 0xb8, 0x83, 0x24, 0x25, 0xa7,
+ 0x9a, 0x1b, 0x9d, 0xd4, 0xe1, 0xa3, 0xcf, 0x8c, 0xd3, 0x9d, 0x8d, 0xbb, 0x84, 0x32, 0x9a, 0xc9,
+ 0x8e, 0x9f, 0x15, 0x74, 0xf8, 0x11, 0x18, 0x09, 0x27, 0xd5, 0x1a, 0x2d, 0x70, 0x9f, 0x70, 0xc1,
+ 0x17, 0xbf, 0x37, 0x61, 0xc7, 0x1a, 0x6d, 0x08, 0xa3, 0x8c, 0x05, 0xb9, 0xb5, 0x93, 0x28, 0xf9,
+ 0x4d, 0x58, 0x9c, 0x34, 0x4a, 0x3f, 0x2d, 0xab, 0x3c, 0x4d, 0x21, 0x84, 0xa7, 0x5b, 0xf3, 0x90,
+ 0x1d, 0xce, 0x13, 0x63, 0x29, 0x47, 0xdf, 0xfe, 0x8e, 0x9b, 0x95, 0x91, 0x9e, 0x73, 0xb7, 0xf8,
+ 0xf9, 0x18, 0x43, 0x9e, 0x10, 0x21, 0xb3, 0xb3, 0x7c, 0x54, 0x99, 0x30, 0x59, 0xd0, 0x00, 0x37,
+ 0x11, 0x7f, 0x13, 0x2d, 0x0c, 0xec, 0xb6, 0x64, 0x1c, 0xd2, 0x39, 0x75, 0xdb, 0x9b, 0x4a, 0x73,
+ 0xb8, 0x64, 0xaf, 0x01, 0x13, 0x89, 0xb9, 0x69, 0xd4, 0x02, 0x28, 0xaa, 0xae, 0x39, 0xf0, 0x57,
+ 0x85, 0x80, 0x1c, 0x2e, 0xe5, 0xec, 0x79, 0x2d, 0x1c, 0x80, 0x12, 0x2f, 0x6b, 0x43, 0xdf, 0x8c,
+ 0x95, 0xcc, 0xb9, 0x8d, 0x3b, 0x29, 0xee, 0x3b, 0x41, 0xda, 0x6f, 0xb0, 0x51, 0xa0, 0xfb, 0x5d,
+ 0x9a, 0x05, 0xf4, 0x46, 0x1b, 0xb4, 0x65, 0xf6, 0xf6, 0x6f, 0xfa, 0xd3, 0x3d, 0x47, 0x5d, 0xb1,
+ 0x68, 0xd1, 0x04, 0x08, 0x59, 0xa5, 0x02, 0x81, 0x81, 0x00, 0xe7, 0xc9, 0x3d, 0x5c, 0xdb, 0x01,
+ 0x1c, 0xc3, 0x2e, 0x57, 0x07, 0x42, 0xee, 0x26, 0x6f, 0xc6, 0x94, 0xd5, 0xe4, 0x38, 0x3a, 0x23,
+ 0xc6, 0x84, 0x54, 0x30, 0x5b, 0x71, 0x4e, 0xf8, 0x55, 0x85, 0x6d, 0x4d, 0x06, 0x42, 0x38, 0x00,
+ 0xed, 0x0a, 0x5b, 0x63, 0x8f, 0x93, 0x4a, 0x0a, 0x32, 0x56, 0xfd, 0x43, 0x6e, 0x4a, 0xff, 0x7f,
+ 0x19, 0x9a, 0xe1, 0x99, 0xb6, 0x81, 0x9c, 0x53, 0x9a, 0x9b, 0x51, 0x53, 0x90, 0x0d, 0x12, 0xd5,
+ 0x4e, 0xe1, 0x8e, 0x2e, 0x03, 0xd5, 0x04, 0x5e, 0x19, 0xe2, 0x27, 0xbb, 0xa7, 0xb8, 0x44, 0x7d,
+ 0xc8, 0x9b, 0xb5, 0x2b, 0x5d, 0x51, 0x85, 0xcd, 0xcb, 0xb9, 0x4c, 0x3b, 0x49, 0xfa, 0x1d, 0x60,
+ 0x56, 0x2f, 0x4a, 0x94, 0x5c, 0x96, 0xbf, 0xab, 0xc6, 0xcb, 0xeb, 0x87, 0x93, 0x6b, 0x67, 0xe2,
+ 0xd0, 0xc6, 0xa2, 0x2e, 0x86, 0x97, 0x40, 0x60, 0x4e, 0xf7, 0x02, 0x81, 0x81, 0x00, 0xe6, 0x30,
+ 0x11, 0x32, 0x5e, 0x9b, 0xe7, 0xdb, 0xbb, 0xcb, 0x35, 0x4f, 0x37, 0x90, 0xad, 0x48, 0x15, 0xc6,
+ 0x91, 0x40, 0x45, 0x7a, 0xa5, 0x72, 0xca, 0x62, 0x07, 0xb4, 0x00, 0x65, 0xc2, 0xd2, 0x5e, 0x0c,
+ 0xe0, 0x48, 0x00, 0xe4, 0x6f, 0x9c, 0x5b, 0xbd, 0xf1, 0xf4, 0x9b, 0x4f, 0xd1, 0xe6, 0xcc, 0xc3,
+ 0xd9, 0x36, 0x4a, 0x30, 0x1b, 0x4b, 0xbe, 0xf3, 0x24, 0xb8, 0x63, 0x34, 0x08, 0x8d, 0x08, 0x9b,
+ 0xe0, 0x37, 0xf8, 0x3e, 0x1d, 0xc9, 0x45, 0xf7, 0x49, 0x5b, 0x98, 0x0d, 0xa1, 0x77, 0x11, 0x82,
+ 0xab, 0xbf, 0x52, 0xc8, 0x42, 0x00, 0x07, 0xb8, 0x1e, 0xbd, 0xfc, 0xaa, 0x17, 0x7b, 0x1c, 0x29,
+ 0x87, 0x2f, 0xbd, 0x2f, 0x8e, 0xd2, 0x8e, 0xe1, 0xb9, 0x03, 0xe7, 0xb7, 0x1a, 0x50, 0xe2, 0x29,
+ 0xa8, 0xf1, 0xec, 0x39, 0x22, 0xcb, 0xc1, 0x5d, 0x01, 0xa3, 0x45, 0xf6, 0x50, 0x8f, 0x02, 0x81,
+ 0x80, 0x44, 0x27, 0x11, 0xd9, 0xe9, 0xb3, 0x4c, 0x07, 0xbf, 0xea, 0x6b, 0x02, 0x2d, 0x10, 0x34,
+ 0x31, 0x89, 0xb5, 0xd2, 0xa3, 0x0d, 0xc5, 0x53, 0x2b, 0xb9, 0xad, 0x76, 0x55, 0xbc, 0xc8, 0x9c,
+ 0x2c, 0xdd, 0x54, 0x96, 0x90, 0x85, 0xf3, 0x0f, 0xbf, 0xc9, 0xdb, 0x5e, 0x6e, 0x0a, 0x89, 0x31,
+ 0x00, 0x0e, 0xfb, 0xf2, 0xc4, 0x2e, 0x97, 0xea, 0xa9, 0x75, 0xc8, 0x42, 0xb7, 0x9d, 0x85, 0x9f,
+ 0xa2, 0x27, 0xa9, 0x90, 0x63, 0xa7, 0xb3, 0xfc, 0xbb, 0xa9, 0x98, 0xb2, 0x1b, 0xc2, 0x6b, 0x00,
+ 0xe5, 0x54, 0x95, 0x82, 0xdd, 0x55, 0x96, 0x3e, 0x94, 0x3a, 0x13, 0x04, 0x1f, 0x62, 0x5e, 0x7e,
+ 0x96, 0x7f, 0x69, 0xb7, 0x78, 0xc9, 0x86, 0x78, 0x10, 0xf3, 0xb6, 0xe7, 0xfa, 0x93, 0x65, 0x28,
+ 0xd0, 0xf0, 0xf2, 0x2e, 0x50, 0x98, 0x7d, 0x42, 0xb2, 0x05, 0x21, 0xf5, 0x05, 0x28, 0x32, 0xa9,
+ 0x45, 0x02, 0x81, 0x81, 0x00, 0xbb, 0xff, 0x63, 0xfc, 0x24, 0x62, 0xe6, 0xb1, 0x82, 0xa5, 0xcb,
+ 0x8b, 0x40, 0x51, 0x6c, 0x04, 0xa4, 0xac, 0x41, 0x33, 0x21, 0xcb, 0xb2, 0x56, 0x97, 0x4e, 0x0b,
+ 0x06, 0x8b, 0x10, 0x91, 0x56, 0x28, 0xb4, 0x11, 0x75, 0x1d, 0x2d, 0x74, 0xae, 0x5a, 0x0b, 0x3f,
+ 0x12, 0x4c, 0xca, 0x9b, 0x1f, 0x09, 0xfb, 0xa6, 0x6a, 0x7d, 0x9a, 0xde, 0xa0, 0x35, 0x7a, 0xf5,
+ 0x71, 0x96, 0xac, 0x07, 0x93, 0xd0, 0x05, 0x26, 0xd1, 0xef, 0x70, 0x23, 0xf9, 0x9f, 0xa8, 0x00,
+ 0x84, 0xcb, 0x21, 0xce, 0xce, 0xa5, 0x41, 0x78, 0xad, 0xd0, 0x99, 0x77, 0xb5, 0xf8, 0x97, 0xfa,
+ 0x9b, 0xa6, 0x40, 0xf0, 0xde, 0x7e, 0x38, 0xb8, 0x8d, 0x57, 0xd1, 0x00, 0xaf, 0x9d, 0x3c, 0x63,
+ 0x53, 0xfa, 0x2a, 0x84, 0x56, 0xac, 0xef, 0xe3, 0x68, 0x7a, 0x4a, 0x8b, 0xcd, 0xa7, 0xc6, 0x23,
+ 0x31, 0x4b, 0x51, 0x89, 0xa7, 0x02, 0x81, 0x80, 0x38, 0xdc, 0xdb, 0x2e, 0x32, 0x05, 0xf5, 0x81,
+ 0xa7, 0x0a, 0x9d, 0x08, 0x8e, 0x09, 0x0e, 0x33, 0xd2, 0x42, 0xdd, 0x86, 0x13, 0xe5, 0x5f, 0xeb,
+ 0xe5, 0xe9, 0xbd, 0x16, 0x21, 0x6e, 0x30, 0x0e, 0xc4, 0x4c, 0x40, 0xac, 0x88, 0xda, 0x11, 0x1b,
+ 0xd6, 0x16, 0xd3, 0x3a, 0x61, 0x03, 0x43, 0x02, 0x69, 0xf0, 0x0a, 0xa8, 0xa1, 0xa4, 0x66, 0x14,
+ 0xc2, 0x2c, 0x68, 0xc8, 0x43, 0x5d, 0x19, 0x75, 0x4b, 0xee, 0x4f, 0xd3, 0xff, 0xd3, 0x67, 0x47,
+ 0x9d, 0x1a, 0xb1, 0x6b, 0x1d, 0x31, 0xd4, 0xa9, 0x71, 0xec, 0x09, 0x87, 0xc9, 0xf8, 0xe2, 0x3b,
+ 0xef, 0x6e, 0x9b, 0xd2, 0xa3, 0x5d, 0xcb, 0x27, 0x1c, 0xef, 0xcb, 0x25, 0x36, 0x00, 0x05, 0xfe,
+ 0x26, 0xd7, 0xed, 0xa0, 0xb1, 0x7f, 0x1a, 0xdb, 0x4a, 0xd6, 0x0e, 0xb0, 0x06, 0x51, 0xa9, 0x90,
+ 0x2c, 0x5a, 0x71, 0xa1, 0xa9, 0xc0, 0x3f, 0xaf
+};
+unsigned int test_server_key_der_len = 1192;
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_0_1_1_ecc_server_test.c b/test/regression/interoperability_test/nx_secure_test/tls_1_0_1_1_ecc_server_test.c
new file mode 100644
index 00000000..46a8492d
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_0_1_1_ecc_server_test.c
@@ -0,0 +1,210 @@
+#include "tls_test_frame.h"
+
+INT nx_secure_ecc_server_ciphersuites_entry(TLS_TEST_INSTANCE* instance_ptr);
+INT openssl_ecc_client_entry(TLS_TEST_INSTANCE* instance_ptr);
+extern UINT ciphersuites_server_count;
+
+/* Global demo semaphore. */
+TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+INT main( INT argc, CHAR* argv[])
+{
+INT status, exit_status[2];
+TLS_TEST_INSTANCE *ins0;
+TLS_TEST_INSTANCE *ins1;
+
+ /* Create two test instances. */
+ status = tls_test_instance_create(&ins0, /* test instance ptr */
+ "nx_secure_ecc_server_ciphersuites_entry",/* instance name */
+ nx_secure_ecc_server_ciphersuites_entry, /* test entry */
+ 0, /* delay(seconds) */
+ 60, /* timeout(seconds) */
+ 1024, /* shared buffer size */
+ NULL); /* reserved */
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ status = tls_test_instance_create(&ins1,
+ "openssl_ecc_client_entry",
+ openssl_ecc_client_entry,
+ 0,
+ 60,
+ 1024,
+ NULL);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Create a semaphore and set the initial value as 0. */
+ status = tls_test_semaphore_create(&semaphore_echo_server_prepared, 0);
+
+ /* Create the test director. */
+ TLS_TEST_DIRECTOR *director;
+ status = tls_test_director_create(&director, NULL /* reserved */);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Register test instances to the director. */
+ status = tls_test_director_register_test_instance(director, ins0);
+ status += tls_test_director_register_test_instance(director, ins1);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Launch test. */
+ status = tls_test_director_test_start(director);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Collect exit code. */
+ tls_test_instance_show_exit_status(ins0);
+ tls_test_instance_show_exit_status(ins1);
+
+ /* Call the verify method to determine whether the test is passed. */
+ status = tls_test_instance_get_exit_status(ins0, &exit_status[0]);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+ status = tls_test_instance_get_exit_status(ins1, &exit_status[1]);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Destroy registered test instances and the director. */
+ tls_test_director_clean_all(director);
+
+ /* Destroy the semaphore. */
+ tls_test_semaphore_destroy(semaphore_echo_server_prepared);
+
+ /* Return error if get unexpected test results. */
+ if ((TLS_TEST_NOT_AVAILABLE == exit_status[0]) || (TLS_TEST_NOT_AVAILABLE == exit_status[1]))
+ return TLS_TEST_NOT_AVAILABLE;
+
+ /* Return the result of verification. */
+ return exit_status[0] | exit_status[1];
+}
+
+typedef struct
+{
+ UINT cipher_index;
+ UCHAR *version;
+ UINT session_succ;
+} CIPHERSUITE;
+
+static CHAR *ciphers[] =
+{
+ "ALL",
+ "ECDH-ECDSA-AES128-SHA",
+ "ECDH-RSA-AES128-SHA",
+ "ECDHE-ECDSA-AES128-SHA",
+ "ECDHE-RSA-AES128-SHA",
+ "ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES128-SHA:ECDH-RSA-AES128-SHA:ECDH-ECDSA-AES128-SHA",
+};
+
+static CIPHERSUITE ciphersuites_client[] =
+{
+#ifdef NX_SECURE_TLS_ENABLE_TLS_1_0
+ /* Select ciphersuite according to certificate. */
+ {0, "-tls1", NX_TRUE},
+ {0, "-tls1", NX_TRUE},
+ {0, "-tls1", NX_TRUE},
+ {0, "-tls1", NX_TRUE},
+
+ /* Select ciphersuite according to certificate.
+ * The order of client ciphersuites are reversed of server. */
+ {5, "-tls1", NX_TRUE},
+ {5, "-tls1", NX_TRUE},
+ {5, "-tls1", NX_TRUE},
+
+ /* Specified ciphersuites. */
+ /*{1, "-tls1", NX_TRUE},*/
+ /*{2, "-tls1", NX_TRUE},*/
+ {3, "-tls1", NX_TRUE},
+ {4, "-tls1", NX_TRUE},
+
+ /* The Server cert supports ECDH_ECDSA and ECDHE_ECDSA. */
+ /*{1, "-tls1", NX_TRUE},*/
+ /*{2, "-tls1", NX_FALSE},*/ /* ECDH_RSA not supported. */
+ {3, "-tls1", NX_TRUE},
+ {4, "-tls1", NX_FALSE}, /* ECDHE_RSA not supported. */
+
+ /* Let the server pickup supported ciphersuite. */
+ /*{0, "-tls1", NX_TRUE},*/
+ /*{0, "-tls1", NX_TRUE},*/
+ {0, "-tls1", NX_TRUE},
+ {0, "-tls1", NX_TRUE},
+ /*{0, "-tls1", NX_TRUE},*/
+ {0, "-tls1", NX_TRUE},
+ /*{0, "-tls1", NX_TRUE},*/
+ {0, "-tls1", NX_TRUE},
+#endif /* NX_SECURE_TLS_ENABLE_TLS_1_0 */
+
+#ifdef NX_SECURE_TLS_ENABLE_TLS_1_1
+ /* Select ciphersuite according to certificate. */
+ {0, "-tls1_1", NX_TRUE},
+ {0, "-tls1_1", NX_TRUE},
+ {0, "-tls1_1", NX_TRUE},
+ {0, "-tls1_1", NX_TRUE},
+
+ /* Select ciphersuite according to certificate.
+ * The order of client ciphersuites are reversed of server. */
+ {5, "-tls1_1", NX_TRUE},
+ {5, "-tls1_1", NX_TRUE},
+ {5, "-tls1_1", NX_TRUE},
+
+ /* Specified ciphersuites. */
+ /*{1, "-tls1_1", NX_TRUE},*/
+ /*{2, "-tls1_1", NX_TRUE},*/
+ {3, "-tls1_1", NX_TRUE},
+ {4, "-tls1_1", NX_TRUE},
+
+ /* The Server cert supports ECDH_ECDSA and ECDHE_ECDSA. */
+ /*{1, "-tls1_1", NX_TRUE},*/
+ /*{2, "-tls1_1", NX_FALSE},*/ /* ECDH_RSA not supported. */
+ {3, "-tls1_1", NX_TRUE},
+ {4, "-tls1_1", NX_FALSE}, /* ECDHE_RSA not supported. */
+
+ /* Let the server pickup supported ciphersuite. */
+ /*{0, "-tls1_1", NX_TRUE},*/
+ /*{0, "-tls1_1", NX_TRUE},*/
+ {0, "-tls1_1", NX_TRUE},
+ {0, "-tls1_1", NX_TRUE},
+ /*{0, "-tls1_1", NX_TRUE},*/
+ {0, "-tls1_1", NX_TRUE},
+ /*{0, "-tls1_1", NX_TRUE},*/
+ {0, "-tls1_1", NX_TRUE},
+#endif /* NX_SECURE_TLS_ENABLE_TLS_1_1 */
+};
+
+/* Instance two test entry. */
+INT openssl_ecc_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) && (defined(NX_SECURE_TLS_ENABLE_TLS_1_0) || defined(NX_SECURE_TLS_ENABLE_TLS_1_1))
+
+/* Just use TLSv1.2 */
+CHAR* external_cmd[] = { "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING,
+ "-cipher", "", "", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ for ( ; i < sizeof(ciphersuites_client) / sizeof(CIPHERSUITE); i++)
+ {
+
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+ /* Call an external program to connect to tls server. */
+ external_cmd[4] = ciphers[ciphersuites_client[i].cipher_index];
+ external_cmd[5] = ciphersuites_client[i].version;
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ if ((exit_status && ciphersuites_client[i].session_succ) ||
+ (!exit_status && !ciphersuites_client[i].session_succ))
+ {
+
+ /* Record errors. */
+ instance_status = TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED;
+ }
+ }
+ return instance_status;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_0_openssl_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_0_openssl_echo_client_entry.c
new file mode 100644
index 00000000..68dcac3f
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_0_openssl_echo_client_entry.c
@@ -0,0 +1,35 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Instance two test entry. */
+INT openssl_echo_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if defined(NX_SECURE_TLS_ENABLE_1_0) && !defined(NX_SECURE_TLS_SERVER_DISABLED)
+
+/* Just use TLSv1.2 */
+CHAR* external_cmd[] = { "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING, "-tls1", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_FAILED);
+ return TLS_TEST_SUCCESS;
+
+#else /* defined(NX_SECURE_TLS_ENABLE_1_0) && !defined(NX_SECURE_TLS_SERVER_DISABLED) */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* defined(NX_SECURE_TLS_ENABLE_1_0) && !defined(NX_SECURE_TLS_SERVER_DISABLED) */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_0_openssl_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_0_openssl_echo_server_entry.c
new file mode 100644
index 00000000..23398ada
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_0_openssl_echo_server_entry.c
@@ -0,0 +1,33 @@
+#include "tls_test_frame.h"
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+/* Openssl echo server entry. */
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if defined(NX_SECURE_TLS_ENABLE_TLS_1_0) && !defined(NX_SECURE_TLS_CLIENT_DISABLED)
+
+INT status, exit_status;
+
+/* Added -rev option to send reverse text received from clients back to the client. Added -naccept 1 to close the server after one tls session. */
+CHAR* external_cmd[] = { "openssl", "s_server", "-port", DEVICE_SERVER_PORT_STRING, "-rev", "-key", "key.pem", "-cert", "cert.pem", "-naccept", "1", "-tls1", (CHAR*)NULL};
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+ return TLS_TEST_SUCCESS;
+
+#else /* if defined(NX_SECURE_TLS_ENABLE_TLS_1_0) && !defined(NX_SECURE_TLS_CLIENT_DISABLED) */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* if defined(NX_SECURE_TLS_ENABLE_TLS_1_0) && !defined(NX_SECURE_TLS_CLIENT_DISABLED) */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_1_openssl_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_1_openssl_echo_client_entry.c
new file mode 100644
index 00000000..dcde0d85
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_1_openssl_echo_client_entry.c
@@ -0,0 +1,35 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Instance two test entry. */
+INT openssl_echo_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if defined(NX_SECURE_TLS_ENABLE_TLS_1_1) && !defined(NX_SECURE_TLS_SERVER_DISABLED)
+
+/* Just use TLSv1.2 */
+CHAR* external_cmd[] = { "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING, "-tls1_1", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_FAILED);
+ return TLS_TEST_SUCCESS;
+
+#else /* if defined(NX_SECURE_TLS_ENABLE_TLS_1_1) && !defined(NX_SECURE_TLS_SERVER_DISABLED) */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* if defined(NX_SECURE_TLS_ENABLE_TLS_1_1) && !defined(NX_SECURE_TLS_SERVER_DISABLED) */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_1_openssl_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_1_openssl_echo_server_entry.c
new file mode 100644
index 00000000..d065038c
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_1_openssl_echo_server_entry.c
@@ -0,0 +1,33 @@
+#include "tls_test_frame.h"
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+/* Openssl echo server entry. */
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if defined(NX_SECURE_TLS_ENABLE_TLS_1_1) && !defined(NX_SECURE_TLS_CLIENT_DISABLED)
+
+INT status, exit_status;
+
+/* Added -rev option to send reverse text received from clients back to the client. Added -naccept 1 to close the server after one tls session. */
+CHAR* external_cmd[] = { "openssl", "s_server", "-port", DEVICE_SERVER_PORT_STRING, "-rev", "-key", "key.pem", "-cert", "cert.pem", "-naccept", "1", "-tls1_1", (CHAR*)NULL};
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+ return TLS_TEST_SUCCESS;
+
+#else /* defined(NX_SECURE_TLS_ENABLE_TLS_1_1) && !defined(NX_SECURE_TLS_CLIENT_DISABLED) */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* defined(NX_SECURE_TLS_ENABLE_TLS_1_1) && !defined(NX_SECURE_TLS_CLIENT_DISABLED) */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_2_openssl_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_2_openssl_echo_client_entry.c
new file mode 100644
index 00000000..7032d741
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_2_openssl_echo_client_entry.c
@@ -0,0 +1,35 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Instance two test entry. */
+INT openssl_echo_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#ifndef NX_SECURE_TLS_SERVER_DISABLED
+
+/* Just use TLSv1.2 */
+CHAR* external_cmd[] = { "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING, "-tls1_2", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_FAILED);
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_2_openssl_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_2_openssl_echo_server_entry.c
new file mode 100644
index 00000000..d04408ec
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_2_openssl_echo_server_entry.c
@@ -0,0 +1,33 @@
+#include "tls_test_frame.h"
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+/* Openssl echo server entry. */
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#ifndef NX_SECURE_TLS_CLIENT_DISABLED
+
+INT status, exit_status;
+
+/* Added -rev option to send reverse text received from clients back to the client. Added -naccept 1 to close the server after one tls session. */
+CHAR* external_cmd[] = { "openssl", "s_server", "-port", DEVICE_SERVER_PORT_STRING, "-rev", "-key", "key.pem", "-cert", "cert.pem", "-naccept", "1", "-tls1_2", (CHAR*)NULL};
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_3_alert_test_nx_secure_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_3_alert_test_nx_secure_echo_server_entry.c
new file mode 100644
index 00000000..77538300
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_3_alert_test_nx_secure_echo_server_entry.c
@@ -0,0 +1,269 @@
+/* This test concentrates on TLS ciphersuite TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA. The client certificate is require. */
+#include "tls_test_frame.h"
+
+#if !defined (NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) && (NX_SECURE_TLS_TLS_1_3_ENABLED)
+#include "nx_crypto_ecdh.h"
+#include "../../nx_secure_test/ecc_certs.c"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Define the ThreadX and NetX object control blocks... */
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT server_local_certificate;
+
+UCHAR tls_packet_buffer[4000];
+UCHAR server_cert_buffer[2048];
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+void server_thread_entry(ULONG thread_input);
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+
+/* Define the pointer of current instance control block. */
+static TLS_TEST_INSTANCE* demo_instance_ptr;
+
+/* Define external references. */
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Instance one test entry. */
+INT nx_secure_ecc_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+
+ /* Get instance pointer. */
+ demo_instance_ptr = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+}
+
+/* Define what the initial system looks like. */
+void tx_application_define(void *first_unused_memory)
+{
+ ULONG gateway_ipv4_address;
+ UINT status;
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL, &pool_0, _nx_pcap_network_driver, (UCHAR*)ip_thread_stack, sizeof(ip_thread_stack), 1);
+print_error_message( "ip address number: %lu", TLS_TEST_IP_ADDRESS_NUMBER);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ tx_thread_create(&demo_thread, "demo thread", server_thread_entry, 0, demo_thread_stack, sizeof(demo_thread_stack), 16, 16, 4, TX_AUTO_START);
+}
+
+static ULONG server_callback_plain_alert(NX_SECURE_TLS_SESSION *tls_session, NX_SECURE_TLS_HELLO_EXTENSION *extensions, UINT num_extensions)
+{
+
+ tls_session -> nx_secure_tls_local_sequence_number[0]++;
+
+ return(NX_SUCCESS);
+}
+
+static UCHAR client_hello[] = {
+0x16, 0x03, 0x03, 0x00, 0xe3, 0x01, 0x00, 0x00, 0xdf, 0x03,
+0x03, 0x00, 0x00, 0x00, 0x00, 0x25, 0x3b, 0x00, 0x00, 0x1f, 0x1e, 0x00, 0x00, 0x5d, 0x6e, 0x00,
+0x00, 0xd4, 0x1a, 0x00, 0x00, 0xcb, 0x63, 0x00, 0x00, 0xfc, 0x6b, 0x00, 0x00, 0x96, 0x7f, 0x00,
+0x00, 0x00, 0x00, 0x34, 0x13, 0x01, 0x13, 0x04, 0x13, 0x05, 0xc0, 0x23, 0xc0, 0x09, 0xc0, 0x0a,
+0xc0, 0x27, 0xc0, 0x13, 0xc0, 0x14, 0xc0, 0x2b, 0xc0, 0x2f, 0x00, 0x3d, 0x00, 0x35, 0x00, 0x3c,
+0x00, 0x2f, 0x00, 0x9c, 0xc0, 0x25, 0xc0, 0x04, 0xc0, 0x05, 0xc0, 0x29, 0xc0, 0x0e, 0xc0, 0x0f,
+0xc0, 0x2d, 0xc0, 0x31, 0x00, 0x02, 0x00, 0x01, 0x01, 0x00, 0x00, 0x82, 0x00, 0x0a, 0x00, 0x08,
+0x00, 0x06, 0x00, 0x17, 0x00, 0x18, 0x00, 0x19, 0x00, 0x0b, 0x00, 0x02, 0x01, 0x00, 0x00, 0x2b,
+0x00, 0x07, 0x06, 0x03, 0x04, 0x03, 0x03, 0x03, 0x02, 0x00, 0x33, 0x00, 0x47, 0x00, 0x45, 0x00,
+0x17, 0x00, 0x41, 0x04, 0x35, 0x1d, 0x63, 0xce, 0x8d, 0x7a, 0xee, 0xf7, 0x39, 0xb4, 0x37, 0x0c,
+0x20, 0xe2, 0xe6, 0x26, 0xe9, 0xdb, 0xc8, 0xf3, 0x58, 0x39, 0xb1, 0xa7, 0x2a, 0x06, 0xfe, 0x46,
+0x85, 0xca, 0x35, 0xd8, 0xad, 0xc1, 0xc1, 0xb7, 0x7c, 0xdd, 0x8c, 0x2a, 0xe2, 0x8e, 0xf3, 0x4e,
+0x61, 0x4a, 0x0e, 0xf6, 0x96, 0xbf, 0xa3, 0x9d, 0x89, 0xf5, 0xf1, 0x6f, 0x65, 0x90, 0xc3, 0xf5,
+0x4e, 0x7b, 0xe6, 0xd2, 0x00, 0x0d, 0x00, 0x16, 0x00, 0x14, 0x01, 0x01, 0x02, 0x01, 0x04, 0x01,
+0x05, 0x01, 0x06, 0x01, 0x02, 0x03, 0x03, 0x03, 0x04, 0x03, 0x05, 0x03, 0x06, 0x03,
+};
+
+static ULONG server_callback_second_clienthello(NX_SECURE_TLS_SESSION *tls_session, NX_SECURE_TLS_HELLO_EXTENSION *extensions, UINT num_extensions)
+{
+NX_PACKET *packet_ptr;
+
+ if (tls_session -> nx_secure_tls_server_state == 0)
+ {
+
+ /* Create ClientHello. */
+ nx_packet_allocate(&pool_0, &packet_ptr, NX_TCP_PACKET, NX_NO_WAIT);
+ nx_packet_data_append(packet_ptr, client_hello, sizeof(client_hello), &pool_0, NX_NO_WAIT);
+
+ /* Chain the packet. */
+ if (tls_session -> nx_secure_record_queue_header == NX_NULL)
+ {
+ tls_session -> nx_secure_record_queue_header = packet_ptr;
+ }
+ else
+ {
+
+ /* Link current packet. */
+ tls_session -> nx_secure_record_queue_header -> nx_packet_last -> nx_packet_next = packet_ptr;
+ tls_session -> nx_secure_record_queue_header -> nx_packet_last = packet_ptr -> nx_packet_last;
+ tls_session -> nx_secure_record_queue_header -> nx_packet_length += packet_ptr -> nx_packet_length;
+ }
+ }
+
+ return(NX_SUCCESS);
+}
+
+/* TLS Server example application thread. */
+void server_thread_entry(ULONG thread_input)
+{
+ INT status = 0, i = 0;
+ ULONG actual_status;
+ NX_PACKET *receive_packet;
+ NX_PACKET *send_packet;
+ UCHAR receive_buffer[100];
+ ULONG bytes;
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Server Socket",
+ NX_IP_NORMAL, NX_FRAGMENT_OKAY /*NX_DONT_FRAGMENT*/, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_session_create(&tls_session,
+ &nx_crypto_tls_ciphers_ecc,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Initialize ECC tables. */
+ status = nx_secure_tls_ecc_initialize(&tls_session, nx_crypto_ecc_supported_groups,
+ nx_crypto_ecc_supported_groups_size,
+ nx_crypto_ecc_curves);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(&tls_session, tls_packet_buffer, sizeof(tls_packet_buffer));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ memset(&server_local_certificate, 0, sizeof(server_local_certificate));
+ status = nx_secure_x509_certificate_initialize(&server_local_certificate,
+ ECTestServer2_der, ECTestServer2_der_len,
+ NX_NULL, 0, ECTestServer2_key_der,
+ ECTestServer2_key_der_len,
+ NX_SECURE_X509_KEY_TYPE_EC_DER);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_local_certificate_add(&tls_session,
+ &server_local_certificate);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Setup this thread to listen. */
+ status = nx_tcp_server_socket_listen(&ip_0, DEVICE_SERVER_PORT, &tcp_socket, 5, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ for (i = 0; i < 2; i++)
+ {
+
+ if (i == 0)
+ {
+ nx_secure_tls_session_server_callback_set(&tls_session, server_callback_plain_alert);
+ }
+ else
+ {
+ nx_secure_tls_session_server_callback_set(&tls_session, server_callback_second_clienthello);
+ }
+
+ /* Post semaphore before accept sockets. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Accept a client socket connection. */
+ status = nx_tcp_server_socket_accept(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 1);
+
+ /* Start the TLS Session now that we have a connected socket. */
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+
+ if (i == 0)
+ {
+ exit_if_fail(NX_SECURE_TLS_ALERT_RECEIVED == status, 2);
+ }
+ else
+ {
+ exit_if_fail(NX_SECURE_TLS_UNEXPECTED_CLIENTHELLO == status, 2);
+ }
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 3);
+
+ /* Disconnect the TCP socket, closing the connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 4);
+
+ /* Unaccept the server socket. */
+ status = nx_tcp_server_socket_unaccept(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, 5);
+
+ print_error_message("Connection %d: server unaccept, sleeping...\n", i);
+ tx_thread_sleep(100);
+
+ /* Setup server socket for listening again. */
+ status = nx_tcp_server_socket_relisten(&ip_0, DEVICE_SERVER_PORT, &tcp_socket);
+ exit_if_fail( NX_SUCCESS == status, 6);
+ }
+
+ exit(0);
+}
+#else
+
+/* Instance one test entry. */
+INT nx_secure_ecc_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+ exit(TLS_TEST_NOT_AVAILABLE);
+}
+#endif
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_3_alert_test_openssl_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_3_alert_test_openssl_echo_client_entry.c
new file mode 100644
index 00000000..13c42744
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_3_alert_test_openssl_echo_client_entry.c
@@ -0,0 +1,38 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Instance two test entry. */
+INT openssl_echo_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined (NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) && (NX_SECURE_TLS_TLS_1_3_ENABLED)
+
+/* Just use TLSv1.2 */
+CHAR* external_cmd[] = { "openssl_1_1_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING, "-tls1_3", "-curves", "prime256v1", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ for (i = 0; i < 2; i++)
+ {
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Should be fail. */
+ return_value_if_fail(0 != exit_status, TLS_TEST_INSTANCE_FAILED);
+ }
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_3_client_certificate_verify_test_nx_secure_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_3_client_certificate_verify_test_nx_secure_echo_client_entry.c
new file mode 100644
index 00000000..4ae6009e
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_3_client_certificate_verify_test_nx_secure_echo_client_entry.c
@@ -0,0 +1,250 @@
+#include "tls_test_frame.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer, local_certificate;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+NX_SECURE_X509_CERT trusted_certificate;
+NX_SECURE_X509_CERT client_trusted_ca;
+
+UCHAR tls_packet_buffer[4000];
+
+#include "../../nx_secure_test/ecc_certs.c"
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define an error counter. */
+
+ULONG error_counter;
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+
+
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) && (NX_SECURE_TLS_TLS_1_3_ENABLED)
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) && (NX_SECURE_TLS_TLS_1_3_ENABLED)
+void tx_application_define(void *first_unused_memory)
+{
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+void client_tls_setup(NX_SECURE_TLS_SESSION *tls_session_ptr)
+{
+UINT status;
+
+ /* Create a tls session. */
+ status = nx_secure_tls_session_create(tls_session_ptr,
+ &nx_crypto_tls_ciphers_ecc,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Initialize ECC. */
+ status = nx_secure_tls_ecc_initialize(tls_session_ptr, nx_crypto_ecc_supported_groups,
+ nx_crypto_ecc_supported_groups_size,
+ nx_crypto_ecc_curves);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(tls_session_ptr, tls_packet_buffer, sizeof(tls_packet_buffer));
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Need to allocate space for the certificate coming in from the remote host. */
+ nx_secure_tls_remote_certificate_allocate(tls_session_ptr, &remote_certificate, remote_cert_buffer, sizeof(remote_cert_buffer));
+ nx_secure_tls_remote_certificate_allocate(tls_session_ptr, &remote_issuer, remote_issuer_buffer, sizeof(remote_issuer_buffer));
+
+ memset(&local_certificate, 0, sizeof(local_certificate));
+ status = nx_secure_x509_certificate_initialize(&local_certificate,
+ ECTestServer7_256_der, ECTestServer7_256_der_len,
+ NX_NULL, 0, ECTestServer7_256_key_der,
+ ECTestServer7_256_key_der_len, NX_SECURE_X509_KEY_TYPE_EC_DER);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ status = nx_secure_tls_local_certificate_add(tls_session_ptr, &local_certificate);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ status = nx_secure_x509_certificate_initialize(&client_trusted_ca, ECCA2_der, ECCA2_der_len,
+ NX_NULL, 0, NULL, 0,
+ NX_SECURE_X509_KEY_TYPE_NONE);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ status = nx_secure_tls_trusted_certificate_add(tls_session_ptr, &client_trusted_ca);
+ exit_if_fail(NX_SUCCESS == status, status);
+}
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+NX_PARAMETER_NOT_USED(thread_input);
+
+ /* Address of remote server. */
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup this thread to bind to a port. */
+ status = nx_tcp_client_socket_bind(&tcp_socket, 0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup TLS client. */
+ client_tls_setup(&tls_session);
+
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tx_thread_sleep(100);
+
+ /* Attempt to connect the echo server. */
+ status = nx_tcp_client_socket_connect(&tcp_socket, REMOTE_IP_ADDRESS_NUMBER, DEVICE_SERVER_PORT, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send "hello" message. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Receive the echoed and reversed data, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Extract data received from server. */
+ status = nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Check the reverse text received from openssl server. */
+ exit_if_fail('o' == ((CHAR*)receive_buffer)[0], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[1], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[2], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('e' == ((CHAR*)receive_buffer)[3], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('h' == ((CHAR*)receive_buffer)[4], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('\n' == ((CHAR*)receive_buffer)[5], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail(6 == bytes, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Close the TCP connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Unbind the TCP socket from our port. */
+ status = nx_tcp_client_socket_unbind(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Delete the TCP socket instance to clean up. */
+ status = nx_tcp_socket_delete(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ exit(0);
+}
+#endif
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_3_client_certificate_verify_test_nx_secure_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_3_client_certificate_verify_test_nx_secure_echo_server_entry.c
new file mode 100644
index 00000000..68537b94
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_3_client_certificate_verify_test_nx_secure_echo_server_entry.c
@@ -0,0 +1,242 @@
+/* This test concentrates on TLS ciphersuite TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA. The client certificate is require. */
+#include "tls_test_frame.h"
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) && defined(NX_SECURE_ENABLE_CLIENT_CERTIFICATE_VERIFY)
+#include "nx_crypto_ecdh.h"
+#include "../../nx_secure_test/ecc_certs.c"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Define the ThreadX and NetX object control blocks... */
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT server_trusted_ca;
+NX_SECURE_X509_CERT server_remote_cert;
+NX_SECURE_X509_CERT server_local_certificate;
+
+UCHAR tls_packet_buffer[4000];
+UCHAR server_cert_buffer[2048];
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+void server_thread_entry(ULONG thread_input);
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+
+/* Define the pointer of current instance control block. */
+static TLS_TEST_INSTANCE* demo_instance_ptr;
+
+/* Define external references. */
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Instance one test entry. */
+INT nx_secure_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+
+ /* Get instance pointer. */
+ demo_instance_ptr = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+}
+
+/* Define what the initial system looks like. */
+void tx_application_define(void *first_unused_memory)
+{
+ ULONG gateway_ipv4_address;
+ UINT status;
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL, &pool_0, _nx_pcap_network_driver, (UCHAR*)ip_thread_stack, sizeof(ip_thread_stack), 1);
+print_error_message( "ip address number: %lu", TLS_TEST_IP_ADDRESS_NUMBER);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ tx_thread_create(&demo_thread, "demo thread", server_thread_entry, 0, demo_thread_stack, sizeof(demo_thread_stack), 16, 16, 4, TX_AUTO_START);
+}
+
+/* TLS Server example application thread. */
+void server_thread_entry(ULONG thread_input)
+{
+ INT status = 0, i = 0;
+ ULONG actual_status;
+ NX_PACKET *receive_packet;
+ NX_PACKET *send_packet;
+ UCHAR receive_buffer[100];
+ ULONG bytes;
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Server Socket",
+ NX_IP_NORMAL, NX_FRAGMENT_OKAY /*NX_DONT_FRAGMENT*/, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_session_create(&tls_session,
+ &nx_crypto_tls_ciphers_ecc,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Initialize ECC tables. */
+ status = nx_secure_tls_ecc_initialize(&tls_session, nx_crypto_ecc_supported_groups,
+ nx_crypto_ecc_supported_groups_size,
+ nx_crypto_ecc_curves);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Enable Client Certificate Verification. */
+ status = nx_secure_tls_session_client_verify_enable(&tls_session);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(&tls_session, tls_packet_buffer, sizeof(tls_packet_buffer));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ memset(&server_remote_cert, 0, sizeof(server_remote_cert));
+ status = nx_secure_tls_remote_certificate_allocate(&tls_session,
+ &server_remote_cert,
+ server_cert_buffer,
+ sizeof(server_cert_buffer));
+
+ memset(&server_local_certificate, 0, sizeof(server_local_certificate));
+ status = nx_secure_x509_certificate_initialize(&server_local_certificate,
+ ECTestServer2_der, ECTestServer2_der_len,
+ NX_NULL, 0, ECTestServer2_key_der,
+ ECTestServer2_key_der_len,
+ NX_SECURE_X509_KEY_TYPE_EC_DER);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_local_certificate_add(&tls_session,
+ &server_local_certificate);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_x509_certificate_initialize(&server_trusted_ca, ECCA4_der, ECCA4_der_len,
+ NX_NULL, 0, NULL, 0,
+ NX_SECURE_X509_KEY_TYPE_NONE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_trusted_certificate_add(&tls_session,
+ &server_trusted_ca);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Setup this thread to listen. */
+ status = nx_tcp_server_socket_listen(&ip_0, DEVICE_SERVER_PORT, &tcp_socket, 5, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ for ( ; i < 3; i++)
+ {
+
+ /* Post semaphore before accept sockets. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Accept a client socket connection. */
+ status = nx_tcp_server_socket_accept(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 1);
+
+ /* Start the TLS Session now that we have a connected socket. */
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 2);
+
+ /* Receive the HTTP request, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 3);
+
+ /* Show received data. */
+ nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ receive_buffer[bytes] = 0;
+ print_error_message("Received data: %s\n", receive_buffer);
+
+ /* Allocate a return packet and send our HTML data back to the client. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 4);
+
+ /* Echo the message received. */
+ status = nx_packet_data_append(send_packet, receive_buffer, bytes, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 5);
+
+ /* TLS send the HTML/HTTPS data back to the client. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ /* Exit the test process directly without release packet. */
+ exit_if_fail(NX_SUCCESS == status, 6);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 7);
+
+ /* Disconnect the TCP socket, closing the connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 8);
+
+ /* Unaccept the server socket. */
+ status = nx_tcp_server_socket_unaccept(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, 9);
+
+ print_error_message("Connection %d: server unaccept, sleeping...\n", i);
+ tx_thread_sleep(100);
+
+ /* Setup server socket for listening again. */
+ status = nx_tcp_server_socket_relisten(&ip_0, DEVICE_SERVER_PORT, &tcp_socket);
+ exit_if_fail( NX_SUCCESS == status, 10);
+ }
+
+ exit(0);
+}
+#else
+
+/* Instance one test entry. */
+INT nx_secure_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+ exit(TLS_TEST_NOT_AVAILABLE);
+}
+#endif
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_3_client_certificate_verify_test_openssl_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_3_client_certificate_verify_test_openssl_echo_client_entry.c
new file mode 100644
index 00000000..c6ef2a9c
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_3_client_certificate_verify_test_openssl_echo_client_entry.c
@@ -0,0 +1,47 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+#define VERSION_STR "-tls1_3"
+#else
+#define VERSION_STR ""
+#endif
+
+/* Instance two test entry. */
+INT openssl_echo_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined (NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+
+CHAR* external_cmd[] = { "openssl_1_1_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING, "-curves", "prime256v1", VERSION_STR,
+ "-cert", "../../ecc_certificates/ECTestServer7_256.crt",
+ "-key", "../../ecc_certificates/ECTestServer7_256.key", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+
+ for (; i < 3; i++)
+ {
+
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tls_test_sleep(1);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_FAILED);
+ }
+
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_3_client_certificate_verify_test_openssl_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_3_client_certificate_verify_test_openssl_echo_server_entry.c
new file mode 100644
index 00000000..cf1f1de9
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_3_client_certificate_verify_test_openssl_echo_server_entry.c
@@ -0,0 +1,41 @@
+#include "tls_test_frame.h"
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Openssl echo server entry. */
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) && (NX_SECURE_TLS_TLS_1_3_ENABLED)
+
+INT status, exit_status;
+
+/* Added -rev option to send reverse text received from clients back to the client. Added -naccept 1 to close the server after one tls session. */
+CHAR* external_cmd[] = { "openssl-1.1", "s_server",
+ "-port", DEVICE_SERVER_PORT_STRING,
+ "-key", "../ecc_certificates/ECTestServer2.key",
+ "-cert", "../ecc_certificates/ECTestServer2.crt",
+ "-naccept", "1",
+ "-rev", "-tls1_3",
+ "-Verify", "10",
+ "-CAfile", "../ecc_certificates/ECCA4.crt", (CHAR*)NULL};
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+ return TLS_TEST_SUCCESS;
+
+#else
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_3_client_session_reuse_test_nx_secure_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_3_client_session_reuse_test_nx_secure_echo_client_entry.c
new file mode 100644
index 00000000..52645ea7
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_3_client_session_reuse_test_nx_secure_echo_client_entry.c
@@ -0,0 +1,256 @@
+#include "tls_test_frame.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+NX_SECURE_X509_CERT trusted_certificate;
+NX_SECURE_X509_CERT client_trusted_ca;
+
+UCHAR tls_packet_buffer[4000];
+
+#include "../../nx_secure_test/ecc_certs.c"
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define an error counter. */
+
+ULONG error_counter;
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) && (NX_SECURE_TLS_TLS_1_3_ENABLED)
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+void tx_application_define(void *first_unused_memory)
+{
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+void client_tls_setup(NX_SECURE_TLS_SESSION *tls_session_ptr)
+{
+UINT status;
+
+ /* Create a tls session. */
+ status = nx_secure_tls_session_create(tls_session_ptr,
+ &nx_crypto_tls_ciphers_ecc,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Initialize ECC. */
+ status = nx_secure_tls_ecc_initialize(tls_session_ptr, nx_crypto_ecc_supported_groups,
+ nx_crypto_ecc_supported_groups_size,
+ nx_crypto_ecc_curves);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(tls_session_ptr, tls_packet_buffer, sizeof(tls_packet_buffer));
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Need to allocate space for the certificate coming in from the remote host. */
+ nx_secure_tls_remote_certificate_allocate(tls_session_ptr, &remote_certificate, remote_cert_buffer, sizeof(remote_cert_buffer));
+ nx_secure_tls_remote_certificate_allocate(tls_session_ptr, &remote_issuer, remote_issuer_buffer, sizeof(remote_issuer_buffer));
+
+ status = nx_secure_x509_certificate_initialize(&client_trusted_ca, ECCA2_der, ECCA2_der_len,
+ NX_NULL, 0, NULL, 0,
+ NX_SECURE_X509_KEY_TYPE_NONE);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ status = nx_secure_tls_trusted_certificate_add(tls_session_ptr, &client_trusted_ca);
+ exit_if_fail(NX_SUCCESS == status, status);
+}
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status, i;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+NX_PARAMETER_NOT_USED(thread_input);
+
+ /* Address of remote server. */
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup this thread to bind to a port. */
+ status = nx_tcp_client_socket_bind(&tcp_socket, 0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup TLS client. */
+ client_tls_setup(&tls_session);
+
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+
+ for (i = 0; i < 5; i++)
+ {
+
+ tx_thread_sleep(100);
+
+ /* Attempt to connect the echo server. */
+ status = nx_tcp_client_socket_connect(&tcp_socket, REMOTE_IP_ADDRESS_NUMBER, DEVICE_SERVER_PORT, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ if (i == 4)
+ break;
+
+ status = nx_secure_tls_session_end(&tls_session, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, status);
+ }
+
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send "hello" message. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Receive the echoed and reversed data, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Extract data received from server. */
+ status = nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Check the reverse text received from openssl server. */
+ exit_if_fail('o' == ((CHAR*)receive_buffer)[0], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[1], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[2], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('e' == ((CHAR*)receive_buffer)[3], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('h' == ((CHAR*)receive_buffer)[4], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('\n' == ((CHAR*)receive_buffer)[5], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail(6 == bytes, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_session_delete(&tls_session);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Close the TCP connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Unbind the TCP socket from our port. */
+ status = nx_tcp_client_socket_unbind(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Delete the TCP socket instance to clean up. */
+ status = nx_tcp_socket_delete(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ exit(0);
+}
+#endif
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_3_client_session_reuse_test_openssl_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_3_client_session_reuse_test_openssl_echo_server_entry.c
new file mode 100644
index 00000000..16547498
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_3_client_session_reuse_test_openssl_echo_server_entry.c
@@ -0,0 +1,38 @@
+#include "tls_test_frame.h"
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Openssl echo server entry. */
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && (NX_SECURE_TLS_TLS_1_3_ENABLED)
+
+INT status, exit_status;
+
+/* Added -rev option to send reverse text received from clients back to the client. Added -naccept 1 to close the server after one tls session. */
+CHAR* external_cmd[] = { "openssl-1.1", "s_server", "-rev",
+ "-port", DEVICE_SERVER_PORT_STRING,
+ "-key", "../ecc_certificates/ECTestServer2.key",
+ "-cert", "../ecc_certificates/ECTestServer2.crt",
+ "-naccept", "5", "-tls1_3", (CHAR*)NULL};
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+ return TLS_TEST_SUCCESS;
+
+#else
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_3_hello_retry_cookie_test_nx_secure_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_3_hello_retry_cookie_test_nx_secure_echo_client_entry.c
new file mode 100644
index 00000000..4709f7d5
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_3_hello_retry_cookie_test_nx_secure_echo_client_entry.c
@@ -0,0 +1,249 @@
+#include "tls_test_frame.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+NX_SECURE_X509_CERT trusted_certificate;
+NX_SECURE_X509_CERT client_trusted_ca;
+
+UCHAR tls_packet_buffer[4000];
+
+#include "../../nx_secure_test/ecc_certs.c"
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define an error counter. */
+
+ULONG error_counter;
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) && (NX_SECURE_TLS_TLS_1_3_ENABLED)
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+void tx_application_define(void *first_unused_memory)
+{
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+void client_tls_setup(NX_SECURE_TLS_SESSION *tls_session_ptr)
+{
+UINT status;
+
+ /* Create a tls session. */
+ status = nx_secure_tls_session_create(tls_session_ptr,
+ &nx_crypto_tls_ciphers_ecc,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Initialize ECC. */
+ status = nx_secure_tls_ecc_initialize(tls_session_ptr, nx_crypto_ecc_supported_groups,
+ nx_crypto_ecc_supported_groups_size,
+ nx_crypto_ecc_curves);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(tls_session_ptr, tls_packet_buffer, sizeof(tls_packet_buffer));
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Need to allocate space for the certificate coming in from the remote host. */
+ nx_secure_tls_remote_certificate_allocate(tls_session_ptr, &remote_certificate, remote_cert_buffer, sizeof(remote_cert_buffer));
+ nx_secure_tls_remote_certificate_allocate(tls_session_ptr, &remote_issuer, remote_issuer_buffer, sizeof(remote_issuer_buffer));
+
+ status = nx_secure_x509_certificate_initialize(&client_trusted_ca, ECCA2_der, ECCA2_der_len,
+ NX_NULL, 0, NULL, 0,
+ NX_SECURE_X509_KEY_TYPE_NONE);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ status = nx_secure_tls_trusted_certificate_add(tls_session_ptr, &client_trusted_ca);
+ exit_if_fail(NX_SUCCESS == status, status);
+}
+
+static ULONG client_callback(NX_SECURE_TLS_SESSION *tls_session, NX_SECURE_TLS_HELLO_EXTENSION *extensions, UINT num_extensions)
+{
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ tls_session -> nx_secure_tls_cookie_length = 0;
+#endif
+ return(NX_SUCCESS);
+}
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+NX_PARAMETER_NOT_USED(thread_input);
+
+ /* Address of remote server. */
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup this thread to bind to a port. */
+ status = nx_tcp_client_socket_bind(&tcp_socket, 0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup TLS client. */
+ client_tls_setup(&tls_session);
+
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tx_thread_sleep(20 * NX_IP_PERIODIC_RATE);
+
+ /* Test client receives a second HelloRetryRequest. */
+ nx_secure_tls_session_client_callback_set(&tls_session, client_callback);
+
+ /* Attempt to connect the echo server. */
+ status = nx_tcp_client_socket_connect(&tcp_socket, REMOTE_IP_ADDRESS_NUMBER, DEVICE_SERVER_PORT, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS != status, status);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ nx_secure_tls_session_end(&tls_session, NX_NO_WAIT);
+
+ /* Close the TCP connection. */
+ nx_tcp_socket_disconnect(&tcp_socket, NX_NO_WAIT);
+
+ /* Reset the client callback function. */
+ tls_session.nx_secure_tls_session_client_callback = NX_NULL;
+
+ /* Attempt to connect the echo server. */
+ status = nx_tcp_client_socket_connect(&tcp_socket, REMOTE_IP_ADDRESS_NUMBER, DEVICE_SERVER_PORT, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send "hello" message. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_NO_WAIT);
+ //exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Close the TCP connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_NO_WAIT);
+ //exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Unbind the TCP socket from our port. */
+ status = nx_tcp_client_socket_unbind(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Delete the TCP socket instance to clean up. */
+ status = nx_tcp_socket_delete(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ exit(0);
+}
+#endif
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_3_hello_retry_cookie_test_openssl_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_3_hello_retry_cookie_test_openssl_echo_server_entry.c
new file mode 100644
index 00000000..71a1817e
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_3_hello_retry_cookie_test_openssl_echo_server_entry.c
@@ -0,0 +1,43 @@
+#include "tls_test_frame.h"
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Openssl echo server entry. */
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && (NX_SECURE_TLS_TLS_1_3_ENABLED)
+
+INT status, exit_status;
+
+/* Added -naccept 1 to close the server after one tls session. */
+/* Added -named_curve to use specific curve(secp384r1). Client is using secp256r1, so server will send HelloRetryRequest for the mismatch of "key_share". */
+/* Added -stateless to include "cookie" in the HelloRetryRequest. */
+CHAR* external_cmd[] = { "openssl_1_1_echo_server.sh",
+ "../../ecc_certificates/ECTestServer2.key",
+ "../../ecc_certificates/ECTestServer2.crt",
+ "-port", DEVICE_SERVER_PORT_STRING,
+ "-naccept", "2",
+ "-tls1_3",
+ "-named_curve", "secp384r1",
+ "-stateless", (CHAR*)NULL};
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+ return TLS_TEST_SUCCESS;
+
+#else
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_3_hello_retry_request_test_openssl_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_3_hello_retry_request_test_openssl_echo_server_entry.c
new file mode 100644
index 00000000..1c432203
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_3_hello_retry_request_test_openssl_echo_server_entry.c
@@ -0,0 +1,42 @@
+#include "tls_test_frame.h"
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Openssl echo server entry. */
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && (NX_SECURE_TLS_TLS_1_3_ENABLED)
+
+INT status, exit_status;
+
+/* Added -rev option to send reverse text received from clients back to the client. Added -naccept 1 to close the server after one tls session. */
+/* Added -named_curve to use specific curve(secp384r1). Client is using secp256r1, so server will send HelloRetryRequest for the mismatch of "key_share". */
+CHAR* external_cmd[] = { "openssl-1.1", "s_server",
+ "-port", DEVICE_SERVER_PORT_STRING,
+ "-key", "../ecc_certificates/ECTestServer2.key",
+ "-cert", "../ecc_certificates/ECTestServer2.crt",
+ "-naccept", "1",
+ "-rev", "-tls1_3",
+ "-named_curve", "secp384r1",
+ (CHAR*)NULL};
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+ return TLS_TEST_SUCCESS;
+
+#else
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_3_nx_secure_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_3_nx_secure_echo_client_entry.c
new file mode 100644
index 00000000..7632ef90
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_3_nx_secure_echo_client_entry.c
@@ -0,0 +1,241 @@
+#include "tls_test_frame.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+NX_SECURE_X509_CERT trusted_certificate;
+NX_SECURE_X509_CERT client_trusted_ca;
+
+UCHAR tls_packet_buffer[4000];
+
+#include "../../nx_secure_test/ecc_certs.c"
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define an error counter. */
+
+ULONG error_counter;
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+void tx_application_define(void *first_unused_memory)
+{
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+void client_tls_setup(NX_SECURE_TLS_SESSION *tls_session_ptr)
+{
+UINT status;
+
+ /* Create a tls session. */
+ status = nx_secure_tls_session_create(tls_session_ptr,
+ &nx_crypto_tls_ciphers_ecc,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Initialize ECC. */
+ status = nx_secure_tls_ecc_initialize(tls_session_ptr, nx_crypto_ecc_supported_groups,
+ nx_crypto_ecc_supported_groups_size,
+ nx_crypto_ecc_curves);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(tls_session_ptr, tls_packet_buffer, sizeof(tls_packet_buffer));
+ exit_if_fail(NX_SUCCESS == status, status);
+
+#if 0 /* Packet buffer is used to hold certificate. */
+ /* Need to allocate space for the certificate coming in from the remote host. */
+ nx_secure_tls_remote_certificate_allocate(tls_session_ptr, &remote_certificate, remote_cert_buffer, sizeof(remote_cert_buffer));
+ nx_secure_tls_remote_certificate_allocate(tls_session_ptr, &remote_issuer, remote_issuer_buffer, sizeof(remote_issuer_buffer));
+#endif
+
+ status = nx_secure_x509_certificate_initialize(&client_trusted_ca, ECCA2_der, ECCA2_der_len,
+ NX_NULL, 0, NULL, 0,
+ NX_SECURE_X509_KEY_TYPE_NONE);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ status = nx_secure_tls_trusted_certificate_add(tls_session_ptr, &client_trusted_ca);
+ exit_if_fail(NX_SUCCESS == status, status);
+}
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+NX_PARAMETER_NOT_USED(thread_input);
+
+ /* Address of remote server. */
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup this thread to bind to a port. */
+ status = nx_tcp_client_socket_bind(&tcp_socket, 0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup TLS client. */
+ client_tls_setup(&tls_session);
+
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tx_thread_sleep(100);
+
+ /* Attempt to connect the echo server. */
+ status = nx_tcp_client_socket_connect(&tcp_socket, REMOTE_IP_ADDRESS_NUMBER, DEVICE_SERVER_PORT, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send "hello" message. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Receive the echoed and reversed data, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Extract data received from server. */
+ status = nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Check the reverse text received from openssl server. */
+ exit_if_fail('o' == ((CHAR*)receive_buffer)[0], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[1], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[2], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('e' == ((CHAR*)receive_buffer)[3], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('h' == ((CHAR*)receive_buffer)[4], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('\n' == ((CHAR*)receive_buffer)[5], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail(6 == bytes, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Close the TCP connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Unbind the TCP socket from our port. */
+ status = nx_tcp_client_socket_unbind(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Delete the TCP socket instance to clean up. */
+ status = nx_tcp_socket_delete(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ exit(0);
+}
+#endif
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_3_openssl_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_3_openssl_echo_server_entry.c
new file mode 100644
index 00000000..8ad80b2d
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_3_openssl_echo_server_entry.c
@@ -0,0 +1,44 @@
+#include "tls_test_frame.h"
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Openssl echo server entry. */
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED)
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+#define VERSION_STR "-tls1_3"
+#else
+#define VERSION_STR ""
+#endif
+
+INT status, exit_status;
+
+/* Added -rev option to send reverse text received from clients back to the client. Added -naccept 1 to close the server after one tls session. */
+CHAR* external_cmd[] = { "openssl-1.1", "s_server", "-rev",
+ "-port", DEVICE_SERVER_PORT_STRING,
+ "-key", "../ecc_certificates/ECTestServer2.key",
+ "-cert", "../ecc_certificates/ECTestServer2.crt",
+ "-naccept", "1", VERSION_STR, (CHAR*)NULL};
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+ return TLS_TEST_SUCCESS;
+
+#else
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_hello_retry_test_openssl_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_hello_retry_test_openssl_echo_client_entry.c
new file mode 100644
index 00000000..56213b35
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_hello_retry_test_openssl_echo_client_entry.c
@@ -0,0 +1,38 @@
+#include "tls_test_frame.h"
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Openssl echo client entry. */
+INT openssl_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && (NX_SECURE_TLS_TLS_1_3_ENABLED) && defined(NX_SECURE_ENABLE_PSK_CIPHERSUITES)
+
+
+INT status, exit_status;
+
+/* Added -curves prime256v1 to avoid hello retry. */
+CHAR* external_cmd[] = { "openssl_1_1_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING,
+ "-psk", "112233445566",
+ "-psk_identity", "psk_test",
+ (CHAR*)NULL};
+
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tls_test_sleep(1);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_FAILED);
+
+ return TLS_TEST_SUCCESS;
+
+#else
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif
+
+} \ No newline at end of file
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_test_nx_secure_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_test_nx_secure_echo_client_entry.c
new file mode 100644
index 00000000..693e2098
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_test_nx_secure_echo_client_entry.c
@@ -0,0 +1,248 @@
+#include "tls_test_frame.h"
+
+/* Define the ThreadX and NetX object control blocks... */
+
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT remote_certificate, remote_issuer;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+NX_SECURE_X509_CERT trusted_certificate;
+NX_SECURE_X509_CERT client_trusted_ca;
+
+UCHAR tls_packet_buffer[4000];
+#define REMOTE_SERVER_PORT 4433
+#define LOCAL_CLIENT_PORT 30024
+
+#include "../../nx_secure_test/ecc_certs.c"
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define an error counter. */
+
+ULONG error_counter;
+
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+
+TLS_TEST_INSTANCE* client_instance_ptr;
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+void client_thread_entry(ULONG thread_input);
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+
+INT nx_secure_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) && (NX_SECURE_TLS_TLS_1_3_ENABLED) && defined(NX_SECURE_ENABLE_PSK_CIPHERSUITES)
+
+ client_instance_ptr = instance_ptr;
+ tx_kernel_enter();
+
+#else /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+ exit(TLS_TEST_NOT_AVAILABLE);
+
+#endif /* ifndef NX_SECURE_TLS_CLIENT_DISABLED */
+
+}
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE) && (NX_SECURE_TLS_TLS_1_3_ENABLED) && defined(NX_SECURE_ENABLE_PSK_CIPHERSUITES)
+void tx_application_define(void *first_unused_memory)
+{
+UINT status;
+
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0,
+ "NetX IP Instance 0",
+ TLS_TEST_IP_ADDRESS_NUMBER,
+ 0xFFFFFF00UL,
+ &pool_0,
+ _nx_pcap_network_driver,
+ (UCHAR*)ip_thread_stack,
+ sizeof(ip_thread_stack),
+ 1);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail(NX_SUCCESS == status);
+
+ nx_secure_tls_initialize();
+
+ tx_thread_create(&demo_thread, "demo thread", client_thread_entry, 0,
+ demo_thread_stack, sizeof(demo_thread_stack),
+ 16, 16, 4, TX_AUTO_START);
+}
+
+void client_tls_setup(NX_SECURE_TLS_SESSION *tls_session_ptr)
+{
+UINT status;
+
+ /* Create a tls session. */
+ status = nx_secure_tls_session_create(tls_session_ptr,
+ &nx_crypto_tls_ciphers_ecc,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Initialize ECC. */
+ status = nx_secure_tls_ecc_initialize(tls_session_ptr, nx_crypto_ecc_supported_groups,
+ nx_crypto_ecc_supported_groups_size,
+ nx_crypto_ecc_curves);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(tls_session_ptr, tls_packet_buffer, sizeof(tls_packet_buffer));
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ /* Need to allocate space for the certificate coming in from the remote host. */
+ nx_secure_tls_remote_certificate_allocate(tls_session_ptr, &remote_certificate, remote_cert_buffer, sizeof(remote_cert_buffer));
+ nx_secure_tls_remote_certificate_allocate(tls_session_ptr, &remote_issuer, remote_issuer_buffer, sizeof(remote_issuer_buffer));
+
+ status = nx_secure_x509_certificate_initialize(&client_trusted_ca, ECCA2_der, ECCA2_der_len,
+ NX_NULL, 0, NULL, 0,
+ NX_SECURE_X509_KEY_TYPE_NONE);
+ exit_if_fail(NX_SUCCESS == status, status);
+
+ status = nx_secure_tls_trusted_certificate_add(tls_session_ptr, &client_trusted_ca);
+ exit_if_fail(NX_SUCCESS == status, status);
+}
+
+void client_thread_entry(ULONG thread_input)
+{
+UINT status;
+ULONG actual_status;
+NX_PACKET *send_packet;
+NX_PACKET *receive_packet;
+UCHAR receive_buffer[100];
+ULONG bytes;
+UCHAR psk_test[] = {0x11, 0x22, 0x33, 0x44, 0x55, 0x66};
+NX_PARAMETER_NOT_USED(thread_input);
+
+ /* Address of remote server. */
+ print_error_message( "remote ip address number %lu, remote ip address string %s.\n", REMOTE_IP_ADDRESS_NUMBER, REMOTE_IP_ADDRESS_STRING);
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Client Socket",
+ NX_IP_NORMAL, NX_DONT_FRAGMENT, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup this thread to bind to a port. */
+ status = nx_tcp_client_socket_bind(&tcp_socket, LOCAL_CLIENT_PORT, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Setup TLS client. */
+ client_tls_setup(&tls_session);
+
+ /* Add psk. */
+ status = nx_secure_tls_client_psk_set(&tls_session, psk_test, sizeof(psk_test), "psk_test", 8, "", 0);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+ status = nx_secure_tls_psk_add(&tls_session, psk_test, sizeof(psk_test), "psk_test", 8, "", 0);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Wait for the semaphore. */
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tx_thread_sleep(100);
+
+ /* Attempt to connect the echo server. */
+ status = nx_tcp_client_socket_connect(&tcp_socket, REMOTE_IP_ADDRESS_NUMBER, REMOTE_SERVER_PORT, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send some data to be echoed by the OpenSSL s_server echo instance. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Append application to the allocated packet. */
+ status = nx_packet_data_append(send_packet, "hello\n", 6, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Send "hello" message. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Receive the echoed and reversed data, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Extract data received from server. */
+ status = nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Check the reverse text received from openssl server. */
+ exit_if_fail('o' == ((CHAR*)receive_buffer)[0], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[1], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('l' == ((CHAR*)receive_buffer)[2], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('e' == ((CHAR*)receive_buffer)[3], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('h' == ((CHAR*)receive_buffer)[4], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail('\n' == ((CHAR*)receive_buffer)[5], TLS_TEST_UNKNOWN_TYPE_ERROR);
+ exit_if_fail(6 == bytes, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Close the TCP connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Unbind the TCP socket from our port. */
+ status = nx_tcp_client_socket_unbind(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Delete the TCP socket instance to clean up. */
+ status = nx_tcp_socket_delete(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ exit(0);
+}
+#endif
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_test_nx_secure_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_test_nx_secure_echo_server_entry.c
new file mode 100644
index 00000000..7b5a2f29
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_test_nx_secure_echo_server_entry.c
@@ -0,0 +1,215 @@
+/* This test concentrates on TLS ciphersuite TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA. The client certificate is require. */
+#include "tls_test_frame.h"
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && (NX_SECURE_TLS_TLS_1_3_ENABLED) && defined(NX_SECURE_ENABLE_PSK_CIPHERSUITES)
+#include "nx_crypto_ecdh.h"
+#include "../../nx_secure_test/ecc_certs.c"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Define the ThreadX and NetX object control blocks... */
+NX_PACKET_POOL pool_0;
+NX_IP ip_0;
+
+NX_TCP_SOCKET tcp_socket;
+NX_SECURE_TLS_SESSION tls_session;
+NX_SECURE_X509_CERT server_local_certificate;
+
+UCHAR tls_packet_buffer[4000];
+UCHAR server_cert_buffer[2048];
+
+/* Define the IP thread's stack area. */
+ULONG ip_thread_stack[3 * 1024 / sizeof(ULONG)];
+
+/* Define packet pool for the demonstration. */
+#define NX_PACKET_POOL_SIZE ((1536 + sizeof(NX_PACKET)) * 32)
+ULONG packet_pool_area[NX_PACKET_POOL_SIZE/sizeof(ULONG) + 64 / sizeof(ULONG)];
+
+/* Define the ARP cache area. */
+ULONG arp_space_area[512 / sizeof(ULONG)];
+
+/* Define the demo thread. */
+ULONG demo_thread_stack[6 * 1024 / sizeof(ULONG)];
+TX_THREAD demo_thread;
+void server_thread_entry(ULONG thread_input);
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
+UCHAR remote_cert_buffer[2000];
+UCHAR remote_issuer_buffer[2000];
+CHAR crypto_metadata[30000]; // 2*sizeof(NX_AES) + sizeof(NX_SHA1_HMAC) + 2*sizeof(NX_CRYPTO_RSA) + (2 * (sizeof(NX_MD5) + sizeof(NX_SHA1) + sizeof(NX_SHA256)))];
+
+extern const USHORT nx_crypto_ecc_supported_groups[];
+extern const NX_CRYPTO_METHOD *nx_crypto_ecc_curves[];
+extern const UINT nx_crypto_ecc_supported_groups_size;
+extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers_ecc;
+
+/* Define the pointer of current instance control block. */
+static TLS_TEST_INSTANCE* demo_instance_ptr;
+
+/* Define external references. */
+VOID _nx_pcap_network_driver(NX_IP_DRIVER *driver_req_ptr);
+
+/* Instance one test entry. */
+INT nx_secure_ecc_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+
+ /* Get instance pointer. */
+ demo_instance_ptr = instance_ptr;
+
+ /* Enter the ThreadX kernel. */
+ tx_kernel_enter();
+}
+
+/* Define what the initial system looks like. */
+void tx_application_define(void *first_unused_memory)
+{
+ ULONG gateway_ipv4_address;
+ UINT status;
+
+ /* Initialize the NetX system. */
+ nx_system_initialize();
+
+ /* Create a packet pool. */
+ status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 1536, (ULONG*)(((int)packet_pool_area + 64) & ~63) , NX_PACKET_POOL_SIZE);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Create an IP instance. */
+ status = nx_ip_create(&ip_0, "NetX IP Instance 0", TLS_TEST_IP_ADDRESS_NUMBER, 0xFFFFFF00UL, &pool_0, _nx_pcap_network_driver, (UCHAR*)ip_thread_stack, sizeof(ip_thread_stack), 1);
+print_error_message( "ip address number: %lu", TLS_TEST_IP_ADDRESS_NUMBER);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ARP and supply ARP cache memory for IP Instance 0. */
+ status = nx_arp_enable(&ip_0, (void *)arp_space_area, sizeof(arp_space_area));
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable TCP traffic. */
+ status = nx_tcp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable UDP traffic. */
+ status = nx_udp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ /* Enable ICMP. */
+ status = nx_icmp_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ status = nx_ip_fragment_enable(&ip_0);
+ show_error_message_if_fail( status == NX_SUCCESS);
+
+ tx_thread_create(&demo_thread, "demo thread", server_thread_entry, 0, demo_thread_stack, sizeof(demo_thread_stack), 16, 16, 4, TX_AUTO_START);
+}
+
+/* TLS Server example application thread. */
+void server_thread_entry(ULONG thread_input)
+{
+ INT status = 0;
+ ULONG actual_status;
+ NX_PACKET *receive_packet;
+ NX_PACKET *send_packet;
+ UCHAR receive_buffer[100];
+ ULONG bytes;
+ UCHAR psk_test[] = {0x11, 0x22, 0x33, 0x44, 0x55, 0x66};
+
+ /* Ensure the IP instance has been initialized. */
+ status = nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Create a socket. */
+ status = nx_tcp_socket_create(&ip_0, &tcp_socket, "Server Socket",
+ NX_IP_NORMAL, NX_FRAGMENT_OKAY /*NX_DONT_FRAGMENT*/, NX_IP_TIME_TO_LIVE, 8192,
+ NX_NULL, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_session_create(&tls_session,
+ &nx_crypto_tls_ciphers_ecc,
+ crypto_metadata,
+ sizeof(crypto_metadata));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Initialize ECC tables. */
+ status = nx_secure_tls_ecc_initialize(&tls_session, nx_crypto_ecc_supported_groups,
+ nx_crypto_ecc_supported_groups_size,
+ nx_crypto_ecc_curves);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Allocate space for packet reassembly. */
+ status = nx_secure_tls_session_packet_buffer_set(&tls_session, tls_packet_buffer, sizeof(tls_packet_buffer));
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ memset(&server_local_certificate, 0, sizeof(server_local_certificate));
+ status = nx_secure_x509_certificate_initialize(&server_local_certificate,
+ ECTestServer2_der, ECTestServer2_der_len,
+ NX_NULL, 0, ECTestServer2_key_der,
+ ECTestServer2_key_der_len,
+ NX_SECURE_X509_KEY_TYPE_EC_DER);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ status = nx_secure_tls_local_certificate_add(&tls_session,
+ &server_local_certificate);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Add psk info. */
+ status = nx_secure_tls_psk_add(&tls_session, psk_test, sizeof(psk_test), "psk_test", 8, "psk_test", 8);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Setup this thread to listen. */
+ status = nx_tcp_server_socket_listen(&ip_0, DEVICE_SERVER_PORT, &tcp_socket, 5, NX_NULL);
+ show_error_message_if_fail( NX_SUCCESS == status);
+
+ /* Post semaphore before accept sockets. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Accept a client socket connection. */
+ status = nx_tcp_server_socket_accept(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 1);
+
+ /* Start the TLS Session now that we have a connected socket. */
+ status = nx_secure_tls_session_start(&tls_session, &tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 2);
+
+ /* Receive the HTTP request, and print it out. */
+ status = nx_secure_tls_session_receive(&tls_session, &receive_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 3);
+
+ /* Show received data. */
+ nx_packet_data_extract_offset(receive_packet, 0, receive_buffer, 100, &bytes);
+ receive_buffer[bytes] = 0;
+ print_error_message("Received data: %s\n", receive_buffer);
+
+ /* Allocate a return packet and send our HTML data back to the client. */
+ status = nx_secure_tls_packet_allocate(&tls_session, &pool_0, &send_packet, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 4);
+
+ /* Echo the message received. */
+ status = nx_packet_data_append(send_packet, receive_buffer, bytes, &pool_0, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 5);
+
+ /* TLS send the HTML/HTTPS data back to the client. */
+ status = nx_secure_tls_session_send(&tls_session, send_packet, NX_IP_PERIODIC_RATE);
+ /* Exit the test process directly without release packet. */
+ exit_if_fail(NX_SUCCESS == status, 6);
+
+ /* End the TLS session. This is required to properly shut down the TLS connection. */
+ status = nx_secure_tls_session_end(&tls_session, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 7);
+
+ /* Disconnect the TCP socket, closing the connection. */
+ status = nx_tcp_socket_disconnect(&tcp_socket, NX_WAIT_FOREVER);
+ exit_if_fail(NX_SUCCESS == status, 8);
+
+ /* Unaccept the server socket. */
+ status = nx_tcp_server_socket_unaccept(&tcp_socket);
+ exit_if_fail(NX_SUCCESS == status, 9);
+
+ exit(0);
+}
+#else
+
+/* Instance one test entry. */
+INT nx_secure_ecc_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+ exit(TLS_TEST_NOT_AVAILABLE);
+}
+#endif
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_test_openssl_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_test_openssl_echo_client_entry.c
new file mode 100644
index 00000000..0d1429f8
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_test_openssl_echo_client_entry.c
@@ -0,0 +1,38 @@
+#include "tls_test_frame.h"
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Openssl echo client entry. */
+INT openssl_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && (NX_SECURE_TLS_TLS_1_3_ENABLED) && defined(NX_SECURE_ENABLE_PSK_CIPHERSUITES)
+
+
+INT status, exit_status;
+
+/* Added -curves prime256v1 to avoid hello retry. */
+CHAR* external_cmd[] = { "openssl_1_1_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING, "-curves", "prime256v1",
+ "-psk", "112233445566",
+ "-psk_identity", "psk_test",
+ (CHAR*)NULL};
+
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tls_test_sleep(1);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_FAILED);
+
+ return TLS_TEST_SUCCESS;
+
+#else
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif
+
+} \ No newline at end of file
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_test_openssl_echo_server_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_test_openssl_echo_server_entry.c
new file mode 100644
index 00000000..feffa502
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_1_3_psk_test_openssl_echo_server_entry.c
@@ -0,0 +1,39 @@
+#include "tls_test_frame.h"
+
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+/* Openssl echo server entry. */
+INT openssl_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_CLIENT_DISABLED) && (NX_SECURE_TLS_TLS_1_3_ENABLED) && defined(NX_SECURE_ENABLE_PSK_CIPHERSUITES)
+
+
+INT status, exit_status;
+
+/* Added -rev option to send reverse text received from clients back to the client. Added -naccept 1 to close the server after one tls session. */
+CHAR* external_cmd[] = { "openssl-1.1", "s_server", "-rev",
+ "-nocert",
+ "-psk", "112233445566",
+ "-psk_identity", "psk_test",
+ "-naccept", "1", (CHAR*)NULL};
+
+ /* Post the semaphore to notify that the reverse echo server is prepared. */
+ tls_test_semaphore_post(semaphore_echo_server_prepared);
+
+ /* Launch the openssl server. */
+ tls_test_launch_external_test_process(&exit_status, external_cmd);
+
+#if 0 /* openssl exit with 0 no matter TLS session is established or not. */
+ /* Check for the exit status of external program. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED);
+#endif
+ return TLS_TEST_SUCCESS;
+
+#else
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_ecc_negotiation_test.c b/test/regression/interoperability_test/nx_secure_test/tls_ecc_negotiation_test.c
new file mode 100644
index 00000000..1d08de65
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_ecc_negotiation_test.c
@@ -0,0 +1,73 @@
+#include "tls_test_frame.h"
+
+INT nx_secure_ecc_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr);
+INT openssl_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr);
+
+/* Global demo semaphore. */
+TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+INT main( INT argc, CHAR* argv[])
+{
+INT status, exit_status[2];
+TLS_TEST_INSTANCE *ins0;
+TLS_TEST_INSTANCE *ins1;
+
+ /* Create two test instances. */
+ status = tls_test_instance_create(&ins0, /* test instance ptr */
+ "nx_secure_ecc_echo_server", /* instance name */
+ nx_secure_ecc_echo_server_entry, /* test entry */
+ 0, /* delay(seconds) */
+ 60, /* timeout(seconds) */
+ 1024, /* shared buffer size */
+ NULL); /* reserved */
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ status = tls_test_instance_create(&ins1,
+ "openssl_echo_client",
+ openssl_echo_client_entry,
+ 0,
+ 60,
+ 1024,
+ NULL);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Create a semaphore and set the initial value as 0. */
+ status = tls_test_semaphore_create(&semaphore_echo_server_prepared, 0);
+
+ /* Create the test director. */
+ TLS_TEST_DIRECTOR *director;
+ status = tls_test_director_create(&director, NULL /* reserved */);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Register test instances to the director. */
+ status = tls_test_director_register_test_instance(director, ins0);
+ status += tls_test_director_register_test_instance(director, ins1);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Launch test. */
+ status = tls_test_director_test_start(director);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Collect exit code. */
+ tls_test_instance_show_exit_status(ins0);
+ tls_test_instance_show_exit_status(ins1);
+
+ /* Call the verify method to determine whether the test is passed. */
+ status = tls_test_instance_get_exit_status(ins0, &exit_status[0]);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+ status = tls_test_instance_get_exit_status(ins1, &exit_status[1]);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Destroy registered test instances and the director. */
+ tls_test_director_clean_all(director);
+
+ /* Destroy the semaphore. */
+ tls_test_semaphore_destroy(semaphore_echo_server_prepared);
+
+ /* Return error if get unexpected test results. */
+ if ((TLS_TEST_NOT_AVAILABLE == exit_status[0]) || (TLS_TEST_NOT_AVAILABLE == exit_status[1]))
+ return TLS_TEST_NOT_AVAILABLE;
+
+ /* Return the result of verification. */
+ return exit_status[0] | exit_status[1];
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_ecc_server_cert_test.c b/test/regression/interoperability_test/nx_secure_test/tls_ecc_server_cert_test.c
new file mode 100644
index 00000000..909d178d
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_ecc_server_cert_test.c
@@ -0,0 +1,103 @@
+#include "tls_test_frame.h"
+
+INT nx_secure_ecc_server_cert_entry(TLS_TEST_INSTANCE* instance_ptr);
+INT openssl_ecc_client_entry(TLS_TEST_INSTANCE* instance_ptr);
+extern UINT ciphersuites_server_count;
+
+/* Global demo semaphore. */
+TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+INT main( INT argc, CHAR* argv[])
+{
+INT status, exit_status[2];
+TLS_TEST_INSTANCE *ins0;
+TLS_TEST_INSTANCE *ins1;
+
+ /* Create two test instances. */
+ status = tls_test_instance_create(&ins0, /* test instance ptr */
+ "nx_secure_ecc_server_cert_entry", /* instance name */
+ nx_secure_ecc_server_cert_entry, /* test entry */
+ 0, /* delay(seconds) */
+ 30, /* timeout(seconds) */
+ 1024, /* shared buffer size */
+ NULL); /* reserved */
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ status = tls_test_instance_create(&ins1,
+ "openssl_ecc_client_entry",
+ openssl_ecc_client_entry,
+ 0,
+ 30,
+ 1024,
+ NULL);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Create a semaphore and set the initial value as 0. */
+ status = tls_test_semaphore_create(&semaphore_echo_server_prepared, 0);
+
+ /* Create the test director. */
+ TLS_TEST_DIRECTOR *director;
+ status = tls_test_director_create(&director, NULL /* reserved */);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Register test instances to the director. */
+ status = tls_test_director_register_test_instance(director, ins0);
+ status += tls_test_director_register_test_instance(director, ins1);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Launch test. */
+ status = tls_test_director_test_start(director);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Collect exit code. */
+ tls_test_instance_show_exit_status(ins0);
+ tls_test_instance_show_exit_status(ins1);
+
+ /* Call the verify method to determine whether the test is passed. */
+ status = tls_test_instance_get_exit_status(ins0, &exit_status[0]);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+ status = tls_test_instance_get_exit_status(ins1, &exit_status[1]);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Destroy registered test instances and the director. */
+ tls_test_director_clean_all(director);
+
+ /* Destroy the semaphore. */
+ tls_test_semaphore_destroy(semaphore_echo_server_prepared);
+
+ /* Return error if get unexpected test results. */
+ if ((TLS_TEST_NOT_AVAILABLE == exit_status[0]) || (TLS_TEST_NOT_AVAILABLE == exit_status[1]))
+ return TLS_TEST_NOT_AVAILABLE;
+
+ /* Return the result of verification. */
+ return exit_status[0] | exit_status[1];
+}
+
+/* Instance two test entry. */
+INT openssl_ecc_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+/* Just use TLSv1.2 */
+CHAR* external_cmd[] = { "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING,
+ "-cert", "../../ecc_certificates/ECTestServer7_256.crt",
+ "-key", "../../ecc_certificates/ECTestServer7_256.key", (CHAR*)NULL};
+INT status, exit_status;
+
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tls_test_sleep(1);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ return exit_status;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_ecc_server_ciphersuites_test.c b/test/regression/interoperability_test/nx_secure_test/tls_ecc_server_ciphersuites_test.c
new file mode 100644
index 00000000..10ff91c2
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_ecc_server_ciphersuites_test.c
@@ -0,0 +1,213 @@
+#include "tls_test_frame.h"
+
+INT nx_secure_ecc_server_ciphersuites_entry(TLS_TEST_INSTANCE* instance_ptr);
+INT openssl_ecc_client_entry(TLS_TEST_INSTANCE* instance_ptr);
+extern UINT ciphersuites_server_count;
+
+/* Global demo semaphore. */
+TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+INT main( INT argc, CHAR* argv[])
+{
+INT status, exit_status[2];
+TLS_TEST_INSTANCE *ins0;
+TLS_TEST_INSTANCE *ins1;
+
+ /* Create two test instances. */
+ status = tls_test_instance_create(&ins0, /* test instance ptr */
+ "nx_secure_ecc_server_ciphersuites_entry",/* instance name */
+ nx_secure_ecc_server_ciphersuites_entry, /* test entry */
+ 0, /* delay(seconds) */
+ 60, /* timeout(seconds) */
+ 1024, /* shared buffer size */
+ NULL); /* reserved */
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ status = tls_test_instance_create(&ins1,
+ "openssl_ecc_client_entry",
+ openssl_ecc_client_entry,
+ 0,
+ 60,
+ 1024,
+ NULL);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Create a semaphore and set the initial value as 0. */
+ status = tls_test_semaphore_create(&semaphore_echo_server_prepared, 0);
+
+ /* Create the test director. */
+ TLS_TEST_DIRECTOR *director;
+ status = tls_test_director_create(&director, NULL /* reserved */);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Register test instances to the director. */
+ status = tls_test_director_register_test_instance(director, ins0);
+ status += tls_test_director_register_test_instance(director, ins1);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Launch test. */
+ status = tls_test_director_test_start(director);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Collect exit code. */
+ tls_test_instance_show_exit_status(ins0);
+ tls_test_instance_show_exit_status(ins1);
+
+ /* Call the verify method to determine whether the test is passed. */
+ status = tls_test_instance_get_exit_status(ins0, &exit_status[0]);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+ status = tls_test_instance_get_exit_status(ins1, &exit_status[1]);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Destroy registered test instances and the director. */
+ tls_test_director_clean_all(director);
+
+ /* Destroy the semaphore. */
+ tls_test_semaphore_destroy(semaphore_echo_server_prepared);
+
+ /* Return error if get unexpected test results. */
+ if ((TLS_TEST_NOT_AVAILABLE == exit_status[0]) || (TLS_TEST_NOT_AVAILABLE == exit_status[1]))
+ return TLS_TEST_NOT_AVAILABLE;
+
+ /* Return the result of verification. */
+ return exit_status[0] | exit_status[1];
+}
+
+typedef struct
+{
+ UINT cipher_index;
+ UINT session_succ;
+} CIPHERSUITE;
+
+static CHAR *ciphers[] =
+{
+ "ALL",
+ "ECDH-ECDSA-AES128-SHA",
+ "ECDH-RSA-AES128-SHA",
+ "ECDHE-ECDSA-AES128-SHA256",
+ "ECDHE-RSA-AES128-SHA256",
+ "ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDH-RSA-AES128-SHA256:ECDH-ECDSA-AES128-SHA256",
+ "ECDHE-ECDSA-AES128-GCM-SHA256",
+ "ECDHE-RSA-AES128-GCM-SHA256",
+ "ECDH-ECDSA-AES128-GCM-SHA256",
+ "ECDH-RSA-AES128-GCM-SHA256",
+ "TLS_AES_128_GCM_SHA256",
+ "TLS_AES_256_GCM_SHA384",
+ "TLS_AES_128_CCM_SHA256",
+ "TLS_AES_128_CCM_8_SHA256",
+};
+
+static CIPHERSUITE ciphersuites_client[] =
+{
+
+ /* Select ciphersuite according to certificate. */
+ {0, NX_TRUE},
+ {0, NX_TRUE},
+ {0, NX_TRUE},
+ {0, NX_TRUE},
+
+ /* Select ciphersuite according to certificate.
+ * The order of client ciphersuites are reversed of server. */
+ {5, NX_TRUE},
+ {5, NX_TRUE},
+ {5, NX_TRUE},
+
+ /* Specified ciphersuites. */
+ /* {1, NX_TRUE}, */
+ /* {2, NX_TRUE}, */
+ {3, NX_TRUE},
+ {4, NX_TRUE},
+
+ /* The Server cert supports ECDH_ECDSA and ECDHE_ECDSA. */
+ /* {1, NX_TRUE}, */
+ /* {2, NX_FALSE},*/ /* ECDH_RSA not supported. */
+ {3, NX_TRUE},
+ {4, NX_FALSE}, /* ECDHE_RSA not supported. */
+
+ /* Let the server pickup supported ciphersuite. */
+ {0, NX_TRUE},
+ {0, NX_TRUE},
+ {0, NX_TRUE},
+ {0, NX_TRUE},
+ /*{0, NX_TRUE},*/
+ /*{0, NX_TRUE},*/
+ /*{0, NX_TRUE},*/
+ /*{0, NX_TRUE},*/
+ /*{0, NX_TRUE},*/
+ /*{0, NX_TRUE},*/
+ /*{0, NX_TRUE},*/
+ /*{0, NX_TRUE},*/
+ /*{0, NX_TRUE},*/
+ /*{0, NX_TRUE},*/
+ /*{0, NX_TRUE},*/
+ /*{0, NX_TRUE},*/
+
+#ifdef NX_SECURE_ENABLE_AEAD_CIPHER
+ /* AES128-GCM ciphersuites. */
+ {6, NX_TRUE},
+ {7, NX_TRUE},
+ /*{8, NX_TRUE},*/
+ /*{9, NX_TRUE},*/
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ /* Test TLS 1.3 ciphersuites. */
+ {10, NX_TRUE},
+ {12, NX_TRUE},
+ {13, NX_TRUE},
+
+ /* Client sends ciphersuites not supported by server. */
+ {11, NX_FALSE},
+#endif
+#endif
+};
+
+/* Instance two test entry. */
+INT openssl_ecc_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+/* Just use TLSv1.2 */
+CHAR* external_cmd[] = { "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING,
+ "-cipher", "", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ for ( ; i < sizeof(ciphersuites_client) / sizeof(CIPHERSUITE); i++)
+ {
+
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ if (ciphersuites_client[i].cipher_index == 10)
+ {
+ external_cmd[0] = "openssl_1_1_echo_client.sh";
+ external_cmd[3] = "-ciphersuites";
+ }
+#endif
+
+ /* Call an external program to connect to tls server. */
+ external_cmd[4] = ciphers[ciphersuites_client[i].cipher_index];
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ if ((exit_status && ciphersuites_client[i].session_succ) ||
+ (!exit_status && !ciphersuites_client[i].session_succ))
+ {
+
+ /* Record errors. */
+ instance_status = TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED;
+ }
+ }
+ return instance_status;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_ecc_server_curves_test.c b/test/regression/interoperability_test/nx_secure_test/tls_ecc_server_curves_test.c
new file mode 100644
index 00000000..de5a6829
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_ecc_server_curves_test.c
@@ -0,0 +1,213 @@
+#include "tls_test_frame.h"
+
+INT nx_secure_ecc_server_curves_entry(TLS_TEST_INSTANCE* instance_ptr);
+INT openssl_ecc_client_entry(TLS_TEST_INSTANCE* instance_ptr);
+extern UINT ciphersuites_server_count;
+
+/* Global demo semaphore. */
+TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+INT main( INT argc, CHAR* argv[])
+{
+INT status, exit_status[2];
+TLS_TEST_INSTANCE *ins0;
+TLS_TEST_INSTANCE *ins1;
+
+ /* Create two test instances. */
+ status = tls_test_instance_create(&ins0, /* test instance ptr */
+ "nx_secure_ecc_server_curves_entry", /* instance name */
+ nx_secure_ecc_server_curves_entry, /* test entry */
+ 0, /* delay(seconds) */
+ 60, /* timeout(seconds) */
+ 1024, /* shared buffer size */
+ NULL); /* reserved */
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ status = tls_test_instance_create(&ins1,
+ "openssl_ecc_client_entry",
+ openssl_ecc_client_entry,
+ 0,
+ 60,
+ 1024,
+ NULL);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Create a semaphore and set the initial value as 0. */
+ status = tls_test_semaphore_create(&semaphore_echo_server_prepared, 0);
+
+ /* Create the test director. */
+ TLS_TEST_DIRECTOR *director;
+ status = tls_test_director_create(&director, NULL /* reserved */);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Register test instances to the director. */
+ status = tls_test_director_register_test_instance(director, ins0);
+ status += tls_test_director_register_test_instance(director, ins1);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Launch test. */
+ status = tls_test_director_test_start(director);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Collect exit code. */
+ tls_test_instance_show_exit_status(ins0);
+ tls_test_instance_show_exit_status(ins1);
+
+ /* Call the verify method to determine whether the test is passed. */
+ status = tls_test_instance_get_exit_status(ins0, &exit_status[0]);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+ status = tls_test_instance_get_exit_status(ins1, &exit_status[1]);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Destroy registered test instances and the director. */
+ tls_test_director_clean_all(director);
+
+ /* Destroy the semaphore. */
+ tls_test_semaphore_destroy(semaphore_echo_server_prepared);
+
+ /* Return error if get unexpected test results. */
+ if ((TLS_TEST_NOT_AVAILABLE == exit_status[0]) || (TLS_TEST_NOT_AVAILABLE == exit_status[1]))
+ return TLS_TEST_NOT_AVAILABLE;
+
+ /* Return the result of verification. */
+ return exit_status[0] | exit_status[1];
+}
+
+typedef struct
+{
+ UINT curve_index;
+ UINT ca_index;
+ UINT session_succ;
+} TEST_CASE;
+
+static CHAR *curves[] =
+{
+ "prime192v1:secp224r1:prime256v1:secp384r1:secp521r1",
+ "prime192v1",
+ "secp224r1",
+ "prime256v1",
+ "secp384r1",
+ "secp521r1",
+ "prime192v1:prime256v1",
+ "secp224r1:prime256v1",
+};
+
+static UCHAR *cas[] =
+{
+ "../../ecc_certificates/ECCA2.crt",
+ "../../ecc_certificates/ECCA3.crt",
+ "../../ecc_certificates/ECCA4.crt",
+};
+
+static TEST_CASE curves_client[] =
+{
+
+ /* Select curve by certificate. */
+ {0, 0, NX_TRUE},
+ {0, 0, NX_TRUE},
+ {0, 0, NX_TRUE},
+ {0, 2, NX_TRUE},
+ {0, 1, NX_TRUE},
+
+ /* Specify curve from client. */
+ {6, 0, NX_TRUE},
+ {7, 0, NX_TRUE},
+ {3, 0, NX_TRUE},
+ {4, 2, NX_TRUE},
+ {5, 1, NX_TRUE},
+
+ /* Specify curve from server. */
+ {0, 0, NX_TRUE},
+ {0, 0, NX_TRUE},
+ {0, 0, NX_TRUE},
+ {0, 2, NX_TRUE},
+ {0, 1, NX_TRUE},
+
+ /* Configure invalid curves at server side. */
+ {0, 0, NX_FALSE},
+ {0, 0, NX_FALSE},
+ {0, 0, NX_FALSE},
+ {0, 0, NX_FALSE},
+
+#if 0
+ /* Though the P256 is not in supported list, openssl is still able to verify the issuer. */
+ /* Multiple curves used by server and CA cert. */
+ {1, 0, NX_FALSE}, /* ECCA2_der uses P256 which is not supported. */
+ {2, 0, NX_FALSE}, /* ECCA2_der uses P256 which is not supported. */
+#endif
+
+ /* Client curve not supported by server. */
+ {3, 0, NX_FALSE},
+ {3, 0, NX_FALSE},
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ /* Specify curve from client. */
+ {3, 0, NX_TRUE},
+ {4, 2, NX_TRUE},
+ {5, 1, NX_TRUE},
+
+ /* Specify curve from server. */
+ {0, 0, NX_TRUE},
+ {0, 2, NX_TRUE},
+ {0, 1, NX_TRUE},
+
+ /* Configure invalid curves at server side. */
+ {0, 0, NX_FALSE},
+ {0, 0, NX_FALSE},
+
+ /* Client curve not supported by server. */
+ {5, 1, NX_FALSE},
+ {5, 1, NX_FALSE},
+#endif
+};
+
+/* Instance two test entry. */
+INT openssl_ecc_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && defined(NX_SECURE_ENABLE_ECC_CIPHERSUITE)
+
+/* Just use TLSv1.2 */
+CHAR* external_cmd[] = { "openssl_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING,
+ "-curves", "", "-CAfile", "", (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ for ( ; i < sizeof(curves_client) / sizeof(TEST_CASE); i++)
+ {
+
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+ if (i == 21)
+ {
+ external_cmd[0] = "openssl_1_1_echo_client.sh";
+ }
+#endif
+
+ /* Call an external program to connect to tls server. */
+ external_cmd[4] = curves[curves_client[i].curve_index];
+ external_cmd[6] = cas[curves_client[i].ca_index];
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ if ((exit_status && curves_client[i].session_succ) ||
+ (!exit_status && !curves_client[i].session_succ))
+ {
+
+ /* Record errors. */
+ instance_status = TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED;
+ }
+ }
+ return instance_status;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_negotiation_test.c b/test/regression/interoperability_test/nx_secure_test/tls_negotiation_test.c
new file mode 100644
index 00000000..900bf619
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_negotiation_test.c
@@ -0,0 +1,73 @@
+#include "tls_test_frame.h"
+
+INT nx_secure_echo_server_entry(TLS_TEST_INSTANCE* instance_ptr);
+INT openssl_echo_client_entry(TLS_TEST_INSTANCE* instance_ptr);
+
+/* Global demo semaphore. */
+TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+INT main( INT argc, CHAR* argv[])
+{
+INT status, exit_status[2];
+TLS_TEST_INSTANCE *ins0;
+TLS_TEST_INSTANCE *ins1;
+
+ /* Create two test instances. */
+ status = tls_test_instance_create(&ins0, /* test instance ptr */
+ "nx_secure_echo_server", /* instance name */
+ nx_secure_echo_server_entry, /* test entry */
+ 0, /* delay(seconds) */
+ 60, /* timeout(seconds) */
+ 1024, /* shared buffer size */
+ NULL); /* reserved */
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ status = tls_test_instance_create(&ins1,
+ "openssl_echo_client",
+ openssl_echo_client_entry,
+ 0,
+ 60,
+ 1024,
+ NULL);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Create a semaphore and set the initial value as 0. */
+ status = tls_test_semaphore_create(&semaphore_echo_server_prepared, 0);
+
+ /* Create the test director. */
+ TLS_TEST_DIRECTOR *director;
+ status = tls_test_director_create(&director, NULL /* reserved */);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Register test instances to the director. */
+ status = tls_test_director_register_test_instance(director, ins0);
+ status += tls_test_director_register_test_instance(director, ins1);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, TLS_TEST_UNKNOWN_TYPE_ERROR);
+
+ /* Launch test. */
+ status = tls_test_director_test_start(director);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Collect exit code. */
+ tls_test_instance_show_exit_status(ins0);
+ tls_test_instance_show_exit_status(ins1);
+
+ /* Call the verify method to determine whether the test is passed. */
+ status = tls_test_instance_get_exit_status(ins0, &exit_status[0]);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+ status = tls_test_instance_get_exit_status(ins1, &exit_status[1]);
+ show_error_message_if_fail(TLS_TEST_SUCCESS == status);
+
+ /* Destroy registered test instances and the director. */
+ tls_test_director_clean_all(director);
+
+ /* Destroy the semaphore. */
+ tls_test_semaphore_destroy(semaphore_echo_server_prepared);
+
+ /* Return error if get unexpected test results. */
+ if ((TLS_TEST_NOT_AVAILABLE == exit_status[0]) || (TLS_TEST_NOT_AVAILABLE == exit_status[1]))
+ return TLS_TEST_NOT_AVAILABLE;
+
+ /* Return the result of verification. */
+ return exit_status[0] | exit_status[1];
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_openssl_1_1_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_openssl_1_1_echo_client_entry.c
new file mode 100644
index 00000000..3f8fef08
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_openssl_1_1_echo_client_entry.c
@@ -0,0 +1,41 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+#define VERSION_STR "-tls1_3"
+#else
+#define VERSION_STR ""
+#endif
+
+/* Instance two test entry. */
+INT openssl_echo_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#ifndef NX_SECURE_TLS_SERVER_DISABLED
+
+/* Just use TLSv1.2 */
+CHAR* external_cmd[] = { "openssl_1_1_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING, VERSION_STR, (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_FAILED);
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/nx_secure_test/tls_openssl_1_1_prime256v1_echo_client_entry.c b/test/regression/interoperability_test/nx_secure_test/tls_openssl_1_1_prime256v1_echo_client_entry.c
new file mode 100644
index 00000000..480df76b
--- /dev/null
+++ b/test/regression/interoperability_test/nx_secure_test/tls_openssl_1_1_prime256v1_echo_client_entry.c
@@ -0,0 +1,41 @@
+#include "tls_test_frame.h"
+
+/* Global demo emaphore. */
+extern TLS_TEST_SEMAPHORE* semaphore_echo_server_prepared;
+
+#if (NX_SECURE_TLS_TLS_1_3_ENABLED)
+#define VERSION_STR "-tls1_3"
+#else
+#define VERSION_STR ""
+#endif
+
+/* Instance two test entry. */
+INT openssl_echo_client_entry( TLS_TEST_INSTANCE* instance_ptr)
+{
+
+#if !defined(NX_SECURE_TLS_SERVER_DISABLED) && !defined(NX_SECURE_TLS_DISABLE_SECURE_RENEGOTIATION)
+
+/* Just use TLSv1.2 */
+CHAR* external_cmd[] = { "openssl_1_1_echo_client.sh", TLS_TEST_IP_ADDRESS_STRING, DEVICE_SERVER_PORT_STRING, "-curves", "prime256v1", VERSION_STR, (CHAR*)NULL};
+INT status, exit_status, instance_status = TLS_TEST_SUCCESS, i = 0;
+
+ print_error_message("Connection %d: waiting for semaphore.\n", i);
+ tls_test_semaphore_wait(semaphore_echo_server_prepared);
+ tls_test_sleep(1);
+ print_error_message("Connection %d: client get semaphore. Launch a external test program.\n", i);
+
+ /* Call an external program to connect to tls server. */
+ status = tls_test_launch_external_test_process(&exit_status, external_cmd);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Check for exit_status. */
+ return_value_if_fail(0 == exit_status, TLS_TEST_INSTANCE_FAILED);
+ return TLS_TEST_SUCCESS;
+
+#else /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+ return TLS_TEST_NOT_AVAILABLE;
+
+#endif /* ifndef NX_SECURE_TLS_SERVER_DISABLED */
+
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_director_clean_all.c b/test/regression/interoperability_test/test_frame/tls_test_director_clean_all.c
new file mode 100644
index 00000000..529b7d19
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_director_clean_all.c
@@ -0,0 +1,16 @@
+#include "tls_test_frame.h"
+
+/* Destroy both registered instances and director. */
+INT tls_test_director_clean_all(TLS_TEST_DIRECTOR* director_ptr)
+{
+INT status = 0;
+
+ /* Clear registered test instances. */
+ status = tls_test_director_cleanup_registered_instances(director_ptr);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ /* Destroy the test director. */
+ status = tls_test_director_destroy(director_ptr);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_director_cleanup_registered_instances.c b/test/regression/interoperability_test/test_frame/tls_test_director_cleanup_registered_instances.c
new file mode 100644
index 00000000..4b4451c1
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_director_cleanup_registered_instances.c
@@ -0,0 +1,24 @@
+#include "tls_test_frame.h"
+
+/* Cleanup registered instances. */
+INT tls_test_director_cleanup_registered_instances(TLS_TEST_DIRECTOR* director_ptr)
+{
+TLS_TEST_INSTANCE* iter;
+INT status;
+
+ /* While there is a registered instance. */
+ while (NULL != director_ptr -> tls_test_first_instance_ptr)
+ {
+ /* Store the pointer to the second instance. */
+ iter = director_ptr -> tls_test_first_instance_ptr -> tls_test_next_instance_ptr;
+
+ /* Destroy the first instance. */
+ status = tls_test_instance_destroy(director_ptr -> tls_test_first_instance_ptr);
+
+ /* Maintain the number of existed instances and the pointer to the firster registered instance. */
+ director_ptr -> tls_test_registered_test_instances--;
+ director_ptr -> tls_test_first_instance_ptr = iter;
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+ }
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_director_create.c b/test/regression/interoperability_test/test_frame/tls_test_director_create.c
new file mode 100644
index 00000000..2101aa6a
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_director_create.c
@@ -0,0 +1,27 @@
+#include "tls_test_frame.h"
+
+/* Construct tls test director. */
+INT tls_test_director_create(TLS_TEST_DIRECTOR** director_ptr_ptr, VOID* description)
+{
+TLS_TEST_DIRECTOR* director_ptr;
+
+ /* Check parameters. */
+ return_value_if_fail(NULL != director_ptr_ptr, TLS_TEST_INVALID_POINTER);
+
+ /* Atempt to allocate the space of test_director. */
+ director_ptr = (TLS_TEST_DIRECTOR*)malloc(sizeof(TLS_TEST_DIRECTOR));
+ return_value_if_fail(NULL != director_ptr, TLS_TEST_INSTANTIATION_FAILED);
+
+ /* Return director. */
+ *director_ptr_ptr = director_ptr;
+
+ /* Intialize the members of the new director instance. */
+ director_ptr -> tls_test_registered_test_instances = 0;
+ director_ptr -> tls_test_first_instance_ptr = NULL;
+ return TLS_TEST_SUCCESS;
+}
+
+/* Stub function to avoid link issue. */
+void tx_application_define(void *first_unused_memory)
+{
+} \ No newline at end of file
diff --git a/test/regression/interoperability_test/test_frame/tls_test_director_destroy.c b/test/regression/interoperability_test/test_frame/tls_test_director_destroy.c
new file mode 100644
index 00000000..9440303f
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_director_destroy.c
@@ -0,0 +1,9 @@
+#include "tls_test_frame.h"
+
+/* Destroy test director. */
+INT tls_test_director_destroy(TLS_TEST_DIRECTOR* director_ptr)
+{
+ return_value_if_fail(NULL != director_ptr, TLS_TEST_INVALID_POINTER);
+ free(director_ptr);
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_director_register_test_instance.c b/test/regression/interoperability_test/test_frame/tls_test_director_register_test_instance.c
new file mode 100644
index 00000000..cb19e2f9
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_director_register_test_instance.c
@@ -0,0 +1,51 @@
+#include "tls_test_frame.h"
+
+/* Register tlst test instance to tls test director. */
+INT tls_test_director_register_test_instance(TLS_TEST_DIRECTOR* director_ptr, TLS_TEST_INSTANCE* instance_ptr)
+{
+TLS_TEST_INSTANCE *iter, *iter2;
+INT status = TLS_TEST_SUCCESS;
+UINT id = 0;
+
+ /* Check parameters. */
+ return_value_if_fail(NULL != director_ptr, TLS_TEST_INVALID_POINTER);
+ return_value_if_fail(NULL != instance_ptr, TLS_TEST_INVALID_POINTER);
+ return_value_if_fail(director_ptr -> tls_test_registered_test_instances < TLS_TEST_MAX_TEST_INSTANCE_NUMBER, TLS_TEST_TOO_MANY_TEST_INSTANCES);
+
+ /* Check test instance status. */
+ return_value_if_fail(instance_ptr -> tls_test_instance_status & TLS_TEST_INSTANCE_STATUS_INITIALIZED, TLS_TEST_INSTANCE_UNINITIALIZED);
+ return_value_if_fail(!(instance_ptr -> tls_test_instance_status & TLS_TEST_INSTANCE_STATUS_REGISTERED), TLS_TEST_ALREADY_REGISTERED);
+
+ /* No instances has been registered. */
+ if (NULL == director_ptr -> tls_test_first_instance_ptr)
+ {
+ director_ptr -> tls_test_first_instance_ptr = instance_ptr;
+ director_ptr -> tls_test_registered_test_instances = 1;
+ instance_ptr -> tls_test_instance_identify = 0;
+ return TLS_TEST_SUCCESS;
+ }
+
+ /* Initialize instance iterator. */
+ iter = director_ptr -> tls_test_first_instance_ptr;
+ iter2 = NULL;
+
+ /* Loop to find last instance. */
+ while(1)
+ {
+ /* Ensure id to be the max identify. */
+ id = id > iter -> tls_test_instance_identify? id : iter -> tls_test_instance_identify;
+ tls_test_instance_find_next(iter, &iter2);
+ if (NULL == iter2)
+ {
+ break;
+ }
+ iter = iter2;
+ }
+
+ /* Append the new instance. */
+ status = tls_test_instance_append(iter, instance_ptr);
+ instance_ptr -> tls_test_instance_identify = id + 1;
+ instance_ptr -> tls_test_instance_status |= TLS_TEST_INSTANCE_STATUS_REGISTERED;
+ director_ptr -> tls_test_registered_test_instances++;
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_director_test_start.c b/test/regression/interoperability_test/test_frame/tls_test_director_test_start.c
new file mode 100644
index 00000000..411da1a1
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_director_test_start.c
@@ -0,0 +1,169 @@
+#include "tls_test_frame.h"
+
+static void signal_handler_wait_all( int signum)
+{
+ /* Wait for all processes in current process group. */
+ while ( -1 != wait(NULL));
+
+ /* Raise the same signal to kill itself. */
+ raise( signum);
+}
+
+static void signal_handler_kill_process_group( int signum)
+{
+ /* Install an one shot signal handler. */
+ struct sigaction sig_act;
+ sig_act.sa_handler = signal_handler_wait_all;
+ sig_act.sa_flags = SA_RESETHAND;
+ sigaction( signum, &sig_act, NULL);
+
+ /* Send received signal to every process in current process group. */
+ kill( 0, signum);
+}
+
+/* Run test programs. */
+INT tls_test_director_test_start( TLS_TEST_DIRECTOR* director_ptr)
+{
+pid_t pid;
+TLS_TEST_INSTANCE* iter, *iter_term, *iter_wait;
+INT status = TLS_TEST_SUCCESS, exit_status = 0;
+int err = 0;
+
+ /* Check parameters. */
+ return_value_if_fail( NULL != director_ptr, TLS_TEST_INVALID_POINTER);
+ return_value_if_fail( 0 != director_ptr -> tls_test_registered_test_instances, TLS_TEST_NO_REGISTERED_INSTANCE);
+
+ /* Get the first instance. */
+ iter = director_ptr -> tls_test_first_instance_ptr;
+
+ /* Loop to launch all test instances. */
+ while ( NULL != iter)
+ {
+
+ /* Launch next test instance after given seconds. */
+ if ( iter -> tls_test_delay)
+ {
+ sleep(iter -> tls_test_delay);
+ }
+
+ pid = fork();
+
+ /* Error handle. */
+ show_error_message_if_fail( -1 != pid);
+ if ( -1 == pid)
+ {
+ /* Cleanup all running test process if fail to fork a new process for the new instance. */
+ for ( iter_term = director_ptr -> tls_test_first_instance_ptr; iter_term != iter; tls_test_instance_find_next( iter_term, &iter_term))
+ {
+ /* Kill the process group of the test instance. */
+ status = kill( - iter_term -> tls_test_instance_current_pid, SIGTERM);
+ show_error_message_if_fail( -1 != status);
+ if ( -1 == status)
+ continue;
+
+ /* Get exit status of test instances. */
+ status = waitpid( iter_term -> tls_test_instance_current_pid, &exit_status, 0);
+ show_error_message_if_fail( -1 != status);
+ if ( -1 == status)
+ continue;
+
+ status = tls_test_instance_set_exit_status( iter_term, exit_status);
+ return_value_if_fail( TLS_TEST_SUCCESS == status, status);
+
+ } /* for iter_term */
+
+ return TLS_TEST_UNABLE_TO_CREATE_TEST_PROCESS;
+ } /* if -1 == pid */
+
+ /* Child process. */
+ else if (0 == pid)
+ {
+
+ /* Create a new process group. */
+ setpgid( 0, 0);
+
+ /* Install signal handler for SIGALRM and SIGTERM. */
+ struct sigaction sig_act;
+ sig_act.sa_handler = signal_handler_kill_process_group; /* Specify signal handler. */
+ sig_act.sa_flags = SA_RESETHAND; /* Set the signal handler as a one shot handler. */
+ status = sigaction( SIGALRM, &sig_act, NULL);
+ return_value_if_fail( -1 != status, TLS_TEST_SYSTEM_CALL_FAILED);
+ status = sigaction( SIGTERM, &sig_act, NULL);
+ return_value_if_fail( -1 != status, TLS_TEST_SYSTEM_CALL_FAILED);
+
+ /* Set timeer for the test process. */
+ alarm( iter -> tls_test_timeout);
+
+ /* Enter test entry. */
+ status = iter -> tls_test_entry( iter);
+
+ /* Wait until all child process terminated. */
+ tls_test_wait_all_child_process( NULL);
+
+ exit( status);
+ }
+ /* Parent process. */
+ else
+ {
+ /* Set the gid of the child process again. */
+ setpgid( pid, pid);
+
+ iter -> tls_test_instance_current_pid = pid;
+ iter -> tls_test_instance_status |= TLS_TEST_INSTANCE_STATUS_RUNNING;
+ tls_test_instance_find_next( iter, &iter);
+ }
+ } /* NULL != iter */
+
+ /* Wait for all test instances. */
+ iter_wait = director_ptr -> tls_test_first_instance_ptr;
+ while (iter_wait != NULL && TLS_TEST_SUCCESS == ( status = tls_test_uninterruptable_wait( &pid, &exit_status)))
+ {
+ iter = director_ptr -> tls_test_first_instance_ptr;
+ while ( NULL != iter)
+ {
+ if (iter -> tls_test_instance_current_pid == pid)
+ {
+ status = tls_test_instance_set_exit_status( iter, exit_status);
+ show_error_message_if_fail( TLS_TEST_SUCCESS == status);
+ if (iter -> tls_test_instance_exit_status != TLS_TEST_SUCCESS)
+ {
+ err = 1;
+ }
+
+ break; /* NULL != iter */
+ } /* if iter -> tls_test_instance_current_pid == pid */
+
+ tls_test_instance_find_next( iter, &iter);
+ } /* NULL != iter */
+
+ if (err == 1)
+ {
+ for (iter_term = director_ptr -> tls_test_first_instance_ptr; iter_term != NULL;)
+ {
+ if (iter != iter_term)
+ {
+ /* Kill the process group of the test instance. */
+ status = kill(-iter_term -> tls_test_instance_current_pid, SIGTERM);
+ show_error_message_if_fail(-1 != status);
+ if (-1 != status)
+ {
+
+ /* Get exit status of test instances. */
+ status = waitpid(iter_term -> tls_test_instance_current_pid, &exit_status, 0);
+ show_error_message_if_fail(-1 != status);
+ if (-1 != status)
+ {
+ status = tls_test_instance_set_exit_status(iter_term, exit_status);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+ }
+ }
+ }
+ tls_test_instance_find_next( iter_term, &iter_term);
+ }
+ break;
+ }
+ tls_test_instance_find_next(iter_wait, &iter_wait);
+ } /* while exited_test_intances < director_ptr -> tls_tset_registered_test_instances */
+
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_frame.h b/test/regression/interoperability_test/test_frame/tls_test_frame.h
new file mode 100644
index 00000000..c4626e8f
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_frame.h
@@ -0,0 +1,227 @@
+#ifndef __TLS_TEST_FRAME__
+#define __TLS_TEST_FRAME__
+
+/* System headers. */
+#include <fcntl.h>
+#include <semaphore.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <sys/mman.h>
+#include <sys/wait.h>
+#include <sys/types.h>
+#include <unistd.h>
+#include <errno.h>
+
+/* The compile definition of TEST_FOR_FRAME means that the current test program is only for the interoperability itself. */
+#ifndef TEST_FOR_FRAME
+
+/* Product headers. */
+#include "tx_api.h"
+#include "nx_api.h"
+#include "nx_crypto.h"
+#include "nx_secure_tls_api.h"
+#include "nx_secure_dtls_api.h"
+#include "nx_secure_x509.h"
+
+#else /* ! TEST_FOR_FRAME */
+
+typedef int INT;
+typedef unsigned int UINT;
+typedef void VOID;
+typedef long LONG;
+typedef unsigned long ULONG;
+typedef char CHAR;
+typedef unsigned char UCHAR;
+
+#endif /* TEST_FOR_FRAME */
+
+/* Type of test instance structure. */
+typedef struct _TLS_TEST_INSTANCE TLS_TEST_INSTANCE;
+
+/* Test entry function. */
+typedef INT ( *InstanceTestEntryFunc)( TLS_TEST_INSTANCE* instance_ptr);
+
+/* Test instance structure. */
+struct _TLS_TEST_INSTANCE
+{
+
+ /* Members related to shared memory. */
+ UINT tls_test_shared_buffer_size; /* The size of shared buffer. */
+ UINT tls_test_shared_buffer_offset; /* The location of the variable of current shared buffer offset. */
+ VOID* tls_test_shared_buffer; /* The location of user's shared buffer. */
+
+ /* Other attributes. */
+ CHAR* tls_test_instance_name; /* Instance name. */
+ UINT tls_test_timeout; /* Timeout before reciving SIGRECV. */
+ UINT tls_test_delay; /* Delay after last test process started. */
+ UINT tls_test_instance_identify; /* The location in director's registry table. */
+ UINT tls_test_instance_status; /* The indication of test instance status. */
+ InstanceTestEntryFunc tls_test_entry; /* The test entry of this test instance. */
+ pid_t tls_test_instance_current_pid; /* The process id of test process. */
+ TLS_TEST_INSTANCE* tls_test_next_instance_ptr; /* The pointer to the next test instance. */
+ INT tls_test_instance_exit_status; /* The return code of the test process.(A negative value -N indicate that the test process wat terminated by signal N). */
+};
+
+/* Test director structure. */
+typedef struct _TLS_TEST_DIRECTOR
+{
+ UINT tls_test_registered_test_instances;
+ TLS_TEST_INSTANCE* tls_test_first_instance_ptr;
+} TLS_TEST_DIRECTOR;
+
+typedef sem_t TLS_TEST_SEMAPHORE;
+
+typedef struct _TLS_TEST_EXTERNAL_TEST_PROCESS
+{
+ INT tls_test_external_test_process_id;
+} TLS_TEST_EXTERNAL_TEST_PROCESS;
+
+/* Test instance methods. */
+INT tls_test_instance_append( TLS_TEST_INSTANCE* instance_ptr, TLS_TEST_INSTANCE* next_instance_ptr);
+INT tls_test_instance_create( TLS_TEST_INSTANCE** instance_ptr_ptr, CHAR* instance_name, InstanceTestEntryFunc test_entry, UINT delay, UINT timeout, UINT shared_buffer_size, VOID* reserved);
+INT tls_test_instance_destroy( TLS_TEST_INSTANCE* instance_ptr);
+INT tls_test_instance_find_next( TLS_TEST_INSTANCE* instance_ptr, TLS_TEST_INSTANCE** next_instance_ptr_ptr);
+INT tls_test_instance_get_exit_status( TLS_TEST_INSTANCE* instance_ptr, INT* exit_status_ptr);
+INT tls_test_instance_get_name( TLS_TEST_INSTANCE* instance_ptr, CHAR** name_ptr);
+INT tls_test_instance_show_exit_status(TLS_TEST_INSTANCE* instance_ptr);
+INT tls_test_instance_set_exit_status( TLS_TEST_INSTANCE* instance_ptr, INT exit_status);
+INT tls_test_instance_set_exit_status( TLS_TEST_INSTANCE* instance_ptr, INT exit_status);
+
+/* Test director methods. */
+INT tls_test_director_create( TLS_TEST_DIRECTOR** director_ptr, VOID* description);
+INT tls_test_director_register_test_instance( TLS_TEST_DIRECTOR* director_ptr, TLS_TEST_INSTANCE* instance_ptr);
+INT tls_test_director_cleanup_registered_instances( TLS_TEST_DIRECTOR* director_ptr);
+INT tls_test_director_destroy( TLS_TEST_DIRECTOR* director_ptr);
+INT tls_test_director_clean_all( TLS_TEST_DIRECTOR* director_ptr);
+INT tls_test_director_test_start( TLS_TEST_DIRECTOR* director_ptr);
+
+/* Shared buffer manipulation. */
+INT tls_test_instance_get_shared_buffer( TLS_TEST_INSTANCE* instance_ptr, VOID** shared_buffer_ptr);
+INT tls_test_instance_get_shared_buffer_offset( TLS_TEST_INSTANCE* instance_ptr, UINT* offset);
+INT tls_test_instance_set_shared_buffer_offset( TLS_TEST_INSTANCE* instance_ptr, UINT offset);
+INT tls_test_instance_append_data_to_shared_buffer( TLS_TEST_INSTANCE* instance_ptr, VOID* data, UINT* length);
+
+/* Semaphore methods. */
+INT tls_test_semaphore_create( TLS_TEST_SEMAPHORE** semaphore_ptr_ptr, UINT initial_value);
+INT tls_test_semaphore_post( TLS_TEST_SEMAPHORE* semaphore_ptr);
+INT tls_test_semaphore_wait( TLS_TEST_SEMAPHORE* semaphore_ptr);
+INT tls_test_semaphore_destroy( TLS_TEST_SEMAPHORE* semaphore_ptr);
+
+/* External programs calling. */
+INT tls_test_get_external_test_process_output( INT* exit_status_ptr, CHAR* argv[], VOID* output_buffer, ULONG* length_ptr);
+INT tls_test_launch_external_test_process( INT* exit_status_ptr, CHAR* argv[]);
+INT tls_test_launch_external_test_process_in_background( TLS_TEST_EXTERNAL_TEST_PROCESS* test_process_ptr, CHAR* argv[]);
+INT tls_test_kill_external_test_process( TLS_TEST_EXTERNAL_TEST_PROCESS* test_process_ptr);
+INT tls_test_wait_all_child_process( void* reserved_ptr);
+INT tls_test_wait_external_test_process( TLS_TEST_EXTERNAL_TEST_PROCESS* test_process_ptr, INT* exit_status_ptr);
+INT tls_test_instance_append_external_program_output_to_shared_buffer( TLS_TEST_INSTANCE* instance_ptr, INT* exit_status_ptr, CHAR* argv[]);
+INT tls_test_uninterruptable_wait( pid_t* pid_ptr, INT* exit_status_ptr);
+#define tls_test_sleep( secs) sleep( secs)
+
+/* Return code macros. */
+#define TLS_TEST_SUCCESS 0
+#define TLS_TEST_UNABLE_TO_CREATE_SHARED_MEMORY 1
+#define TLS_TEST_INVALID_POINTER 2
+#define TLS_TEST_TOO_MANY_TEST_INSTANCES 3
+#define TLS_TEST_UNKNOWN_TYPE_ERROR 4
+#define TLS_TEST_ALREADY_REGISTERED 5
+#define TLS_TEST_NO_REGISTERED_INSTANCE 6
+#define TLS_TEST_INSTANCE_UNINITIALIZED 7
+#define TLS_TEST_UNABLE_TO_CREATE_TEST_PROCESS 8
+#define TLS_TEST_ILLEGAL_SHARED_BUFFER_ACCESS 9
+#define TLS_TEST_UNABLE_TO_REDIRECT_EXTERNAL_PROGRAM_OUTPUT 10
+#define TLS_TEST_SYSTEM_CALL_FAILED 11
+#define TLS_TEST_INSTANCE_EXTERNAL_PROGRAM_FAILED 12
+#define TLS_TEST_INSTANTIATION_FAILED 13
+#define TLS_TEST_ENTRY_FUNCTION_FAILED 14
+#define TLS_TEST_INSTANCE_UNEXITED 15
+#define TLS_TEST_INSTANCE_FAILED 16
+#define TLS_TEST_INSTANCE_NO_TIME_LEFT 17
+#define TLS_TEST_NOT_AVAILABLE 233
+
+/* Test instance status */
+#define TLS_TEST_INSTANCE_STATUS_INITIALIZED 0x1
+#define TLS_TEST_INSTANCE_STATUS_REGISTERED 0x10
+#define TLS_TEST_INSTANCE_STATUS_RUNNING 0x100
+#define TLS_TEST_INSTANCE_STATUS_EXITED 0x1000
+#define TLS_TEST_INSTANCE_STATUS_SIGNALED 0x10000
+
+/* Default timeout for every test process. */
+#define TLS_TEST_PROCESS_DEFAULT_TIMEOUT (60*15)
+
+/* Maximum of instances registered in a director instance. */
+#define TLS_TEST_MAX_TEST_INSTANCE_NUMBER 10
+
+/* The buffer size for pipe data. */
+#define TLS_TEST_PIPE_BUFFER_SIZE 1024
+
+/* The maximum of external program parameters. */
+#define TLS_TEST_MAXIMUM_EXTERNAL_PROGRAM_PARAMETERS 1024
+
+/* Take use of two levels of macros to stringize the result of expansison of a macro argument. */
+#define xstr(s) str(s)
+#define str(s) #s
+
+/* Specify the ipv4 address of the test device. */
+#if defined(TLS_TEST_IP_BYTE_0) || defined(TLS_TEST_IP_BYTE_1) || defined(TLS_TEST_IP_BYTE_2) || defined(TLS_TEST_IP_BYTE_3)
+#define TLS_TEST_IP_ADDRESS_STRING xstr(TLS_TEST_IP_BYTE_0)"."xstr(TLS_TEST_IP_BYTE_1)"."xstr(TLS_TEST_IP_BYTE_2)"."xstr(TLS_TEST_IP_BYTE_3)
+#define TLS_TEST_IP_ADDRESS_NUMBER IP_ADDRESS( TLS_TEST_IP_BYTE_0, TLS_TEST_IP_BYTE_1, TLS_TEST_IP_BYTE_2, TLS_TEST_IP_BYTE_3)
+#endif /* defined() && defined() && defined() && defined() */
+
+/* TLS_TEST_IP_ADDRESS_STRING */
+#ifndef TLS_TEST_IP_ADDRESS_STRING
+#define TLS_TEST_IP_ADDRESS_STRING "10.0.0.1"
+#endif /* ifndef TLS_TEST_IP_ADDRESS_STRING */
+
+#ifndef TLS_TEST_IP_ADDRESS_NUMBER
+#define TLS_TEST_IP_ADDRESS_NUMBER IP_ADDRESS( 10, 0, 0, 1)
+#endif /* ifndef TLS_TEST_IP_ADDRESS_NUMBER */
+
+/* Specify the ipv4 address of the remote device. */
+#if defined(REMOTE_IP_BYTE_0) || defined(REMOTE_IP_BYTE_1) || defined(REMOTE_IP_BYTE_2) || defined(REMOTE_IP_BYTE_3)
+#define REMOTE_IP_ADDRESS_STRING xstr(REMOTE_IP_BYTE_0)"."xstr(REMOTE_IP_BYTE_1)"."xstr(REMOTE_IP_BYTE_2)"."xstr(REMOTE_IP_BYTE_3)
+#define REMOTE_IP_ADDRESS_NUMBER IP_ADDRESS( REMOTE_IP_BYTE_0, REMOTE_IP_BYTE_1, REMOTE_IP_BYTE_2, REMOTE_IP_BYTE_3)
+#endif /* defined() && defined() && defined() && defined() */
+
+#ifndef REMOTE_IP_ADDRESS_STRING
+#define REMOTE_IP_ADDRESS_STRING "10.0.0.2"
+#endif /* ifndef REMOTE_IP_ADDRESS_STRING */
+
+#ifndef REMOTE_IP_ADDRESS_NUMBER
+#define REMOTE_IP_ADDRESS_NUMBER IP_ADDRESS( 10, 0, 0, 2)
+#endif /* ifndef REMOTE_IP_ADDRESS_NUMBER */
+
+
+/* For parallel processing, all ports are using in arrangement. */
+#ifdef INTEROPERABILITY_TEST_ENABLE_PARALLEL_PROCESSING
+
+#ifndef DEVICE_SERVER_PORT
+#define DEVICE_SERVER_PORT 4433
+#endif /* DEVICE_SERVER_PORT */
+
+/* the string for DEVICE_SERVER_PORT */
+#define DEVICE_SERVER_PORT_STRING xstr(DEVICE_SERVER_PORT)
+
+#ifndef LOCAL_CLIENT_PORT
+#define LOCAL_CLIENT_PORT 30024
+#endif /* LOCAL_CLIENT_PORT */
+
+/* the string for LOCAL_CLIENT_PORT */
+#define LOCAL_CLIENT_PORT_STRING xstr(LOCAL_CLIENT_PORT)
+
+#endif /* INTEROPERABILITY_TEST_ENABLE_PARALLEL_PROCESSING */
+
+
+/* Output error message to stderr. */
+#define print_error_message( format, ...) printf( format, ##__VA_ARGS__)
+
+#define return_value_if_fail( p, val) if(!(p)){print_error_message("Error! %s:%d, "#p" failed.\n", __func__, __LINE__);return(val);}
+
+#define exit_if_fail( p, val) if(!(p)){print_error_message("Error! %s:%d, "#p" failed.\n", __func__, __LINE__);exit(val);}
+
+#define show_error_message_if_fail( p) if(!(p)){print_error_message("Error! %s:%d, "#p" failed.\n", __func__, __LINE__);}
+
+#define add_error_counter_if_fail( p, counter) if(!(p)){print_error_message("Error! %s:%d, "#p" failed.\n", __func__, __LINE__);counter++;}
+
+#endif /* __TLS_TEST_FRAME__ */
diff --git a/test/regression/interoperability_test/test_frame/tls_test_get_external_test_process_output.c b/test/regression/interoperability_test/test_frame/tls_test_get_external_test_process_output.c
new file mode 100644
index 00000000..92ca5cfb
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_get_external_test_process_output.c
@@ -0,0 +1,64 @@
+#include "tls_test_frame.h"
+
+/* Launch an external test process and redirect the output to a given buffer. */
+INT tls_test_get_external_test_process_output( INT* exit_status_ptr, CHAR* argv[], VOID* output_buffer, ULONG* length_ptr)
+{
+ /* Check pointer arguments. */
+ return_value_if_fail( NULL != exit_status_ptr, TLS_TEST_INVALID_POINTER);
+ return_value_if_fail( NULL != output_buffer, TLS_TEST_INVALID_POINTER);
+ return_value_if_fail( NULL != length_ptr, TLS_TEST_INVALID_POINTER);
+
+ ULONG length_limitation = *length_ptr;
+ INT status;
+
+ /* Create a pipe to get the output of external test process. */
+ int pipe_fd[2];
+ status = pipe( pipe_fd);
+ return_value_if_fail( -1 != status, TLS_TEST_SYSTEM_CALL_FAILED);
+
+ /* Fork a child process to execute external command. */
+ pid_t pid = fork();
+ return_value_if_fail( -1 != pid, TLS_TEST_SYSTEM_CALL_FAILED);
+
+ if ( 0 == pid)
+ {
+ /* Child process. */
+
+ /* Closed unused read end. */
+ close( pipe_fd[0]);
+
+ /* Redirect stdout and stderr to write end. */
+ status = dup2( pipe_fd[1], 1);
+ exit_if_fail( -1 != status, TLS_TEST_SYSTEM_CALL_FAILED);
+
+ /* Call the system call of exec to execute test programs under $PATH. */
+ status = execvp( argv[0], argv);
+ exit_if_fail( -1 != status, TLS_TEST_SYSTEM_CALL_FAILED);
+ exit( status);
+ }
+ else
+ {
+ /* Parent process. */
+
+ /* Closed unused write end. */
+ close( pipe_fd[1]);
+
+ UINT len = 0;
+
+ /* Read data from pipe. */
+ len = read( pipe_fd[0], output_buffer, length_limitation);
+ return_value_if_fail( -1 != len, TLS_TEST_SYSTEM_CALL_FAILED);
+
+ /* Return bytes actually read. */
+ *length_ptr = len;
+
+ /* Close the pipe. */
+ close( pipe_fd[0]);
+
+ /* Wait for external test process. */
+ status = waitpid( pid, exit_status_ptr, 0);
+ return_value_if_fail( -1 != status, TLS_TEST_SYSTEM_CALL_FAILED);
+
+ return TLS_TEST_SUCCESS;
+ }
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_instance_append.c b/test/regression/interoperability_test/test_frame/tls_test_instance_append.c
new file mode 100644
index 00000000..ca57ed50
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_instance_append.c
@@ -0,0 +1,16 @@
+#include "tls_test_frame.h"
+
+/* Appended next_instance_ptr to instance_ptr. */
+INT tls_test_instance_append(TLS_TEST_INSTANCE* instance_ptr, TLS_TEST_INSTANCE* next_instance_ptr)
+{
+ return_value_if_fail(NULL != instance_ptr, TLS_TEST_INVALID_POINTER);
+ return_value_if_fail(NULL != next_instance_ptr, TLS_TEST_INVALID_POINTER);
+ return_value_if_fail(instance_ptr != next_instance_ptr, TLS_TEST_INVALID_POINTER);
+
+ /* Store original next instance. */
+ next_instance_ptr -> tls_test_next_instance_ptr = instance_ptr -> tls_test_next_instance_ptr;
+
+ /* Insert next_instance_ptr. */
+ instance_ptr -> tls_test_next_instance_ptr = next_instance_ptr;
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_instance_attributes_access.c b/test/regression/interoperability_test/test_frame/tls_test_instance_attributes_access.c
new file mode 100644
index 00000000..191fc5dd
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_instance_attributes_access.c
@@ -0,0 +1,45 @@
+#include "tls_test_frame.h"
+
+/* Get the name of the instance. */
+INT tls_test_instance_get_name( TLS_TEST_INSTANCE* instance_ptr, CHAR** name_ptr)
+{
+ *name_ptr = instance_ptr -> tls_test_instance_name;
+ return_value_if_fail(NULL != *name_ptr, TLS_TEST_UNKNOWN_TYPE_ERROR);
+ return TLS_TEST_SUCCESS;
+}
+
+/* Get the exit code of the instance. */
+INT tls_test_instance_get_exit_status( TLS_TEST_INSTANCE* instance_ptr, INT* exit_status_ptr)
+{
+ *exit_status_ptr = instance_ptr -> tls_test_instance_exit_status;
+ return TLS_TEST_SUCCESS;
+}
+
+/* Print the comments of the exit status of test instances. */
+INT tls_test_instance_show_exit_status(TLS_TEST_INSTANCE* instance_ptr)
+{
+INT status, exit_status;
+CHAR *name;
+
+ /* Check instance pointer. */
+ return_value_if_fail(NULL != instance_ptr, TLS_TEST_INVALID_POINTER);
+
+ /* Ensure that the test instance is exited or signaled. */
+ return_value_if_fail(instance_ptr -> tls_test_instance_status & (TLS_TEST_INSTANCE_STATUS_EXITED | TLS_TEST_INSTANCE_STATUS_SIGNALED), TLS_TEST_INSTANCE_UNEXITED);
+
+ status = tls_test_instance_get_exit_status(instance_ptr, &exit_status);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ status = tls_test_instance_get_name(instance_ptr, &name);
+ return_value_if_fail(TLS_TEST_SUCCESS == status, status);
+
+ if (0 <= exit_status)
+ {
+ print_error_message("Instance %s exited with return code %d.\n", name, exit_status);
+ }
+ else if (0 > exit_status)
+ {
+ print_error_message("Instance %s is killed by signal %d.\n", name, -exit_status);
+ }
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_instance_create.c b/test/regression/interoperability_test/test_frame/tls_test_instance_create.c
new file mode 100644
index 00000000..c04b70b3
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_instance_create.c
@@ -0,0 +1,50 @@
+#include "tls_test_frame.h"
+
+/* Construct a tls test instance. */
+INT tls_test_instance_create( TLS_TEST_INSTANCE** instance_ptr_ptr, CHAR* instance_name, InstanceTestEntryFunc test_entry, UINT delay, UINT timeout, UINT shared_buffer_size, VOID* reserved)
+{
+ /* Check parameters. */
+ return_value_if_fail( NULL != instance_ptr_ptr, TLS_TEST_INVALID_POINTER);
+ return_value_if_fail( NULL != instance_name, TLS_TEST_INVALID_POINTER);
+ return_value_if_fail( NULL != test_entry, TLS_TEST_INVALID_POINTER);
+
+ /* Allocate shared memory of this test instance and its shared buffer. */
+ TLS_TEST_INSTANCE* instance_ptr;
+ instance_ptr = mmap( NULL, sizeof(TLS_TEST_INSTANCE) + shared_buffer_size, PROT_READ | PROT_WRITE, MAP_ANONYMOUS | MAP_SHARED, 0, 0);
+ return_value_if_fail( NULL != instance_ptr, TLS_TEST_UNABLE_TO_CREATE_SHARED_MEMORY);
+
+ /* Return instance ptr. */
+ *instance_ptr_ptr = instance_ptr;
+
+ /* Initialize members related to shared buffer. */
+ instance_ptr -> tls_test_shared_buffer_size = shared_buffer_size;
+ instance_ptr -> tls_test_shared_buffer_offset = 0;
+ if ( shared_buffer_size)
+ {
+ instance_ptr -> tls_test_shared_buffer = (VOID*)( (CHAR*)instance_ptr + sizeof(TLS_TEST_INSTANCE));
+ }
+ else
+ {
+ instance_ptr -> tls_test_shared_buffer = NULL;
+ }
+
+ /* Initialize other members. */
+ instance_ptr -> tls_test_instance_name = instance_name;
+ instance_ptr -> tls_test_entry = test_entry;
+ instance_ptr -> tls_test_delay = delay;
+ if ( !timeout)
+ {
+ /* Assign timeout as default value, if timeout is 0. */
+ instance_ptr -> tls_test_timeout = TLS_TEST_PROCESS_DEFAULT_TIMEOUT;
+ }
+ else
+ {
+ instance_ptr -> tls_test_timeout = timeout;
+ }
+
+ instance_ptr -> tls_test_instance_identify = 0;
+ instance_ptr -> tls_test_instance_status = TLS_TEST_INSTANCE_STATUS_INITIALIZED;
+ instance_ptr -> tls_test_next_instance_ptr = NULL;
+
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_instance_destroy.c b/test/regression/interoperability_test/test_frame/tls_test_instance_destroy.c
new file mode 100644
index 00000000..8a72ac47
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_instance_destroy.c
@@ -0,0 +1,12 @@
+#include "tls_test_frame.h"
+
+/* Destroy test instance. */
+INT tls_test_instance_destroy( TLS_TEST_INSTANCE* instance_ptr)
+{
+ return_value_if_fail( NULL != instance_ptr, TLS_TEST_INVALID_POINTER);
+
+ /* Release the shared memory occupied by the test intance. */
+ INT status = munmap( instance_ptr, instance_ptr -> tls_test_shared_buffer_size + sizeof(TLS_TEST_INSTANCE));
+ return_value_if_fail( TLS_TEST_SUCCESS == status, TLS_TEST_SYSTEM_CALL_FAILED);
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_instance_find_next.c b/test/regression/interoperability_test/test_frame/tls_test_instance_find_next.c
new file mode 100644
index 00000000..f137f630
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_instance_find_next.c
@@ -0,0 +1,11 @@
+#include "tls_test_frame.h"
+
+/* Find next instance. */
+INT tls_test_instance_find_next( TLS_TEST_INSTANCE* instance_ptr, TLS_TEST_INSTANCE** next_instance_ptr_ptr)
+{
+ return_value_if_fail( NULL != instance_ptr, TLS_TEST_INVALID_POINTER);
+ return_value_if_fail( NULL != next_instance_ptr_ptr, TLS_TEST_INVALID_POINTER);
+
+ *next_instance_ptr_ptr = instance_ptr -> tls_test_next_instance_ptr;
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_instance_set_exit_status.c b/test/regression/interoperability_test/test_frame/tls_test_instance_set_exit_status.c
new file mode 100644
index 00000000..d897fed0
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_instance_set_exit_status.c
@@ -0,0 +1,33 @@
+#include "tls_test_frame.h"
+
+/* Set the exit status of the test instance. */
+/* The argument of exit_status must be set by system call of wait or waitpid. */
+INT tls_test_instance_set_exit_status( TLS_TEST_INSTANCE* instance_ptr, INT exit_status)
+{
+
+ /* Check for pointers. */
+ return_value_if_fail( NULL != instance_ptr, TLS_TEST_INVALID_POINTER);
+
+ /* Clear running flag. */
+ instance_ptr -> tls_test_instance_status &= ~TLS_TEST_INSTANCE_STATUS_RUNNING;
+ instance_ptr -> tls_test_instance_exit_status = 0;
+
+ /* Set the exit_status member of the test instance. */
+ if ( WIFEXITED( exit_status))
+ {
+ instance_ptr -> tls_test_instance_status |= TLS_TEST_INSTANCE_STATUS_EXITED;
+ instance_ptr -> tls_test_instance_exit_status = WEXITSTATUS( exit_status);
+ }
+ else if ( WIFSIGNALED( exit_status))
+ {
+ instance_ptr -> tls_test_instance_status |= TLS_TEST_INSTANCE_STATUS_SIGNALED;
+ instance_ptr -> tls_test_instance_exit_status = -WTERMSIG( exit_status);
+ }
+ else
+ {
+ /* unresolvable exit status. */
+ return TLS_TEST_UNKNOWN_TYPE_ERROR;
+ }
+
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_instance_shared_buffer_manipulate.c b/test/regression/interoperability_test/test_frame/tls_test_instance_shared_buffer_manipulate.c
new file mode 100644
index 00000000..3588ee91
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_instance_shared_buffer_manipulate.c
@@ -0,0 +1,80 @@
+#include "tls_test_frame.h"
+
+/* Get offset of the shared buffer. */
+INT tls_test_instance_get_shared_buffer_offset( TLS_TEST_INSTANCE* instance_ptr, UINT* offset)
+{
+ /* Validate pointers. */
+ return_value_if_fail( NULL != instance_ptr, TLS_TEST_INVALID_POINTER);
+ return_value_if_fail( NULL != offset, TLS_TEST_INVALID_POINTER);
+
+ /* Return shared buffer offset. */
+ *offset = instance_ptr -> tls_test_shared_buffer_offset;
+ return TLS_TEST_SUCCESS;
+}
+
+/* Set offset of the shared buffer preparing for appending data. */
+INT tls_test_instance_set_shared_buffer_offset( TLS_TEST_INSTANCE* instance_ptr, UINT offset)
+{
+ /* Validate pointers. */
+ return_value_if_fail( NULL != instance_ptr, TLS_TEST_INVALID_POINTER);
+
+ /* Avoid offset exceeding shared_buffer_size. */
+ return_value_if_fail( offset <= instance_ptr -> tls_test_shared_buffer_size, TLS_TEST_ILLEGAL_SHARED_BUFFER_ACCESS);
+
+ /* Set shared buffer offset. */
+ instance_ptr -> tls_test_shared_buffer_offset = offset;
+ return TLS_TEST_SUCCESS;
+}
+
+/* Append data to the shared buffer after offset. */
+INT tls_test_instance_append_data_to_shared_buffer( TLS_TEST_INSTANCE* instance_ptr, VOID* data, UINT* length)
+{
+ /* Validate pointers. */
+ return_value_if_fail( NULL != instance_ptr, TLS_TEST_INVALID_POINTER);
+ return_value_if_fail( NULL != instance_ptr -> tls_test_shared_buffer, TLS_TEST_INVALID_POINTER);
+ return_value_if_fail( NULL != data, TLS_TEST_INVALID_POINTER);
+ return_value_if_fail( NULL != length, TLS_TEST_INVALID_POINTER);
+
+ INT status;
+ UINT shared_buffer_offset;
+ status = tls_test_instance_get_shared_buffer_offset( instance_ptr, &shared_buffer_offset);
+ return_value_if_fail( TLS_TEST_SUCCESS == status, status);
+
+ /* Write data as long as possible. */
+ if ( shared_buffer_offset + *length > instance_ptr -> tls_test_shared_buffer_size)
+ {
+
+ /* Return actual copy size. */
+ *length = instance_ptr -> tls_test_shared_buffer_size - shared_buffer_offset;
+
+ /* Set return code. */
+ status = TLS_TEST_ILLEGAL_SHARED_BUFFER_ACCESS;
+ }
+ else
+ {
+
+ /* Set return code. */
+ status = TLS_TEST_SUCCESS;
+ }
+
+ /* Append all data. */
+ memcpy( (CHAR*)instance_ptr -> tls_test_shared_buffer + shared_buffer_offset, data, *length);
+
+ /* Update shared buffer offset. */
+ tls_test_instance_set_shared_buffer_offset( instance_ptr, shared_buffer_offset + *length);
+
+ return status;
+}
+
+/* Get shared buffer. */
+INT tls_test_instance_get_shared_buffer( TLS_TEST_INSTANCE* instance_ptr, VOID** shared_buffer_ptr)
+{
+
+ /* Validate pointers. */
+ return_value_if_fail( NULL != instance_ptr, TLS_TEST_INVALID_POINTER);
+
+ /* Return shared buffer. */
+ *shared_buffer_ptr = instance_ptr -> tls_test_shared_buffer;
+ return_value_if_fail( NULL != *shared_buffer_ptr, TLS_TEST_ILLEGAL_SHARED_BUFFER_ACCESS);
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_kill_external_test_process.c b/test/regression/interoperability_test/test_frame/tls_test_kill_external_test_process.c
new file mode 100644
index 00000000..6fabc9cf
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_kill_external_test_process.c
@@ -0,0 +1,14 @@
+#include "tls_test_frame.h"
+
+/* Call external program without output redirecting. */
+INT tls_test_kill_external_test_process( TLS_TEST_EXTERNAL_TEST_PROCESS* test_process_ptr)
+{
+ /* Validate pointers. */
+ return_value_if_fail( NULL != test_process_ptr, TLS_TEST_INVALID_POINTER);
+
+ INT status;
+ status = kill( test_process_ptr -> tls_test_external_test_process_id, SIGTERM);
+ return_value_if_fail( -1 != status, TLS_TEST_SYSTEM_CALL_FAILED);
+
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_launch_external_test_process.c b/test/regression/interoperability_test/test_frame/tls_test_launch_external_test_process.c
new file mode 100644
index 00000000..6b794154
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_launch_external_test_process.c
@@ -0,0 +1,42 @@
+#include "tls_test_frame.h"
+
+/* Call external program without output redirecting. */
+INT tls_test_launch_external_test_process( INT* exit_status_ptr, CHAR* argv[])
+{
+ /* Validate pointers. */
+ return_value_if_fail( NULL != exit_status_ptr, TLS_TEST_INVALID_POINTER);
+
+ INT status, process_status;
+ pid_t pid;
+
+ pid = fork();
+ return_value_if_fail( -1 != pid, TLS_TEST_SYSTEM_CALL_FAILED);
+
+ if ( 0 == pid)
+ {
+ /* Child process. */
+
+ /* Enable the timer in child process which will not be inherited by forked child process. */
+ INT exec_status = execvp( argv[0], argv);
+ return_value_if_fail( -1 != exec_status, TLS_TEST_SYSTEM_CALL_FAILED);
+ }
+ else
+ {
+ /* Parent process. */
+
+ status = waitpid( pid, &process_status, 0);
+ return_value_if_fail( -1 != status, TLS_TEST_SYSTEM_CALL_FAILED);
+
+ *exit_status_ptr = 0;
+ if ( WIFEXITED( process_status))
+ {
+ *exit_status_ptr = WEXITSTATUS( process_status);
+ }
+ else if ( WIFSIGNALED( process_status))
+ {
+ *exit_status_ptr = -WTERMSIG( process_status);
+ }
+ return TLS_TEST_SUCCESS;
+ }
+}
+
diff --git a/test/regression/interoperability_test/test_frame/tls_test_launch_external_test_process_in_background.c b/test/regression/interoperability_test/test_frame/tls_test_launch_external_test_process_in_background.c
new file mode 100644
index 00000000..bc9d363a
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_launch_external_test_process_in_background.c
@@ -0,0 +1,29 @@
+#include "tls_test_frame.h"
+
+/* Call external program without output redirecting. */
+INT tls_test_launch_external_test_process_in_background( TLS_TEST_EXTERNAL_TEST_PROCESS* test_process_ptr, CHAR* argv[])
+{
+ /* Validate pointers. */
+ return_value_if_fail( NULL != test_process_ptr, TLS_TEST_INVALID_POINTER);
+
+ pid_t pid;
+
+ pid = fork();
+ return_value_if_fail( -1 != pid, TLS_TEST_SYSTEM_CALL_FAILED);
+
+ if ( 0 == pid)
+ {
+ /* Child process. */
+
+ INT exec_status = execvp( argv[0], argv);
+ exit_if_fail( -1 != exec_status, TLS_TEST_SYSTEM_CALL_FAILED);
+ }
+ else
+ {
+ /* Parent process. */
+
+ test_process_ptr -> tls_test_external_test_process_id = pid;
+ return TLS_TEST_SUCCESS;
+ }
+}
+
diff --git a/test/regression/interoperability_test/test_frame/tls_test_semaphore_create.c b/test/regression/interoperability_test/test_frame/tls_test_semaphore_create.c
new file mode 100644
index 00000000..dd966068
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_semaphore_create.c
@@ -0,0 +1,20 @@
+#include "tls_test_frame.h"
+
+/* Create semaphore. */
+INT tls_test_semaphore_create( TLS_TEST_SEMAPHORE** semaphore_ptr_ptr, UINT initial_value)
+{
+ INT status;
+ TLS_TEST_SEMAPHORE* semaphore_ptr = *semaphore_ptr_ptr;
+ semaphore_ptr = mmap( NULL, sizeof(TLS_TEST_SEMAPHORE), PROT_READ | PROT_WRITE, MAP_ANONYMOUS | MAP_SHARED, 0, 0);
+ return_value_if_fail( NULL != semaphore_ptr, TLS_TEST_UNABLE_TO_CREATE_SHARED_MEMORY);
+
+ status = sem_init( semaphore_ptr, 1, initial_value);
+ if ( -1 == status)
+ {
+ munmap( semaphore_ptr, sizeof(TLS_TEST_SEMAPHORE));
+ }
+ return_value_if_fail( -1 != status, TLS_TEST_SYSTEM_CALL_FAILED);
+
+ *semaphore_ptr_ptr = semaphore_ptr;
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_semaphore_destroy.c b/test/regression/interoperability_test/test_frame/tls_test_semaphore_destroy.c
new file mode 100644
index 00000000..3e4542af
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_semaphore_destroy.c
@@ -0,0 +1,9 @@
+#include "tls_test_frame.h"
+
+/* Release the shared memory of the semaphore. */
+INT tls_test_semaphore_destroy(TLS_TEST_SEMAPHORE* semaphore_ptr)
+{
+ INT status = sem_destroy(semaphore_ptr);
+ return_value_if_fail(-1 != status, TLS_TEST_SYSTEM_CALL_FAILED);
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_semaphore_post.c b/test/regression/interoperability_test/test_frame/tls_test_semaphore_post.c
new file mode 100644
index 00000000..28dc3367
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_semaphore_post.c
@@ -0,0 +1,8 @@
+#include "tls_test_frame.h"
+
+/* Post semaphore. */
+INT tls_test_semaphore_post( TLS_TEST_SEMAPHORE* semaphore_ptr)
+{
+ return sem_post( semaphore_ptr);
+}
+
diff --git a/test/regression/interoperability_test/test_frame/tls_test_semaphore_wait.c b/test/regression/interoperability_test/test_frame/tls_test_semaphore_wait.c
new file mode 100644
index 00000000..45d8bff4
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_semaphore_wait.c
@@ -0,0 +1,14 @@
+#include "tls_test_frame.h"
+
+/* Wait the system call return success regardless of signals that do not cause test process to terminate. */
+INT tls_test_semaphore_wait( TLS_TEST_SEMAPHORE* semaphore_ptr)
+{
+ INT ret;
+
+ /* Wait for the semaphore ignoring signals. */
+ while ( -1 == ( ret = sem_wait( semaphore_ptr)) && ( errno == EINTR));
+
+ /* Check for return value of the system call. */
+ return_value_if_fail( -1 != ret, TLS_TEST_SYSTEM_CALL_FAILED);
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_uninterruptable_wait.c b/test/regression/interoperability_test/test_frame/tls_test_uninterruptable_wait.c
new file mode 100644
index 00000000..80134812
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_uninterruptable_wait.c
@@ -0,0 +1,18 @@
+#include "tls_test_frame.h"
+
+/* Wait for child processed ignoring signals. */
+INT tls_test_uninterruptable_wait( pid_t* pid_ptr, INT* exit_status_ptr)
+{
+ /* Check for pointers. */
+ return_value_if_fail( NULL != pid_ptr, TLS_TEST_INVALID_POINTER);
+ return_value_if_fail( NULL != exit_status_ptr, TLS_TEST_INVALID_POINTER);
+
+ /* Wait for child process terminations and restart wait if interrupted by signals. */
+ while ( ( *pid_ptr = wait( exit_status_ptr)) == -1 && (errno == EINTR));
+
+ /* Check for return value. */
+ if ( -1 == *pid_ptr)
+ return TLS_TEST_SYSTEM_CALL_FAILED;
+
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_wait_all_child_process.c b/test/regression/interoperability_test/test_frame/tls_test_wait_all_child_process.c
new file mode 100644
index 00000000..e112c6f6
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_wait_all_child_process.c
@@ -0,0 +1,12 @@
+#include "tls_test_frame.h"
+
+/* Wait until all child processes terminated. */
+INT tls_test_wait_all_child_process( void* reserved_ptr)
+{
+ pid_t pid;
+ INT exit_status;
+
+ while ( TLS_TEST_SUCCESS == tls_test_uninterruptable_wait( &pid, &exit_status));
+
+ return TLS_TEST_SUCCESS;
+}
diff --git a/test/regression/interoperability_test/test_frame/tls_test_wait_external_test_process.c b/test/regression/interoperability_test/test_frame/tls_test_wait_external_test_process.c
new file mode 100644
index 00000000..6f40a7a7
--- /dev/null
+++ b/test/regression/interoperability_test/test_frame/tls_test_wait_external_test_process.c
@@ -0,0 +1,24 @@
+#include "tls_test_frame.h"
+
+/* Call external program without output redirecting. */
+INT tls_test_wait_external_test_process( TLS_TEST_EXTERNAL_TEST_PROCESS* test_process_ptr, INT* exit_status_ptr)
+{
+ /* Validate pointers. */
+ return_value_if_fail( NULL != test_process_ptr, TLS_TEST_INVALID_POINTER);
+ return_value_if_fail( NULL != exit_status_ptr, TLS_TEST_INVALID_POINTER);
+
+ INT process_status = 0, status;
+ status = waitpid( test_process_ptr -> tls_test_external_test_process_id, &process_status, 0);
+ return_value_if_fail( -1 != status, TLS_TEST_SYSTEM_CALL_FAILED);
+
+ *exit_status_ptr = 0;
+ if ( WIFEXITED( process_status))
+ {
+ *exit_status_ptr = WEXITSTATUS( process_status);
+ }
+ else if ( WIFSIGNALED( process_status))
+ {
+ *exit_status_ptr = -WTERMSIG( process_status);
+ }
+ return TLS_TEST_SUCCESS;
+}