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