Reenable the client SSLCompression advanced option.

Add spec for some of the additions to Rex::Proto::Http::Client
bug/bundler_fix
Joe Vennix 2013-11-20 01:03:13 -06:00
parent d51b92b06f
commit f8b57d45cd
3 changed files with 96 additions and 19 deletions

View File

@ -51,6 +51,7 @@ module Exploit::Remote::HttpClient
OptBool.new('DigestAuthIIS', [false, 'Conform to IIS, should work for most servers. Only set to false for non-IIS servers', true]),
OptBool.new('SSL', [ false, 'Negotiate SSL for outgoing connections', false]),
OptEnum.new('SSLVersion', [ false, 'Specify the version of SSL that should be used', 'SSL3', ['SSL2', 'SSL3', 'TLS1']]),
OptBool.new('SSLCompression', [ false, 'Enable SSL/TLS-level compression', false ]),
OptBool.new('FingerprintCheck', [ false, 'Conduct a pre-exploit fingerprint verification', true]),
OptString.new('DOMAIN', [ true, 'The domain to use for windows authentification', 'WORKSTATION'])
], self.class
@ -147,6 +148,7 @@ module Exploit::Remote::HttpClient
client_username = opts['username'] || datastore['USERNAME'] || ''
client_password = opts['password'] || datastore['PASSWORD'] || ''
ssl_compression = opts['SSLCompression'] || datastore['SSLCompression']
nclient = Rex::Proto::Http::Client.new(
opts['rhost'] || rhost,
@ -159,7 +161,8 @@ module Exploit::Remote::HttpClient
ssl_version,
proxies,
client_username,
client_password
client_password,
ssl_compression
)
# Configure the HTTP client with the supplied parameter
@ -187,14 +190,14 @@ module Exploit::Remote::HttpClient
'uri_fake_end' => datastore['HTTP::uri_fake_end'],
'uri_fake_params_start' => datastore['HTTP::uri_fake_params_start'],
'header_folding' => datastore['HTTP::header_folding'],
'usentlm2_session' => datastore['NTLM::UseNTLM2_session'],
'use_ntlmv2' => datastore['NTLM::UseNTLMv2'],
'send_lm' => datastore['NTLM::SendLM'],
'send_ntlm' => datastore['NTLM::SendNTLM'],
'SendSPN' => datastore['NTLM::SendSPN'],
'UseLMKey' => datastore['NTLM::UseLMKey'],
'domain' => datastore['DOMAIN'],
'DigestAuthIIS' => datastore['DigestAuthIIS']
'usentlm2_session' => datastore['NTLM::UseNTLM2_session'],
'use_ntlmv2' => datastore['NTLM::UseNTLMv2'],
'send_lm' => datastore['NTLM::SendLM'],
'send_ntlm' => datastore['NTLM::SendNTLM'],
'SendSPN' => datastore['NTLM::SendSPN'],
'UseLMKey' => datastore['NTLM::UseLMKey'],
'domain' => datastore['DOMAIN'],
'DigestAuthIIS' => datastore['DigestAuthIIS']
)
# If this connection is global, persist it

View File

