tttls1.3 0.3.3 → 0.3.4

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: fa5d7f448e0c984d75be22a995278853b4d4b0c505aaaa92fc5e99f48371fc82
4
- data.tar.gz: 4a0d95465cabfd048ea1d7190c1c617dcc26a5395e06f7acc0173fcbbfe0bd04
3
+ metadata.gz: '0913f70f0bdbfd6740f41ce7902f55660ea1bd99533a8f765f9d98a1bd56a58c'
4
+ data.tar.gz: 611a063ae74498d19636ebf3ee3741b76164856341bb38ec9966a999579bdfb1
5
5
  SHA512:
6
- metadata.gz: 4035648fa81ae715315e1efbddd9b0b0506395180d0c7e994d6c8dd49d714e0754717b0cfa93bee702b4ef5a4d8e29bb765fae6045fdb7b24a3e25a1098eca38
7
- data.tar.gz: 3c9d5286f1724b4998325ab811bf2e6ce44dbbbebb3ffb3c6c01ffe76f2d730797a599196b1ec6c3a894265b16ed0b12a78f2eeca53a36b52980de85db76f247
6
+ metadata.gz: 88f39003d30f4642c67a61169923fe248bc572b4a1c638eb36803dc4278aa91a499919784cd060fa35c522bcb935745d1b4542abb1963514aba1f86f1ea789fd
7
+ data.tar.gz: cd2ae8cd383cd9737a732d53c8ca27cbacdcd3c4a5b6bee62f5f43faba4fd8eb8067b0621df18d8b77db679823c3aa26947508fe5827939bf6741e6f417a1d80
data/Gemfile CHANGED
@@ -9,11 +9,12 @@ gem 'openssl'
9
9
  gem 'rake'
10
10
 
11
11
  group :development do
12
+ gem 'base64'
12
13
  gem 'byebug'
13
14
  gem 'http_parser.rb'
15
+ gem 'resolv', '~> 0.4.0'
14
16
  gem 'rspec', '3.9.0'
15
17
  gem 'rubocop', '0.78.0'
16
- gem 'svcb_rr_patch'
17
18
  gem 'webrick'
18
19
  end
19
20
 
data/example/helper.rb CHANGED
@@ -2,6 +2,8 @@
2
2
 
3
3
  $LOAD_PATH << __dir__ + '/../lib'
4
4
 
5
+ require 'base64'
6
+ require 'resolv'
5
7
  require 'socket'
6
8
  require 'time'
7
9
  require 'uri'
@@ -9,7 +11,6 @@ require 'webrick'
9
11
 
10
12
  require 'ech_config'
11
13
  require 'http/parser'
12
- require 'svcb_rr_patch'
13
14
 
14
15
  require 'tttls1.3'
15
16
 
@@ -86,7 +87,8 @@ def transcript_htmlize(transcript)
86
87
  end
87
88
 
88
89
  def parse_echconfigs_pem(pem)
89
- s = pem.gsub(/-----(BEGIN|END) ECH CONFIGS-----/, '')
90
+ # https://datatracker.ietf.org/doc/html/draft-farrell-tls-pemesni-08#section-3-4
91
+ s = pem.gsub(/-----(BEGIN|END) (ECH CONFIGS|ECHCONFIG)-----/, '')
90
92
  .gsub("\n", '')
91
93
  b = Base64.decode64(s)
92
94
  raise 'failed to parse ECHConfigs' \
@@ -100,8 +102,15 @@ def resolve_echconfig(hostname)
100
102
  hostname,
101
103
  Resolv::DNS::Resource::IN::HTTPS
102
104
  )
105
+
106
+ # https://datatracker.ietf.org/doc/html/draft-ietf-tls-svcb-ech-01#section-6
107
+ ech = 5
103
108
  raise "failed to resolve echconfig via #{hostname} HTTPS RR" \
