Fix #4866, msfvenom not properly handling platform & arch

This fixes #4866, an issue with msfvenom not properly handling special
cases with generic payloads. So the story behind this fix is that
we have these two problems:

Problem 1: The current payload selection design relies on the payload
module in order to set the platform and arch. Almost all MSF payloads
contain a default platform and arch, however, the bind and reverse
generic payloads don't.

Problem 2: By default, Msf::Payload::Generic also explicitly sets the
PLATFORM and ARCH datastore options to nil. So there is no way the
payload generator can figure out what platform and arch to use.

As a result of these problems, msfvenom will actually end up getting
a Msf::Module::Platform as the default platform, which doesn't
actually represent any valid platform we can use (such as
Msf::Module::Platform::Windows). And the first item of ARCH_ALL for
the arch.

In addition, msfvenom has these two arguments that the user can use:
--platform and --arch. In most cases, these arguments are used more
like checks than actually setting anything. Because remember:
Framework's payload selector retreives the platform & arch from the
module (trusted), not the user input (untrusted). But from the user's
perspective it's impossible to know this.

After experimenting different ways to fix this, I came up with this
patch. It feels sort of more like a hack than a real fix, but as
far as I can tell, this is the best you can get unless you want to
redesign generic payload selection.
bug/bundler_fix
sinn3r 2015-04-09 16:01:11 -05:00
parent ec28992ce2
commit 56793d11c8
1 changed files with 16 additions and 0 deletions

View File

@ -144,8 +144,10 @@ module Msf
if arch.blank? if arch.blank?
@arch = mod.arch.first @arch = mod.arch.first
cli_print "No Arch selected, selecting Arch: #{arch} from the payload" cli_print "No Arch selected, selecting Arch: #{arch} from the payload"
datastore['ARCH'] = arch if mod.kind_of?(Msf::Payload::Generic)
return mod.arch.first return mod.arch.first
elsif mod.arch.include? arch elsif mod.arch.include? arch
datastore['ARCH'] = arch if mod.kind_of?(Msf::Payload::Generic)
return arch return arch
else else
return nil return nil
@ -157,7 +159,10 @@ module Msf
# @param mod [Msf::Payload] The module class to choose a platform for # @param mod [Msf::Payload] The module class to choose a platform for
# @return [Msf::Module::PlatformList] The selected platform list # @return [Msf::Module::PlatformList] The selected platform list
def choose_platform(mod) def choose_platform(mod)
# By default, platform_list will at least return Msf::Module::Platform
# if there is absolutely no pre-configured platform info at all
chosen_platform = platform_list chosen_platform = platform_list
if chosen_platform.platforms.empty? if chosen_platform.platforms.empty?
chosen_platform = mod.platform chosen_platform = mod.platform
cli_print "No platform was selected, choosing #{chosen_platform.platforms.first} from the payload" cli_print "No platform was selected, choosing #{chosen_platform.platforms.first} from the payload"
@ -165,6 +170,17 @@ module Msf
elsif (chosen_platform & mod.platform).empty? elsif (chosen_platform & mod.platform).empty?
chosen_platform = Msf::Module::PlatformList.new chosen_platform = Msf::Module::PlatformList.new
end end
begin
platform_object = Msf::Module::Platform.find_platform(platform)
rescue ArgumentError
platform_object = nil
end
if mod.kind_of?(Msf::Payload::Generic) && mod.send(:module_info)['Platform'].empty? && platform_object
datastore['PLATFORM'] = platform
end
chosen_platform chosen_platform
end end