@@ -1610,73 +1610,10 @@ def connect
16101610 s . setsockopt ( Socket ::IPPROTO_TCP , Socket ::TCP_NODELAY , 1 )
16111611 debug "opened"
16121612 if use_ssl?
1613- if proxy?
1614- plain_sock = BufferedIO . new ( s , read_timeout : @read_timeout ,
1615- write_timeout : @write_timeout ,
1616- continue_timeout : @continue_timeout ,
1617- debug_output : @debug_output )
1618- buf = "CONNECT #{ conn_address } :#{ @port } HTTP/#{ HTTPVersion } \r \n "
1619- buf << "Host: #{ @address } :#{ @port } \r \n "
1620- if proxy_user
1621- credential = [ "#{ proxy_user } :#{ proxy_pass } " ] . pack ( 'm0' )
1622- buf << "Proxy-Authorization: Basic #{ credential } \r \n "
1623- end
1624- buf << "\r \n "
1625- plain_sock . write ( buf )
1626- HTTPResponse . read_new ( plain_sock ) . value
1627- # assuming nothing left in buffers after successful CONNECT response
1628- end
1629-
1630- ssl_parameters = Hash . new
1631- iv_list = instance_variables
1632- SSL_IVNAMES . each_with_index do |ivname , i |
1633- if iv_list . include? ( ivname )
1634- value = instance_variable_get ( ivname )
1635- unless value . nil?
1636- ssl_parameters [ SSL_ATTRIBUTES [ i ] ] = value
1637- end
1638- end
1639- end
1640- @ssl_context . set_params ( ssl_parameters )
1641- unless @ssl_context . session_cache_mode . nil? # a dummy method on JRuby
1642- @ssl_context . session_cache_mode =
1643- OpenSSL ::SSL ::SSLContext ::SESSION_CACHE_CLIENT |
1644- OpenSSL ::SSL ::SSLContext ::SESSION_CACHE_NO_INTERNAL_STORE
1645- end
1646- if @ssl_context . respond_to? ( :session_new_cb ) # not implemented under JRuby
1647- @ssl_context . session_new_cb = proc { |sock , sess | @ssl_session = sess }
1648- end
1649-
1650- # Still do the post_connection_check below even if connecting
1651- # to IP address
1652- verify_hostname = @ssl_context . verify_hostname
1653-
1654- # Server Name Indication (SNI) RFC 3546/6066
1655- case @address
1656- when Resolv ::IPv4 ::Regex , Resolv ::IPv6 ::Regex
1657- # don't set SNI, as IP addresses in SNI is not valid
1658- # per RFC 6066, section 3.
1659-
1660- # Avoid openssl warning
1661- @ssl_context . verify_hostname = false
1662- else
1663- ssl_host_address = @address
1664- end
1665-
1666- debug "starting SSL for #{ conn_addr } :#{ conn_port } ..."
1667- s = OpenSSL ::SSL ::SSLSocket . new ( s , @ssl_context )
1668- s . sync_close = true
1669- s . hostname = ssl_host_address if s . respond_to? ( :hostname= ) && ssl_host_address
1670-
1671- if @ssl_session and
1672- Process . clock_gettime ( Process ::CLOCK_REALTIME ) < @ssl_session . time . to_f + @ssl_session . timeout
1673- s . session = @ssl_session
1674- end
1675- ssl_socket_connect ( s , @open_timeout )
1676- if ( @ssl_context . verify_mode != OpenSSL ::SSL ::VERIFY_NONE ) && verify_hostname
1677- s . post_connection_check ( @address )
1678- end
1679- debug "SSL established, protocol: #{ s . ssl_version } , cipher: #{ s . cipher [ 0 ] } "
1613+ proxy_connect ( s , conn_address ) if proxy?
1614+ setup_ssl_context
1615+ s = setup_ssl_socket ( s , conn_addr , conn_port )
1616+ ssl_connect ( s )
16801617 end
16811618 @socket = BufferedIO . new ( s , read_timeout : @read_timeout ,
16821619 write_timeout : @write_timeout ,
@@ -1693,6 +1630,85 @@ def connect
16931630 end
16941631 private :connect
16951632
1633+ def proxy_connect ( s , conn_address )
1634+ plain_sock = BufferedIO . new ( s , read_timeout : @read_timeout ,
1635+ write_timeout : @write_timeout ,
1636+ continue_timeout : @continue_timeout ,
1637+ debug_output : @debug_output )
1638+ buf = "CONNECT #{ conn_address } :#{ @port } HTTP/#{ HTTPVersion } \r \n "
1639+ buf << "Host: #{ @address } :#{ @port } \r \n "
1640+ if proxy_user
1641+ credential = [ "#{ proxy_user } :#{ proxy_pass } " ] . pack ( 'm0' )
1642+ buf << "Proxy-Authorization: Basic #{ credential } \r \n "
1643+ end
1644+ buf << "\r \n "
1645+ plain_sock . write ( buf )
1646+ HTTPResponse . read_new ( plain_sock ) . value
1647+ # assuming nothing left in buffers after successful CONNECT response
1648+ end
1649+ private :proxy_connect
1650+
1651+ def setup_ssl_context
1652+ ssl_parameters = Hash . new
1653+ iv_list = instance_variables
1654+ SSL_IVNAMES . each_with_index do |ivname , i |
1655+ if iv_list . include? ( ivname )
1656+ value = instance_variable_get ( ivname )
1657+ unless value . nil?
1658+ ssl_parameters [ SSL_ATTRIBUTES [ i ] ] = value
1659+ end
1660+ end
1661+ end
1662+ @ssl_context . set_params ( ssl_parameters )
1663+ unless @ssl_context . session_cache_mode . nil? # a dummy method on JRuby
1664+ @ssl_context . session_cache_mode =
1665+ OpenSSL ::SSL ::SSLContext ::SESSION_CACHE_CLIENT |
1666+ OpenSSL ::SSL ::SSLContext ::SESSION_CACHE_NO_INTERNAL_STORE
1667+ end
1668+ if @ssl_context . respond_to? ( :session_new_cb ) # not implemented under JRuby
1669+ @ssl_context . session_new_cb = proc { |sock , sess | @ssl_session = sess }
1670+ end
1671+ end
1672+ private :setup_ssl_context
1673+
1674+ def setup_ssl_socket ( s , conn_addr , conn_port )
1675+ # Still do the post_connection_check below even if connecting
1676+ # to IP address
1677+ verify_hostname = @ssl_context . verify_hostname
1678+
1679+ # Server Name Indication (SNI) RFC 3546/6066
1680+ case @address
1681+ when Resolv ::IPv4 ::Regex , Resolv ::IPv6 ::Regex
1682+ # don't set SNI, as IP addresses in SNI is not valid
1683+ # per RFC 6066, section 3.
1684+
1685+ # Avoid openssl warning
1686+ @ssl_context . verify_hostname = false
1687+ else
1688+ ssl_host_address = @address
1689+ end
1690+
1691+ debug "starting SSL for #{ conn_addr } :#{ conn_port } ..."
1692+ s = OpenSSL ::SSL ::SSLSocket . new ( s , @ssl_context )
1693+ s . sync_close = true
1694+ s . hostname = ssl_host_address if s . respond_to? ( :hostname= ) && ssl_host_address
1695+ s
1696+ end
1697+ private :setup_ssl_socket
1698+
1699+ def ssl_connect ( s )
1700+ if @ssl_session and
1701+ Process . clock_gettime ( Process ::CLOCK_REALTIME ) < @ssl_session . time . to_f + @ssl_session . timeout
1702+ s . session = @ssl_session
1703+ end
1704+ ssl_socket_connect ( s , @open_timeout )
1705+ if ( @ssl_context . verify_mode != OpenSSL ::SSL ::VERIFY_NONE ) && verify_hostname
1706+ s . post_connection_check ( @address )
1707+ end
1708+ debug "SSL established, protocol: #{ s . ssl_version } , cipher: #{ s . cipher [ 0 ] } "
1709+ end
1710+ private :ssl_connect
1711+
16961712 def on_connect
16971713 end
16981714 private :on_connect
0 commit comments