jruby-openssl 0.11.0.cr1-java → 0.12.2-java

Sign up to get free protection for your applications and to get access to all the features.
Files changed (59) hide show
  1. checksums.yaml +5 -5
  2. data/History.md +45 -0
  3. data/Mavenfile +20 -25
  4. data/README.md +3 -0
  5. data/Rakefile +21 -35
  6. data/lib/jopenssl/load.rb +49 -14
  7. data/lib/jopenssl/version.rb +2 -1
  8. data/lib/jopenssl.jar +0 -0
  9. data/lib/openssl/bn.rb +40 -9
  10. data/lib/openssl/buffering.rb +478 -9
  11. data/lib/openssl/cipher.rb +67 -9
  12. data/lib/openssl/config.rb +496 -12
  13. data/lib/openssl/digest.rb +73 -9
  14. data/lib/openssl/hmac.rb +13 -0
  15. data/lib/openssl/marshal.rb +30 -0
  16. data/lib/openssl/pkcs5.rb +3 -3
  17. data/lib/openssl/pkey.rb +42 -5
  18. data/lib/openssl/ssl.rb +543 -9
  19. data/lib/openssl/x509.rb +369 -9
  20. data/lib/openssl.rb +3 -1
  21. data/pom.xml +35 -126
  22. metadata +9 -44
  23. data/lib/jopenssl19/openssl/bn.rb +0 -29
  24. data/lib/jopenssl19/openssl/buffering.rb +0 -449
  25. data/lib/jopenssl19/openssl/cipher.rb +0 -28
  26. data/lib/jopenssl19/openssl/config.rb +0 -472
  27. data/lib/jopenssl19/openssl/digest.rb +0 -32
  28. data/lib/jopenssl19/openssl/ssl-internal.rb +0 -223
  29. data/lib/jopenssl19/openssl/ssl.rb +0 -2
  30. data/lib/jopenssl19/openssl/x509-internal.rb +0 -115
  31. data/lib/jopenssl19/openssl/x509.rb +0 -2
  32. data/lib/jopenssl19/openssl.rb +0 -22
  33. data/lib/jopenssl21/openssl/bn.rb +0 -28
  34. data/lib/jopenssl21/openssl/buffering.rb +0 -1
  35. data/lib/jopenssl21/openssl/cipher.rb +0 -1
  36. data/lib/jopenssl21/openssl/config.rb +0 -1
  37. data/lib/jopenssl21/openssl/digest.rb +0 -1
  38. data/lib/jopenssl21/openssl/ssl.rb +0 -1
  39. data/lib/jopenssl21/openssl/x509.rb +0 -119
  40. data/lib/jopenssl21/openssl.rb +0 -22
  41. data/lib/jopenssl22/openssl/bn.rb +0 -39
  42. data/lib/jopenssl22/openssl/buffering.rb +0 -456
  43. data/lib/jopenssl22/openssl/cipher.rb +0 -28
  44. data/lib/jopenssl22/openssl/config.rb +0 -313
  45. data/lib/jopenssl22/openssl/digest.rb +0 -54
  46. data/lib/jopenssl22/openssl/ssl.rb +0 -330
  47. data/lib/jopenssl22/openssl/x509.rb +0 -139
  48. data/lib/jopenssl22/openssl.rb +0 -22
  49. data/lib/jopenssl23/openssl/bn.rb +0 -38
  50. data/lib/jopenssl23/openssl/buffering.rb +0 -455
  51. data/lib/jopenssl23/openssl/cipher.rb +0 -25
  52. data/lib/jopenssl23/openssl/config.rb +0 -474
  53. data/lib/jopenssl23/openssl/digest.rb +0 -43
  54. data/lib/jopenssl23/openssl/pkey.rb +0 -25
  55. data/lib/jopenssl23/openssl/ssl.rb +0 -508
  56. data/lib/jopenssl23/openssl/x509.rb +0 -208
  57. data/lib/jopenssl23/openssl.rb +0 -19
  58. data/lib/openssl/ssl-internal.rb +0 -5
  59. data/lib/openssl/x509-internal.rb +0 -5