104
- if rr.first.nil? || !rr.first.svc_params.keys.include?('ech')
109
+ if rr.first.nil? || rr.first.params[ech].nil?
110
+
111
+ octet = rr.first.params[ech].value
112
+ raise 'failed to parse ECHConfigs' \
113
+ unless octet.length == octet.slice(0, 2).unpack1('n') + 2
105
114
 
106
- rr.first.svc_params['ech'].echconfiglist.first
115
+ ECHConfig.decode_vectors(octet.slice(2..)).first
107
116
  end
@@ -89,8 +89,8 @@ module TTTLS13
89
89
  class Client
90
90
  include Logging
91
91
 
92
- HpkeSymmetricCipherSuit = \
93
- ECHConfig::ECHConfigContents::HpkeKeyConfig::HpkeSymmetricCipherSuite
92
+ HpkeSymmetricCipherSuit \
93
+ = ECHConfig::ECHConfigContents::HpkeKeyConfig::HpkeSymmetricCipherSuite
94
94
 
95
95
  attr_reader :transcript
96
96
 
@@ -110,7 +110,6 @@ module TTTLS13
110
110
  raise Error::ConfigError unless valid_settings?
111
111
  end
112
112
 
113
- # NOTE:
114
113
  # START <----+
115
114
  # Send ClientHello | | Recv HelloRetryRequest
116
115
  # [K_send = early data] | |
@@ -327,7 +326,7 @@ module TTTLS13
327
326
  )
328
327
 
329
328
  # rejected ECH
330
- # NOTE: It can compute (hrr_)accept_ech until client selects the
329
+ # It can compute (hrr_)accept_ech until client selects the
331
330
  # cipher_suite.
332
331
  if !sh.hrr? && use_ech?
333
332
  if !@transcript.include?(HRR) && !key_schedule.accept_ech?
@@ -1008,7 +1007,6 @@ module TTTLS13
1008
1007
  [new_exs, priv_keys]
1009
1008
  end
1010
1009
 
1011
- # NOTE:
1012
1010
  # https://datatracker.ietf.org/doc/html/rfc8446#section-4.1.2
1013
1011
  #
1014
1012
  # @param ch1 [TTTLS13::Message::ClientHello]
@@ -23,8 +23,6 @@ module TTTLS13
23
23
  when CipherSuite::TLS_CHACHA20_POLY1305_SHA256
24
24
  @cipher = OpenSSL::Cipher.new('chacha20-poly1305')
25
25
  else
26
- # Note:
27
- # not supported
28
26
  # CipherSuite::TLS_AES_128_CCM_SHA256
29
27
  # CipherSuite::TLS_AES_128_CCM_8_SHA256
30
28
  raise Error::ErrorAlerts, :internal_error
@@ -36,7 +34,6 @@ module TTTLS13
36
34
  @auth_tag_len = CipherSuite.auth_tag_len(@cipher_suite)
37
35
  end
38
36
 
39
- # NOTE:
40
37
  # AEAD-Encrypt(write_key, nonce, additional_data, plaintext)
41
38
  #
42
39
  # @param content [String]
@@ -53,7 +50,6 @@ module TTTLS13
53
50
  encrypted_data + cipher.auth_tag
54
51
  end
55
52
 
56
- # NOTE:
57
53
  # AEAD-Decrypt(peer_write_key, nonce,
58
54
  # additional_data, AEADEncrypted)
59
55
  #
@@ -78,7 +74,6 @@ module TTTLS13
78
74
  [clear[0...-postfix_len], clear[-postfix_len]]
79
75
  end
80
76
 
81
- # NOTE:
82
77
  # struct {
83
78
  # opaque content[TLSPlaintext.length];
84
79
  # ContentType type;
data/lib/tttls1.3/ech.rb CHANGED
@@ -19,7 +19,7 @@ module TTTLS13
19
19
  # @param hpke_cipher_suite_selector [Method]
20
20
  #
21
21
  # @return [TTTLS13::Message::ClientHello]
22
- # @return [TTTLS13::Message::ClientHello]
22
+ # @return [TTTLS13::Message::ClientHello] ClientHelloInner
23
23
  # @return [TTTLS13::EchState]
