Esempio n. 1
0
    def _get_workstation_by_source_ip(self, source_ip) -> str:
        """
            查找最近该IP认证主机名

            返回主机名和域名
        """
        account_history = AccountHistory()
        return account_history.get_last_workstation_by_ip(source_ip)
Esempio n. 2
0
class MachineAuth(object):
    def __init__(self):
        self.account_history = AccountHistory()

    def run(self, log: Log):
        ip = log.source_info.ip_address
        if ip_filter(ip):
            return

        if log.event_data["Status"] != "0x0":
            return

        if log.event_data["PreAuthType"] != 2:
            return

        if not log.target_info.user_name.endswith("$"):
            return

        workstation = log.target_info.user_name[:-1]

        self.account_history.set_workstation_by_ip(ip=ip,
                                                   workstation=workstation)
        self.account_history.set_ip_by_workstation(ip=ip,
                                                   workstation=workstation)
Esempio n. 3
0
 def __init__(self):
     super().__init__(code=ALERT_CODE, title=TITLE, desc=DESC_TEMPLATE)
     self.account_info = AccountInfo()
     self.account_history = AccountHistory()
Esempio n. 4
0
class NTLMRelay(DetectBase):
    def __init__(self):
        super().__init__(code=ALERT_CODE, title=TITLE, desc=DESC_TEMPLATE)
        self.account_history = AccountHistory()
        self.account_info = AccountInfo()
        self.es = ElasticHelper()

    def run(self, log: Log):
        self.init(log=log)

        # 处于数据统计时间内,不检测
        if datetime_now_obj() < main_config.learning_end_time:
            return

        if not log.source_info.ip_address:
            return

        if log.event_data["AuthenticationPackageName"] != "NTLM":
            return

        work_station = log.source_info.work_station_name
        netbios_name = get_netbios_domain(log.target_info.domain_name)
        if filter_domain(netbios_name):
            return

        # 为较小误报 目前只考虑来源主机为敏感主机的行为
        if not self.account_info.computer_is_sensitive_by_name(
                work_station, domain=netbios_name):
            return

        ip_address = log.source_info.ip_address
        if ip_filter(ip_address):
            return

        # 根据主机名去查最近的认证IP
        last_ip = self.account_history.search_last_ip_by_workstation(
            work_station)
        if not last_ip or last_ip == "unknown" or last_ip == ip_address:
            return

        # 二次确认,如果上次认证IP与当前IP不相同,则对主机名进行解析,判断IP是否相等
        resolver_ips = self._get_host_ip(log)
        if ip_address in resolver_ips:
            return

        if "V1" in log.event_data["LmPackageName"]:
            version = "v1"
        else:
            version = "v2"

        relay_workstation = self.account_history.get_last_workstation_by_ip(
            ip_address)

        return self._generate_alert_doc(relay_workstation=relay_workstation,
                                        ntlm_version=version,
                                        resolver_ips=resolver_ips,
                                        last_ip=last_ip)

    def _generate_alert_doc(self, **kwargs) -> dict:
        form_data = {
            "source_ip": self.log.source_info.ip_address,
            "relay_ip": self.log.source_info.ip_address,
            "source_workstation": self.log.source_info.work_station_name,
            "target_user_name": self.log.target_info.user_name,
            "target_domain": self.log.target_info.domain_name,
            "target_user_sid": self.log.target_info.user_sid,
            "target_logon_id": self.log.target_info.logon_id,
            "dc_hostname": self.log.dc_host_name,
            **kwargs
        }
        doc = self._get_base_doc(level=self._get_level(),
                                 unique_id=self._get_unique_id(
                                     self.code,
                                     self.log.source_info.ip_address),
                                 form_data=form_data)
        return doc

    def _get_level(self) -> str:
        return HIGH_LEVEL

    def _get_host_ip(self, log: Log) -> list:
        """
            对主机名进行DNS解析
        """
        dns_name = "{workstation}.{domain}".format(
            workstation=log.source_info.work_station_name,
            domain=self.get_FQDN_domain(log.target_info.domain_name))
        try:
            ip_list = get_ip_from_domain(dns_name)
        except Exception as e:
            return []
        return ip_list

    def get_FQDN_domain(self, domain) -> str:
        for each in main_config.domain_list:
            if each.startswith(domain.lower()):
                return each
        return ""
Esempio n. 5
0
 def __init__(self):
     self.redis = RedisHelper()
     self.account_history = AccountHistory()
     self.es = ElasticHelper()
Esempio n. 6
0
 def __init__(self):
     self.account_history = AccountHistory()
Esempio n. 7
0
 def _get_source_ip_by_workstation(self, source_ip) -> str:
     """
     """
     account_history = AccountHistory()
     return account_history.get_last_ip_by_workstation(source_ip)