# Path: sibyl/heuristics/heuristic.py
# class Heuristic(object):
#     """Main class for heuristics, handle common methods related to them"""
# 
#     # Enabled passes
#     # passes are functions taking 'self' and returning a dict:
#     #    candidates -> estimated probability
#     heuristics = []
# 
#     def __init__(self):
#         self._votes = None
# 
#     def do_votes(self):
#         """Call heuristics and get back votes
#         Use a cumulative linear strategy for comparison
#         """
#         votes = {}
#         for heuristic in self.heuristics:
#             for name, vote in heuristic(self).iteritems():
#                 votes[name] = votes.get(name, 0) + vote
#         self._votes = votes
# 
#     @property
#     def votes(self):
#         """Cumulative votes for each candidates"""
#         if not self._votes:
#             self.do_votes()
#         return self._votes
# 
#     @property
#     def heuristic_names(self):
#         """Return the list of available heuristics"""
#         return [func.__name__ for func in self.heuristics]
# 
#     def name2heuristic(self, name):
#         """Return the heuristic named @name"""
#         for func in self.heuristics:
#             if func.__name__ == name:
#                 return func
#         else:
#             raise KeyError("Unable to find %s" % name)
# 
#     def guess(self):
#         """Return the best candidate"""
#         sorted_votes = sorted(self.votes.iteritems(), key=lambda x:x[1])
#         if not sorted_votes:
#             # No solution
#             return False
#         best, _ = sorted_votes[-1]
#         return best
# 
# Path: sibyl/config.py
# class Config(object):
#     def __init__(self, default_config, files):
#     def expandpath(path):
#     def parse_files(self, files):
#     def dump(self):
#     def jit_engine(self):
#     def available_tests(self):
#     def miasm_engine(self):
#     def pin_root(self):
#     def pin_tracer(self):
#     def prune_strategy(self):
#     def prune_keep(self):
#     def prune_keep_max(self):
#     def stubs(self):
#     def idaq64_path(self):
#     def ghidra_headless_path(self):
#     def ghidra_export_function(self):


import logging
import re
import tempfile
import subprocess
import shutil
import os
import sibyl.heuristics.csts as csts
from miasm2.core.asmblock import AsmBlockBad, log_asmblock
from sibyl.heuristics.heuristic import Heuristic
from sibyl.config import config
                           stdout=subprocess.PIPE,
                           stderr=subprocess.PIPE,
    )
    run.communicate()

    # Get back addresses
    tmp_out.seek(0)
    addresses = {int(x, 16): 1 for x in tmp_out}

    # Clean-up
    tmp_script.close()
    tmp_out.close()

    return addresses


def ghidra_funcs(func_heur):
    """Use GHIDRA heuristics to find functions"""

    ghidra_headless_path = config.ghidra_headless_path
    if not ghidra_headless_path:
        return {}

    # Prepare temporary files: GHIDRA project location and output
    tmp_project_location = tempfile.mkdtemp(prefix="sibyl_ghidra_fakeproj")
    tmp_log = tempfile.NamedTemporaryFile(suffix=".log", delete=True)

    # Launch GHIDRA
    env = os.environ.copy()
    script_path = os.path.dirname(config.ghidra_export_function)

# Path: sibyl/heuristics/heuristic.py
# class Heuristic(object):
#     """Main class for heuristics, handle common methods related to them"""
# 
#     # Enabled passes
#     # passes are functions taking 'self' and returning a dict:
#     #    candidates -> estimated probability
#     heuristics = []
# 
#     def __init__(self):
#         self._votes = None
# 
#     def do_votes(self):
#         """Call heuristics and get back votes
#         Use a cumulative linear strategy for comparison
#         """
#         votes = {}
#         for heuristic in self.heuristics:
#             for name, vote in heuristic(self).iteritems():
#                 votes[name] = votes.get(name, 0) + vote
#         self._votes = votes
# 
#     @property
#     def votes(self):
#         """Cumulative votes for each candidates"""
#         if not self._votes:
#             self.do_votes()
#         return self._votes
# 
#     @property
#     def heuristic_names(self):
#         """Return the list of available heuristics"""
#         return [func.__name__ for func in self.heuristics]
# 
#     def name2heuristic(self, name):
#         """Return the heuristic named @name"""
#         for func in self.heuristics:
#             if func.__name__ == name:
#                 return func
#         else:
#             raise KeyError("Unable to find %s" % name)
# 
#     def guess(self):
#         """Return the best candidate"""
#         sorted_votes = sorted(self.votes.iteritems(), key=lambda x:x[1])
#         if not sorted_votes:
#             # No solution
#             return False
#         best, _ = sorted_votes[-1]
#         return best
# 
# Path: sibyl/config.py
# class Config(object):
#     def __init__(self, default_config, files):
#     def expandpath(path):
#     def parse_files(self, files):
#     def dump(self):
#     def jit_engine(self):
#     def available_tests(self):
#     def miasm_engine(self):
#     def pin_root(self):
#     def pin_tracer(self):
#     def prune_strategy(self):
#     def prune_keep(self):
#     def prune_keep_max(self):
#     def stubs(self):
#     def idaq64_path(self):
#     def ghidra_headless_path(self):
#     def ghidra_export_function(self):


# Path: sibyl/heuristics/func.py
import logging
import re
import tempfile
import subprocess
import shutil
import os
import sibyl.heuristics.csts as csts
from miasm2.core.asmblock import AsmBlockBad, log_asmblock
from sibyl.heuristics.heuristic import Heuristic
from sibyl.config import config

                           stdout=subprocess.PIPE,
                           stderr=subprocess.PIPE,
    )
    run.communicate()

    # Get back addresses
    tmp_out.seek(0)
    addresses = {int(x, 16): 1 for x in tmp_out}

    # Clean-up
    tmp_script.close()
    tmp_out.close()

    return addresses


def ghidra_funcs(func_heur):
    """Use GHIDRA heuristics to find functions"""

    ghidra_headless_path = config.ghidra_headless_path
    if not ghidra_headless_path:
        return {}

    # Prepare temporary files: GHIDRA project location and output
    tmp_project_location = tempfile.mkdtemp(prefix="sibyl_ghidra_fakeproj")
    tmp_log = tempfile.NamedTemporaryFile(suffix=".log", delete=True)

    # Launch GHIDRA
    env = os.environ.copy()
    script_path = os.path.dirname(config.ghidra_export_function)

    script_name = os.path.basename(config.ghidra_export_function)