@@ -1,313 +0,0 @@
1
- =begin
2
- = Ruby-space definitions that completes C-space funcs for Config
3
-
4
- = Info
5
- Copyright (C) 2010 Hiroshi Nakamura <nahi@ruby-lang.org>
6
-
7
- = Licence
8
- This program is licenced under the same licence as Ruby.
9
- (See the file 'LICENCE'.)
10
-
11
- =end
12
-
13
- require 'stringio'
14
-
15
- module OpenSSL
16
- class Config
17
- include Enumerable
18
-
19
- class << self
20
- def parse(str)
21
- c = new()
22
- parse_config(StringIO.new(str)).each do |section, hash|
23
- c[section] = hash
24
- end
25
- c
26
- end
27
-
28
- alias load new
29
-
30
- def parse_config(io)
31
- begin
32
- parse_config_lines(io)
33
- rescue ConfigError => e
34
- e.message.replace("error in line #{io.lineno}: " + e.message)
35
- raise
36
- end
37
- end
38
-
39
- def get_key_string(data, section, key) # :nodoc:
40
- if v = data[section] && data[section][key]
41
- return v
42
- elsif section == 'ENV'
43
- if v = ENV[key]
44
- return v
45
- end
46
- end
47
- if v = data['default'] && data['default'][key]
48
- return v
49
- end
50
- end
51
-
52
- private
53
-
54
- def parse_config_lines(io)
55
- section = 'default'
56
- data = {section => {}}
57
- while definition = get_definition(io)
58
- definition = clear_comments(definition)
59
- next if definition.empty?
60
- if definition[0] == ?[
61
- if /\[([^\]]*)\]/ =~ definition
62
- section = $1.strip
63
- data[section] ||= {}
64
- else
65
- raise ConfigError, "missing close square bracket"
66
- end
67
- else
68
- if /\A([^:\s]*)(?:::([^:\s]*))?\s*=(.*)\z/ =~ definition
69
- if $2
70
- section = $1
71
- key = $2
72
- else
73
- key = $1
74
- end
75
- value = unescape_value(data, section, $3)
76
- (data[section] ||= {})[key] = value.strip
77
- else
78
- raise ConfigError, "missing equal sign"
79
- end
80
- end
81
- end
82
- data
83
- end
84
-
85
- # escape with backslash
86
- QUOTE_REGEXP_SQ = /\A([^'\\]*(?:\\.[^'\\]*)*)'/
87
- # escape with backslash and doubled dq
88
- QUOTE_REGEXP_DQ = /\A([^"\\]*(?:""[^"\\]*|\\.[^"\\]*)*)"/
89
- # escaped char map
90
- ESCAPE_MAP = {
91
- "r" => "\r",
92
- "n" => "\n",
93
- "b" => "\b",
94
- "t" => "\t",
95
- }
96
-
97
- def unescape_value(data, section, value)
98
- scanned = []
99
- while m = value.match(/['"\\$]/)
100
- scanned << m.pre_match
101
- c = m[0]
102
- value = m.post_match
103
- case c
104
- when "'"
105
- if m = value.match(QUOTE_REGEXP_SQ)
106
- scanned << m[1].gsub(/\\(.)/, '\\1')
107
- value = m.post_match
108
- else
109
- break
110
- end
111
- when '"'
112
- if m = value.match(QUOTE_REGEXP_DQ)
113
- scanned << m[1].gsub(/""/, '').gsub(/\\(.)/, '\\1')
114
- value = m.post_match
115
- else
116
- break
117
- end
118
- when "\\"
119
- c = value.slice!(0, 1)
120
- scanned << (ESCAPE_MAP[c] || c)
121
- when "$"
122
- ref, value = extract_reference(value)
123
- refsec = section
124
- if ref.index('::')
125
- refsec, ref = ref.split('::', 2)
126
- end
127
- if v = get_key_string(data, refsec, ref)
128
- scanned << v
129
- else
130
- raise ConfigError, "variable has no value"
131
- end
132
- else
133
- raise 'must not reaced'
134
- end
135
- end
136
- scanned << value
137
- scanned.join
138
- end
139
-
140
- def extract_reference(value)
141
- rest = ''
142
- if m = value.match(/\(([^)]*)\)|\{([^}]*)\}/)
143
- value = m[1] || m[2]
144
- rest = m.post_match
145
- elsif [?(, ?{].include?(value[0])
146
- raise ConfigError, "no close brace"
147
- end
148
- if m = value.match(/[a-zA-Z0-9_]*(?:::[a-zA-Z0-9_]*)?/)
149
- return m[0], m.post_match + rest
150
- else
151
- raise
152
- end
153
- end
154
-
155
- def clear_comments(line)
156
- # FCOMMENT
157
- if m = line.match(/\A([\t\n\f ]*);.*\z/)
158
- return m[1]
159
- end
160
- # COMMENT
161
- scanned = []
162
- while m = line.match(/[#'"\\]/)
163
- scanned << m.pre_match
164
- c = m[0]
165
- line = m.post_match
166
- case c
167
- when '#'
168
- line = nil
169
- break
170
- when "'", '"'
171
- regexp = (c == "'") ? QUOTE_REGEXP_SQ : QUOTE_REGEXP_DQ
172
- scanned << c
173
- if m = line.match(regexp)
174
- scanned << m[0]
175
- line = m.post_match
176
- else
177
- scanned << line
178
- line = nil
179
- break
180
- end
181
- when "\\"
182
- scanned << c
183
- scanned << line.slice!(0, 1)
184
- else
185
- raise 'must not reaced'
186
- end
187
- end
188
- scanned << line
189
- scanned.join
190
- end
191
-
192
- def get_definition(io)
193
- if line = get_line(io)
194
- while /[^\\]\\\z/ =~ line
195
- if extra = get_line(io)
196
- line += extra
197
- else
198
- break
199
- end
200
- end
201
- return line.strip
202
- end
203
- end
204
-
205
- def get_line(io)
206
- if line = io.gets
207
- line.gsub(/[\r\n]*/, '')
208
- end
209
- end
210
- end
211
-
212
- def initialize(filename = nil)
213
- @data = {}
214
- if filename
215
- File.open(filename.to_s) do |file|
216
- Config.parse_config(file).each do |section, hash|
217
- self[section] = hash
218
- end
219
- end
220
- end
221
- end
222
-
223
- def get_value(section, key)
224
- if section.nil?
225
- raise TypeError.new('nil not allowed')
226
- end
227
- section = 'default' if section.empty?
228
- get_key_string(section, key)
229
- end
230
-
231
- def value(arg1, arg2 = nil)
232
- warn('Config#value is deprecated; use Config#get_value')
233
- if arg2.nil?
234
- section, key = 'default', arg1
235
- else
236
- section, key = arg1, arg2
237
- end
238
- section ||= 'default'
239
- section = 'default' if section.empty?
240
- get_key_string(section, key)
241
- end
242
-
243
- def add_value(section, key, value)
244
- check_modify
245
- (@data[section] ||= {})[key] = value
246
- end
247
-
248
- def [](section)
249
- @data[section] || {}
250
- end
251
-
252
- def section(name)
253
- warn('Config#section is deprecated; use Config#[]')
254
- @data[name] || {}
255
- end
256
-
257
- def []=(section, pairs)
258
- check_modify
259
- @data[section] ||= {}
260
- pairs.each do |key, value|
261
- self.add_value(section, key, value)
262
- end
263
- end
264
-
265
- def sections
266
- @data.keys
267
- end
268
-
269
- def to_s
270
- ary = []
271
- @data.keys.sort.each do |section|
272
- ary << "[ #{section} ]\n"
273
- @data[section].keys.each do |key|
274
- ary << "#{key}=#{@data[section][key]}\n"
275
- end
276
- ary << "\n"
277
- end
278
- ary.join
279
- end
280
-
281
- def each
282
- @data.each do |section, hash|
283
- hash.each do |key, value|
284
- yield [section, key, value]
285
- end
286
- end
287
- end
288
-
289
- def inspect
290
- "#<#{self.class.name} sections=#{sections.inspect}>"
291
- end
292
-
293
- protected
294
-
295
- def data
296
- @data
297
- end
298
-
299
- private
300
-
301
- def initialize_copy(other)
302
- @data = other.data.dup
303
- end
304
-
305
- def check_modify
306
- raise TypeError.new("Insecure: can't modify OpenSSL config") if frozen?
307
- end
308
-
309
- def get_key_string(section, key)
310
- Config.get_key_string(@data, section, key)
311
- end
312
- end
313
- end
@@ -1,54 +0,0 @@
1
- #--
2
- #
3
- # $RCSfile$
4
- #
5
- # = Ruby-space predefined Digest subclasses
6
- #
7
- # = Info
8
- # 'OpenSSL for Ruby 2' project
9
- # Copyright (C) 2002 Michal Rokos <m.rokos@sh.cvut.cz>
10
- # All rights reserved.
11
- #
12
- # = Licence
13
- # This program is licenced under the same licence as Ruby.
14
- # (See the file 'LICENCE'.)
15
- #
16
- # = Version
17
- # $Id$
18
- #
19
- #++
20
-
21
- module OpenSSL
22
- class Digest
23
- # Deprecated.
24
- #
25
- # This class is only provided for backwards compatibility.
26
- class Digest < Digest # :nodoc:
27
- # Deprecated.
28
- #
29
- # See OpenSSL::Digest.new
30
- def initialize(*args)
31
- warn('Digest::Digest is deprecated; use Digest')
32
- super(*args)
33
- end
34
- end
35
-
36
- end # Digest
37
-
38
- # Returns a Digest subclass by +name+.
39
- #
40
- # require 'openssl'
41
- #
42
- # OpenSSL::Digest("MD5")
43
- # # => OpenSSL::Digest::MD5
44
- #
45
- # Digest("Foo")
46
- # # => NameError: wrong constant name Foo
47
-
48
- def Digest(name)
49
- OpenSSL::Digest.const_get(name)
50
- end
51
-
52
- module_function :Digest
53
-
54
- end # OpenSSL
@@ -1,330 +0,0 @@
1
- =begin
2
- = $RCSfile$ -- Ruby-space definitions that completes C-space funcs for SSL
3
-
4
- = Info
5
- 'OpenSSL for Ruby 2' project
6
- Copyright (C) 2001 GOTOU YUUZOU <gotoyuzo@notwork.org>
7
- All rights reserved.
8
-
9
- = Licence
10
- This program is licenced under the same licence as Ruby.
11
- (See the file 'LICENCE'.)
12
-
13
- = Version
14
- $Id$
15
- =end
16
-
17
- require "openssl/buffering"
18
- require "fcntl"
19
-
20
- module OpenSSL
21
- module SSL
22
- class SSLContext
23
- DEFAULT_PARAMS = {
24
- :ssl_version => "SSLv23",
25
- :verify_mode => OpenSSL::SSL::VERIFY_PEER,
26
- :ciphers => %w{
27
- ECDHE-ECDSA-AES128-GCM-SHA256
28
- ECDHE-RSA-AES128-GCM-SHA256
29
- ECDHE-ECDSA-AES256-GCM-SHA384
30
- ECDHE-RSA-AES256-GCM-SHA384
31
- DHE-RSA-AES128-GCM-SHA256
32
- DHE-DSS-AES128-GCM-SHA256
33
- DHE-RSA-AES256-GCM-SHA384
34
- DHE-DSS-AES256-GCM-SHA384
35
- ECDHE-ECDSA-AES128-SHA256
36
- ECDHE-RSA-AES128-SHA256
37
- ECDHE-ECDSA-AES128-SHA
38
- ECDHE-RSA-AES128-SHA
39
- ECDHE-ECDSA-AES256-SHA384
40
- ECDHE-RSA-AES256-SHA384
41
- ECDHE-ECDSA-AES256-SHA
42
- ECDHE-RSA-AES256-SHA
43
- DHE-RSA-AES128-SHA256
44
- DHE-RSA-AES256-SHA256
45
- DHE-RSA-AES128-SHA
46
- DHE-RSA-AES256-SHA
47
- DHE-DSS-AES128-SHA256
48
- DHE-DSS-AES256-SHA256
49
- DHE-DSS-AES128-SHA
50
- DHE-DSS-AES256-SHA
51
- AES128-GCM-SHA256
52
- AES256-GCM-SHA384
53
- AES128-SHA256
54
- AES256-SHA256
55
- AES128-SHA
56
- AES256-SHA
57
- ECDHE-ECDSA-RC4-SHA
58
- ECDHE-RSA-RC4-SHA
59
- RC4-SHA
60
- }.join(":"),
61
- :options => -> {
62
- opts = OpenSSL::SSL::OP_ALL
63
- opts &= ~OpenSSL::SSL::OP_DONT_INSERT_EMPTY_FRAGMENTS if defined?(OpenSSL::SSL::OP_DONT_INSERT_EMPTY_FRAGMENTS)
64
- opts |= OpenSSL::SSL::OP_NO_COMPRESSION if defined?(OpenSSL::SSL::OP_NO_COMPRESSION)
65
- opts |= OpenSSL::SSL::OP_NO_SSLv2 if defined?(OpenSSL::SSL::OP_NO_SSLv2)
66
- opts |= OpenSSL::SSL::OP_NO_SSLv3 if defined?(OpenSSL::SSL::OP_NO_SSLv3)
67
- opts
68
- }.call
69
- } unless const_defined? :DEFAULT_PARAMS # JRuby does it in Java
70
-
71
- begin
72
- DEFAULT_CERT_STORE = OpenSSL::X509::Store.new
73
- DEFAULT_CERT_STORE.set_default_paths
74
- if defined?(OpenSSL::X509::V_FLAG_CRL_CHECK_ALL)
75
- DEFAULT_CERT_STORE.flags = OpenSSL::X509::V_FLAG_CRL_CHECK_ALL
76
- end
77
- end unless const_defined? :DEFAULT_CERT_STORE
78
-
79
- ##
80
- # Sets the parameters for this SSL context to the values in +params+.
81
- # The keys in +params+ must be assignment methods on SSLContext.
82
- #
83
- # If the verify_mode is not VERIFY_NONE and ca_file, ca_path and
84
- # cert_store are not set then the system default certificate store is
85
- # used.
86
-
87
- def set_params(params={})
88
- params = DEFAULT_PARAMS.merge(params)
89
- params.each { |name, value| self.__send__("#{name}=", value) }
90
- if self.verify_mode != OpenSSL::SSL::VERIFY_NONE
91
- unless self.ca_file or self.ca_path or self.cert_store
92
- self.cert_store = DEFAULT_CERT_STORE
93
- end
94
- end
95
- return params
96
- end unless method_defined? :set_params
97
- end
98
-
99
- module SocketForwarder
100
- def addr
101
- to_io.addr
102
- end
103
-
104
- def peeraddr
105
- to_io.peeraddr
106
- end
107
-
108
- def setsockopt(level, optname, optval)
109
- to_io.setsockopt(level, optname, optval)
110
- end
111
-
112
- def getsockopt(level, optname)
113
- to_io.getsockopt(level, optname)
114
- end
115
-
116
- def fcntl(*args)
117
- to_io.fcntl(*args)
118
- end
119
-
120
- def closed?
121
- to_io.closed?
122
- end
123
-
124
- def do_not_reverse_lookup=(flag)
125
- to_io.do_not_reverse_lookup = flag
126
- end
127
- end
128
-
129
- module Nonblock
130
- def initialize(*args)
131
- flag = File::NONBLOCK
132
- flag |= @io.fcntl(Fcntl::F_GETFL) if defined?(Fcntl::F_GETFL)
133
- @io.fcntl(Fcntl::F_SETFL, flag)
134
- super
135
- end
136
- end unless const_defined? :Nonblock # JRuby: hooked up in "native" Java
137
-
138
- def verify_certificate_identity(cert, hostname)
139
- should_verify_common_name = true
140
- cert.extensions.each { |ext|
141
- next if ext.oid != "subjectAltName"
142
- ext.value.split(/,\s+/).each { |general_name|
143
- #case san.tag
144
- # MRI 2.2.3 (JRuby parses ASN.1 differently)
145
- #when 2 # dNSName in GeneralName (RFC5280)
146
- if /\ADNS:(.*)/ =~ general_name
147
- should_verify_common_name = false
148
- return true if verify_hostname(hostname, $1)
149
- # MRI 2.2.3 (JRuby parses ASN.1 differently)
150
- #when 7 # iPAddress in GeneralName (RFC5280)
151
- elsif /\AIP(?: Address)?:(.*)/ =~ general_name
152
- should_verify_common_name = false
153
- return true if $1 == hostname
154
- # NOTE: bellow logic makes little sense JRuby reads exts differently
155
- # follows GENERAL_NAME_print() in x509v3/v3_alt.c
156
- #if san.value.size == 4
157
- # return true if san.value.unpack('C*').join('.') == hostname
158
- #elsif san.value.size == 16
159
- # return true if san.value.unpack('n*').map { |e| sprintf("%X", e) }.join(':') == hostname
160
- #end
161
- end
162
- }
163
- }
164
- if should_verify_common_name
165
- cert.subject.to_a.each{|oid, value|
166
- if oid == "CN"
167
- return true if verify_hostname(hostname, value)
168
- end
169
- }
170
- end
171
- return false
172
- end
173
- module_function :verify_certificate_identity
174
-
175
- def verify_hostname(hostname, san) # :nodoc:
176
- # RFC 5280, IA5String is limited to the set of ASCII characters
177
- return false unless san.ascii_only?
178
- return false unless hostname.ascii_only?
179
-
180
- # See RFC 6125, section 6.4.1
181
- # Matching is case-insensitive.
182
- san_parts = san.downcase.split(".")
183
-
184
- # TODO: this behavior should probably be more strict
185
- return san == hostname if san_parts.size < 2
186
-
187
- # Matching is case-insensitive.
188
- host_parts = hostname.downcase.split(".")
189
-
190
- # RFC 6125, section 6.4.3, subitem 2.
191
- # If the wildcard character is the only character of the left-most
192
- # label in the presented identifier, the client SHOULD NOT compare
193
- # against anything but the left-most label of the reference
194
- # identifier (e.g., *.example.com would match foo.example.com but
195
- # not bar.foo.example.com or example.com).
196
- return false unless san_parts.size == host_parts.size
197
-
198
- # RFC 6125, section 6.4.3, subitem 1.
199
- # The client SHOULD NOT attempt to match a presented identifier in
200
- # which the wildcard character comprises a label other than the
201
- # left-most label (e.g., do not match bar.*.example.net).
202
- return false unless verify_wildcard(host_parts.shift, san_parts.shift)
203
-
204
- san_parts.join(".") == host_parts.join(".")
205
- end
206
- module_function :verify_hostname
207
-
208
- def verify_wildcard(domain_component, san_component) # :nodoc:
209
- parts = san_component.split("*", -1)
210
-
211
- return false if parts.size > 2
212
- return san_component == domain_component if parts.size == 1
213
-
214
- # RFC 6125, section 6.4.3, subitem 3.
215
- # The client SHOULD NOT attempt to match a presented identifier
216
- # where the wildcard character is embedded within an A-label or
217
- # U-label of an internationalized domain name.
218
- return false if domain_component.start_with?("xn--") && san_component != "*"
219
-
220
- parts[0].length + parts[1].length < domain_component.length &&
221
- domain_component.start_with?(parts[0]) &&
222
- domain_component.end_with?(parts[1])
223
- end
224
- module_function :verify_wildcard
225
-
226
- class SSLSocket
227
- include Buffering
228
- include SocketForwarder
229
- include Nonblock
230
-
231
- def sysclose
232
- return if closed?
233
- stop
234
- io.close if sync_close
235
- end unless method_defined? :sysclose
236
-
237
- ##
238
- # Perform hostname verification after an SSL connection is established
239
- #
240
- # This method MUST be called after calling #connect to ensure that the
241
- # hostname of a remote peer has been verified.
242
- def post_connection_check(hostname)
243
- if peer_cert.nil?
244
- msg = "Peer verification enabled, but no certificate received."
245
- if using_anon_cipher?
246
- msg += " Anonymous cipher suite #{cipher[0]} was negotiated. Anonymous suites must be disabled to use peer verification."
247
- end
248
- raise SSLError, msg
249
- end
250
-
251
- unless OpenSSL::SSL.verify_certificate_identity(peer_cert, hostname)
252
- raise SSLError, "hostname \"#{hostname}\" does not match the server certificate"
253
- end
254
- return true
255
- end
256
-
257
- private
258
-
259
- def using_anon_cipher?
260
- ctx = OpenSSL::SSL::SSLContext.new
261
- ctx.ciphers = "aNULL"
262
- ctx.ciphers.include?(cipher)
263
- end
264
- end
265
-
266
- ##
267
- # SSLServer represents a TCP/IP server socket with Secure Sockets Layer.
268
- class SSLServer
269
- include SocketForwarder
270
- # When true then #accept works exactly the same as TCPServer#accept
271
- attr_accessor :start_immediately
272
-
273
- # Creates a new instance of SSLServer.
274
- # * +srv+ is an instance of TCPServer.
275
- # * +ctx+ is an instance of OpenSSL::SSL::SSLContext.
276
- def initialize(svr, ctx)
277
- @svr = svr
278
- @ctx = ctx
279
- unless ctx.session_id_context
280
- # see #6137 - session id may not exceed 32 bytes
281
- prng = ::Random.new($0.hash)
282
- session_id = prng.bytes(16).unpack('H*')[0]
283
- @ctx.session_id_context = session_id
284
- end
285
- @start_immediately = true
286
- end
287
-
288
- # Returns the TCPServer passed to the SSLServer when initialized.
289
- def to_io
290
- @svr
291
- end
292
-
293
- # See TCPServer#listen for details.
294
- def listen(backlog=5)
295
- @svr.listen(backlog)
296
- end
297
-
298
- # See BasicSocket#shutdown for details.
299
- def shutdown(how=Socket::SHUT_RDWR)
300
- @svr.shutdown(how)
301
- end
302
-
303
- # Works similar to TCPServer#accept.
304
- def accept
305
- # Socket#accept returns [socket, addrinfo].
306
- # TCPServer#accept returns a socket.
307
- # The following comma strips addrinfo.
308
- sock, = @svr.accept
309
- begin
310
- ssl = OpenSSL::SSL::SSLSocket.new(sock, @ctx)
311
- ssl.sync_close = true
312
- ssl.accept if @start_immediately
313
- ssl
314
- rescue Exception => ex
315
- if ssl
316
- ssl.close
317
- else
318
- sock.close
319
- end
320
- raise ex
321
- end
322
- end
323
-
324
- # See IO#close for details.
325
- def close
326
- @svr.close
327
- end
328
- end
329
- end
330
- end