Esempio n. 1
0
async def run(indicators: dict) -> None:
    """Accept a dict containing events indicators and write out to the OUTPUT_DIR specified by chirp.common.

    :param indicators: A dict containing parsed registry indicator files.
    :type indicators: dict
    """
    if not indicators:
        return
    logging.debug("(REGISTRY) Entered registry plugin.")
    report = {indicator["name"]: build_report(indicator) for indicator in indicators}
    for indicator in indicators:
        ind = indicator["indicator"]
        indicator_list = [(k, v) for k, v in ind.items() if k != "registry_key"]
        logging.log(REGISTRY, "Reading {}".format(ind["registry_key"]))
        async for value in enumerate_registry_values(ind["registry_key"]):
            if value == "ERROR":
                logging.log(REGISTRY, "Hit an error, exiting.")
                return
            hits, search_criteria, match = await check_matches(indicator_list, value)
            if hits != len(indicator_list):
                continue
            report[indicator["name"]]["_search_criteria"] = search_criteria
            if match:
                report[indicator["name"]]["matches"].append(match)
    [await _report_hits(k, v) for k, v in report.items()]
    with open(os.path.join(OUTPUT_DIR, "registry.json"), "w+") as writeout:
        writeout.write(
            json.dumps({r: report[r] for r in report if report[r]["matches"]})
        )
Esempio n. 2
0
async def run(indicators: dict) -> None:
    """Accept a dict containing events indicators and writes out to the OUTPUT_DIR specified by chirp.common.

    :param indicators: A dict containing parsed network indicator files.
    :type indicators: dict
    """
    if not indicators:
        return

    hits = 0
    CONSOLE("[cyan][NETWORK][/cyan] Entered network plugin.")
    saved_ns = parse_netstat(grab_netstat())
    saved_dns = parse_dns(grab_dns())

    report = {
        indicator["name"]: build_report(indicator)
        for indicator in indicators
    }

    for indicator in indicators:
        try:
            for ioc in indicator["indicator"]["ips"].splitlines():
                if await hunter(saved_ns + ["\n"] + saved_dns, ioc):
                    report[indicator["name"]]["matches"].append(ioc)
                    hits += 1
        except KeyError:
            ERROR("{} appears to be malformed.".format(indicator))
    CONSOLE(
        "[cyan][NETWORK][/cyan] Read {} records, found {} IoC hits.".format(
            len(saved_dns) + len(saved_ns), hits))

    with open(os.path.join(OUTPUT_DIR, "network.json"), "w+") as writeout:
        writeout.write(
            json.dumps({r: report[r]
                        for r in report if report[r]["matches"]}))
Esempio n. 3
0
File: run.py Progetto: xorilog/CHIRP
    async def run(indicators: dict) -> None:
        """Accept a dict containing yara indicators and write out to the OUTPUT_DIR specified by chirp.common.

        :param indicators: A NamespaceDict containing parsed yara indicator files.
        :type indicators: dict
        """
        if not indicators:
            return

        CONSOLE("[cyan][YARA][/cyan] Entered yara plugin.")

        files = [i["indicator"]["files"] for i in indicators]
        files = "\\**" if "\\**" in files else ", ".join(files)

        if files == "\\**":
            blame = [
                i["name"] for i in indicators
                if i["indicator"]["files"] == "\\**"
            ]
            CONSOLE(
                "[cyan][YARA][/cyan] Enumerating the entire filesystem due to {}... this is going to take a while."
                .format(blame))

        report = {
            indicator["name"]: build_report(indicator)
            for indicator in indicators
        }

        hits = 0
        run_args = []

        # Normalize every path, for every path
        try:
            run_args = [(a, b, indicators)
                        for a, b in enumerate(normalize_paths(files), 1)]
            async with aiomp.Pool() as pool:
                try:
                    async for result in pool.map(_run, tuple(run_args)):
                        if result:
                            report[result["namespace"]]["matches"].append(
                                result)
                            hits += 1
                except KeyboardInterrupt:
                    pass
        except IndexError:
            pass

        count = len(run_args)

        CONSOLE("[cyan][YARA][/cyan] Done. Processed {} files.".format(count))
        CONSOLE(
            "[cyan][YARA][/cyan] Found {} hit(s) for yara indicators.".format(
                hits))

        with open(os.path.join(OUTPUT_DIR, "yara.json"), "w+") as writeout:
            writeout.write(
                json.dumps(
                    {r: report[r]
                     for r in report if report[r]["matches"]}))
Esempio n. 4
0
    async def run(indicators: dict) -> None:
        """Accept a dict containing yara indicators and write out to the OUTPUT_DIR specified by chirp.common.

        :param indicators: A NamespaceDict containing parsed yara indicator files.
        :type indicators: dict
        """
        if not indicators:
            return

        logging.info("Entered yara plugin.")

        files = (
            [i["indicator"]["files"] for i in indicators] if not TARGETS else TARGETS
        )
        files = "\\**" if "\\**" in files else ", ".join(files)

        logging.info("Yara targets: {}".format(files))

        if files == "\\**":
            blame = [i["name"] for i in indicators if i["indicator"]["files"] == "\\**"]
            logging.log(
                YARA,
                "Enumerating the entire filesystem due to {}... this is going to take a while.".format(
                    blame
                ),
            )

        report = {
            indicator["name"]: build_report(indicator) for indicator in indicators
        }

        hits = 0
        count = 0

        # Normalize every path, for every path
        try:
            with Pool(initializer=_signal_handler) as pool:
                for result in pool.imap_unordered(
                    partial(_run, indicators),
                    enumerate(normalize_paths(files), 1),
                    chunksize=1000,
                ):
                    if result:
                        report[result["namespace"]]["matches"].append(result)
                        hits += 1
                    count += 1
        except IndexError:
            pass
        except KeyboardInterrupt:
            logging.log(YARA, "Received a keyboard interrupt. Killing workers.")

        logging.log(YARA, "Done. Processed {} files.".format(count))
        logging.log(YARA, "Found {} hit(s) for yara indicators.".format(hits))

        with open(os.path.join(OUTPUT_DIR, "yara.json"), "w+") as writeout:
            writeout.write(
                json.dumps({r: report[r] for r in report if report[r]["matches"]})
            )
Esempio n. 5
0
async def run(indicators: dict) -> None:
    """Accept a dict containing events indicators and writes out to the OUTPUT_DIR specified by chirp.common.

    :param indicators: A dict containing parsed events indicator files.
    :type indicators: dict
    """
    if not indicators:
        return
    hits = 0
    num_logs = 0
    logging.debug("Entered events plugin.")
    event_types = {
        indicator["indicator"]["event_type"]
        for indicator in indicators
    }
    report = {
        indicator["name"]: build_report(indicator)
        for indicator in indicators
    }
    run_args = [(event_type, indicators, report, num_logs)
                for event_type in event_types]
    async with aiomp.Pool() as pool:
        try:
            async for i in pool.map(_run, tuple(run_args)):
                _rep = i[0]
                num_logs += i[1]
                for k, v in _rep.items():
                    try:
                        report[k]["_search_criteria"] = v["_search_criteria"]
                    except KeyError:
                        pass
                    report[k]["matches"] += v["matches"]
        except KeyboardInterrupt:
            pass

    hits = sum(len(v["matches"]) for _, v in report.items())
    logging.log(EVENTS,
                "Read {} logs, found {} matches.".format(num_logs, hits))
    with open(os.path.join(OUTPUT_DIR, "events.json"), "w+") as writeout:
        writeout.write(
            json.dumps({r: report[r]
                        for r in report if report[r]["matches"]}))