70-test_tlsextms.t 7.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255
  1. #! /usr/bin/env perl
  2. # Copyright 2015-2021 The OpenSSL Project Authors. All Rights Reserved.
  3. #
  4. # Licensed under the Apache License 2.0 (the "License"). You may not use
  5. # this file except in compliance with the License. You can obtain a copy
  6. # in the file LICENSE in the source distribution or at
  7. # https://www.openssl.org/source/license.html
  8. use strict;
  9. use OpenSSL::Test qw/:DEFAULT cmdstr srctop_file bldtop_dir/;
  10. use OpenSSL::Test::Utils;
  11. use TLSProxy::Proxy;
  12. use File::Temp qw(tempfile);
  13. my $test_name = "test_tlsextms";
  14. setup($test_name);
  15. plan skip_all => "TLSProxy isn't usable on $^O"
  16. if $^O =~ /^(VMS)$/;
  17. plan skip_all => "$test_name needs the dynamic engine feature enabled"
  18. if disabled("engine") || disabled("dynamic-engine");
  19. plan skip_all => "$test_name needs the sock feature enabled"
  20. if disabled("sock");
  21. plan skip_all => "$test_name needs TLSv1.0, TLSv1.1 or TLSv1.2 enabled"
  22. if disabled("tls1") && disabled("tls1_1") && disabled("tls1_2");
  23. sub checkmessages($$$$$);
  24. sub setrmextms($$);
  25. sub clearall();
  26. my $crmextms = 0;
  27. my $srmextms = 0;
  28. my $cextms = 0;
  29. my $sextms = 0;
  30. my $fullhand = 0;
  31. my $proxy = TLSProxy::Proxy->new(
  32. \&extms_filter,
  33. cmdstr(app(["openssl"]), display => 1),
  34. srctop_file("apps", "server.pem"),
  35. (!$ENV{HARNESS_ACTIVE} || $ENV{HARNESS_VERBOSE})
  36. );
  37. #Note that EXTMS is only relevant for <TLS1.3
  38. #Test 1: By default server and client should send extended master secret
  39. # extension.
  40. #Expected result: ClientHello extension seen; ServerHello extension seen
  41. # Full handshake
  42. setrmextms(0, 0);
  43. $proxy->clientflags("-no_tls1_3");
  44. $proxy->start() or plan skip_all => "Unable to start up Proxy for tests";
  45. plan tests => 10;
  46. checkmessages(1, "Default extended master secret test", 1, 1, 1);
  47. #Test 2: If client omits extended master secret extension, server should too.
  48. #Expected result: ClientHello extension not seen; ServerHello extension not seen
  49. # Full handshake
  50. clearall();
  51. setrmextms(1, 0);
  52. $proxy->clientflags("-no_tls1_3");
  53. $proxy->start();
  54. checkmessages(2, "No client extension extended master secret test", 0, 0, 1);
  55. # Test 3: same as 1 but with session tickets disabled.
  56. # Expected result: same as test 1.
  57. clearall();
  58. $proxy->clientflags("-no_ticket -no_tls1_3");
  59. setrmextms(0, 0);
  60. $proxy->start();
  61. checkmessages(3, "No ticket extended master secret test", 1, 1, 1);
  62. # Test 4: same as 2 but with session tickets disabled.
  63. # Expected result: same as test 2.
  64. clearall();
  65. $proxy->clientflags("-no_ticket -no_tls1_3");
  66. setrmextms(1, 0);
  67. $proxy->start();
  68. checkmessages(4, "No ticket, no client extension extended master secret test", 0, 0, 1);
  69. #Test 5: Session resumption extended master secret test
  70. #
  71. #Expected result: ClientHello extension seen; ServerHello extension seen
  72. # Abbreviated handshake
  73. clearall();
  74. setrmextms(0, 0);
  75. (undef, my $session) = tempfile();
  76. $proxy->serverconnects(2);
  77. $proxy->clientflags("-no_tls1_3 -sess_out ".$session);
  78. $proxy->start();
  79. $proxy->clearClient();
  80. $proxy->clientflags("-no_tls1_3 -sess_in ".$session);
  81. $proxy->clientstart();
  82. checkmessages(5, "Session resumption extended master secret test", 1, 1, 0);
  83. unlink $session;
  84. #Test 6: Session resumption extended master secret test original session
  85. # omits extension. Server must not resume session.
  86. #Expected result: ClientHello extension seen; ServerHello extension seen
  87. # Full handshake
  88. clearall();
  89. setrmextms(1, 0);
  90. (undef, $session) = tempfile();
  91. $proxy->serverconnects(2);
  92. $proxy->clientflags("-no_tls1_3 -sess_out ".$session);
  93. $proxy->start();
  94. $proxy->clearClient();
  95. $proxy->clientflags("-no_tls1_3 -sess_in ".$session);
  96. setrmextms(0, 0);
  97. $proxy->clientstart();
  98. checkmessages(6, "Session resumption extended master secret test", 1, 1, 1);
  99. unlink $session;
  100. #Test 7: Session resumption extended master secret test resumed session
  101. # omits client extension. Server must abort connection.
  102. #Expected result: aborted connection.
  103. clearall();
  104. setrmextms(0, 0);
  105. (undef, $session) = tempfile();
  106. $proxy->serverconnects(2);
  107. $proxy->clientflags("-no_tls1_3 -sess_out ".$session);
  108. $proxy->start();
  109. $proxy->clearClient();
  110. $proxy->clientflags("-no_tls1_3 -sess_in ".$session);
  111. setrmextms(1, 0);
  112. $proxy->clientstart();
  113. ok(TLSProxy::Message->fail(), "Client inconsistent session resumption");
  114. unlink $session;
  115. #Test 8: Session resumption extended master secret test resumed session
  116. # omits server extension. Client must abort connection.
  117. #Expected result: aborted connection.
  118. clearall();
  119. setrmextms(0, 0);
  120. (undef, $session) = tempfile();
  121. $proxy->serverconnects(2);
  122. $proxy->clientflags("-no_tls1_3 -sess_out ".$session);
  123. $proxy->start();
  124. $proxy->clearClient();
  125. $proxy->clientflags("-no_tls1_3 -sess_in ".$session);
  126. setrmextms(0, 1);
  127. $proxy->clientstart();
  128. ok(TLSProxy::Message->fail(), "Server inconsistent session resumption 1");
  129. unlink $session;
  130. #Test 9: Session resumption extended master secret test initial session
  131. # omits server extension. Client must abort connection.
  132. #Expected result: aborted connection.
  133. clearall();
  134. setrmextms(0, 1);
  135. (undef, $session) = tempfile();
  136. $proxy->serverconnects(2);
  137. $proxy->clientflags("-no_tls1_3 -sess_out ".$session);
  138. $proxy->start();
  139. $proxy->clearClient();
  140. $proxy->clientflags("-no_tls1_3 -sess_in ".$session);
  141. setrmextms(0, 0);
  142. $proxy->clientstart();
  143. ok(TLSProxy::Message->fail(), "Server inconsistent session resumption 2");
  144. unlink $session;
  145. SKIP: {
  146. skip "TLS 1.3 disabled", 1
  147. if disabled("tls1_3") || (disabled("ec") && disabled("dh"));
  148. #Test 10: In TLS1.3 we should not negotiate extended master secret
  149. #Expected result: ClientHello extension seen; ServerHello extension not seen
  150. # TLS1.3 handshake (will appear as abbreviated handshake
  151. # because of no CKE message)
  152. clearall();
  153. setrmextms(0, 0);
  154. $proxy->start();
  155. checkmessages(10, "TLS1.3 extended master secret test", 1, 0, 0);
  156. }
  157. sub extms_filter
  158. {
  159. my $proxy = shift;
  160. foreach my $message (@{$proxy->message_list}) {
  161. if ($crmextms && $message->mt == TLSProxy::Message::MT_CLIENT_HELLO) {
  162. $message->delete_extension(TLSProxy::Message::EXT_EXTENDED_MASTER_SECRET);
  163. $message->repack();
  164. }
  165. if ($srmextms && $message->mt == TLSProxy::Message::MT_SERVER_HELLO) {
  166. $message->delete_extension(TLSProxy::Message::EXT_EXTENDED_MASTER_SECRET);
  167. $message->repack();
  168. }
  169. }
  170. }
  171. sub checkmessages($$$$$)
  172. {
  173. my ($testno, $testname, $testcextms, $testsextms, $testhand) = @_;
  174. subtest $testname => sub {
  175. foreach my $message (@{$proxy->message_list}) {
  176. if ($message->mt == TLSProxy::Message::MT_CLIENT_HELLO
  177. || $message->mt == TLSProxy::Message::MT_SERVER_HELLO) {
  178. #Get the extensions data
  179. my %extensions = %{$message->extension_data};
  180. if (defined
  181. $extensions{TLSProxy::Message::EXT_EXTENDED_MASTER_SECRET}) {
  182. if ($message->mt == TLSProxy::Message::MT_CLIENT_HELLO) {
  183. $cextms = 1;
  184. } else {
  185. $sextms = 1;
  186. }
  187. }
  188. } elsif ($message->mt == TLSProxy::Message::MT_CLIENT_KEY_EXCHANGE) {
  189. #Must be doing a full handshake
  190. $fullhand = 1;
  191. }
  192. }
  193. plan tests => 4;
  194. ok(TLSProxy::Message->success, "Handshake");
  195. ok($testcextms == $cextms,
  196. "ClientHello extension extended master secret check");
  197. ok($testsextms == $sextms,
  198. "ServerHello extension extended master secret check");
  199. ok($testhand == $fullhand,
  200. "Extended master secret full handshake check");
  201. }
  202. }
  203. sub setrmextms($$)
  204. {
  205. ($crmextms, $srmextms) = @_;
  206. }
  207. sub clearall()
  208. {
  209. $cextms = 0;
  210. $sextms = 0;
  211. $fullhand = 0;
  212. $proxy->clear();
  213. }