Skip to content

Commit ed74c37

Browse files
committed
Proxy session events.
This enables modules to use report_loot with a remote data service
1 parent f88840e commit ed74c37

File tree

10 files changed

+138
-3
lines changed

10 files changed

+138
-3
lines changed

lib/metasploit/framework/data_service/proxy/data_proxy_auto_loader.rb

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ module DataProxyAutoLoader
1313
autoload :SessionDataProxy, 'metasploit/framework/data_service/proxy/session_data_proxy'
1414
autoload :ExploitDataProxy, 'metasploit/framework/data_service/proxy/exploit_data_proxy'
1515
autoload :LootDataProxy, 'metasploit/framework/data_service/proxy/loot_data_proxy'
16+
autoload :SessionEventDataProxy, 'metasploit/framework/data_service/proxy/session_event_data_proxy'
1617
include ServiceDataProxy
1718
include HostDataProxy
1819
include VulnDataProxy
@@ -23,4 +24,5 @@ module DataProxyAutoLoader
2324
include SessionDataProxy
2425
include ExploitDataProxy
2526
include LootDataProxy
27+
include SessionEventDataProxy
2628
end
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
module SessionEventDataProxy
2+
3+
def report_session_event(opts)
4+
begin
5+
data_service = self.get_data_service()
6+
# The full Session object contains in-memory instances of data we do not need to store.
7+
opts[:session] = opts[:session].sid
8+
data_service.report_session_event(opts)
9+
rescue Exception => e
10+
puts "Call to #{data_service.class}#report_session_event threw exception: #{e.message}"
11+
end
12+
end
13+
end

lib/metasploit/framework/data_service/remote/http/core.rb

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -59,7 +59,9 @@ def post_data(path, data_hash)
5959
end
6060
rescue Exception => e
6161
puts "Problem with POST request: #{e.message}"
62-
puts "#{e.backtrace}"
62+
e.backtrace.each do |line|
63+
puts "#{line}\n"
64+
end
6365
ensure
6466
@client_pool << client
6567
end

lib/metasploit/framework/data_service/remote/http/data_service_auto_loader.rb

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ module DataServiceAutoLoader
1212
autoload :RemoteSessionDataService, 'metasploit/framework/data_service/remote/http/remote_session_data_service'
1313
autoload :RemoteExploitDataService, 'metasploit/framework/data_service/remote/http/remote_exploit_data_service'
1414
autoload :RemoteLootDataService, 'metasploit/framework/data_service/remote/http/remote_loot_data_service'
15+
autoload :RemoteSessionEventDataService, 'metasploit/framework/data_service/remote/http/remote_session_event_data_service'
1516
include RemoteHostDataService
1617
include RemoteEventDataService
1718
include RemoteNoteDataService
@@ -22,4 +23,5 @@ module DataServiceAutoLoader
2223
include RemoteSessionDataService
2324
include RemoteExploitDataService
2425
include RemoteLootDataService
26+
include RemoteSessionEventDataService
2527
end
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
require 'metasploit/framework/data_service/remote/http/response_data_helper'
2+
3+
module RemoteSessionEventDataService
4+
include ResponseDataHelper
5+
6+
SESSION_EVENT_PATH = '/api/1/msf/session_event'
7+
SESSION_EVENT_SEARCH_PATH = SESSION_EVENT_PATH + "/search"
8+
9+
def report_session_event(opts)
10+
self.post_data_async(SESSION_EVENT_PATH, opts)
11+
end
12+
end
Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
module SessionEventDataService
2+
3+
def report_session_event(opts)
4+
raise 'SessionEventDataService#report_session_event is not implemented'
5+
end
6+
end
Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
module SessionEventServlet
2+
3+
def self.api_path
4+
'/api/1/msf/session_event'
5+
end
6+
7+
def self.registered(app)
8+
app.get SessionEventServlet.api_path, &get_session_event
9+
app.post SessionEventServlet.api_path, &report_session_event
10+
end
11+
12+
#######
13+
private
14+
#######
15+
16+
def self.get_session_event
17+
lambda {
18+
begin
19+
opts = parse_json_request(request, false)
20+
data = get_db().session_events(opts)
21+
set_json_response(data)
22+
rescue Exception => e
23+
set_error_on_response(e)
24+
end
25+
}
26+
end
27+
28+
def self.report_session_event
29+
lambda {
30+
job = lambda { |opts| get_db().report_session_event(opts) }
31+
exec_report_job(request, &job)
32+
}
33+
end
34+
end

