raioquic 0.1.0
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 +7 -0
- data/.containerignore +4 -0
- data/.rubocop.yml +93 -0
- data/CHANGELOG.md +5 -0
- data/CODE_OF_CONDUCT.md +84 -0
- data/Containerfile +6 -0
- data/Gemfile +24 -0
- data/Gemfile.lock +113 -0
- data/LICENSE +28 -0
- data/README.md +48 -0
- data/Rakefile +16 -0
- data/Steepfile +8 -0
- data/example/curlcatcher.rb +18 -0
- data/example/interoperability/README.md +9 -0
- data/example/interoperability/aioquic/aioquic_client.py +47 -0
- data/example/interoperability/aioquic/aioquic_server.py +34 -0
- data/example/interoperability/key.pem +28 -0
- data/example/interoperability/localhost-unasuke-dev.crt +21 -0
- data/example/interoperability/quic-go/sample_server.go +61 -0
- data/example/interoperability/raioquic_client.rb +42 -0
- data/example/interoperability/raioquic_server.rb +43 -0
- data/example/parse_curl_example.rb +108 -0
- data/lib/raioquic/buffer.rb +202 -0
- data/lib/raioquic/core_ext.rb +54 -0
- data/lib/raioquic/crypto/README.md +5 -0
- data/lib/raioquic/crypto/aesgcm.rb +52 -0
- data/lib/raioquic/crypto/backend/aead.rb +52 -0
- data/lib/raioquic/crypto/backend.rb +12 -0
- data/lib/raioquic/crypto.rb +10 -0
- data/lib/raioquic/quic/configuration.rb +81 -0
- data/lib/raioquic/quic/connection.rb +2776 -0
- data/lib/raioquic/quic/crypto.rb +317 -0
- data/lib/raioquic/quic/event.rb +69 -0
- data/lib/raioquic/quic/logger.rb +272 -0
- data/lib/raioquic/quic/packet.rb +471 -0
- data/lib/raioquic/quic/packet_builder.rb +301 -0
- data/lib/raioquic/quic/rangeset.rb +113 -0
- data/lib/raioquic/quic/recovery.rb +528 -0
- data/lib/raioquic/quic/stream.rb +343 -0
- data/lib/raioquic/quic.rb +20 -0
- data/lib/raioquic/tls.rb +1659 -0
- data/lib/raioquic/version.rb +5 -0
- data/lib/raioquic.rb +12 -0
- data/misc/export_x25519.py +43 -0
- data/misc/gen_rfc8448_keypair.rb +90 -0
- data/raioquic.gemspec +37 -0
- data/sig/raioquic/buffer.rbs +37 -0
- data/sig/raioquic/core_ext.rbs +7 -0
- data/sig/raioquic/crypto/aesgcm.rbs +20 -0
- data/sig/raioquic/crypto/backend/aead.rbs +11 -0
- data/sig/raioquic/quic/configuration.rbs +34 -0
- data/sig/raioquic/quic/connection.rbs +277 -0
- data/sig/raioquic/quic/crypto.rbs +88 -0
- data/sig/raioquic/quic/event.rbs +51 -0
- data/sig/raioquic/quic/logger.rbs +57 -0
- data/sig/raioquic/quic/packet.rbs +157 -0
- data/sig/raioquic/quic/packet_builder.rbs +76 -0
- data/sig/raioquic/quic/rangeset.rbs +17 -0
- data/sig/raioquic/quic/recovery.rbs +142 -0
- data/sig/raioquic/quic/stream.rbs +87 -0
- data/sig/raioquic/tls.rbs +444 -0
- data/sig/raioquic.rbs +9 -0
- metadata +121 -0
data/lib/raioquic.rb
ADDED
@@ -0,0 +1,12 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require_relative "raioquic/version"
|
4
|
+
require_relative "raioquic/buffer"
|
5
|
+
require_relative "raioquic/quic"
|
6
|
+
require_relative "raioquic/crypto"
|
7
|
+
|
8
|
+
module Raioquic
|
9
|
+
class Error < StandardError; end
|
10
|
+
# Your code goes here...
|
11
|
+
class ValueError < Error; end
|
12
|
+
end
|
@@ -0,0 +1,43 @@
|
|
1
|
+
# Create X25519 kay pair as PEM format it illustrated in RFC 8448.
|
2
|
+
|
3
|
+
from cryptography.hazmat.primitives import serialization
|
4
|
+
from cryptography.hazmat.primitives.asymmetric import x25519
|
5
|
+
import binascii
|
6
|
+
|
7
|
+
client_priv_key = x25519.X25519PrivateKey.from_private_bytes(
|
8
|
+
binascii.unhexlify("49af42ba7f7994852d713ef2784bcbcaa7911de26adc5642cb634540e7ea5005")
|
9
|
+
)
|
10
|
+
|
11
|
+
print(client_priv_key.private_bytes(
|
12
|
+
encoding=serialization.Encoding.PEM,
|
13
|
+
format=serialization.PrivateFormat.PKCS8,
|
14
|
+
encryption_algorithm=serialization.NoEncryption()
|
15
|
+
))
|
16
|
+
|
17
|
+
client_pub_key = x25519.X25519PublicKey.from_public_bytes(
|
18
|
+
binascii.unhexlify("99381de560e4bd43d23d8e435a7dbafeb3c06e51c13cae4d5413691e529aaf2c")
|
19
|
+
)
|
20
|
+
|
21
|
+
print(client_pub_key.public_bytes(
|
22
|
+
encoding=serialization.Encoding.PEM,
|
23
|
+
format=serialization.PublicFormat.SubjectPublicKeyInfo
|
24
|
+
))
|
25
|
+
|
26
|
+
server_priv_key = x25519.X25519PrivateKey.from_private_bytes(
|
27
|
+
binascii.unhexlify("b1580eeadf6dd589b8ef4f2d5652578cc810e9980191ec8d058308cea216a21e")
|
28
|
+
)
|
29
|
+
|
30
|
+
print(server_priv_key.private_bytes(
|
31
|
+
encoding=serialization.Encoding.PEM,
|
32
|
+
format=serialization.PrivateFormat.PKCS8,
|
33
|
+
encryption_algorithm=serialization.NoEncryption()
|
34
|
+
))
|
35
|
+
|
36
|
+
server_pub_key = x25519.X25519PublicKey.from_public_bytes(
|
37
|
+
binascii.unhexlify("c9828876112095fe66762bdbf7c672e156d6cc253b833df1dd69b1b04e751f0f")
|
38
|
+
)
|
39
|
+
|
40
|
+
print(server_pub_key.public_bytes(
|
41
|
+
encoding=serialization.Encoding.PEM,
|
42
|
+
format=serialization.PublicFormat.SubjectPublicKeyInfo
|
43
|
+
))
|
@@ -0,0 +1,90 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "openssl"
|
4
|
+
|
5
|
+
# Generate key pair illustrated in RFC 8448.
|
6
|
+
# https://datatracker.ietf.org/doc/html/rfc8448
|
7
|
+
#
|
8
|
+
# In OpenSSL 3 environtment, openssl gem did not support OpenSSL::PKey::RSA#set_key, OpenSSL::PKey::RSA#set_factors,
|
9
|
+
# and OpenSSL::PKey::RSA#set_crt_params because PKey object made immutable from OpenSSL 3.
|
10
|
+
# Run this script in OpenSSL 1 env (like a container), get key pair with PEM format,
|
11
|
+
# then read in OpenSSL 3 env by OpenSSL::Pkey.read method and so on.
|
12
|
+
|
13
|
+
rfc8448_rsa_pkey_moduls = <<~MODULUS.split.map(&:hex).map(&:chr).join
|
14
|
+
b4 bb 49 8f 82 79 30 3d 98 08 36 39 9b 36 c6 98
|
15
|
+
8c 0c 68 de 55 e1 bd b8 26 d3 90 1a 24 61 ea fd
|
16
|
+
2d e4 9a 91 d0 15 ab bc 9a 95 13 7a ce 6c 1a f1
|
17
|
+
9e aa 6a f9 8c 7c ed 43 12 09 98 e1 87 a8 0e e0
|
18
|
+
cc b0 52 4b 1b 01 8c 3e 0b 63 26 4d 44 9a 6d 38
|
19
|
+
e2 2a 5f da 43 08 46 74 80 30 53 0e f0 46 1c 8c
|
20
|
+
a9 d9 ef bf ae 8e a6 d1 d0 3e 2b d1 93 ef f0 ab
|
21
|
+
9a 80 02 c4 74 28 a6 d3 5a 8d 88 d7 9f 7f 1e 3f
|
22
|
+
MODULUS
|
23
|
+
|
24
|
+
rfc8448_rsa_pkey_public_exponent = <<~EXPONENT.split.map(&:hex).map(&:chr).join
|
25
|
+
01 00 01
|
26
|
+
EXPONENT
|
27
|
+
|
28
|
+
rfc8448_rsa_pkey_private_exponent = <<~EXPONENT.split.map(&:hex).map(&:chr).join
|
29
|
+
04 de a7 05 d4 3a 6e a7 20 9d d8 07 21 11 a8 3c
|
30
|
+
81 e3 22 a5 92 78 b3 34 80 64 1e af 7c 0a 69 85
|
31
|
+
b8 e3 1c 44 f6 de 62 e1 b4 c2 30 9f 61 26 e7 7b
|
32
|
+
7c 41 e9 23 31 4b bf a3 88 13 05 dc 12 17 f1 6c
|
33
|
+
81 9c e5 38 e9 22 f3 69 82 8d 0e 57 19 5d 8c 84
|
34
|
+
88 46 02 07 b2 fa a7 26 bc f7 08 bb d7 db 7f 67
|
35
|
+
9f 89 34 92 fc 2a 62 2e 08 97 0a ac 44 1c e4 e0
|
36
|
+
c3 08 8d f2 5a e6 79 23 3d f8 a3 bd a2 ff 99 41
|
37
|
+
EXPONENT
|
38
|
+
|
39
|
+
rfc8448_rsa_pkey_prime1 = <<~PRIME1.split.map(&:hex).map(&:chr).join
|
40
|
+
e4 35 fb 7c c8 37 37 75 6d ac ea 96 ab 7f 59 a2
|
41
|
+
cc 10 69 db 7d eb 19 0e 17 e3 3a 53 2b 27 3f 30
|
42
|
+
a3 27 aa 0a aa bc 58 cd 67 46 6a f9 84 5f ad c6
|
43
|
+
75 fe 09 4a f9 2c 4b d1 f2 c1 bc 33 dd 2e 05 15
|
44
|
+
PRIME1
|
45
|
+
|
46
|
+
rfc8448_rsa_pkey_prime2 = <<~PRIME2.split.map(&:hex).map(&:chr).join
|
47
|
+
ca bd 3b c0 e0 43 86 64 c8 d4 cc 9f 99 97 7a 94
|
48
|
+
d9 bb fe ad 8e 43 87 0a ba e3 f7 eb 8b 4e 0e ee
|
49
|
+
8a f1 d9 b4 71 9b a6 19 6c f2 cb ba ee eb f8 b3
|
50
|
+
49 0a fe 9e 9f fa 74 a8 8a a5 1f c6 45 62 93 03
|
51
|
+
PRIME2
|
52
|
+
|
53
|
+
rfc8448_rsa_pkey_exponent1 = <<~EXPONENT1.split.map(&:hex).map(&:chr).join
|
54
|
+
3f 57 34 5c 27 fe 1b 68 7e 6e 76 16 27 b7 8b 1b
|
55
|
+
82 64 33 dd 76 0f a0 be a6 a6 ac f3 94 90 aa 1b
|
56
|
+
47 cd a4 86 9d 68 f5 84 dd 5b 50 29 bd 32 09 3b
|
57
|
+
82 58 66 1f e7 15 02 5e 5d 70 a4 5a 08 d3 d3 19
|
58
|
+
EXPONENT1
|
59
|
+
|
60
|
+
rfc8448_rsa_pkey_exponent2 = <<~EXPONENT2.split.map(&:hex).map(&:chr).join
|
61
|
+
18 3d a0 13 63 bd 2f 28 85 ca cb dc 99 64 bf 47
|
62
|
+
64 f1 51 76 36 f8 64 01 28 6f 71 89 3c 52 cc fe
|
63
|
+
40 a6 c2 3d 0d 08 6b 47 c6 fb 10 d8 fd 10 41 e0
|
64
|
+
4d ef 7e 9a 40 ce 95 7c 41 77 94 e1 04 12 d1 39
|
65
|
+
EXPONENT2
|
66
|
+
|
67
|
+
rfc8448_rsa_pkey_coefficient = <<~COEF.split.map(&:hex).map(&:chr).join
|
68
|
+
83 9c a9 a0 85 e4 28 6b 2c 90 e4 66 99 7a 2c 68
|
69
|
+
1f 21 33 9a a3 47 78 14 e4 de c1 18 33 05 0e d5
|
70
|
+
0d d1 3c c0 38 04 8a 43 c5 9b 2a cc 41 68 89 c0
|
71
|
+
37 66 5f e5 af a6 05 96 9f 8c 01 df a5 ca 96 9d
|
72
|
+
COEF
|
73
|
+
|
74
|
+
rsa_cert = OpenSSL::PKey::RSA.new
|
75
|
+
rsa_cert.set_key(
|
76
|
+
OpenSSL::BN.new(rfc8448_rsa_pkey_moduls, 2),
|
77
|
+
OpenSSL::BN.new(rfc8448_rsa_pkey_public_exponent, 2),
|
78
|
+
OpenSSL::BN.new(rfc8448_rsa_pkey_private_exponent, 2),
|
79
|
+
)
|
80
|
+
rsa_cert.set_factors(
|
81
|
+
OpenSSL::BN.new(rfc8448_rsa_pkey_prime1, 2),
|
82
|
+
OpenSSL::BN.new(rfc8448_rsa_pkey_prime2, 2),
|
83
|
+
)
|
84
|
+
rsa_cert.set_crt_params(
|
85
|
+
OpenSSL::BN.new(rfc8448_rsa_pkey_exponent1, 2),
|
86
|
+
OpenSSL::BN.new(rfc8448_rsa_pkey_exponent2, 2),
|
87
|
+
OpenSSL::BN.new(rfc8448_rsa_pkey_coefficient, 2),
|
88
|
+
)
|
89
|
+
|
90
|
+
File.write("rfc8448.pem", rsa_cert.to_pem)
|
data/raioquic.gemspec
ADDED
@@ -0,0 +1,37 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require_relative "lib/raioquic/version"
|
4
|
+
|
5
|
+
Gem::Specification.new do |spec|
|
6
|
+
spec.name = "raioquic"
|
7
|
+
spec.version = Raioquic::VERSION
|
8
|
+
spec.authors = ["Yusuke Nakamura"]
|
9
|
+
spec.email = ["yusuke1994525@gmail.com"]
|
10
|
+
|
11
|
+
spec.summary = "Write a short summary, because RubyGems requires one."
|
12
|
+
spec.description = "Write a longer description or delete this line."
|
13
|
+
spec.homepage = "https://example.com"
|
14
|
+
spec.required_ruby_version = ">= 3.0.0"
|
15
|
+
|
16
|
+
spec.metadata["homepage_uri"] = spec.homepage
|
17
|
+
spec.metadata["source_code_uri"] = spec.homepage
|
18
|
+
spec.metadata["changelog_uri"] = spec.homepage
|
19
|
+
spec.metadata["rubygems_mfa_required"] = "true"
|
20
|
+
|
21
|
+
# Specify which files should be added to the gem when it is released.
|
22
|
+
# The `git ls-files -z` loads the files in the RubyGem that have been added into git.
|
23
|
+
spec.files = Dir.chdir(File.expand_path(__dir__)) do
|
24
|
+
`git ls-files -z`.split("\x0").reject do |f|
|
25
|
+
(f == __FILE__) || f.match(%r{\A(?:(?:bin|test|spec|features)/|\.(?:git|travis|circleci)|appveyor)})
|
26
|
+
end
|
27
|
+
end
|
28
|
+
spec.bindir = "exe"
|
29
|
+
spec.executables = spec.files.grep(%r{\Aexe/}) { |f| File.basename(f) }
|
30
|
+
spec.require_paths = ["lib"]
|
31
|
+
|
32
|
+
# Uncomment to register a new dependency of your gem
|
33
|
+
spec.add_dependency "tttls1.3"
|
34
|
+
|
35
|
+
# For more information and examples about making a new gem, check out our
|
36
|
+
# guide at: https://bundler.io/guides/creating_gem.html
|
37
|
+
end
|
@@ -0,0 +1,37 @@
|
|
1
|
+
module Raioquic
|
2
|
+
class Buffer
|
3
|
+
# extend Forwardable
|
4
|
+
|
5
|
+
UINT_VAR_MAX: ::Integer
|
6
|
+
UINT_VAR_MAX_SIZE: 8
|
7
|
+
|
8
|
+
class BufferReadError < StandardError
|
9
|
+
end
|
10
|
+
class BufferWriteError < StandardError
|
11
|
+
end
|
12
|
+
|
13
|
+
def self.encode_uint_var: (Integer) -> String
|
14
|
+
def self.size_uint_var: (Integer) -> (1 | 2 | 4 | 8)
|
15
|
+
def initialize: (?capacity: Integer?, ?data: String) -> void
|
16
|
+
def dealloc: () -> nil
|
17
|
+
def data: () -> String
|
18
|
+
def tell: () -> ::Integer # delegated method
|
19
|
+
def seek: (Integer) -> void
|
20
|
+
def capacity: -> ::Integer
|
21
|
+
def data_slice: (start: Integer, ends: Integer) -> untyped
|
22
|
+
def pull_bytes: (Integer) -> String
|
23
|
+
def pull_uint8: () -> Integer
|
24
|
+
def pull_uint16: () -> Integer
|
25
|
+
def pull_uint32: () -> Integer
|
26
|
+
def pull_uint64: () -> Integer
|
27
|
+
def pull_uint_var: () -> Integer
|
28
|
+
def push_bytes: (String) -> void
|
29
|
+
def push_uint8: (Integer) -> void
|
30
|
+
def push_uint16: (Integer) -> void
|
31
|
+
def push_uint32: (Integer) -> void
|
32
|
+
def push_uint64: (Integer) -> void
|
33
|
+
def push_uint_var: (Integer) -> void
|
34
|
+
def encode_uint_var: (Integer) -> nil
|
35
|
+
private def check_read_bounds: (Integer) -> void
|
36
|
+
end
|
37
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
module Raioquic
|
2
|
+
module Crypto
|
3
|
+
class AESGCM
|
4
|
+
MAX_SIZE: Numeric
|
5
|
+
|
6
|
+
class OverflowError < StandardError
|
7
|
+
end
|
8
|
+
|
9
|
+
attr_reader key: ::String
|
10
|
+
|
11
|
+
def initialize: (String) -> void
|
12
|
+
def encrypt: (nonce: ::String, data: ::String, associated_data: ::String) -> ::String
|
13
|
+
| (nonce: ::String, data: ::String) -> ::String
|
14
|
+
def decrypt: (nonce: ::String, data: ::String, associated_data: ::String) -> ::String
|
15
|
+
| (nonce: ::String, data: ::String) -> ::String
|
16
|
+
def validate_length: (nonce: ::String, data: ::String) -> void
|
17
|
+
def check_nonce: (::String) -> void
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
@@ -0,0 +1,11 @@
|
|
1
|
+
module Raioquic
|
2
|
+
module Crypto
|
3
|
+
module Backend
|
4
|
+
class Aead
|
5
|
+
def self.aead_cipher_name: (::Raioquic::Crypto::AESGCM | untyped) -> String
|
6
|
+
def self.encrypt: (cipher: untyped, key: String, nonce: String, data: String, associated_data: Array[String?], tag_length: Integer) -> String
|
7
|
+
def self.decrypt: (cipher: untyped, key: String, nonce: String, data: String, associated_data: Array[String?], tag_length: Integer) -> String
|
8
|
+
end
|
9
|
+
end
|
10
|
+
end
|
11
|
+
end
|
@@ -0,0 +1,34 @@
|
|
1
|
+
module Raioquic
|
2
|
+
module Quic
|
3
|
+
module QuicConfiguration
|
4
|
+
attr_accessor alpn_protocols: ::Array[untyped]
|
5
|
+
attr_accessor connection_id_length: ::Integer
|
6
|
+
attr_accessor idle_timeout: ::Float
|
7
|
+
attr_accessor is_client: bool
|
8
|
+
attr_accessor max_data: ::Integer
|
9
|
+
attr_accessor max_stream_data: ::Integer
|
10
|
+
attr_accessor quic_logger: ::Raioquic::Quic::Logger::QuicLogger
|
11
|
+
attr_accessor secrets_log_file: untyped
|
12
|
+
attr_accessor server_name: ::String | nil
|
13
|
+
attr_accessor session_ticket: ::String | nil
|
14
|
+
attr_accessor cadata: ::String | nil
|
15
|
+
attr_accessor cafile: ::String | nil
|
16
|
+
attr_accessor capath: ::String | nil
|
17
|
+
attr_accessor certificate: untyped
|
18
|
+
attr_accessor certificate_chain: ::Array[untyped]
|
19
|
+
attr_accessor cipher_suites: ::Array[::Integer]
|
20
|
+
attr_accessor initial_rtt: ::Float
|
21
|
+
attr_accessor max_datagram_frame_size: ::Integer
|
22
|
+
attr_accessor private_key: untyped
|
23
|
+
attr_accessor quantam_readiness_test: bool
|
24
|
+
attr_accessor supported_versions: ::Array[::Integer]
|
25
|
+
attr_accessor verify_mode: ::Integer # OpenSSL::SSL::VERIFY_NONE or OpenSSL::SSL::VERIFY_PEER
|
26
|
+
|
27
|
+
def initialize: (untyped) -> void
|
28
|
+
def load_cert_chain: (::String certfile) -> void
|
29
|
+
| (::String certfile, ::String keyfile) -> void
|
30
|
+
| (::String certfile, ::String keyfile, ::String password) -> void
|
31
|
+
def load_verify_locations: (?cafile: ::String|nil, ?capath: ::String|nil, ?cadata: ::String|nil) -> void
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
@@ -0,0 +1,277 @@
|
|
1
|
+
module Raioquic
|
2
|
+
module Quic
|
3
|
+
module Connection
|
4
|
+
CRYPTO_BUFFER_SIZE: ::Integer
|
5
|
+
EPOCH_SHORTCUTS: ::Hash[::String, ::Integer]
|
6
|
+
MAX_EARLY_DATA: ::Integer
|
7
|
+
SECRETS_LABELS: ::Array[::Array[::String | nil]]
|
8
|
+
STREAM_FLAGS: ::Integer
|
9
|
+
STREAM_COUNT_MAX: ::Integer
|
10
|
+
UDP_HEADER_SIZE: 8
|
11
|
+
ACK_FRAME_CAPACITY: ::Integer
|
12
|
+
APPLICATION_CLOSE_FRAME_CAPACITY: ::Integer
|
13
|
+
CONNECTION_LIMIT_FRAME_CAPACITY: ::Integer
|
14
|
+
HANDSHAKE_DONE_FRAME_CAPACITY: ::Integer
|
15
|
+
MAX_STREAM_DATA_FRAME_CAPACITY: ::Integer
|
16
|
+
NEW_CONNECTION_ID_FRAME_CAPACITY: ::Integer
|
17
|
+
PATH_CHALLENGE_FRAME_CAPACITY: ::Integer
|
18
|
+
PATH_RESPONSE_FRAME_CAPACITY: ::Integer
|
19
|
+
PING_FRAME_CAPACITY: ::Integer
|
20
|
+
RESET_STREAM_FRAME_CAPACITY: ::Integer
|
21
|
+
RETIRE_CONNECTION_ID_CAPACITY: ::Integer
|
22
|
+
STOP_SENDING_FRAME_CAPACITY: ::Integer
|
23
|
+
STREAMS_BLOCKED_CAPACITY: ::Integer
|
24
|
+
TRANSPORT_CLOSE_FLAME_CAPACITY: ::Integer
|
25
|
+
|
26
|
+
def self.epochs: (::String shortcut) -> ::Array[::Integer]
|
27
|
+
def self.dump_cid: (::String cid) -> ::String
|
28
|
+
def self.get_epoch: (::Integer packet_type) -> ::Integer
|
29
|
+
def self.get_transport_parameters_extension: (::Integer version) -> ::Integer
|
30
|
+
def self.stream_is_client_initialized: (::Integer stream_id) -> bool
|
31
|
+
def self.stream_is_unidirectional: (::Integer stream_id) -> bool
|
32
|
+
|
33
|
+
class Limit
|
34
|
+
@frame_type: ::Integer
|
35
|
+
@name: ::String
|
36
|
+
@sent: ::Integer
|
37
|
+
@used: ::Integer
|
38
|
+
@value: ::Integer
|
39
|
+
|
40
|
+
attr_reader frame_type: ::Integer
|
41
|
+
|
42
|
+
attr_accessor used: ::Integer
|
43
|
+
attr_accessor sent: ::Integer
|
44
|
+
attr_accessor value: ::Integer
|
45
|
+
|
46
|
+
def initialize: (frame_type: ::Integer, name: ::String, value: ::Integer) -> void
|
47
|
+
end
|
48
|
+
|
49
|
+
class QuicConnectionError < Error
|
50
|
+
@error_code: ::Integer
|
51
|
+
@frame_type: ::Integer
|
52
|
+
@reason_phrase: ::String
|
53
|
+
end
|
54
|
+
|
55
|
+
# TODO: QuicConnectionAdapter
|
56
|
+
|
57
|
+
class QuicConnectionId
|
58
|
+
attr_accessor cid: ::String
|
59
|
+
attr_accessor sequence_number: ::Integer
|
60
|
+
attr_accessor stateless_reset_token: ::String
|
61
|
+
attr_accessor was_sent: bool
|
62
|
+
end
|
63
|
+
|
64
|
+
class QuicConnectionState
|
65
|
+
FIRSTFLIGHT: 0
|
66
|
+
CONNECTED: 1
|
67
|
+
CLOSING: 2
|
68
|
+
DRAINING: 3
|
69
|
+
TERMINATED: 4
|
70
|
+
end
|
71
|
+
|
72
|
+
class QuicNetworkPath
|
73
|
+
attr_accessor addr: untyped
|
74
|
+
attr_accessor bytes_received: ::Integer
|
75
|
+
attr_accessor bytes_sent: ::Integer
|
76
|
+
attr_accessor is_validated: bool
|
77
|
+
attr_accessor local_challenge: ::String | nil
|
78
|
+
attr_accessor remote_challenge: ::String | nil
|
79
|
+
|
80
|
+
def can_send: (::Integer size) -> bool
|
81
|
+
end
|
82
|
+
|
83
|
+
class QuicReceiveContext
|
84
|
+
attr_accessor epoch: ::Integer
|
85
|
+
attr_accessor host_cid: ::String
|
86
|
+
attr_accessor network_path: QuicNetworkPath
|
87
|
+
attr_accessor quic_logger_frames: ::Array[untyped] | nil
|
88
|
+
attr_accessor time: ::Float
|
89
|
+
end
|
90
|
+
|
91
|
+
END_STATES: ::Array[::Integer]
|
92
|
+
|
93
|
+
|
94
|
+
class QuicConnection
|
95
|
+
attr_reader configuration: QuicConfiguration
|
96
|
+
attr_reader original_destination_connection_id: ::String
|
97
|
+
attr_reader loss: Quic::Recovery::QuicPacketRecovery
|
98
|
+
attr_reader tls: ::Raioquic::TLS::Context
|
99
|
+
attr_reader local_max_streams_bidi: Limit
|
100
|
+
|
101
|
+
attr_accessor ack_delay: ::Float
|
102
|
+
attr_accessor is_client: bool
|
103
|
+
|
104
|
+
@configuration: QuicConfiguration
|
105
|
+
@is_client: bool
|
106
|
+
@ack_delay: ::Float
|
107
|
+
@close_at: ::Float | nil
|
108
|
+
@close_event: untyped # TODO: events
|
109
|
+
@connect_called: bool
|
110
|
+
@cryptos: ::Hash[::Integer, ::Raioquic::Quic::Crypto::CryptoPair]
|
111
|
+
@crypto_buffers: ::Hash[::Integer, ::Raioquic::Buffer]
|
112
|
+
@crypto_retransmitted: bool
|
113
|
+
@crypto_streams: ::Hash[::Integer, ::Raioquic::Quic::Stream::QuicStream] # TODO: QuicStream
|
114
|
+
@events: untyped # TODO: deque?
|
115
|
+
@handshake_complete: bool
|
116
|
+
@handshake_confirmed: bool
|
117
|
+
@host_cids: ::Array[QuicConnectionId]
|
118
|
+
@host_cid: ::String
|
119
|
+
@host_cid_seq: ::Integer
|
120
|
+
@local_ack_delay_exponent: ::Integer
|
121
|
+
@local_active_connection_id_limit: ::Integer
|
122
|
+
@local_initial_source_connection_id: ::String
|
123
|
+
@local_max_data: Limit
|
124
|
+
@local_max_stream_data_bidi_local: ::Integer
|
125
|
+
@local_max_stream_data_bidi_remote: ::Integer
|
126
|
+
@local_max_stream_data_uni: ::Integer
|
127
|
+
@local_max_streams_bidi: Limit
|
128
|
+
@local_max_streams_uni: Limit
|
129
|
+
@loss_at: ::Float | nil
|
130
|
+
@network_paths: ::Array[QuicNetworkPath]
|
131
|
+
@pacing_at: ::Float | nil
|
132
|
+
@packet_number: ::Integer
|
133
|
+
@parameters_received: bool
|
134
|
+
@peer_cid: QuicConnectionId
|
135
|
+
@peer_cid_available: ::Array[QuicConnectionId]
|
136
|
+
@peer_cid_sequence_numbers: ::Array[::Integer] # TODO: set
|
137
|
+
@peer_token: ::String
|
138
|
+
@quic_logger: ::Raioquic::Quic::Logger::QuicLoggerTrace
|
139
|
+
@remote_ack_delay_exponent: ::Integer
|
140
|
+
@remote_active_connection_id_limit: ::Integer
|
141
|
+
@remote_initial_source_connection_id: ::String | nil
|
142
|
+
@remote_max_idle_timeout: ::Float
|
143
|
+
@remote_max_data: ::Integer
|
144
|
+
@remote_max_data_used: ::Integer
|
145
|
+
@remote_max_datagram_frame_size: ::Integer | nil
|
146
|
+
@remote_max_stream_data_bidi_local: ::Integer
|
147
|
+
@remote_max_stream_data_bidi_remote: ::Integer
|
148
|
+
@remote_max_stream_data_uni: ::Integer
|
149
|
+
@remote_max_streams_bidi: ::Integer
|
150
|
+
@remote_max_streams_uni: ::Integer
|
151
|
+
@retry_count: ::Integer
|
152
|
+
@retry_source_connection_id: ::String | nil
|
153
|
+
@spaces: ::Hash[::Integer, Quic::Recovery::QuicPacketSpace]
|
154
|
+
@spin_bit: bool
|
155
|
+
@spin_highest_pn: ::Integer
|
156
|
+
@state: ::Integer
|
157
|
+
@streams: ::Hash[::Integer, Quic::Stream::QuicStream] # TODO: QuicStream
|
158
|
+
@streams_blocked_bidi: ::Array[untyped] # TODO: QuicStream
|
159
|
+
@streams_blocked_uni: ::Array[untyped] # TODO: QuicStream
|
160
|
+
@streams_finished: ::Array[::Integer] # TODO: ::Set
|
161
|
+
@version: ::Integer | nil
|
162
|
+
@version_negotiation_count: ::Integer
|
163
|
+
@original_destination_connection_id: ::String
|
164
|
+
@logger: untyped
|
165
|
+
@loss: Quic::Recovery::QuicPacketRecovery
|
166
|
+
@close_pending: bool
|
167
|
+
@datagrams_pending: untyped # TODO: set
|
168
|
+
@handshake_done_pending: bool
|
169
|
+
@ping_pending: ::Array[::Integer]
|
170
|
+
@probe_pending: bool
|
171
|
+
@retire_connection_ids: ::Array[::Integer]
|
172
|
+
@streams_blocked_pending: bool
|
173
|
+
@session_ticket_fetcher: untyped
|
174
|
+
@session_ticket_handler: untyped
|
175
|
+
@frame_handlers: ::Hash[::Integer, [::Symbol, ::Array[::Integer]]]
|
176
|
+
@tls: ::Raioquic::TLS::Context
|
177
|
+
|
178
|
+
def intialize: (
|
179
|
+
configuration: QuicConfiguration,
|
180
|
+
?original_destination_connection_id: ::String,
|
181
|
+
?retry_source_connection_id: ::String,
|
182
|
+
?session_ticket_fetcher: untyped,
|
183
|
+
?session_ticket_handler: untyped,
|
184
|
+
) -> void
|
185
|
+
def change_connection_id: () -> void
|
186
|
+
def close: (?error_code: ::Integer, ?frame_type: ::Integer|nil, ?reason_phrase: ::String) -> void
|
187
|
+
def connect: (addr: untyped, now: ::Float) -> void # TODO: type of addr
|
188
|
+
def datagrams_to_send: (now: ::Float) -> ::Array[[::String, untyped]] # TODO: NetworkAddress
|
189
|
+
def get_next_available_stream_id: (?is_unidirectional: bool) -> ::Integer
|
190
|
+
def get_timer: () -> (::Float | nil)
|
191
|
+
def handle_timer: (now: ::Float) -> void
|
192
|
+
def next_event: () -> (::Raioquic::Quic::Event::QuicEvent | nil)
|
193
|
+
def receive_datagram: (data: ::String, addr: untyped, now: ::Float) -> void # TODO: NetworkAddress
|
194
|
+
def request_key_update: () -> void
|
195
|
+
def reset_stream: (stream_id: ::Integer, error_code: ::Integer) -> void
|
196
|
+
def send_ping: (::Integer uid) -> void
|
197
|
+
def send_datagram_frame: (:String data) -> void
|
198
|
+
def send_stream_data: (stream_id: ::Integer, data: ::String, ?end_stream: bool) -> void
|
199
|
+
def stop_stream: (stream_id: ::Integer, error_code: ::Integer) -> void
|
200
|
+
private def alpn_handler: (::String alpn_protocol) -> void
|
201
|
+
private def assert_stream_can_receive: (frame_type: ::Integer, stream_id: ::Integer) -> void
|
202
|
+
private def assert_stream_can_send: (frame_type: ::Integer, stream_id: ::Integer) -> void
|
203
|
+
private def consume_peer_cid: () -> void
|
204
|
+
private def close_begin: (is_initiator: bool, now: ::Float) -> void
|
205
|
+
private def close_end: () -> void
|
206
|
+
private def _connect: (now: ::Float) -> void
|
207
|
+
private def discard_epoch: (::Integer epoch) -> void
|
208
|
+
private def find_network_path: (untyped addr) -> QuicNetworkPath # TODO: NetworkAddress
|
209
|
+
private def get_or_create_stream: (frame_type: ::Integer, stream_id: ::Integer) -> ::Raioquic::Quic::Stream::QuicStream
|
210
|
+
private def get_or_create_stream_for_send: (::Integer stream_id) -> ::Raioquic::Quic::Stream::QuicStream
|
211
|
+
private def handle_session_ticket: (::Raioquic::TLS::SessionTicket session_ticket) -> void
|
212
|
+
private def initialize_connection: (::String peer_cid) -> void
|
213
|
+
private def handle_ack_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
214
|
+
private def handle_connection_close_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
215
|
+
private def handle_crypto_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
216
|
+
private def handle_data_blocked_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
217
|
+
private def handle_datagram_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
218
|
+
private def handle_handshake_done_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
219
|
+
private def handle_max_data_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
220
|
+
private def handle_max_stream_data_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
221
|
+
private def handle_max_streams_bidi_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
222
|
+
private def handle_max_streams_uni_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
223
|
+
private def handle_new_connection_id_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
224
|
+
private def handle_new_token_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
225
|
+
private def handle_padding_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
226
|
+
private def handle_path_challenge_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
227
|
+
private def handle_path_response_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
228
|
+
private def handle_ping_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
229
|
+
private def handle_reset_stream_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
230
|
+
private def handle_retire_connection_id_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
231
|
+
private def handle_stop_sending_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
232
|
+
private def handle_stream_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
233
|
+
private def handle_stream_data_blocked_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
234
|
+
private def handle_streams_blocked_frame: (context: QuicReceiveContext, frame_type: ::Integer, buf: ::Raioquic::Buffer) -> void
|
235
|
+
private def log_key_retired: (key_type: ::String, trigger: ::String) -> void
|
236
|
+
private def log_key_updated: (key_type: ::String, trigger: ::String) -> void
|
237
|
+
private def on_ack_delivery: (delivery: ::Integer, space: ::Raioquic::Quic::Recovery::QuicPacketSpace, highest_acked: ::Integer) -> void
|
238
|
+
private def on_connection_limit_delivery: (delivery: ::Integer, limit: Limit) -> void
|
239
|
+
private def on_handshake_done_delivery: (delivery: ::Integer) -> void
|
240
|
+
private def on_max_stream_data_delivery: (delivery: ::Integer, stream: ::Raioquic::Quic::Stream::QuicStream) -> void
|
241
|
+
private def on_new_connection_id_delivery: (delivery: ::Integer, connection_id: QuicConnectionId) -> void
|
242
|
+
private def on_ping_delivery: (delivery: ::Integer, uids: ::Array[::Integer]) -> void
|
243
|
+
private def on_retire_connection_id_delivery: (delivery: ::Integer, sequence_number: ::Integer) -> void
|
244
|
+
private def payload_received: (context: QuicReceiveContext, plain: ::String) -> [bool, bool]
|
245
|
+
private def replenish_connection_ids: () -> void
|
246
|
+
private def retire_peer_cid: (QuicConnectionId connection_id) -> void
|
247
|
+
private def push_crypto_data: () -> void
|
248
|
+
private def send_probe: () -> void
|
249
|
+
private def parse_transport_parameters: (data: ::String, ?from_session_ticket: bool) -> void
|
250
|
+
private def serialize_transport_parameters: () -> ::String
|
251
|
+
private def set_state: (::Integer quic_connection_state) -> void
|
252
|
+
private def stream_can_receive: (::Integer stream_id) -> bool
|
253
|
+
private def stream_can_send: (::Integer stream_id) -> bool
|
254
|
+
private def unblock_streams: (bool is_unidirectional) -> void
|
255
|
+
private def update_traffic_key: (direction: ::Integer, epoch: ::Integer, cipher_suite: ::Integer, secret: ::String) -> void
|
256
|
+
private def write_application: (builder: ::Raioquic::Quic::PacketBuilder::QuicPacketBuilder, network_path: QuicNetworkPath, now: ::Float) -> void
|
257
|
+
private def write_handshake: (builder: ::Raioquic::Quic::PacketBuilder::QuicPacketBuilder, epoch: ::Integer, now: ::Float) -> void
|
258
|
+
private def write_ack_frame: (builder: ::Raioquic::Quic::PacketBuilder::QuicPacketBuilder, space: ::Raioquic::Quic::Recovery::QuicPacketSpace, now: ::Float) -> void
|
259
|
+
private def write_connection_close_frame: (builder: ::Raioquic::Quic::PacketBuilder::QuicPacketBuilder, epoch: ::Integer, error_code: ::Integer, ?frame_type: ::Integer, reason_phrase: ::String) -> void
|
260
|
+
private def write_connection_limits: (builder: ::Raioquic::Quic::PacketBuilder::QuicPacketBuilder, space: ::Raioquic::Quic::Recovery::QuicPacketSpace) -> void
|
261
|
+
private def write_crypto_frame: (builder: ::Raioquic::Quic::PacketBuilder::QuicPacketBuilder, space: ::Raioquic::Quic::Recovery::QuicPacketSpace, stream: ::Raioquic::Quic::Stream::QuicStream) -> bool
|
262
|
+
private def write_datagram_frame: (builder: ::Raioquic::Quic::PacketBuilder::QuicPacketBuilder, data: ::String, frame_type: ::Integer) -> bool
|
263
|
+
private def write_handshake_done_frame: (builder: ::Raioquic::Quic::PacketBuilder::QuicPacketBuilder) -> void
|
264
|
+
private def write_new_connection_id_frame: (builder: ::Raioquic::Quic::PacketBuilder::QuicPacketBuilder, connection_id: QuicConnectionId) -> void
|
265
|
+
private def write_path_challenge_frame: (builder: ::Raioquic::Quic::PacketBuilder::QuicPacketBuilder, challenge: ::String) -> void
|
266
|
+
private def write_path_response_frame: (builder: ::Raioquic::Quic::PacketBuilder::QuicPacketBuilder, challenge: ::String) -> void
|
267
|
+
private def write_ping_frame: (builder: ::Raioquic::Quic::PacketBuilder::QuicPacketBuilder, ?uids: ::Array[::Integer], ?comment: ::String) -> void
|
268
|
+
private def write_reset_stream_frame: (builder: ::Raioquic::Quic::PacketBuilder::QuicPacketBuilder, stream: ::Raioquic::Quic::Stream::QuicStream) -> void
|
269
|
+
private def write_retire_connection_id_frame: (builder: ::Raioquic::Quic::PacketBuilder::QuicPacketBuilder, sequence_number: ::Integer) -> void
|
270
|
+
private def write_stop_sending_frame: (builder: ::Raioquic::Quic::PacketBuilder::QuicPacketBuilder, stream: ::Raioquic::Quic::Stream::QuicStream) -> void
|
271
|
+
private def write_stream_frame: (builder: ::Raioquic::Quic::PacketBuilder::QuicPacketBuilder, space: ::Raioquic::Quic::Recovery::QuicPacketSpace, stream: ::Raioquic::Quic::Stream::QuicStream, max_offset: ::Integer) -> ::Integer
|
272
|
+
private def write_stream_limits: (builder: ::Raioquic::Quic::PacketBuilder::QuicPacketBuilder, space: ::Raioquic::Quic::Recovery::QuicPacketSpace, stream: ::Raioquic::Quic::Stream::QuicStream) -> void
|
273
|
+
private def write_streams_blocked_frame: (builder: ::Raioquic::Quic::PacketBuilder::QuicPacketBuilder, frame_type: ::Integer, limit: ::Integer) -> void
|
274
|
+
end
|
275
|
+
end
|
276
|
+
end
|
277
|
+
end
|
@@ -0,0 +1,88 @@
|
|
1
|
+
module Raioquic
|
2
|
+
module Quic
|
3
|
+
module Crypto
|
4
|
+
INITIAL_CIPHER_SUITE: untyped
|
5
|
+
AEAD_KEY_LENGTH_MAX: 32
|
6
|
+
AEAD_NONCE_LENGTH: 12
|
7
|
+
AEAD_TAG_LENGTH: 16
|
8
|
+
PACKET_LENGTH_MAX: 1500
|
9
|
+
PACKET_NUMBER_LENGTH_MAX: 4
|
10
|
+
SAMPLE_LENGTH: 16
|
11
|
+
INITIAL_SALT_VERSION_1: ::String
|
12
|
+
|
13
|
+
|
14
|
+
def self?.derive_key_iv_hp: (untyped, ::String) -> Array[::String]
|
15
|
+
def self?.xor_str: (::String, ::String) -> ::String
|
16
|
+
|
17
|
+
class CryptoError
|
18
|
+
end
|
19
|
+
|
20
|
+
class NoCallback
|
21
|
+
end
|
22
|
+
|
23
|
+
class CryptoContext
|
24
|
+
attr_reader aead: untyped
|
25
|
+
attr_reader key_phase: 0 | 1
|
26
|
+
attr_reader secret: nil | ::String
|
27
|
+
@aead: nil | AEAD
|
28
|
+
@cipher_suite: untyped # TODO: ?
|
29
|
+
@key_phase: 0 | 1
|
30
|
+
@secret: nil | ::String
|
31
|
+
@version: untyped # TODO: ::Raioquic::Quic::Packet::QuicProtocolVersion::VERSION_1
|
32
|
+
@setup_cb: NoCallback | untyped
|
33
|
+
@teardown_cb: NoCallback | untyped
|
34
|
+
@hp: HeaderProtection|nil
|
35
|
+
|
36
|
+
def initialize: (key_phase: 0|1, setup_cb: untyped, teardown_cb: untyped) -> void
|
37
|
+
| (setup_cb: untyped, teardown_cb: untyped) -> void
|
38
|
+
def decrypt_packet: (packet: ::String, encrypted_offset: ::Integer, expected_packet_number: ::Integer) -> [::String, ::String, ::Integer, bool]
|
39
|
+
def encrypt_packet: (plain_header: ::String, plain_payload: ::String, packet_number: ::Integer) -> ::String
|
40
|
+
def is_valid: () -> bool
|
41
|
+
def setup: (cipher_suite: untyped, secret: ::String, version: untyped) -> void
|
42
|
+
def teardown: () -> void
|
43
|
+
def apply_key_phase: (CryptoContext, ::String) -> void
|
44
|
+
def next_key_phase: () -> CryptoContext
|
45
|
+
end
|
46
|
+
|
47
|
+
class CryptoPair
|
48
|
+
attr_reader recv: CryptoContext
|
49
|
+
attr_reader send: CryptoContext
|
50
|
+
|
51
|
+
@aead_tag_size: ::Integer
|
52
|
+
@update_key_requested: bool
|
53
|
+
|
54
|
+
def initialize: (recv_setup_cb: NoCallback|untyped, recv_teardown_cb: NoCallback|untyped, send_setup_cb: NoCallback|untyped, send_teardown_cb: NoCallback|untyped) -> void
|
55
|
+
def decrypt_packet: (packet: ::String, encrypted_offset: ::Integer, expected_packet_number: ::Integer) -> [::String, ::String, ::Integer]
|
56
|
+
def encrypt_packet: (plain_header: ::String, plain_payload: ::Integer, packet_number: ::Integer) -> ::String
|
57
|
+
def setup_initial: (cid: ::String, is_client: bool, version: untyped) -> void
|
58
|
+
def teardown: () -> void
|
59
|
+
def key_phase: () -> ::Integer # TODO: 0 or 1
|
60
|
+
def update_key: () -> void
|
61
|
+
def _update_key: (::String) -> void
|
62
|
+
end
|
63
|
+
|
64
|
+
class AEAD
|
65
|
+
@cipher: OpenSSL::Cipher
|
66
|
+
@key: ::String
|
67
|
+
@iv: ::String
|
68
|
+
@cipher_name: ::String
|
69
|
+
|
70
|
+
def initialize: (cipher_name: ::String, key: ::String, iv: ::String) -> void
|
71
|
+
def decrypt: (data: ::String, associated_data: ::String, packet_number: ::Integer) -> ::String
|
72
|
+
def encrypt: (data: ::String, associated_data: ::String, packet_number: ::Integer) -> ::String
|
73
|
+
end
|
74
|
+
|
75
|
+
class HeaderProtection
|
76
|
+
@cipher: OpenSSL::Cipher
|
77
|
+
@key: ::String
|
78
|
+
@mask: ::String
|
79
|
+
@zero: ::String
|
80
|
+
|
81
|
+
def initialize: (cipher_name: ::String, key: ::String) -> void
|
82
|
+
def apply: (plain_header: ::String, protected_payload: ::String) -> ::String
|
83
|
+
def remove: (packet: ::String, encrypted_offset: ::Integer) -> [::String, ::Integer]
|
84
|
+
private def mask: (::String) -> ::String
|
85
|
+
end
|
86
|
+
end
|
87
|
+
end
|
88
|
+
end
|