24
24
  # rubocop: disable Metrics/AbcSize
25
25
  def self.offer_ech(inner, ech_config, hpke_cipher_suite_selector)
@@ -110,7 +110,7 @@ module TTTLS13
110
110
  # @param ech_state [TTTLS13::EchState]
111
111
  #
112
112
  # @return [TTTLS13::Message::ClientHello]
113
- # @return [TTTLS13::Message::ClientHello]
113
+ # @return [TTTLS13::Message::ClientHello] ClientHelloInner
114
114
  def self.offer_new_ech(inner, ech_state)
115
115
  # for ech_outer_extensions
116
116
  replaced = \
@@ -250,7 +250,7 @@ module TTTLS13
250
250
  #
251
251
  # @raise [TTTLS13::Error::ErrorAlerts]
252
252
  #
253
- # @param [String]
253
+ # @return [String]
254
254
  def self.hkdf_expand(secret, info, length, digest)
255
255
  hash_len = OpenSSL::Digest.new(digest).digest_length
256
256
  raise Error::ErrorAlerts, :internal_error if length > 255 * hash_len
@@ -6,7 +6,7 @@ module TTTLS13
6
6
  class ApplicationData
7
7
  attr_reader :fragment
8
8
 
9
- # @param [String]
9
+ # @param fragment [String]
10
10
  def initialize(fragment)
11
11
  @fragment = fragment
12
12
  end
@@ -160,6 +160,14 @@ module TTTLS13
160
160
  sg_groups.filter { |g| ks_groups.include?(g) } == ks_groups &&
161
161
  ks_groups.uniq == ks_groups
162
162
  end
163
+
164
+ # @return [Boolean]
165
+ def ch_inner?
166
+ ech = @extensions[Message::ExtensionType::ENCRYPTED_CLIENT_HELLO]
167
+ return false if ech.nil?
168
+
169
+ ech.type == Message::Extension::ECHClientHelloType::INNER
170
+ end
163
171
  end
164
172
  end
165
173
  end
@@ -9,7 +9,7 @@ module TTTLS13
9
9
  attr_reader :extension_type
10
10
  attr_reader :protocol_name_list
11
11
 
12
- # @param named_group_list [Array of String]
12
+ # @param protocol_name_list [Array] Array of String
13
13
  #
14
14
  # @raise [TTTLS13::Error::ErrorAlerts]
15
15
  #
@@ -12,7 +12,6 @@ module TTTLS13
12
12
  INNER = "\x01"
13
13
  end
14
14
 
15
- # NOTE:
16
15
  # struct {
17
16
  # ECHClientHelloType type;
18
17
  # select (ECHClientHello.type) {
@@ -165,7 +164,6 @@ module TTTLS13
165
164
  end
166
165
  end
167
166
 
168
- # NOTE:
169
167
  # struct {
170
168
  # ECHConfigList retry_configs;
171
169
  # } ECHEncryptedExtensions;
@@ -202,7 +200,6 @@ module TTTLS13
202
200
  end
203
201
  end
204
202
 
205
- # NOTE:
206
203
  # struct {
207
204
  # opaque confirmation[8];
208
205
  # } ECHHelloRetryRequest;
@@ -5,7 +5,6 @@ module TTTLS13
5
5
  using Refinements
6
6
  module Message
7
7
  module Extension
8
- # NOTE:
9
8
  # ExtensionType OuterExtensions<2..254>;
10
9
  class ECHOuterExtensions
11
10
  attr_reader :extension_type
@@ -11,7 +11,7 @@ module TTTLS13
11
11
  attr_reader :msg_type
12
12
  attr_reader :key_share_entry
13
13
 
14
- # @param msg_type [TTTLS13::Message::ContentType]
14
+ # @param msg_type [TTTLS13::Message::HandshakeType]
15
15
  # @param key_share_entry [Array of KeyShareEntry]
16
16
  #
17
17
  # @raise [TTTLS13::Error::ErrorAlerts]
@@ -108,7 +108,7 @@ module TTTLS13
108
108
  [key_share, priv_keys]
