tttls1.3 0.3.6 → 0.3.7

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (62) hide show
  1. checksums.yaml +4 -4
  2. data/.ruby-version +1 -1
  3. data/lib/tttls1.3/version.rb +1 -1
  4. data/lib/tttls1.3.rb +1 -0
  5. data/tttls1.3.gemspec +5 -2
  6. metadata +3 -113
  7. data/.github/workflows/ci.yml +0 -39
  8. data/.gitignore +0 -17
  9. data/spec/aead_spec.rb +0 -95
  10. data/spec/alert_spec.rb +0 -54
  11. data/spec/alpn_spec.rb +0 -55
  12. data/spec/application_data_spec.rb +0 -26
  13. data/spec/certificate_spec.rb +0 -82
  14. data/spec/certificate_verify_spec.rb +0 -51
  15. data/spec/change_cipher_spec_spec.rb +0 -26
  16. data/spec/cipher_suites_spec.rb +0 -39
  17. data/spec/client_hello_spec.rb +0 -105
  18. data/spec/client_spec.rb +0 -274
  19. data/spec/compress_certificate_spec.rb +0 -54
  20. data/spec/cookie_spec.rb +0 -98
  21. data/spec/early_data_indication_spec.rb +0 -64
  22. data/spec/ech_outer_extensions_spec.rb +0 -42
  23. data/spec/ech_spec.rb +0 -122
  24. data/spec/encrypted_extensions_spec.rb +0 -94
  25. data/spec/end_of_early_data_spec.rb +0 -28
  26. data/spec/endpoint_spec.rb +0 -167
  27. data/spec/error_spec.rb +0 -18
  28. data/spec/extensions_spec.rb +0 -250
  29. data/spec/finished_spec.rb +0 -55
  30. data/spec/fixtures/rsa_ca.crt +0 -18
  31. data/spec/fixtures/rsa_ca.key +0 -27
  32. data/spec/fixtures/rsa_rsa.crt +0 -18
  33. data/spec/fixtures/rsa_rsa.key +0 -27
  34. data/spec/fixtures/rsa_rsa_ocsp.crt +0 -18
  35. data/spec/fixtures/rsa_rsa_ocsp.key +0 -27
  36. data/spec/fixtures/rsa_rsassaPss.crt +0 -20
  37. data/spec/fixtures/rsa_rsassaPss.key +0 -27
  38. data/spec/fixtures/rsa_secp256r1.crt +0 -14
  39. data/spec/fixtures/rsa_secp256r1.key +0 -5
  40. data/spec/fixtures/rsa_secp384r1.crt +0 -14
  41. data/spec/fixtures/rsa_secp384r1.key +0 -6
  42. data/spec/fixtures/rsa_secp521r1.crt +0 -15
  43. data/spec/fixtures/rsa_secp521r1.key +0 -7
  44. data/spec/key_schedule_spec.rb +0 -221
  45. data/spec/key_share_spec.rb +0 -199
  46. data/spec/new_session_ticket_spec.rb +0 -80
  47. data/spec/pre_shared_key_spec.rb +0 -167
  48. data/spec/psk_key_exchange_modes_spec.rb +0 -45
  49. data/spec/record_size_limit_spec.rb +0 -61
  50. data/spec/record_spec.rb +0 -105
  51. data/spec/server_hello_spec.rb +0 -200
  52. data/spec/server_name_spec.rb +0 -110
  53. data/spec/server_spec.rb +0 -232
  54. data/spec/signature_algorithms_cert_spec.rb +0 -77
  55. data/spec/signature_algorithms_spec.rb +0 -104
  56. data/spec/spec_helper.rb +0 -990
  57. data/spec/status_request_spec.rb +0 -140
  58. data/spec/supported_groups_spec.rb +0 -79
  59. data/spec/supported_versions_spec.rb +0 -136
  60. data/spec/transcript_spec.rb +0 -83
  61. data/spec/unknown_extension_spec.rb +0 -90
  62. data/spec/utils_spec.rb +0 -235