@ -28,7 +28,8 @@ class Client
#
# Creates a new client instance
#
def initialize(host, port = 80, context = {}, ssl = nil, ssl_version = nil, proxies = nil, username = '', password = '')
def initialize(host, port = 80, context = {}, ssl = nil, ssl_version = nil, proxies = nil,
username = '', password = '', ssl_compression = false)
self.hostname = host
self.port = port.to_i
self.context = context
@ -37,6 +38,7 @@ class Client
self.proxies = proxies
self.username = username
self.password = password
self.ssl_compression = ssl_compression
# Take ClientRequest's defaults, but override with our own
self.config = Http::ClientRequest::DefaultConfig.merge({
@ -180,15 +182,16 @@ class Client
timeout = (t.nil? or t == -1) ? 0 : t
self.conn = Rex::Socket::Tcp.create(
'PeerHost' => self.hostname,
'PeerPort' => self.port.to_i,
'LocalHost' => self.local_host,
'LocalPort' => self.local_port,
'Context' => self.context,
'SSL' => self.ssl,
'SSLVersion'=> self.ssl_version,
'Proxies' => self.proxies,
'Timeout' => timeout
'PeerHost' => self.hostname,
'PeerPort' => self.port.to_i,
'LocalHost' => self.local_host,
'LocalPort' => self.local_port,
'Context' => self.context,
'SSL' => self.ssl,
'SSLVersion' => self.ssl_version,
'SSLCompression' => self.ssl_compression,
'Proxies' => self.proxies,
'Timeout' => timeout
)
end
@ -707,11 +710,16 @@ class Client
# When parsing the request, thunk off the first response from the server, since junk
attr_accessor :junk_pipeline
protected
# https
attr_accessor :ssl, :ssl_version # :nodoc:
# @return [Bool] use tls/ssl-level compression (gzip/rle)
attr_accessor :ssl_compression
attr_accessor :hostname, :port # :nodoc:

View File

@ -43,6 +43,7 @@ describe Rex::Proto::Http::Client do
cli.instance_variable_get(:@port).should == 80
cli.instance_variable_get(:@context).should == {}
cli.instance_variable_get(:@ssl).should be_false
cli.instance_variable_get(:@ssl_compression).should be_false
cli.instance_variable_get(:@proxies).should be_nil
cli.instance_variable_get(:@username).should be_empty
cli.instance_variable_get(:@password).should be_empty
@ -137,6 +138,69 @@ describe Rex::Proto::Http::Client do
end
context "when SSL is enabled" do
let(:hostname) { ip }
let(:port) { 80 }
let(:context) { Hash.new }
let(:ssl) { true }
let(:ssl_version) { nil }
let(:proxies) { nil }
let(:username) { '' }
let(:password) { '' }
let(:ssl_compression) { false }
subject(:cli) do
Rex::Proto::Http::Client.new(
hostname, port, context, ssl, ssl_version,
proxies, username, password, ssl_compression
)
end
describe '#ssl' do
it 'should return true' do
cli.send(:ssl).should be_true
end
end
describe '#connect' do
# prevent anything from dialing out.
before { Rex::Socket::Tcp.stub(:create => nil) }
it 'should call Rex::Socket::Tcp#create with a hash containing SSL => true' do
Rex::Socket::Tcp.should_receive(:create).once.with hash_including 'SSL' => ssl
cli.connect(1)
end
it 'should call Rex::Socket::Tcp#create with a hash containing SSLCompression => false' do
Rex::Socket::Tcp.should_receive(:create).once.with hash_including 'SSLCompression' => false
cli.connect(1)
end
end
context "when SSLVersion is set to TLS1" do
let(:ssl_version) { 'TLS1' }
describe '#connect' do
before { Rex::Socket::Tcp.stub(:create => nil) }
it 'should call Rex::Socket::Tcp#create with a hash containing SSLVersion => TLS1' do
Rex::Socket::Tcp.should_receive(:create).once.with(hash_including('SSLVersion' => ssl_version))
cli.connect(1)
end
end
context "when SSLCompression is set to true" do
let(:ssl_compression) { true }
it 'should call Rex::Socket::Tcp#create with a hash containing SSLCompression => true' do
Rex::Socket::Tcp.should_receive(:create).once.with(
hash_including('SSLCompression' => ssl_compression)
)
cli.connect(1)
end
end
end
end
it "should attempt to connect to a server" do
this_cli = Rex::Proto::Http::Client.new("127.0.0.1", 1)
expect { this_cli.connect(1) }.to raise_error ::Rex::ConnectionRefused
@ -222,9 +286,11 @@ describe Rex::Proto::Http::Client do
end
# Not super sure why these are protected...
# Me either...
it "should refuse access to its protected accessors" do
expect {cli.ssl}.to raise_error NoMethodError
expect {cli.ssl_version}.to raise_error NoMethodError
expect {cli.ssl_compression}.to raise_error NoMethodError
expect {cli.hostname}.to raise_error NoMethodError
expect {cli.port}.to raise_error NoMethodError
end