diff --git a/lib/msf/core/module.rb b/lib/msf/core/module.rb index f36d5ee257..cbd313a017 100644 --- a/lib/msf/core/module.rb +++ b/lib/msf/core/module.rb @@ -52,6 +52,14 @@ class Module return module_info['Name'] end + # + # Returns the module's alias, if it has one. Otherwise, the module's + # name is returned. + # + def alias + return module_info['Alias'] || name + end + # # Return the module's description # diff --git a/lib/msf/ui/console/command_dispatcher/core.rb b/lib/msf/ui/console/command_dispatcher/core.rb index e154f42303..0429c30726 100644 --- a/lib/msf/ui/console/command_dispatcher/core.rb +++ b/lib/msf/ui/console/command_dispatcher/core.rb @@ -90,10 +90,20 @@ class Core # Dump the contents of the active datastore if no args were supplied if (args.length == 0) + tbl = Table.new( + Table::Style::Default, + 'Columns' => + [ + 'Name', + 'Value' + ]) + datastore.each_pair { |name, value| - print_line("#{name}: #{value}") + tbl << [ name, value ] } + print(tbl.to_s) + return true elsif (args.length < 2) print( @@ -111,6 +121,31 @@ class Core print_line("#{name} => #{value}") end + # Unsets a value if it's been set + def cmd_unset(args) + # Determine which data store we're operating on + if (mod = get_active_module()) + datastore = mod.datastore + else + datastore = driver.datastore + end + + # No arguments? No cookie. + if (args.length == 0) + print( + "Usage: unset var1 var2 var3 ...\n\n" + + "The unset command is used to unset one or more variables.\n") + + return false + end + + while ((val = args.shift)) + print_line("Unsetting #{val}...") + + datastore.delete(val) + end + end + # Displays the list of modules based on their type, or all modules if # no type is provided def cmd_show(args) @@ -206,15 +241,33 @@ protected end def show_module_set(type, module_set) - print_line("#{type}:") + + tbl = Table.new( + Table::Style::Default, + 'Header' => type, + 'Prefix' => "\n", + 'Postfix' => "\n", + 'Columns' => + [ + 'Name', + 'Description' + ], + 'ColProps' => + { + 'Name' => + { + # Default max width to 25 + 'MaxWidth' => 25 + } + }) module_set.each_module { |mod| instance = mod.new - print_line("#{instance.class} #{instance.name}") + tbl << [ instance.alias, instance.description ] } - print_line + print(tbl.to_s) end end diff --git a/lib/msf/ui/console/table.rb b/lib/msf/ui/console/table.rb index be997c0d5e..4689346f4d 100644 --- a/lib/msf/ui/console/table.rb +++ b/lib/msf/ui/console/table.rb @@ -19,15 +19,38 @@ class Table < Rex::Ui::Text::Table end def initialize(style, opts = {}) - if (style == Style::Default) + self.style = style + + if (self.style == Style::Default) opts['Indent'] = 3 - opts['Prefix'] = "\n\n" - opts['Postfix'] = "\n\n" + if (!opts['Prefix']) + opts['Prefix'] = "\n\n" + end + if (!opts['Postfix']) + opts['Postfix'] = "\n\n" + end super(opts) end end + def header_to_s + return super + "\n" + end + + # Print nothing if there are no rows if the style is default + def to_s + if (style == Style::Default) + return '' if (rows.length == 0) + end + + super + end + +protected + + attr_accessor :style + end end diff --git a/lib/rex/ui/text/table.rb b/lib/rex/ui/text/table.rb index fc34527872..c0433d0344 100644 --- a/lib/rex/ui/text/table.rb +++ b/lib/rex/ui/text/table.rb @@ -14,6 +14,8 @@ module Text class Table def initialize(opts = {}) + self.header = opts['Header'] + self.headeri = opts['HeaderIndent'] || 0 self.columns = opts['Columns'] || [] self.rows = opts['Rows'] || [] @@ -24,11 +26,23 @@ class Table self.postfix = opts['Postfix'] || '' self.colprops = [] + # Default column properties self.columns.length.times { |idx| self.colprops[idx] = {} self.colprops[idx]['MaxWidth'] = self.columns[idx].length } + # Merge in options + if (opts['ColProps']) + opts['ColProps'].each_key { |col| + idx = self.columns.index(col) + + if (idx) + self.colprops[idx].merge!(opts['ColProps'][col]) + end + } + end + end # @@ -36,6 +50,7 @@ class Table # def to_s str = prefix + str += header_to_s || '' str += columns_to_s || '' str += hr_to_s || '' @@ -88,6 +103,7 @@ class Table alias p print + attr_accessor :header, :headeri attr_accessor :columns, :rows, :colprops attr_accessor :width, :indent, :cellpad attr_accessor :prefix, :postfix @@ -113,6 +129,21 @@ protected return ((row.kind_of?(String)) && (row == '__hr__')) end + # + # :nodoc: + # + # Returns the header string + # + def header_to_s + if (header) + pad = " " * headeri + + return pad + header + "\n" + pad + "=" * header.length + "\n" + end + + return '' + end + # # :nodoc: # diff --git a/modules/encoders/x86/jmp_call_additive.rb b/modules/encoders/x86/jmp_call_additive.rb index 3b306fbaf1..9da38043bf 100644 --- a/modules/encoders/x86/jmp_call_additive.rb +++ b/modules/encoders/x86/jmp_call_additive.rb @@ -9,6 +9,7 @@ class JmpCallAdditive < Msf::Encoder::XorAdditiveFeedback def initialize super( 'Name' => 'Jump/Call XOR Additive Feedback', + 'Alias' => 'ia32_jmpcalladditive', 'Version' => '$Revision$', 'Description' => 'Jump/Call XOR Additive Feedback', 'Author' => 'skape', diff --git a/modules/nops/x86/single_byte.rb b/modules/nops/x86/single_byte.rb index 7d08089b01..d0d836ccb3 100644 --- a/modules/nops/x86/single_byte.rb +++ b/modules/nops/x86/single_byte.rb @@ -81,6 +81,7 @@ SINGLE_BYTE_SLED = def initialize super( 'Name' => 'Single Byte', + 'Alias' => 'ia32_singlebyte', 'Version' => '$Revision$', 'Description' => 'Single-byte NOP generator', 'Author' => 'spoonm',