data/spec/ech_spec.rb DELETED
@@ -1,122 +0,0 @@
1
- # encoding: ascii-8bit
2
- # frozen_string_literal: true
3
-
4
- require_relative 'spec_helper'
5
- using Refinements
6
-
7
- RSpec.describe ECHClientHello do
8
- context 'valid ECHClientHello outer binary' do
9
- let(:extension) do
10
- ECHClientHello.deserialize(TESTBINARY_ECH_OUTER)
11
- end
12
-
13
- it 'should generate valid object' do
14
- expect(extension.extension_type)
15
- .to eq ExtensionType::ENCRYPTED_CLIENT_HELLO
16
- expect(extension.type).to eq ECHClientHelloType::OUTER
17
- expect(extension.cipher_suite.kdf_id.uint16).to eq 1
18
- expect(extension.cipher_suite.aead_id.uint16).to eq 1
19
- expect(extension.config_id).to eq 32
20
- expect(extension.enc.length).to eq 32
21
- expect(extension.payload.length).to eq 239
22
- end
23
-
24
- it 'should be serialized' do
25
- expect(extension.serialize)
26
- .to eq ExtensionType::ENCRYPTED_CLIENT_HELLO \
27
- + 281.to_uint16 \
28
- + ECHClientHelloType::OUTER \
29
- + 1.to_uint16 \
30
- + 1.to_uint16 \
31
- + 32.to_uint8 \
32
- + extension.enc.prefix_uint16_length \
33
- + extension.payload.prefix_uint16_length
34
- end
35
- end
36
-
37
- context 'valid ECHClientHello inner binary' do
38
- let(:extension) do
39
- ECHClientHello.deserialize(TESTBINARY_ECH_INNER)
40
- end
41
-
42
- it 'should generate valid object' do
43
- expect(extension.extension_type)
44
- .to eq ExtensionType::ENCRYPTED_CLIENT_HELLO
45
- expect(extension.type).to eq ECHClientHelloType::INNER
46
- end
47
-
48
- it 'should be serialized' do
49
- expect(extension.serialize)
50
- .to eq ExtensionType::ENCRYPTED_CLIENT_HELLO \
51
- + 1.to_uint16 \
52
- + ECHClientHelloType::INNER \
53
- end
54
- end
55
-
56
- context 'valid ECHEncryptedExtensions binary' do
57
- let(:extension) do
58
- ECHEncryptedExtensions.deserialize(TESTBINARY_ECH_EE)
59
- end
60
-
61
- it 'should generate valid object' do
62
- expect(extension.extension_type)
63
- .to eq ExtensionType::ENCRYPTED_CLIENT_HELLO
64
- expect(extension.retry_configs.is_a?(Array)).to be_truthy
65
- expect(extension.retry_configs.length).to eq 1
66
- expect(extension.retry_configs.first.is_a?(ECHConfig)).to be_truthy
67
- end
68
- end
69
-
70
- context 'valid ECHHelloRetryRequest binary' do
71
- let(:extension) do
72
- ECHHelloRetryRequest.deserialize(TESTBINARY_ECH_HRR)
73
- end
74
-
75
- it 'should generate valid object' do
76
- expect(extension.extension_type)
77
- .to eq ExtensionType::ENCRYPTED_CLIENT_HELLO
78
- expect(extension.confirmation).to eq "\x00" * 8
79
- end
80
- end
81
- end
82
-
83
- RSpec.describe Ech do
84
- context 'EncodedClientHelloInner length' do
85
- let(:server_name) do
86
- 'localhost'
87
- end
88
-
89
- let(:client) do
90
- Client.new(nil, server_name)
91
- end
92
-
93
- let(:maximum_name_length) do
94
- 0
95
- end
96
-
97
- let(:encoded) do
98
- extensions, = client.send(:gen_ch_extensions)
99
- inner_ech = Message::Extension::ECHClientHello.new_inner
100
- Message::ClientHello.new(
101
- legacy_session_id: '',
102
- cipher_suites: CipherSuites.new(DEFAULT_CH_CIPHER_SUITES),
103
- extensions: extensions.merge(
104
- Message::ExtensionType::ENCRYPTED_CLIENT_HELLO => inner_ech
105
- )
106
- )
107
- end
108
-
109
- let(:padding_encoded_ch_inner) do
110
- Ech.padding_encoded_ch_inner(
111
- encoded.serialize[4..],
112
- server_name.length,
113
- maximum_name_length
114
- )
115
- end
116
-
117
- it 'should be equal placeholder_encoded_ch_inner_len' do
118
- expect(Ech.placeholder_encoded_ch_inner_len)
119
- .to eq padding_encoded_ch_inner.length
120
- end
121
- end
122
- end
@@ -1,94 +0,0 @@
1
- # encoding: ascii-8bit
2
- # frozen_string_literal: true
3
-
4
- require_relative 'spec_helper'
5
- using Refinements
6
-
7
- RSpec.describe EncryptedExtensions do
8
- context 'valid encrypted_extensions' do
9
- let(:server_name) do
10
- ServerName.new('')
11
- end
12
-
13
- let(:supported_groups) do
14
- SupportedGroups.new(
15
- [
16
- NamedGroup::SECP256R1,
17
- NamedGroup::SECP384R1,
18
- NamedGroup::SECP521R1
19
- ]
20
- )
21
- end
22
-
23
- let(:extensions) do
24
- Extensions.new([server_name, supported_groups])
25
- end
26
-
27
- let(:message) do
28
- EncryptedExtensions.new(extensions)
29
- end
30
-
31
- it 'should be generated' do
32
- expect(message.msg_type).to eq HandshakeType::ENCRYPTED_EXTENSIONS
33
- expect(message.extensions).to eq extensions
34
- expect(message.appearable_extensions?).to be true
35
- end
36
-
37
- it 'should be serialized' do
38
- expect(message.serialize)
39
- .to eq HandshakeType::ENCRYPTED_EXTENSIONS \
40
- + extensions.serialize.prefix_uint24_length
41
- end
42
- end
43
-
44
- context 'invalid encrypted_extensions, including forbidden extension type,' do
45
- let(:extensions) do
46
- signature_algorithms \
47
- = SignatureAlgorithms.new([SignatureScheme::ECDSA_SECP256R1_SHA256])
48
- Extensions.new([signature_algorithms])
49
- end
50
-
51
- let(:message) do
52
- EncryptedExtensions.new(extensions)
53
- end
54
-
55
- it 'should be generated' do
56
- expect(message.msg_type).to eq HandshakeType::ENCRYPTED_EXTENSIONS
57
- expect(message.extensions).to eq extensions
58
- expect(message.appearable_extensions?).to be false
59
- end
60
- end
61
-
62
- context 'valid encrypted_extensions, nil argument,' do
63
- let(:message) do
64
- EncryptedExtensions.new(nil)
65
- end
66
-
67
- it 'should be generated' do
68
- expect(message.msg_type).to eq HandshakeType::ENCRYPTED_EXTENSIONS
69
- expect(message.extensions).to eq Extensions.new
70
- expect(message.appearable_extensions?).to be true
71
- end
72
-
73
- it 'should be serialized' do
74
- expect(message.serialize)
75
- .to eq HandshakeType::ENCRYPTED_EXTENSIONS \
76
- + Extensions.new.serialize.prefix_uint24_length
77
- end
78
- end
79
-
80
- context 'valid encrypted_extensions binary' do
81
- let(:message) do
82
- EncryptedExtensions.deserialize(TESTBINARY_ENCRYPTED_EXTENSIONS)
83
- end
84
-
85
- it 'should generate valid object' do
86
- expect(message.msg_type).to eq HandshakeType::ENCRYPTED_EXTENSIONS
87
- expect(message.appearable_extensions?).to be true
88
- end
89
-
90
- it 'should generate valid serializable object' do
91
- expect(message.serialize).to eq TESTBINARY_ENCRYPTED_EXTENSIONS
92
- end
93
- end
94
- end
@@ -1,28 +0,0 @@
1
- # encoding: ascii-8bit
2
- # frozen_string_literal: true
3
-
4
- require_relative 'spec_helper'
5
- using Refinements
6
-
7
- RSpec.describe EndOfEarlyData do
8
- context 'end_of_early_data' do
9
- let(:message) do
10
- EndOfEarlyData.new
11
- end
12
-
13
- it 'should be serialized' do
14
- expect(message.serialize).to eq HandshakeType::END_OF_EARLY_DATA \
15
- + ''.prefix_uint24_length
16
- end
17
- end
18
-
19
- context 'valid end_of_early_data binary' do
20
- let(:message) do
21
- EndOfEarlyData.deserialize(TESTBINARY_0_RTT_END_OF_EARLY_DATA)
22
- end
23
-
24
- it 'should generate valid serializable object' do
25
- expect(message.serialize).to eq TESTBINARY_0_RTT_END_OF_EARLY_DATA
26
- end
27
- end
28
- end
@@ -1,167 +0,0 @@
1
- # encoding: ascii-8bit
2
- # frozen_string_literal: true
3
-
4
- require_relative 'spec_helper'
5
-
6
- RSpec.describe Endpoint do
7
- context 'endpoint, Simple 1-RTT Handshake,' do
8
- let(:key) do
9
- n = OpenSSL::BN.new(TESTBINARY_PKEY_MODULUS, 2)
10
- e = OpenSSL::BN.new(TESTBINARY_PKEY_PUBLIC_EXPONENT, 2)
11
- d = OpenSSL::BN.new(TESTBINARY_PKEY_PRIVATE_EXPONENT, 2)
12
- p = OpenSSL::BN.new(TESTBINARY_PKEY_PRIME1, 2)
13
- q = OpenSSL::BN.new(TESTBINARY_PKEY_PRIME2, 2)
14
- dmp1 = d % (p - 1.to_bn)
15
- dmq1 = d % (q - 1.to_bn)
16
- iqmp = q**-1.to_bn % p
17
- asn1 = OpenSSL::ASN1::Sequence(
18
- [
19
- OpenSSL::ASN1::Integer(0),
20
- OpenSSL::ASN1::Integer(n),
21
- OpenSSL::ASN1::Integer(e),
22
- OpenSSL::ASN1::Integer(d),
23
- OpenSSL::ASN1::Integer(p),
24
- OpenSSL::ASN1::Integer(q),
25
- OpenSSL::ASN1::Integer(dmp1),
26
- OpenSSL::ASN1::Integer(dmq1),
27
- OpenSSL::ASN1::Integer(iqmp)
28
- ]
29
- )
30
- OpenSSL::PKey::RSA.new(asn1)
31
- end
32
-
33
- let(:ct) do
34
- Certificate.deserialize(TESTBINARY_CERTIFICATE)
35
- end
36
-
37
- let(:cv) do
38
- CertificateVerify.deserialize(TESTBINARY_CERTIFICATE_VERIFY)
39
- end
40
-
41
- let(:cf) do
42
- Finished.deserialize(TESTBINARY_CLIENT_FINISHED)
43
- end
44
-
45
- let(:sf) do
46
- Finished.deserialize(TESTBINARY_SERVER_FINISHED)
47
- end
48
-
49
- let(:transcript) do
50
- ch = ClientHello.deserialize(TESTBINARY_CLIENT_HELLO)
51
- sh = ServerHello.deserialize(TESTBINARY_SERVER_HELLO)
52
- ee = EncryptedExtensions.deserialize(TESTBINARY_ENCRYPTED_EXTENSIONS)
53
- transcript = Transcript.new
54
- transcript.merge!(
55
- CH => [ch, TESTBINARY_CLIENT_HELLO],
56
- SH => [sh, TESTBINARY_SERVER_HELLO],
57
- EE => [ee, TESTBINARY_ENCRYPTED_EXTENSIONS],
58
- CT => [ct, TESTBINARY_CERTIFICATE],
59
- CV => [cv, TESTBINARY_CERTIFICATE_VERIFY],
60
- CF => [cf, TESTBINARY_CLIENT_FINISHED],
61
- SF => [sf, TESTBINARY_SERVER_FINISHED]
62
- )
63
- end
64
-
65
- let(:digest) do
66
- CipherSuite.digest(CipherSuite::TLS_AES_128_GCM_SHA256)
67
- end
68
-
69
- it 'should verify server CertificateVerify.signature' do
70
- public_key = ct.certificate_list.first.cert_data.public_key
71
- signature_scheme = cv.signature_scheme
72
- signature = cv.signature
73
-
74
- expect(Endpoint.verified_certificate_verify?(
75
- public_key:,
76
- signature_scheme:,
77
- signature:,
78
- context: 'TLS 1.3, server CertificateVerify',
79
- hash: transcript.hash(digest, CT)
80
- )).to be true
81
- end
82
-
83
- it 'should sign client Finished.verify_data' do
84
- expect(Endpoint.sign_finished(
85
- digest: 'SHA256',
86
- finished_key: TESTBINARY_CLIENT_FINISHED_KEY,
87
- hash: transcript.hash(digest, EOED)
88
- )).to eq cf.verify_data
89
- end
90
-
91
- it 'should verify server Finished.verify_data' do
92
- expect(Endpoint.verified_finished?(
93
- finished: sf,
94
- digest: 'SHA256',
95
- finished_key: TESTBINARY_SERVER_FINISHED_KEY,
96
- hash: transcript.hash(digest, CV)
97
- )).to be true
98
- end
99
-
100
- it 'should sign server CertificateVerify.signature' do
101
- public_key = ct.certificate_list.first.cert_data.public_key
102
- signature_scheme = cv.signature_scheme
103
-
104
- # used RSASSA-PSS signature_scheme, salt is a random sequence.
105
- # CertificateVerify.signature is random.
106
- signature = Endpoint.sign_certificate_verify(
107
- key:,
108
- signature_scheme:,
109
- context: 'TLS 1.3, server CertificateVerify',
110
- hash: transcript.hash(digest, CT)
111
- )
112
- expect(Endpoint.verified_certificate_verify?(
113
- public_key:,
114
- signature_scheme:,
115
- signature:,
116
- context: 'TLS 1.3, server CertificateVerify',
117
- hash: transcript.hash(digest, CT)
118
- )).to be true
119
- end
120
- end
121
-
122
- context 'endpoint, HelloRetryRequest,' do
123
- let(:ct) do
124
- Certificate.deserialize(TESTBINARY_HRR_CERTIFICATE)
125
- end
126
-
127
- let(:cv) do
128
- CertificateVerify.deserialize(TESTBINARY_HRR_CERTIFICATE_VERIFY)
129
- end
130
-
131
- let(:transcript) do
132
- ch1 = ClientHello.deserialize(TESTBINARY_HRR_CLIENT_HELLO1)
133
- hrr = ServerHello.deserialize(TESTBINARY_HRR_HELLO_RETRY_REQUEST)
134
- ch = ClientHello.deserialize(TESTBINARY_HRR_CLIENT_HELLO)
135
- sh = ServerHello.deserialize(TESTBINARY_HRR_SERVER_HELLO)
136
- ee = EncryptedExtensions.deserialize(TESTBINARY_HRR_ENCRYPTED_EXTENSIONS)
137
- transcript = Transcript.new
138
- transcript.merge!(
139
- CH1 => [ch1, TESTBINARY_HRR_CLIENT_HELLO1],
140
- HRR => [hrr, TESTBINARY_HRR_HELLO_RETRY_REQUEST],
141
- CH => [ch, TESTBINARY_HRR_CLIENT_HELLO],
142
- SH => [sh, TESTBINARY_HRR_SERVER_HELLO],
143
- EE => [ee, TESTBINARY_HRR_ENCRYPTED_EXTENSIONS],
144
- CT => [ct, TESTBINARY_HRR_CERTIFICATE],
145
- CV => [cv, TESTBINARY_HRR_CERTIFICATE_VERIFY]
146
- )
147
- end
148
-
149
- let(:digest) do
150
- CipherSuite.digest(CipherSuite::TLS_AES_128_GCM_SHA256)
151
- end
152
-
153
- it 'should verify server CertificateVerify.signature' do
154
- public_key = ct.certificate_list.first.cert_data.public_key
155
- signature_scheme = cv.signature_scheme
156
- signature = cv.signature
157
-
158
- expect(Endpoint.verified_certificate_verify?(
159
- public_key:,
160
- signature_scheme:,
161
- signature:,
162
- context: 'TLS 1.3, server CertificateVerify',
163
- hash: transcript.hash(digest, CT)
164
- )).to be true
165
- end
166
- end
167
- end
data/spec/error_spec.rb DELETED
@@ -1,18 +0,0 @@
1
- # encoding: ascii-8bit
2
- # frozen_string_literal: true
3
-
4
- require_relative 'spec_helper'
5
-
6
- RSpec.describe ErrorAlerts do
7
- let(:error) do
8
- ErrorAlerts.new('unexpected_message')
9
- end
10
-
11
- let(:alert) do
12
- Alert.new(description: ALERT_DESCRIPTION[:unexpected_message])
13
- end
14
-
15
- it 'should return alert' do
16
- expect(error.to_alert.serialize).to eq alert.serialize
17
- end
18
- end
@@ -1,250 +0,0 @@
1
- # encoding: ascii-8bit
2
- # frozen_string_literal: true
3
-
4
- require_relative 'spec_helper'
5
- using Refinements
6
-
7
- RSpec.describe Extensions do
8
- context 'empty extensions' do
9
- let(:extensions) do
10
- Extensions.new
11
- end
12
-
13
- it 'should be generated' do
14
- expect(extensions).to be_empty
15
- end
16
-
17
- it 'should be serialized' do
18
- expect(extensions.serialize).to eq "\x00\x00"
19
- end
20
- end
21
-
22
- let(:supported_versions) do
23
- SupportedVersions.new(
24
- msg_type: HandshakeType::CLIENT_HELLO,
25
- versions: [ProtocolVersion::TLS_1_3]
26
- )
27
- end
28
-
29
- let(:signature_algorithms) do
30
- SignatureAlgorithms.new([SignatureScheme::RSA_PSS_RSAE_SHA256])
31
- end
32
-
33
- let(:supported_groups) do
34
- SupportedGroups.new([NamedGroup::SECP256R1])
35
- end
36
-
37
- let(:key_share) do
38
- ec = OpenSSL::PKey::EC.generate('prime256v1')
39
- KeyShare.new(
40
- msg_type: HandshakeType::CLIENT_HELLO,
41
- key_share_entry: [
42
- KeyShareEntry.new(
43
- group: NamedGroup::SECP256R1,
44
- key_exchange: ec.public_key.to_octet_string(:uncompressed)
45
- )
46
- ]
47
- )
48
- end
49
-
50
- let(:server_name) do
51
- ServerName.new('example.com')
52
- end
53
-
54
- let(:base_exs) do
55
- [
56
- supported_versions,
57
- signature_algorithms,
58
- supported_groups,
59
- key_share,
60
- server_name
61
- ]
62
- end
63
-
64
- context 'client_hello base extensions' do
65
- let(:extensions) do
66
- Extensions.new(base_exs)
67
- end
68
-
69
- it 'should be generated' do
70
- expect(extensions)
71
- .to include ExtensionType::SUPPORTED_VERSIONS => supported_versions
72
- expect(extensions)
73
- .to include ExtensionType::SIGNATURE_ALGORITHMS => signature_algorithms
74
- expect(extensions)
75
- .to include ExtensionType::SUPPORTED_GROUPS => supported_groups
76
- expect(extensions)
77
- .to include ExtensionType::KEY_SHARE => key_share
78
- expect(extensions)
79
- .to include ExtensionType::SERVER_NAME => server_name
80
- end
81
- end
82
-
83
- context 'extensions that include pre_shared_key' do
84
- let(:pre_shared_key) do
85
- PreSharedKey.deserialize(TESTBINARY_PRE_SHARED_KEY_CH,
86
- HandshakeType::CLIENT_HELLO)
87
- end
88
-
89
- let(:extensions) do
90
- exs = [pre_shared_key] + base_exs
91
- Extensions.new(exs)
92
- end
93
-
94
- it 'should be generated' do
95
- expect(extensions)
96
- .to include ExtensionType::SUPPORTED_VERSIONS => supported_versions
97
- expect(extensions)
98
- .to include ExtensionType::SIGNATURE_ALGORITHMS => signature_algorithms
99
- expect(extensions)
100
- .to include ExtensionType::SUPPORTED_GROUPS => supported_groups
101
- expect(extensions)
102
- .to include ExtensionType::KEY_SHARE => key_share
103
- expect(extensions)
104
- .to include ExtensionType::SERVER_NAME => server_name
105
- expect(extensions)
106
- .to include ExtensionType::PRE_SHARED_KEY => pre_shared_key
107
- end
108
-
109
- it 'should be serialized end with pre_shared_key' do
110
- expect(extensions.serialize).to end_with TESTBINARY_PRE_SHARED_KEY_CH
111
- end
112
- end
113
-
114
- context 'extensions that include GREASE' do
115
- let(:unknown_exs_key_aa) do
116
- "\xaa\xaa"
117
- end
118
-
119
- let(:unknown_exs_key_bb) do
120
- "\xbb\xbb"
121
- end
122
-
123
- let(:grease_aa) do
124
- UnknownExtension.new(extension_type: unknown_exs_key_aa,
125
- extension_data: '')
126
- end
127
-
128
- let(:grease_bb) do
129
- UnknownExtension.new(extension_type: unknown_exs_key_bb,
130
- extension_data: "\x00")
131
- end
132
-
133
- let(:extensions) do
134
- exs = [grease_aa] + base_exs + [grease_bb]
135
- Extensions.new(exs)
136
- end
137
-
138
- it 'should be generated' do
139
- expect(extensions)
140
- .to include ExtensionType::SUPPORTED_VERSIONS => supported_versions
141
- expect(extensions)
142
- .to include ExtensionType::SIGNATURE_ALGORITHMS => signature_algorithms
143
- expect(extensions)
144
- .to include ExtensionType::SUPPORTED_GROUPS => supported_groups
145
- expect(extensions)
146
- .to include ExtensionType::KEY_SHARE => key_share
147
- expect(extensions)
148
- .to include ExtensionType::SERVER_NAME => server_name
149
- # ignore UnknownExtension, so return nil
150
- expect(extensions).to include unknown_exs_key_aa => nil
151
- expect(extensions).to include unknown_exs_key_bb => nil
152
- end
153
- end
154
-
155
- context 'extensions binary' do
156
- let(:extensions) do
157
- Extensions.deserialize(TESTBINARY_EXTENSIONS,
158
- HandshakeType::CLIENT_HELLO)
159
- end
160
-
161
- it 'should generate object' do
162
- expect(extensions).to include ExtensionType::SUPPORTED_GROUPS
163
- expect(extensions).to include ExtensionType::KEY_SHARE
164
- expect(extensions).to include ExtensionType::SUPPORTED_VERSIONS
165
- expect(extensions).to include ExtensionType::SIGNATURE_ALGORITHMS
166
- expect(extensions).to include ExtensionType::PSK_KEY_EXCHANGE_MODES
167
- expect(extensions).to include ExtensionType::RECORD_SIZE_LIMIT
168
- end
169
- end
170
-
171
- context 'duplicated extension_type' do
172
- let(:server_name) do
173
- ServerName.new('example.com')
174
- end
175
-
176
- let(:testbinary) do
177
- server_name.serialize * 2
178
- end
179
-
180
- it 'should raise error, if extension_type get duplicated' do
181
- expect { Extensions.deserialize(testbinary, HandshakeType::CLIENT_HELLO) }
182
- .to raise_error(ErrorAlerts)
183
- end
184
- end
185
-
186
- context 'removing and replacing extensions from EncodedClientHelloInner' do
187
- let(:extensions) do
188
- extensions, = Client.new(nil, 'localhost').send(:gen_ch_extensions)
189
- extensions
190
- end
191
-
192
- let(:no_key_share_exs) do
193
- Extensions.new(
194
- extensions.filter { |k, _| k != ExtensionType::KEY_SHARE }.values
195
- )
196
- end
197
-
198
- it 'should be equal remove_and_replace! with []' do
199
- expected = extensions.clone
200
- got = extensions.remove_and_replace!([])
201
-
202
- expect(got.keys).to eq expected.keys
203
- expect(got[ExtensionType::ECH_OUTER_EXTENSIONS]).to eq nil
204
- expect(extensions.keys - got.keys).to eq []
205
- end
206
-
207
- it 'should be equal remove_and_replace! with [key_share]' do
208
- expected = extensions.filter { |k, _| k != ExtensionType::KEY_SHARE }
209
- expected[ExtensionType::ECH_OUTER_EXTENSIONS] = \
210
- Extension::ECHOuterExtensions.new([ExtensionType::KEY_SHARE])
211
- got = extensions.remove_and_replace!([ExtensionType::KEY_SHARE])
212
-
213
- expect(got.keys).to eq expected.keys
214
- expect(got[ExtensionType::ECH_OUTER_EXTENSIONS].outer_extensions)
215
- .to eq expected[ExtensionType::ECH_OUTER_EXTENSIONS].outer_extensions
216
- expect(extensions.keys - got.keys)
217
- .to eq expected[ExtensionType::ECH_OUTER_EXTENSIONS].outer_extensions
218
- end
219
-
220
- it 'should be equal remove_and_replace! with' \
221
- ' [key_share,supported_versions]' do
222
- outer_extensions = [
223
- ExtensionType::KEY_SHARE,
224
- ExtensionType::SUPPORTED_VERSIONS
225
- ]
226
- expected = extensions.filter { |k, _| !outer_extensions.include?(k) }
227
- expected[ExtensionType::ECH_OUTER_EXTENSIONS] = \
228
- Extension::ECHOuterExtensions.new(
229
- extensions.filter { |k, _| outer_extensions.include?(k) }.keys
230
- )
231
- got = extensions.remove_and_replace!(outer_extensions)
232
-
233
- expect(got.keys).to eq expected.keys
234
- expect(got[ExtensionType::ECH_OUTER_EXTENSIONS].outer_extensions)
235
- .to eq expected[ExtensionType::ECH_OUTER_EXTENSIONS].outer_extensions
236
- expect(extensions.keys - got.keys)
237
- .to eq expected[ExtensionType::ECH_OUTER_EXTENSIONS].outer_extensions
238
- end
239
-
240
- it 'should be equal remove_and_replace! with no key_share extensions' \
241
- ' & [key_share]' do
242
- expected = no_key_share_exs.clone
243
- got = no_key_share_exs.remove_and_replace!([ExtensionType::KEY_SHARE])
244
-
245
- expect(got).to eq expected
246
- expect(got[ExtensionType::ECH_OUTER_EXTENSIONS]).to eq nil
247
- expect(no_key_share_exs.keys - got.keys).to eq []
248
- end
249
- end
250
- end