109
109
  end
110
110
 
111
- # @param groups [TTTLS13::NamedGroup]
111
+ # @param group [TTTLS13::NamedGroup]
112
112
  #
113
113
  # @return [TTTLS13::Message::Extensions::KeyShare]
114
114
  # @return [OpenSSL::PKey::EC.$Object]
@@ -129,7 +129,7 @@ module TTTLS13
129
129
  [key_share, ec]
130
130
  end
131
131
 
132
- # @param groups [TTTLS13::NamedGroup]
132
+ # @param group [TTTLS13::NamedGroup]
133
133
  #
134
134
  # @return [TTTLS13::Message::Extensions::KeyShare]
135
135
  def self.gen_hrr_key_share(group)
@@ -143,7 +143,6 @@ module TTTLS13
143
143
  class << self
144
144
  private
145
145
 
146
- # NOTE:
147
146
  # struct {
148
147
  # KeyShareEntry client_shares<0..2^16-1>;
149
148
  # } KeyShareClientHello;
@@ -178,7 +177,6 @@ module TTTLS13
178
177
  key_share_entry
179
178
  end
180
179
 
181
- # NOTE:
182
180
  # struct {
183
181
  # KeyShareEntry server_share;
184
182
  # } KeyShareServerHello;
@@ -201,7 +199,6 @@ module TTTLS13
201
199
  [KeyShareEntry.new(group: group, key_exchange: key_exchange)]
202
200
  end
203
201
 
204
- # NOTE:
205
202
  # struct {
206
203
  # NamedGroup selected_group;
207
204
  # } KeyShareHelloRetryRequest;
@@ -5,7 +5,6 @@ module TTTLS13
5
5
  using Refinements
6
6
  module Message
7
7
  module Extension
8
- # NOTE:
9
8
  # struct {
10
9
  # select (Handshake.msg_type) {
11
10
  # case client_hello: OfferedPsks;
@@ -83,7 +82,6 @@ module TTTLS13
83
82
  end
84
83
  end
85
84
 
86
- # NOTE:
87
85
  # opaque PskBinderEntry<32..255>;
88
86
  #
89
87
  # struct {
@@ -172,7 +170,6 @@ module TTTLS13
172
170
  # rubocop: enable Metrics/PerceivedComplexity
173
171
  end
174
172
 
175
- # NOTE:
176
173
  # struct {
177
174
  # opaque identity<1..2^16-1>;
178
175
  # uint32 obfuscated_ticket_age;
@@ -9,7 +9,6 @@ module TTTLS13
9
9
  HOST_NAME = "\x00"
10
10
  end
11
11
 
12
- # NOTE:
13
12
  # The extension_data field SHALL be empty when @server_name is empty.
14
13
  # Then, serialized extension_data is
15
14
  #
@@ -5,7 +5,7 @@ module TTTLS13
5
5
  module Message
6
6
  module Extension
7
7
  class SignatureAlgorithmsCert < SignatureAlgorithms
8
- # @param versions [Array of SignatureScheme]
8
+ # @param supported_signature_algorithms [Array] Array of SignatureScheme
9
9
  def initialize(supported_signature_algorithms)
10
10
  super(supported_signature_algorithms)
11
11
  @extension_type = ExtensionType::SIGNATURE_ALGORITHMS_CERT
@@ -5,7 +5,6 @@ module TTTLS13
5
5
  using Refinements
6
6
  module Message
7
7
  module Extension
8
- # NOTE:
9
8
  # Client/Server MUST ignore unrecognized extensions,
10
9
  # but transcript MUST include unrecognized extensions.
11
10
  class UnknownExtension
@@ -21,7 +21,6 @@ module TTTLS13
21
21
 
22
22
  alias super_fetch fetch
23
23
 
24
- # NOTE:
25
24
  # "pre_shared_key" MUST be the last extension in the ClientHello
26
25
  #
27
26
  # @return [String]
@@ -136,7 +135,6 @@ module TTTLS13
136
135
  class << self
137
136
  private
138
137
 
