1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
| | # Copyright (C) 2014, all contributors <yahns-public@yhbt.net>
# License: GPLv3 or later (see COPYING for details)
require_relative 'sendfile_compat'
# this is to be included into a Kgio::Socket-derived class
# this requires Ruby 2.1 and later for "exception: false"
module Yahns::OpenSSLClient # :nodoc:
include Yahns::SendfileCompat
def yahns_init_ssl(ssl_ctx)
@need_accept = true
@ssl = OpenSSL::SSL::SSLSocket.new(self, ssl_ctx)
end
def kgio_trywrite(buf)
rv = @ssl.write_nonblock(buf, exception: false)
Integer === rv and
rv = buf.bytesize == rv ? nil : buf.byteslice(rv, buf.bytesize)
rv
end
def kgio_syssend(buf, flags)
kgio_trywrite(buf)
end
def kgio_tryread(len, buf)
if @need_accept
# most protocols require read before write, so we start the negotiation
# process here:
begin
@ssl.accept_nonblock
rescue IO::WaitReadable
return :wait_readable
rescue IO::WaitWritable
return :wait_writable
rescue OpenSSL::SSL::SSLError
return nil
end
@need_accept = false
end
@ssl.read_nonblock(len, buf, exception: false)
end
def close
@ssl.close # flushes SSLSocket
super # IO#close
end
end
|