tttls1.3 0.2.1 → 0.2.2
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.
- checksums.yaml +4 -4
- data/README.md +1 -0
- data/Rakefile +3 -3
- data/example/https_client_using_hrr_and_ticket.rb +40 -0
- data/interop/client_spec.rb +15 -0
- data/interop/server_spec.rb +8 -0
- data/lib/tttls1.3/client.rb +265 -272
- data/lib/tttls1.3/connection.rb +85 -62
- data/lib/tttls1.3/message/certificate.rb +1 -1
- data/lib/tttls1.3/message/client_hello.rb +26 -1
- data/lib/tttls1.3/message/encrypted_extensions.rb +1 -1
- data/lib/tttls1.3/message/new_session_ticket.rb +1 -1
- data/lib/tttls1.3/message/server_hello.rb +21 -1
- data/lib/tttls1.3/server.rb +179 -157
- data/lib/tttls1.3/version.rb +1 -1
- data/spec/certificate_spec.rb +4 -4
- data/spec/client_hello_spec.rb +3 -0
- data/spec/client_spec.rb +96 -157
- data/spec/connection_spec.rb +32 -23
- data/spec/encrypted_extensions_spec.rb +4 -4
- data/spec/fixtures/rsa_ca.crt +16 -27
- data/spec/fixtures/rsa_ca.key +25 -49
- data/spec/fixtures/rsa_rsa.crt +16 -21
- data/spec/fixtures/rsa_rsa.key +25 -25
- data/spec/fixtures/rsa_rsassaPss.crt +20 -0
- data/spec/fixtures/rsa_rsassaPss.key +27 -0
- data/spec/fixtures/rsa_secp256r1.crt +12 -17
- data/spec/fixtures/rsa_secp256r1.key +3 -3
- data/spec/fixtures/rsa_secp384r1.crt +12 -17
- data/spec/fixtures/rsa_secp384r1.key +4 -4
- data/spec/fixtures/rsa_secp521r1.crt +13 -18
- data/spec/fixtures/rsa_secp521r1.key +5 -5
- data/spec/server_hello_spec.rb +60 -0
- data/spec/server_spec.rb +79 -60
- metadata +7 -2
data/lib/tttls1.3/server.rb
CHANGED
@@ -3,6 +3,7 @@
|
|
3
3
|
|
4
4
|
module TTTLS13
|
5
5
|
using Refinements
|
6
|
+
|
6
7
|
module ServerState
|
7
8
|
# initial value is 0, eof value is -1
|
8
9
|
START = 1
|
@@ -124,35 +125,48 @@ module TTTLS13
|
|
124
125
|
# rubocop: disable Metrics/MethodLength
|
125
126
|
# rubocop: disable Metrics/PerceivedComplexity
|
126
127
|
def accept
|
128
|
+
transcript = Transcript.new
|
129
|
+
key_schedule = nil # TTTLS13::KeySchedule
|
130
|
+
priv_key = nil # OpenSSL::PKey::$Object
|
131
|
+
|
132
|
+
hs_wcipher = nil # TTTLS13::Cryptograph::$Object
|
133
|
+
hs_rcipher = nil # TTTLS13::Cryptograph::$Object
|
134
|
+
|
127
135
|
@state = ServerState::START
|
128
136
|
loop do
|
129
137
|
case @state
|
130
138
|
when ServerState::START
|
131
139
|
logger.debug('ServerState::START')
|
132
140
|
|
133
|
-
|
134
|
-
|
141
|
+
receivable_ccs = transcript.include?(CH1)
|
142
|
+
ch = transcript[CH] = recv_client_hello(receivable_ccs)
|
143
|
+
|
144
|
+
# support only TLS 1.3
|
145
|
+
terminate(:protocol_version) unless ch.negotiated_tls_1_3?
|
146
|
+
|
147
|
+
# validate parameters
|
148
|
+
terminate(:illegal_parameter) unless ch.appearable_extensions?
|
149
|
+
terminamte(:illegal_parameter) \
|
150
|
+
unless ch.legacy_compression_methods == ["\x00"]
|
151
|
+
terminate(:illegal_parameter) unless ch.valid_key_share?
|
152
|
+
terminate(:unrecognized_name) unless recognized_server_name?(ch, @crt)
|
153
|
+
|
135
154
|
@state = ServerState::RECVD_CH
|
136
155
|
when ServerState::RECVD_CH
|
137
156
|
logger.debug('ServerState::RECVD_CH')
|
138
157
|
|
139
|
-
#
|
140
|
-
|
141
|
-
|
142
|
-
|
143
|
-
|
144
|
-
terminate(:illegal_parameter) unless valid_ch_key_share?
|
145
|
-
terminate(:unrecognized_name) unless recognized_server_name?
|
146
|
-
@cipher_suite = select_cipher_suite
|
147
|
-
@named_group = select_named_group
|
148
|
-
@signature_scheme = select_signature_scheme
|
158
|
+
# select parameters
|
159
|
+
ch = transcript[CH]
|
160
|
+
@cipher_suite = select_cipher_suite(ch)
|
161
|
+
@named_group = select_named_group(ch)
|
162
|
+
@signature_scheme = select_signature_scheme(ch, @crt)
|
149
163
|
terminate(:handshake_failure) \
|
150
164
|
if @cipher_suite.nil? || @signature_scheme.nil?
|
151
165
|
|
152
166
|
# send HRR
|
153
167
|
if @named_group.nil?
|
154
|
-
|
155
|
-
|
168
|
+
ch1 = transcript[CH1] = transcript.delete(CH)
|
169
|
+
transcript[HRR] = send_hello_retry_request(ch1, @cipher_suite)
|
156
170
|
@state = ServerState::START
|
157
171
|
next
|
158
172
|
end
|
@@ -160,38 +174,58 @@ module TTTLS13
|
|
160
174
|
when ServerState::NEGOTIATED
|
161
175
|
logger.debug('ServerState::NEGOTIATED')
|
162
176
|
|
163
|
-
|
164
|
-
|
177
|
+
ch = transcript[CH]
|
178
|
+
extensions, priv_key = gen_sh_extensions(@named_group)
|
179
|
+
transcript[SH] = send_server_hello(extensions, @cipher_suite,
|
180
|
+
ch.legacy_session_id)
|
165
181
|
send_ccs # compatibility mode
|
166
182
|
|
167
183
|
# generate shared secret
|
168
|
-
ke =
|
169
|
-
|
170
|
-
|
171
|
-
|
172
|
-
shared_secret = gen_shared_secret(ke,
|
173
|
-
|
174
|
-
|
175
|
-
|
176
|
-
|
177
|
-
|
178
|
-
|
179
|
-
|
180
|
-
|
181
|
-
|
182
|
-
|
184
|
+
ke = ch.extensions[Message::ExtensionType::KEY_SHARE]
|
185
|
+
&.key_share_entry
|
186
|
+
&.find { |e| e.group == @named_group }
|
187
|
+
&.key_exchange
|
188
|
+
shared_secret = gen_shared_secret(ke, priv_key, @named_group)
|
189
|
+
key_schedule = KeySchedule.new(
|
190
|
+
psk: @psk,
|
191
|
+
shared_secret: shared_secret,
|
192
|
+
cipher_suite: @cipher_suite,
|
193
|
+
transcript: transcript
|
194
|
+
)
|
195
|
+
@alert_wcipher = hs_wcipher = gen_cipher(
|
196
|
+
@cipher_suite,
|
197
|
+
key_schedule.server_handshake_write_key,
|
198
|
+
key_schedule.server_handshake_write_iv
|
199
|
+
)
|
200
|
+
hs_rcipher = gen_cipher(
|
201
|
+
@cipher_suite,
|
202
|
+
key_schedule.client_handshake_write_key,
|
203
|
+
key_schedule.client_handshake_write_iv
|
204
|
+
)
|
183
205
|
@state = ServerState::WAIT_FLIGHT2
|
184
206
|
when ServerState::WAIT_EOED
|
185
207
|
logger.debug('ServerState::WAIT_EOED')
|
186
208
|
when ServerState::WAIT_FLIGHT2
|
187
209
|
logger.debug('ServerState::WAIT_FLIGHT2')
|
188
210
|
|
189
|
-
|
211
|
+
ch = transcript[CH]
|
212
|
+
ee = transcript[EE] = gen_encrypted_extensions(ch)
|
190
213
|
# TODO: [Send CertificateRequest]
|
191
|
-
ct =
|
192
|
-
|
193
|
-
|
194
|
-
|
214
|
+
ct = transcript[CT] = gen_certificate(@crt)
|
215
|
+
digest = CipherSuite.digest(@cipher_suite)
|
216
|
+
cv = transcript[CV] = gen_certificate_verify(
|
217
|
+
@key,
|
218
|
+
@signature_scheme,
|
219
|
+
transcript.hash(digest, CT)
|
220
|
+
)
|
221
|
+
finished_key = key_schedule.server_finished_key
|
222
|
+
signature = sign_finished(
|
223
|
+
digest: digest,
|
224
|
+
finished_key: finished_key,
|
225
|
+
hash: transcript.hash(digest, CV)
|
226
|
+
)
|
227
|
+
sf = transcript[SF] = Message::Finished.new(signature)
|
228
|
+
send_server_parameters([ee, ct, cv, sf], hs_wcipher)
|
195
229
|
@state = ServerState::WAIT_FINISHED
|
196
230
|
when ServerState::WAIT_CERT
|
197
231
|
logger.debug('ServerState::WAIT_CERT')
|
@@ -200,14 +234,25 @@ module TTTLS13
|
|
200
234
|
when ServerState::WAIT_FINISHED
|
201
235
|
logger.debug('ServerState::WAIT_FINISHED')
|
202
236
|
|
203
|
-
|
204
|
-
|
205
|
-
|
206
|
-
|
207
|
-
|
208
|
-
|
209
|
-
|
210
|
-
|
237
|
+
cf = transcript[CF] = recv_finished(hs_rcipher)
|
238
|
+
digest = CipherSuite.digest(@cipher_suite)
|
239
|
+
verified = verified_finished?(
|
240
|
+
finished: cf,
|
241
|
+
digest: digest,
|
242
|
+
finished_key: key_schedule.client_finished_key,
|
243
|
+
hash: transcript.hash(digest, EOED)
|
244
|
+
)
|
245
|
+
terminate(:decrypt_error) unless verified
|
246
|
+
@alert_wcipher = @ap_wcipher = gen_cipher(
|
247
|
+
@cipher_suite,
|
248
|
+
key_schedule.server_application_write_key,
|
249
|
+
key_schedule.server_application_write_iv
|
250
|
+
)
|
251
|
+
@ap_rcipher = gen_cipher(
|
252
|
+
@cipher_suite,
|
253
|
+
key_schedule.client_application_write_key,
|
254
|
+
key_schedule.client_application_write_iv
|
255
|
+
)
|
211
256
|
@state = ServerState::CONNECTED
|
212
257
|
when ServerState::CONNECTED
|
213
258
|
logger.debug('ServerState::CONNECTED')
|
@@ -241,33 +286,41 @@ module TTTLS13
|
|
241
286
|
true
|
242
287
|
end
|
243
288
|
|
289
|
+
# @param receivable_ccs [Boolean]
|
290
|
+
#
|
244
291
|
# @raise [TTTLS13::Error::ErrorAlerts]
|
245
292
|
#
|
246
293
|
# @return [TTTLS13::Message::ClientHello]
|
247
|
-
def recv_client_hello
|
248
|
-
ch = recv_message
|
294
|
+
def recv_client_hello(receivable_ccs)
|
295
|
+
ch = recv_message(receivable_ccs: receivable_ccs,
|
296
|
+
cipher: Cryptograph::Passer.new)
|
249
297
|
terminate(:unexpected_message) unless ch.is_a?(Message::ClientHello)
|
250
298
|
|
251
299
|
ch
|
252
300
|
end
|
253
301
|
|
254
|
-
# @param
|
302
|
+
# @param extensions [TTTLS13::Message::Extensions]
|
303
|
+
# @param cipher_suite [TTTLS13::CipherSuite]
|
304
|
+
# @param session_id [String]
|
255
305
|
#
|
256
306
|
# @return [TTTLS13::Message::ServerHello]
|
257
|
-
def send_server_hello(
|
258
|
-
ch_session_id = @transcript[CH].legacy_session_id
|
307
|
+
def send_server_hello(extensions, cipher_suite, session_id)
|
259
308
|
sh = Message::ServerHello.new(
|
260
|
-
legacy_session_id_echo:
|
261
|
-
cipher_suite:
|
262
|
-
extensions:
|
309
|
+
legacy_session_id_echo: session_id,
|
310
|
+
cipher_suite: cipher_suite,
|
311
|
+
extensions: extensions
|
263
312
|
)
|
264
|
-
send_handshakes(Message::ContentType::HANDSHAKE, [sh],
|
313
|
+
send_handshakes(Message::ContentType::HANDSHAKE, [sh],
|
314
|
+
Cryptograph::Passer.new)
|
265
315
|
|
266
316
|
sh
|
267
317
|
end
|
268
318
|
|
319
|
+
# @param ch1 [TTTLS13::Message::ClientHello]
|
320
|
+
# @param cipher_suite [TTTLS13::CipherSuite]
|
321
|
+
#
|
269
322
|
# @return [TTTLS13::Message::ServerHello]
|
270
|
-
def send_hello_retry_request
|
323
|
+
def send_hello_retry_request(ch1, cipher_suite)
|
271
324
|
exs = []
|
272
325
|
# supported_versions
|
273
326
|
exs << Message::Extension::SupportedVersions.new(
|
@@ -275,7 +328,6 @@ module TTTLS13
|
|
275
328
|
)
|
276
329
|
|
277
330
|
# key_share
|
278
|
-
ch1 = @transcript[CH1]
|
279
331
|
sp_groups = ch1.extensions[Message::ExtensionType::SUPPORTED_GROUPS]
|
280
332
|
&.named_group_list || []
|
281
333
|
ks_groups = ch1.extensions[Message::ExtensionType::KEY_SHARE]
|
@@ -290,64 +342,73 @@ module TTTLS13
|
|
290
342
|
sh = Message::ServerHello.new(
|
291
343
|
random: Message::HRR_RANDOM,
|
292
344
|
legacy_session_id_echo: ch1.legacy_session_id,
|
293
|
-
cipher_suite:
|
345
|
+
cipher_suite: cipher_suite,
|
294
346
|
extensions: Message::Extensions.new(exs)
|
295
347
|
)
|
296
|
-
send_handshakes(Message::ContentType::HANDSHAKE, [sh],
|
348
|
+
send_handshakes(Message::ContentType::HANDSHAKE, [sh],
|
349
|
+
Cryptograph::Passer.new)
|
297
350
|
|
298
351
|
sh
|
299
352
|
end
|
300
353
|
|
301
354
|
# @param messages [Array of TTTLS13::Message::$Object]
|
355
|
+
# @param cipher [TTTLS13::Cryptograph::Aead]
|
302
356
|
#
|
303
357
|
# @return [Array of TTTLS13::Message::$Object]
|
304
|
-
def send_server_parameters(messages)
|
358
|
+
def send_server_parameters(messages, cipher)
|
305
359
|
send_handshakes(Message::ContentType::APPLICATION_DATA,
|
306
|
-
messages.reject(&:nil?),
|
307
|
-
@write_cipher)
|
360
|
+
messages.reject(&:nil?), cipher)
|
308
361
|
|
309
362
|
messages
|
310
363
|
end
|
311
364
|
|
365
|
+
# @param ch [TTTLS13::Message::ClientHello]
|
366
|
+
#
|
312
367
|
# @return [TTTLS13::Message::EncryptedExtensions]
|
313
|
-
def gen_encrypted_extensions
|
314
|
-
Message::EncryptedExtensions.new(gen_ee_extensions)
|
368
|
+
def gen_encrypted_extensions(ch)
|
369
|
+
Message::EncryptedExtensions.new(gen_ee_extensions(ch))
|
315
370
|
end
|
316
371
|
|
372
|
+
# @param crt [OpenSSL::X509::Certificate]
|
373
|
+
#
|
317
374
|
# @return [TTTLS13::Message::Certificate, nil]
|
318
|
-
def gen_certificate
|
319
|
-
|
320
|
-
|
321
|
-
ce = Message::CertificateEntry.new(@crt)
|
375
|
+
def gen_certificate(crt)
|
376
|
+
ce = Message::CertificateEntry.new(crt)
|
322
377
|
Message::Certificate.new(certificate_list: [ce])
|
323
378
|
end
|
324
379
|
|
380
|
+
# @param key [OpenSSL::PKey::PKey]
|
381
|
+
# @param signature_scheme [TTTLS13::SignatureScheme]
|
382
|
+
# @param hash [String]
|
383
|
+
#
|
325
384
|
# @return [TTTLS13::Message::CertificateVerify, nil]
|
326
|
-
def gen_certificate_verify
|
327
|
-
|
328
|
-
|
329
|
-
|
330
|
-
|
331
|
-
|
332
|
-
|
333
|
-
|
334
|
-
def gen_finished
|
335
|
-
Message::Finished.new(sign_finished)
|
385
|
+
def gen_certificate_verify(key, signature_scheme, hash)
|
386
|
+
signature = sign_certificate_verify(
|
387
|
+
key: key,
|
388
|
+
signature_scheme: signature_scheme,
|
389
|
+
hash: hash
|
390
|
+
)
|
391
|
+
Message::CertificateVerify.new(signature_scheme: signature_scheme,
|
392
|
+
signature: signature)
|
336
393
|
end
|
337
394
|
|
395
|
+
# @param cipher [TTTLS13::Cryptograph::Aead]
|
396
|
+
#
|
338
397
|
# @raise [TTTLS13::Error::ErrorAlerts]
|
339
398
|
#
|
340
399
|
# @return [TTTLS13::Message::Finished]
|
341
|
-
def recv_finished
|
342
|
-
cf = recv_message
|
400
|
+
def recv_finished(cipher)
|
401
|
+
cf = recv_message(receivable_ccs: true, cipher: cipher)
|
343
402
|
terminate(:unexpected_message) unless cf.is_a?(Message::Finished)
|
344
403
|
|
345
404
|
cf
|
346
405
|
end
|
347
406
|
|
407
|
+
# @param named_group [TTTLS13::NamedGroup]
|
408
|
+
#
|
348
409
|
# @return [TTTLS13::Message::Extensions]
|
349
410
|
# @return [OpenSSL::PKey::EC.$Object]
|
350
|
-
def gen_sh_extensions
|
411
|
+
def gen_sh_extensions(named_group)
|
351
412
|
exs = []
|
352
413
|
# supported_versions: only TLS 1.3
|
353
414
|
exs << Message::Extension::SupportedVersions.new(
|
@@ -356,20 +417,21 @@ module TTTLS13
|
|
356
417
|
|
357
418
|
# key_share
|
358
419
|
key_share, priv_key \
|
359
|
-
= Message::Extension::KeyShare.gen_sh_key_share(
|
420
|
+
= Message::Extension::KeyShare.gen_sh_key_share(named_group)
|
360
421
|
exs << key_share
|
361
422
|
|
362
423
|
[Message::Extensions.new(exs), priv_key]
|
363
424
|
end
|
364
425
|
|
426
|
+
# @param ch [TTTLS13::Message::ClientHello]
|
427
|
+
#
|
365
428
|
# @return [TTTLS13::Message::Extensions]
|
366
|
-
def gen_ee_extensions
|
429
|
+
def gen_ee_extensions(ch)
|
367
430
|
exs = []
|
368
431
|
|
369
432
|
# server_name
|
370
433
|
exs << Message::Extension::ServerName.new('') \
|
371
|
-
if
|
372
|
-
.include?(Message::ExtensionType::SERVER_NAME)
|
434
|
+
if ch.extensions.include?(Message::ExtensionType::SERVER_NAME)
|
373
435
|
|
374
436
|
# supported_groups
|
375
437
|
exs \
|
@@ -378,104 +440,64 @@ module TTTLS13
|
|
378
440
|
Message::Extensions.new(exs)
|
379
441
|
end
|
380
442
|
|
443
|
+
# @param key [OpenSSL::PKey::PKey]
|
444
|
+
# @param signature_scheme [TTTLS13::SignatureScheme]
|
445
|
+
# @param hash [String]
|
446
|
+
#
|
381
447
|
# @return [String]
|
382
|
-
def sign_certificate_verify
|
383
|
-
|
384
|
-
|
385
|
-
|
386
|
-
|
387
|
-
|
388
|
-
|
389
|
-
|
390
|
-
# @return [String]
|
391
|
-
def sign_finished
|
392
|
-
digest = CipherSuite.digest(@cipher_suite)
|
393
|
-
finished_key = @key_schedule.server_finished_key
|
394
|
-
do_sign_finished(digest: digest,
|
395
|
-
finished_key: finished_key,
|
396
|
-
handshake_context_end: CV)
|
397
|
-
end
|
398
|
-
|
399
|
-
# @return [Boolean]
|
400
|
-
def verified_finished?
|
401
|
-
digest = CipherSuite.digest(@cipher_suite)
|
402
|
-
finished_key = @key_schedule.client_finished_key
|
403
|
-
signature = @transcript[CF].verify_data
|
404
|
-
do_verified_finished?(digest: digest,
|
405
|
-
finished_key: finished_key,
|
406
|
-
handshake_context_end: EOED,
|
407
|
-
signature: signature)
|
408
|
-
end
|
409
|
-
|
410
|
-
# @return [Boolean]
|
411
|
-
def negotiated_tls_1_3?
|
412
|
-
ch = @transcript[CH]
|
413
|
-
ch_lv = ch.legacy_version
|
414
|
-
ch_sv = ch.extensions[Message::ExtensionType::SUPPORTED_VERSIONS]
|
415
|
-
&.versions || []
|
416
|
-
|
417
|
-
ch_lv == Message::ProtocolVersion::TLS_1_2 &&
|
418
|
-
ch_sv.include?(Message::ProtocolVersion::TLS_1_3)
|
448
|
+
def sign_certificate_verify(key:, signature_scheme:, hash:)
|
449
|
+
do_sign_certificate_verify(
|
450
|
+
key: key,
|
451
|
+
signature_scheme: signature_scheme,
|
452
|
+
context: 'TLS 1.3, server CertificateVerify',
|
453
|
+
hash: hash
|
454
|
+
)
|
419
455
|
end
|
420
456
|
|
457
|
+
# @param ch [TTTLS13::Message::ClientHello]
|
458
|
+
#
|
421
459
|
# @return [TTTLS13::CipherSuite, nil]
|
422
|
-
def select_cipher_suite
|
423
|
-
|
460
|
+
def select_cipher_suite(ch)
|
461
|
+
ch.cipher_suites.find do |cs|
|
424
462
|
@settings[:cipher_suites].include?(cs)
|
425
463
|
end
|
426
464
|
end
|
427
465
|
|
466
|
+
# @param ch [TTTLS13::Message::ClientHello]
|
467
|
+
#
|
428
468
|
# @return [TTTLS13::NamedGroup, nil]
|
429
|
-
def select_named_group
|
430
|
-
ks_groups =
|
431
|
-
|
469
|
+
def select_named_group(ch)
|
470
|
+
ks_groups = ch.extensions[Message::ExtensionType::KEY_SHARE]
|
471
|
+
&.key_share_entry&.map(&:group) || []
|
432
472
|
|
433
473
|
ks_groups.find do |g|
|
434
474
|
@settings[:supported_groups].include?(g)
|
435
475
|
end
|
436
476
|
end
|
437
477
|
|
478
|
+
# @param ch [TTTLS13::Message::ClientHello]
|
479
|
+
# @param crt [OpenSSL::X509::Certificate]
|
480
|
+
#
|
438
481
|
# @return [TTTLS13::SignatureScheme, nil]
|
439
|
-
def select_signature_scheme
|
440
|
-
algorithms
|
441
|
-
|
442
|
-
&.supported_signature_algorithms || []
|
482
|
+
def select_signature_scheme(ch, crt)
|
483
|
+
algorithms = ch.extensions[Message::ExtensionType::SIGNATURE_ALGORITHMS]
|
484
|
+
&.supported_signature_algorithms || []
|
443
485
|
|
444
|
-
do_select_signature_algorithms(algorithms,
|
486
|
+
do_select_signature_algorithms(algorithms, crt).find do |ss|
|
445
487
|
@settings[:signature_algorithms].include?(ss)
|
446
488
|
end
|
447
489
|
end
|
448
490
|
|
491
|
+
# @param ch [TTTLS13::Message::ClientHello]
|
492
|
+
# @param crt [OpenSSL::X509::Certificate]
|
493
|
+
#
|
449
494
|
# @return [Boolean]
|
450
|
-
def
|
451
|
-
|
452
|
-
|
453
|
-
|
454
|
-
# @return [Boolean]
|
455
|
-
def recognized_server_name?
|
456
|
-
server_name \
|
457
|
-
= @transcript[CH].extensions[Message::ExtensionType::SERVER_NAME]
|
458
|
-
&.server_name
|
459
|
-
|
495
|
+
def recognized_server_name?(ch, crt)
|
496
|
+
server_name = ch.extensions[Message::ExtensionType::SERVER_NAME]
|
497
|
+
&.server_name
|
460
498
|
return true if server_name.nil?
|
461
499
|
|
462
|
-
matching_san?(
|
463
|
-
end
|
464
|
-
|
465
|
-
# @return [Boolean]
|
466
|
-
def valid_ch_key_share?
|
467
|
-
ks = @transcript[CH].extensions[Message::ExtensionType::KEY_SHARE]
|
468
|
-
ks_groups = ks&.key_share_entry&.map(&:group) || []
|
469
|
-
sg = @transcript[CH].extensions[Message::ExtensionType::SUPPORTED_GROUPS]
|
470
|
-
sp_groups = sg&.named_group_list || []
|
471
|
-
|
472
|
-
# Each KeyShareEntry value MUST correspond to a group offered in the
|
473
|
-
# "supported_groups" extension and MUST appear in the same order.
|
474
|
-
#
|
475
|
-
# Clients MUST NOT offer multiple KeyShareEntry values for the same group.
|
476
|
-
(ks_groups - sp_groups).empty? &&
|
477
|
-
sp_groups.filter { |g| ks_groups.include?(g) } == ks_groups &&
|
478
|
-
ks_groups.uniq == ks_groups
|
500
|
+
matching_san?(crt, server_name)
|
479
501
|
end
|
480
502
|
end
|
481
503
|
# rubocop: enable Metrics/ClassLength
|
data/lib/tttls1.3/version.rb
CHANGED
data/spec/certificate_spec.rb
CHANGED
@@ -27,10 +27,10 @@ RSpec.describe Certificate do
|
|
27
27
|
|
28
28
|
it 'should be serialized' do
|
29
29
|
expect(message.serialize).to eq HandshakeType::CERTIFICATE \
|
30
|
-
+
|
30
|
+
+ 742.to_uint24 \
|
31
31
|
+ 0.to_uint8 \
|
32
|
-
+
|
33
|
-
+
|
32
|
+
+ 738.to_uint24 \
|
33
|
+
+ 733.to_uint24 \
|
34
34
|
+ certificate.to_der \
|
35
35
|
+ 0.to_uint16
|
36
36
|
end
|
@@ -76,7 +76,7 @@ RSpec.describe Certificate do
|
|
76
76
|
|
77
77
|
it 'should be generated' do
|
78
78
|
expect(message.msg_type).to eq HandshakeType::CERTIFICATE
|
79
|
-
expect(message.
|
79
|
+
expect(message.appearable_extensions?).to be false
|
80
80
|
end
|
81
81
|
end
|
82
82
|
end
|
data/spec/client_hello_spec.rb
CHANGED
@@ -36,6 +36,7 @@ RSpec.describe ClientHello do
|
|
36
36
|
TLS_AES_128_GCM_SHA256]
|
37
37
|
expect(message.legacy_compression_methods).to eq ["\x00"]
|
38
38
|
expect(message.extensions).to be_empty
|
39
|
+
expect(message.negotiated_tls_1_3?).to be false
|
39
40
|
end
|
40
41
|
|
41
42
|
it 'should be serialized' do
|
@@ -59,6 +60,7 @@ RSpec.describe ClientHello do
|
|
59
60
|
it 'should generate valid object' do
|
60
61
|
expect(message.msg_type).to eq HandshakeType::CLIENT_HELLO
|
61
62
|
expect(message.legacy_version).to eq ProtocolVersion::TLS_1_2
|
63
|
+
expect(message.negotiated_tls_1_3?).to be true
|
62
64
|
end
|
63
65
|
|
64
66
|
it 'should generate valid serializable object' do
|
@@ -74,6 +76,7 @@ RSpec.describe ClientHello do
|
|
74
76
|
it 'should generate valid object' do
|
75
77
|
expect(message.msg_type).to eq HandshakeType::CLIENT_HELLO
|
76
78
|
expect(message.legacy_version).to eq ProtocolVersion::TLS_1_2
|
79
|
+
expect(message.negotiated_tls_1_3?).to be true
|
77
80
|
end
|
78
81
|
|
79
82
|
it 'should generate valid serializable object' do
|