139
- # NOTE:
140
138
  # deserialize_extension ignores unparsable extension.
141
139
  # Received unparsable binary, returns nil, doesn't raise
142
140
  # ErrorAlerts :decode_error.
@@ -27,7 +27,6 @@ module TTTLS13
27
27
  @cipher = cipher
28
28
  end
29
29
 
30
- # NOTE:
31
30
  # serialize joins messages.
32
31
  # If serialize is received Server Parameters(EE, CT, CV),
33
32
  # it returns one binary.
@@ -50,7 +49,6 @@ module TTTLS13
50
49
  end.join
51
50
  end
52
51
 
53
- # NOTE:
54
52
  # If previous Record has surplus_binary,
55
53
  # surplus_binary should is given to Record.deserialize as buffered.
56
54
  #
@@ -17,7 +17,6 @@ module TTTLS13
17
17
  # ecdhe_private_use "\xfe\x00" ~ "\xfe\xff"
18
18
 
19
19
  class << self
20
- # NOTE:
21
20
  # For secp256r1, secp384r1, and secp521r1
22
21
  #
23
22
  # struct {
@@ -57,7 +56,6 @@ module TTTLS13
57
56
  end
58
57
  end
59
58
 
60
- # NOTE:
61
59
  # SECG | ANSI X9.62 | NIST
62
60
  # ------------+---------------+-------------
63
61
  # secp256r1 | prime256v1 | NIST P-256
@@ -66,7 +64,7 @@ module TTTLS13
66
64
  #
67
65
  # https://datatracker.ietf.org/doc/html/rfc4492#appendix-A
68
66
  #
69
- # @param groups [Array of TTTLS13::Message::Extension::NamedGroup]
67
+ # @param group [TTTLS13::Message::Extension::NamedGroup]
70
68
  #
71
69
  # @raise [TTTLS13::Error::ErrorAlerts]
72
70
  #
@@ -96,7 +96,6 @@ module TTTLS13
96
96
  end
97
97
  end
98
98
 
99
- # NOTE:
100
99
  # START <-----+
101
100
  # Recv ClientHello | | Send HelloRetryRequest
102
101
  # v |
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module TTTLS13
4
- VERSION = '0.3.3'
4
+ VERSION = '0.3.4'
5
5
  end
@@ -37,6 +37,7 @@ RSpec.describe ClientHello do
37
37
  expect(message.legacy_compression_methods).to eq ["\x00"]
38
38
  expect(message.extensions).to be_empty
39
39
  expect(message.negotiated_tls_1_3?).to be false
40
+ expect(message.ch_inner?).to be false
40
41
  end
41
42
 
42
43
  it 'should be serialized' do
@@ -83,4 +84,22 @@ RSpec.describe ClientHello do
83
84
  expect(message.serialize).to eq TESTBINARY_0_RTT_CLIENT_HELLO
84
85
  end
85
86
  end
87
+
88
+ context 'valid inner client_hello' do
89
+ let(:message) do
90
+ cipher_suites = CipherSuites.new([TLS_AES_256_GCM_SHA384,
91
+ TLS_CHACHA20_POLY1305_SHA256,
92
+ TLS_AES_128_GCM_SHA256])
93
+ ch = ClientHello.new(random: OpenSSL::Random.random_bytes(32),
94
+ legacy_session_id: Array.new(32, 0).map(&:chr).join,
95
+ cipher_suites: cipher_suites)
96
+ ch.extensions[Message::ExtensionType::ENCRYPTED_CLIENT_HELLO] \
97
+ = Message::Extension::ECHClientHello.new_inner
98
+ ch
99
+ end
100
+
101
+ it 'should generate ClientHelloInner' do
102
+ expect(message.ch_inner?).to be true
103
+ end
104
+ end
86
105
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: tttls1.3
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.3.3
4
+ version: 0.3.4
5
5
  platform: ruby
6
6
  authors:
7
7
  - thekuwayama
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2024-04-19 00:00:00.000000000 Z
11
+ date: 2024-12-29 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler