Module: Msf::Payload::Generic

Defined in:
lib/msf/core/payload/generic.rb

Overview

The generic payloads are used to define a generalized payload type that is both architecture and platform independent. Under the hood, generic payloads seek out the correct payload for the appropriate architecture and platform that is being targeted.

Instance Attribute Summary collapse

Instance Method Summary collapse

Instance Attribute Details

#actual_payloadObject (protected)

The actual underlying platform/arch-specific payload instance that should be used.



170
171
172
# File 'lib/msf/core/payload/generic.rb', line 170

def actual_payload
  @actual_payload
end

#explicit_archObject

Accessor that makes it possible to define an explicit architecture. This is used for things like payload regeneration.



162
163
164
# File 'lib/msf/core/payload/generic.rb', line 162

def explicit_arch
  @explicit_arch
end

#explicit_platformObject

Accessor that makes it possible to define an explicit platform. This is used for things like payload regeneration.



157
158
159
# File 'lib/msf/core/payload/generic.rb', line 157

def explicit_platform
  @explicit_platform
end

Instance Method Details

#actual_archObject (protected)

Returns the actual architecture that should be used for the payload.



199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
# File 'lib/msf/core/payload/generic.rb', line 199

def actual_arch
  arch = nil

  if explicit_arch.nil? == false
    arch = explicit_arch
  elsif datastore['ARCH']
    arch = datastore['ARCH']
  elsif assoc_exploit
    arch = assoc_exploit.target_arch || ARCH_X86
  end

  # If we still have an invalid architecture, then we suck.
  if arch.nil?
    raise NoCompatiblePayloadError, "An architecture could not be determined by the generic payload"
  elsif arch.kind_of?(String)
    arch = [ arch ]
  end

  return arch
end

#actual_platformObject (protected)

Returns the actual platform that should be used for the payload.



175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
# File 'lib/msf/core/payload/generic.rb', line 175

def actual_platform
  platform = nil

  if explicit_platform.nil? == false
    platform = explicit_platform
  elsif datastore['PLATFORM']
    platform = datastore['PLATFORM']
  elsif assoc_exploit
    platform = assoc_exploit.target_platform
  end

  # If we still have an invalid platform, then we suck.
  if platform.nil?
    raise NoCompatiblePayloadError, "A platform could not be determined by the generic payload"
  elsif platform.kind_of?(String)
    platform = Msf::Module::PlatformList.transform(platform)
  end

  return platform
end

#compatible_encodersObject



75
76
77
# File 'lib/msf/core/payload/generic.rb', line 75

def compatible_encoders
  redirect_to_actual(:compatible_encoders)
end

#compatible_nopsObject



79
80
81
# File 'lib/msf/core/payload/generic.rb', line 79

def compatible_nops
  redirect_to_actual(:compatible_nops)
end

#find_actual_payloadObject (protected)



220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
# File 'lib/msf/core/payload/generic.rb', line 220

def find_actual_payload
  return if not actual_payload.nil?

  # Look for one based on the exploit's compatible set
  if(assoc_exploit)
    self.actual_payload = framework.payloads.find_payload_from_set(
      assoc_exploit.compatible_payloads,
      actual_platform,
      actual_arch,
      handler_klass,
      session,
      payload_type)
  end

  # Fall back to the generic match (ignores size, compat flags, etc)
  if(actual_payload.nil?)
    self.actual_payload = framework.payloads.find_payload(
      actual_platform,
      actual_arch,
      handler_klass,
      session,
      payload_type)
  end

  if actual_payload.nil?
    raise NoCompatiblePayloadError, "Could not locate a compatible payload for #{actual_platform.names.join("/")}/#{actual_arch}"
  else
    dlog("Selected payload #{actual_payload.refname} from generic payload #{refname}", 'core', LEV_2)
    # Share our datastore with the actual payload so that it has the
    # appropriate values to substitute ad so on.
    self.actual_payload.share_datastore(self.datastore)

    # Set the associated exploit for the payload.
    self.actual_payload.assoc_exploit  = self.assoc_exploit

    # Set the parent payload to this payload so that we can handle
    # things like session creation (so that event notifications will
    # work properly)
    self.actual_payload.parent_payload = self

    # Set the cached user_input/user_output
    self.actual_payload.user_input  = self.user_input
    self.actual_payload.user_output = self.user_output
  end


end

#generate(_opts = {}) ⇒ Object

Generate is different from other methods – it will try to re-detect the actual payload in case settings have changed. Other methods will use the cached version if possible.



46
47
48
49
50
# File 'lib/msf/core/payload/generic.rb', line 46

def generate(_opts = {})
  reset

  redirect_to_actual(:generate)
end

#generate_stage(opts = {}) ⇒ Object



115
116
117
# File 'lib/msf/core/payload/generic.rb', line 115

def generate_stage(opts={})
  redirect_to_actual(:generate_stage, opts)