lib/msf/core/db_manager/http/sinatra_app.rb

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
require 'msf/core/db_manager/http/servlet/session_servlet'
1313
require 'msf/core/db_manager/http/servlet/exploit_servlet'
1414
require 'msf/core/db_manager/http/servlet/loot_servlet'
15+
require 'msf/core/db_manager/http/servlet/session_event_servlet'
1516

1617
class SinatraApp < Sinatra::Base
1718

@@ -31,5 +32,6 @@ class SinatraApp < Sinatra::Base
3132
register SessionServlet
3233
register ExploitServlet
3334
register LootServlet
35+
register SessionEventServlet
3436

3537
end

lib/msf/ui/console/command_dispatcher/db.rb

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1184,7 +1184,7 @@ def cmd_loot_help
11841184

11851185
def cmd_loot(*args)
11861186
return unless active?
1187-
::ActiveRecord::Base.connection_pool.with_connection {
1187+
11881188
mode = :search
11891189
host_ranges = []
11901190
types = nil
@@ -1329,7 +1329,6 @@ def cmd_loot(*args)
13291329
print_line
13301330
print_line(tbl.to_s)
13311331
print_status("Deleted #{delete_count} loots") if delete_count > 0
1332-
}
13331332
end
13341333

13351334
# :category: Deprecated Commands

lib/msf/util/host.rb

Lines changed: 63 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,63 @@
1+
# -*- coding: binary -*-
2+
3+
module Msf
4+
module Util
5+
module Host
6+
7+
#
8+
# Returns something suitable for the +:host+ parameter to the various report_* methods
9+
#
10+
# Takes a Host object, a Session object, an Msf::Session object or a String
11+
# address
12+
#
13+
def self.normalize_host(host)
14+
return host if defined?(::Mdm) && host.kind_of?(::Mdm::Host)
15+
norm_host = nil
16+
17+
puts "in normalize host. host is #{host}"
18+
if (host.kind_of? String)
19+
20+
if Rex::Socket.is_ipv4?(host)
21+
# If it's an IPv4 addr with a port on the end, strip the port
22+
if host =~ /((\d{1,3}\.){3}\d{1,3}):\d+/
23+
norm_host = $1
24+
else
25+
norm_host = host
26+
end
27+
elsif Rex::Socket.is_ipv6?(host)
28+
# If it's an IPv6 addr, drop the scope
29+
address, scope = host.split('%', 2)
30+
norm_host = address
31+
else
32+
norm_host = Rex::Socket.getaddress(host, true)
33+
end
34+
elsif defined?(::Mdm) && host.kind_of?(::Mdm::Session)
35+
norm_host = host.host
36+
elsif host.respond_to?(:session_host)
37+
# Then it's an Msf::Session object
38+
norm_host = host.session_host
39+
end
40+
41+
# If we got here and don't have a norm_host yet, it could be a
42+
# Msf::Session object with an empty or nil tunnel_host and tunnel_peer;
43+
# see if it has a socket and use its peerhost if so.
44+
if (
45+
norm_host.nil? &&
46+
host.respond_to?(:sock) &&
47+
host.sock.respond_to?(:peerhost) &&
48+
host.sock.peerhost.to_s.length > 0
49+
)
50+
norm_host = session.sock.peerhost
51+
end
52+
# If We got here and still don't have a real host, there's nothing left
53+
# to try, just log it and return what we were given
54+
if !norm_host
55+
dlog("Host could not be normalized: #{host.inspect}")
56+
norm_host = host
57+
end
58+
59+
norm_host
60+
end
61+
end
62+
end
63+
end

0 commit comments

Comments
 (0)