Files
metasploit-gs/lib/metasploit/framework/compiler/mingw.rb
T

Ignoring revisions in .git-blame-ignore-revs. Click here to bypass and see the normal blame view.

139 lines
4.1 KiB
Ruby
Raw Normal View History

2019-10-31 16:09:44 -05:00
require 'open3'
2019-09-10 14:00:49 -05:00
module Metasploit
module Framework
module Compiler
module Mingw
MINGW_X86 = 'i686-w64-mingw32-gcc'
MINGW_X64 = 'x86_64-w64-mingw32-gcc'
2019-12-10 19:03:38 -06:00
INCLUDE_DIR = File.join(Msf::Config.data_directory, 'headers', 'windows', 'c_payload_util')
UTILITY_DIR = File.join(Msf::Config.data_directory, 'utilities', 'encrypted_payload')
2021-09-10 22:56:04 +03:00
OPTIMIZATION_FLAGS = [ 'Os', 'O0', 'O1', 'O2', 'O3', 'Og' ]
2019-09-10 14:00:49 -05:00
2019-11-17 19:45:22 -06:00
def compile_c(src)
cmd = build_cmd(src)
2021-09-23 14:59:18 -05:00
if self.show_compile_cmd
print("#{cmd}\n")
end
2023-03-15 21:00:13 +01:00
2019-10-31 16:09:44 -05:00
stdin_err, status = Open3.capture2e(cmd)
stdin_err
2019-09-10 14:00:49 -05:00
end
2019-11-17 19:45:22 -06:00
def build_cmd(src)
src_file = "#{self.file_name}.c"
exe_file = "#{self.file_name}.exe"
2019-09-10 14:00:49 -05:00
cmd = ''
link_options = '-Wl,'
File.write(src_file, src)
2019-09-10 14:00:49 -05:00
2021-09-10 22:56:04 +03:00
opt_level = OPTIMIZATION_FLAGS.include?(self.opt_lvl) ? "-#{self.opt_lvl} " : "-O2 "
2023-03-15 20:58:42 +01:00
2019-11-17 19:45:22 -06:00
cmd << "#{self.mingw_bin} "
cmd << "#{src_file} -I #{INCLUDE_DIR} "
cmd << "#{self.include_dirs.map { |include_dir| "-iquote #{include_dir}" }.join(' ')} " if self.include_dirs.any?
cmd << "-o #{exe_file} "
2019-09-10 14:00:49 -05:00
# gives each function its own section
# allowing them to be reordered
cmd << '-ffunction-sections '
cmd << '-fno-asynchronous-unwind-tables '
cmd << '-fno-ident '
2019-10-07 08:45:56 -05:00
cmd << opt_level
2021-09-23 14:59:18 -05:00
if self.compile_options
cmd << self.compile_options
else
2021-09-23 14:59:18 -05:00
link_options << '--image-base=0x0,'
cmd << '-nostdlib '
end
2021-09-23 14:59:18 -05:00
link_options << '--no-seh'
link_options << ',-s' if self.strip_syms
link_options << ",-T#{self.link_script}" if self.link_script
2019-09-10 14:00:49 -05:00
cmd << link_options
cmd
end
2019-10-14 13:34:30 -05:00
2019-11-17 19:45:22 -06:00
def cleanup_files
src_file = "#{self.file_name}.c"
exe_file = "#{self.file_name}.exe"
2019-10-14 13:34:30 -05:00
2019-11-17 19:45:22 -06:00
unless self.keep_src
2019-12-10 19:03:38 -06:00
File.delete(src_file) if File.exist?(src_file)
2019-10-14 13:34:30 -05:00
end
2019-11-17 19:45:22 -06:00
unless self.keep_exe
2019-12-10 19:03:38 -06:00
File.delete(exe_file) if File.exist?(exe_file)
2019-10-14 13:34:30 -05:00
end
rescue Errno::ENOENT
print_error("Failed to delete file")
end
2019-11-17 19:45:22 -06:00
class X86
include Mingw
2019-11-17 19:45:22 -06:00
attr_reader :file_name, :keep_exe, :keep_src, :strip_syms, :link_script, :opt_lvl, :mingw_bin, :compile_options, :show_compile_cmd, :include_dirs
2019-11-17 19:45:22 -06:00
def initialize(opts={})
@file_name = opts[:f_name]
@keep_exe = opts[:keep_exe]
@keep_src = opts[:keep_src]
@strip_syms = opts[:strip_symbols]
2021-09-23 14:59:18 -05:00
@show_compile_cmd = opts[:show_compile_cmd]
@link_script = opts[:linker_script]
@compile_options = opts[:compile_options]
@opt_lvl = opts[:opt_lvl]
@include_dirs = opts[:include_dirs] || []
@mingw_bin = MINGW_X86
end
2019-11-17 19:45:22 -06:00
def self.available?
!!(Msf::Util::Helper.which(MINGW_X86))
end
2019-11-17 19:45:22 -06:00
end
class X64
include Mingw
2019-11-17 19:45:22 -06:00
attr_reader :file_name, :keep_exe, :keep_src, :strip_syms, :link_script, :opt_lvl, :mingw_bin, :compile_options, :show_compile_cmd, :include_dirs
2019-11-17 19:45:22 -06:00
def initialize(opts={})
@file_name = opts[:f_name]
@keep_exe = opts[:keep_exe]
@keep_src = opts[:keep_src]
@strip_syms = opts[:strip_symbols]
2021-09-23 14:59:18 -05:00
@show_compile_cmd = opts[:show_compile_cmd]
@link_script = opts[:linker_script]
@compile_options = opts[:compile_options]
@opt_lvl = opts[:opt_lvl]
@include_dirs = opts[:include_dirs] || []
@mingw_bin = MINGW_X64
end
2019-11-17 19:45:22 -06:00
def self.available?
!!(Msf::Util::Helper.which(MINGW_X64))
end
2019-11-17 19:45:22 -06:00
end
class UncompilablePayloadError < StandardError
def initialize(msg='')
super(msg)
end
end
2019-11-17 19:45:22 -06:00
class CompiledPayloadNotFoundError < StandardError
def initialize(msg='Compiled executable not found')
super(msg)
end
end
end
2019-09-10 14:00:49 -05:00
end
end
end