end

#handle_connection(*args) ⇒ Object



83
84
85
# File 'lib/msf/core/payload/generic.rb', line 83

def handle_connection(*args)
  redirect_to_actual(:handle_connection, *args)
end

#handle_connection_stage(*args) ⇒ Object



119
120
121
# File 'lib/msf/core/payload/generic.rb', line 119

def handle_connection_stage(*args)
  redirect_to_actual(:handle_connection_stage, *args)
end

#handle_intermediate_stage(*args) ⇒ Object



123
124
125
# File 'lib/msf/core/payload/generic.rb', line 123

def handle_intermediate_stage(*args)
  redirect_to_actual(:handle_intermediate_stage, *args)
end

#initialize(info = {}) ⇒ Object

Registers options that are common to all generic payloads, such as platform and arch.



19
20
21
22
23
24
25
26
27
28
29
# File 'lib/msf/core/payload/generic.rb', line 19

def initialize(info = {})
  super(merge_info(info,
    'Arch'     => ARCH_ALL - [ARCH_TTY],
    'Platform' => ''
  ))

  register_advanced_options([
    OptString.new('PLATFORM', [false, "The platform that is being targeted", nil]),
    OptString.new('ARCH', [false, "The architecture that is being targeted", nil])
  ], Msf::Payload::Generic)
end

#offsetsObject



63
64
65
# File 'lib/msf/core/payload/generic.rb', line 63

def offsets
  redirect_to_actual(:offsets)
end

#on_session(*args) ⇒ Object



87
88
89
# File 'lib/msf/core/payload/generic.rb', line 87

def on_session(*args)
  redirect_to_actual(:on_session, *args)
end

#payloadObject

Overrides – we have to redirect all potential payload methods to the actual payload so that they get handled appropriately, cuz we’re like a proxy and stuff. We can’t use method_undefined because all of these methods are actually defined.



59
60
61
# File 'lib/msf/core/payload/generic.rb', line 59

def payload
  redirect_to_actual(:payload)
end

#redirect_to_actual(name, *args) ⇒ Object

First, find the underlying payload and then pass all methods onto it.



148
149
150
151
# File 'lib/msf/core/payload/generic.rb', line 148

def redirect_to_actual(name, *args)
  find_actual_payload
  actual_payload.send(name, *args)
end

#replace_var(*args) ⇒ Object



71
72
73
# File 'lib/msf/core/payload/generic.rb', line 71

def replace_var(*args)
  redirect_to_actual(:replace_var, *args)
end

#resetObject

Reset’s the generic payload’s internal state so that it can find a new actual payload.



35
36
37
38
39
# File 'lib/msf/core/payload/generic.rb', line 35

def reset
  self.explicit_arch     = nil
  self.explicit_platform = nil
  self.actual_payload    = nil
end

#stage_offsetsObject



99
100
101
# File 'lib/msf/core/payload/generic.rb', line 99

def stage_offsets
  redirect_to_actual(:stage_offsets)
end

#stage_over_connection?Boolean

Returns:

  • (Boolean)


111
112
113
# File 'lib/msf/core/payload/generic.rb', line 111

def stage_over_connection?
  redirect_to_actual(:stage_over_connection?)
end

#stage_payload(*args) ⇒ Object

Stager overrides



95
96
97
# File 'lib/msf/core/payload/generic.rb', line 95

def stage_payload(*args)
  redirect_to_actual(:stage_payload, *args)
end

#stage_prefixObject



127
128
129
# File 'lib/msf/core/payload/generic.rb', line 127

def stage_prefix
  redirect_to_actual(:stage_prefix)
end

#stage_prefix=(*args) ⇒ Object



131
132
133
# File 'lib/msf/core/payload/generic.rb', line 131

def stage_prefix=(*args)
  redirect_to_actual(:stage_prefix=, *args)
end

#stager_offsetsObject



107
108
109
# File 'lib/msf/core/payload/generic.rb', line 107

def stager_offsets
  redirect_to_actual(:stager_offsets)
end

#stager_payloadObject



103
104
105
# File 'lib/msf/core/payload/generic.rb', line 103

def stager_payload
  redirect_to_actual(:stager_payload)
end

#substitute_vars(*args) ⇒ Object



67
68
69
# File 'lib/msf/core/payload/generic.rb', line 67

def substitute_vars(*args)
  redirect_to_actual(:substitute_vars, *args)
end

#user_input=(h) ⇒ Object



135
136
137
138
# File 'lib/msf/core/payload/generic.rb', line 135

def user_input=(h)
  @user_input = h
  redirect_to_actual(:user_input, h) if actual_payload
end

#user_output=(h) ⇒ Object



140
141
142
143
# File 'lib/msf/core/payload/generic.rb', line 140

def user_output=(h)
  @user_output = h
  redirect_to_actual(:user_output, h) if actual_payload
end