Prototype changes that fix redundant exploitations, but break multiple iterations

This commit is contained in:
VakarisZ 2020-05-15 10:42:03 +03:00
parent 87e50d37f1
commit 54ac059d5e
6 changed files with 48 additions and 14 deletions

View File

@ -8,6 +8,9 @@ from itertools import product
__author__ = 'itamar' __author__ = 'itamar'
from infection_monkey.utils.exceptions.planned_shutdown_exception import PlannedShutdownException
from infection_monkey.network import info
GUID = str(uuid.getnode()) GUID = str(uuid.getnode())
EXTERNAL_CONFIG_FILE = os.path.join(os.path.abspath(os.path.dirname(sys.argv[0])), 'monkey.bin') EXTERNAL_CONFIG_FILE = os.path.join(os.path.abspath(os.path.dirname(sys.argv[0])), 'monkey.bin')
@ -277,5 +280,12 @@ class Configuration(object):
password_hashed = hashlib.sha512(sensitive_data.encode()).hexdigest() password_hashed = hashlib.sha512(sensitive_data.encode()).hexdigest()
return password_hashed return password_hashed
@staticmethod
def should_monkey_run():
local_ips = info.local_ips()
if set(local_ips).intersection(set(WormConfiguration.blocked_ips)):
raise PlannedShutdownException("Monkey shouldn't run on current machine "
"(blocked ip or redundant exploitation).")
WormConfiguration = Configuration() WormConfiguration = Configuration()

View File

@ -10,6 +10,7 @@ from infection_monkey.network.HostFinger import HostFinger
from infection_monkey.utils.monkey_dir import create_monkey_dir, get_monkey_dir_path, remove_monkey_dir from infection_monkey.utils.monkey_dir import create_monkey_dir, get_monkey_dir_path, remove_monkey_dir
from infection_monkey.utils.monkey_log_path import get_monkey_log_path from infection_monkey.utils.monkey_log_path import get_monkey_log_path
from infection_monkey.utils.environment import is_windows_os from infection_monkey.utils.environment import is_windows_os
from infection_monkey.utils.exceptions.planned_shutdown_exception import PlannedShutdownException
from infection_monkey.config import WormConfiguration from infection_monkey.config import WormConfiguration
from infection_monkey.control import ControlClient from infection_monkey.control import ControlClient
from infection_monkey.model import DELAY_DELETE_CMD from infection_monkey.model import DELAY_DELETE_CMD
@ -40,10 +41,6 @@ __author__ = 'itamar'
LOG = logging.getLogger(__name__) LOG = logging.getLogger(__name__)
class PlannedShutdownException(Exception):
pass
class InfectionMonkey(object): class InfectionMonkey(object):
def __init__(self, args): def __init__(self, args):
self._keep_running = False self._keep_running = False
@ -129,6 +126,8 @@ class InfectionMonkey(object):
StateTelem(is_done=False, version=get_version()).send() StateTelem(is_done=False, version=get_version()).send()
TunnelTelem().send() TunnelTelem().send()
WormConfiguration.should_monkey_run()
LOG.debug("Starting the post-breach phase.") LOG.debug("Starting the post-breach phase.")
self.collect_system_info_if_configured() self.collect_system_info_if_configured()
PostBreach().execute_all_configured() PostBreach().execute_all_configured()

View File

@ -0,0 +1,2 @@
class PlannedShutdownException(Exception):
pass

View File

@ -74,16 +74,11 @@ class Monkey(flask_restful.Resource):
# if new monkey telem, change config according to "new monkeys" config. # if new monkey telem, change config according to "new monkeys" config.
db_monkey = mongo.db.monkey.find_one({"guid": monkey_json["guid"]}) db_monkey = mongo.db.monkey.find_one({"guid": monkey_json["guid"]})
if not db_monkey:
# we pull it encrypted because we then decrypt it for the monkey in get # Update monkey configuration
new_config = ConfigService.get_flat_config(False, False) new_config = ConfigService.get_flat_config(False, False)
monkey_json['config'] = monkey_json.get('config', {}) monkey_json['config'] = monkey_json.get('config', {})
monkey_json['config'].update(new_config) monkey_json['config'].update(new_config)
else:
db_config = db_monkey.get('config', {})
if 'current_server' in db_config:
del db_config['current_server']
monkey_json.get('config', {}).update(db_config)
# try to find new monkey parent # try to find new monkey parent
parent = monkey_json.get('parent') parent = monkey_json.get('parent')

View File

@ -74,6 +74,12 @@ class ConfigService:
mongo.db.config.update({'name': 'newconfig'}, mongo.db.config.update({'name': 'newconfig'},
{"$set": {mongo_key: value}}) {"$set": {mongo_key: value}})
@staticmethod
def append_to_config_array(config_key_as_arr, value):
mongo_key = ".".join(config_key_as_arr)
mongo.db.config.update({'name': 'newconfig'},
{"$push": {mongo_key: value}})
@staticmethod @staticmethod
def get_flat_config(is_initial_config=False, should_decrypt=True): def get_flat_config(is_initial_config=False, should_decrypt=True):
config_json = ConfigService.get_config(is_initial_config, should_decrypt) config_json = ConfigService.get_config(is_initial_config, should_decrypt)
@ -311,3 +317,7 @@ class ConfigService:
@staticmethod @staticmethod
def is_test_telem_export_enabled(): def is_test_telem_export_enabled():
return ConfigService.get_config_value(['internal', 'testing', 'export_monkey_telems']) return ConfigService.get_config_value(['internal', 'testing', 'export_monkey_telems'])
@staticmethod
def add_blocked_ip(ip_):
ConfigService.append_to_config_array(['basic_network', 'general', 'blocked_ips'], ip_)

View File

@ -1,4 +1,5 @@
import logging import logging
from ipaddress import ip_address
from monkey_island.cc.encryptor import encryptor from monkey_island.cc.encryptor import encryptor
from monkey_island.cc.services import mimikatz_utils from monkey_island.cc.services import mimikatz_utils
@ -17,6 +18,7 @@ def process_system_info_telemetry(telemetry_json):
process_ssh_info, process_ssh_info,
process_credential_info, process_credential_info,
process_mimikatz_and_wmi_info, process_mimikatz_and_wmi_info,
try_process_network_info,
dispatcher.dispatch_collector_results_to_relevant_processors dispatcher.dispatch_collector_results_to_relevant_processors
] ]
@ -101,3 +103,19 @@ def process_mimikatz_and_wmi_info(telemetry_json):
monkey_id = NodeService.get_monkey_by_guid(telemetry_json['monkey_guid']).get('_id') monkey_id = NodeService.get_monkey_by_guid(telemetry_json['monkey_guid']).get('_id')
wmi_handler = WMIHandler(monkey_id, telemetry_json['data']['wmi'], users_secrets) wmi_handler = WMIHandler(monkey_id, telemetry_json['data']['wmi'], users_secrets)
wmi_handler.process_and_handle_wmi_info() wmi_handler.process_and_handle_wmi_info()
def try_process_network_info(telemetry_json):
try:
process_network_info(telemetry_json)
except KeyError:
pass
def process_network_info(telemetry_json):
interfaces = telemetry_json['data']['network_info']['networks']
for interface in interfaces:
ip_ = ip_address(interface['addr'])
if not ip_.is_loopback:
ConfigService.add_blocked_ip(ip_.exploded)