(self,
                 context_sensitivity_level=1,
                 start=None,
                 avoid_runs=None,
                 enable_function_hints=False,
                 call_depth=None,
                 call_tracing_filter=None,
                 initial_state=None,
                 starts=None,
                 keep_state=False,
                 indirect_jump_target_limit=100000,
                 resolve_indirect_jumps=True,
                 enable_advanced_backward_slicing=False,
                 enable_symbolic_back_traversal=False,
                 indirect_jump_resolvers=None,
                 additional_edges=None,
                 no_construct=False,
                 normalize=False,
                 max_iterations=1,
                 address_whitelist=None,
                 base_graph=None,
                 iropt_level=None,
                 max_steps=None,
                 state_add_options=None,
                 state_remove_options=None,
                 model=None,
                 )
All parameters are optional.

        :param context_sensitivity_level:           The level of context-sensitivity of this CFG (see documentation for
                                                    further details). It ranges from 0 to infinity. Default 1.
        :param avoid_runs:                          A list of runs to avoid.
        :param enable_function_hints:               Whether to use function hints (constants that might be used as exit
                                                    targets) or not.
        :param call_depth:                          How deep in the call stack to trace.
        :param call_tracing_filter:                 Filter to apply on a given path and jumpkind to determine if it
                                                    should be skipped when call_depth is reached.
        :param initial_state:                       An initial state to use to begin analysis.
        :param iterable starts:                     A collection of starting points to begin analysis. It can contain
                                                    the following three different types of entries: an address specified
                                                    as an integer, a 2-tuple that includes an integer address and a
                                                    jumpkind, or a SimState instance. Unsupported entries in starts will
                                                    lead to an AngrCFGError being raised.
        :param keep_state:                          Whether to keep the SimStates for each CFGNode.
        :param resolve_indirect_jumps:              Whether to enable the indirect jump resolvers for resolving indirect jumps
        :param enable_advanced_backward_slicing:    Whether to enable an intensive technique for resolving indirect jumps
        :param enable_symbolic_back_traversal:      Whether to enable an intensive technique for resolving indirect jumps
        :param list indirect_jump_resolvers:        A custom list of indirect jump resolvers. If this list is None or empty,
                                                    default indirect jump resolvers specific to this architecture and binary
                                                    types will be loaded.
        :param additional_edges:                    A dict mapping addresses of basic blocks to addresses of
                                                    successors to manually include and analyze forward from.
        :param bool no_construct:                   Skip the construction procedure. Only used in unit-testing.
        :param bool normalize:                      If the CFG as well as all Function graphs should be normalized or
                                                    not.
        :param int max_iterations:                  The maximum number of iterations that each basic block should be
                                                    "executed". 1 by default. Larger numbers of iterations are usually
                                                    required for complex analyses like loop analysis.
        :param iterable address_whitelist:          A list of allowed addresses. Any basic blocks outside of this
                                                    collection of addresses will be ignored.
        :param networkx.DiGraph base_graph:         A basic control flow graph to follow. Each node inside this graph
                                                    must have the following properties: `addr` and `size`. CFG recovery
                                                    will strictly follow nodes and edges shown in the graph, and discard
                                                    any contorl flow that does not follow an existing edge in the base
                                                    graph. For example, you can pass in a Function local transition
                                                    graph as the base graph, and CFGEmulated will traverse nodes and
                                                    edges and extract useful information.
        :param int iropt_level:                     The optimization level of VEX IR (0, 1, 2). The default level will
                                                    be used if `iropt_level` is None.
        :param int max_steps:                       The maximum number of basic blocks to recover forthe longest path
                                                    from each start before pausing the recovery procedure.
        :param state_add_options:                   State options that will be added to the initial state.
        :param state_remove_options:                State options that will be removed from the initial state.
All parameters are optional.
All parameters are optional .
def __init__(self,
                 context_sensitivity_level=1,
                 start=None,
                 avoid_runs=None,
                 enable_function_hints=False,
                 call_depth=None,
                 call_tracing_filter=None,
                 initial_state=None,
                 starts=None,
                 keep_state=False,
                 indirect_jump_target_limit=100000,
                 resolve_indirect_jumps=True,
                 enable_advanced_backward_slicing=False,
                 enable_symbolic_back_traversal=False,
                 indirect_jump_resolvers=None,
                 additional_edges=None,
                 no_construct=False,
                 normalize=False,
                 max_iterations=1,
                 address_whitelist=None,
                 base_graph=None,
                 iropt_level=None,
                 max_steps=None,
                 state_add_options=None,
                 state_remove_options=None,
                 model=None,
                 ):
        """
        All parameters are optional.

        :param context_sensitivity_level:           The level of context-sensitivity of this CFG (see documentation for
                                                    further details). It ranges from 0 to infinity. Default 1.
        :param avoid_runs:                          A list of runs to avoid.
        :param enable_function_hints:               Whether to use function hints (constants that might be used as exit
                                                    targets) or not.
        :param call_depth:                          How deep in the call stack to trace.
        :param call_tracing_filter:                 Filter to apply on a given path and jumpkind to determine if it
                                                    should be skipped when call_depth is reached.
        :param initial_state:                       An initial state to use to begin analysis.
        :param iterable starts:                     A collection of starting points to begin analysis. It can contain
                                                    the following three different types of entries: an address specified
                                                    as an integer, a 2-tuple that includes an integer address and a
                                                    jumpkind, or a SimState instance. Unsupported entries in starts will
                                                    lead to an AngrCFGError being raised.
        :param keep_state:                          Whether to keep the SimStates for each CFGNode.
        :param resolve_indirect_jumps:              Whether to enable the indirect jump resolvers for resolving indirect jumps
        :param enable_advanced_backward_slicing:    Whether to enable an intensive technique for resolving indirect jumps
        :param enable_symbolic_back_traversal:      Whether to enable an intensive technique for resolving indirect jumps
        :param list indirect_jump_resolvers:        A custom list of indirect jump resolvers. If this list is None or empty,
                                                    default indirect jump resolvers specific to this architecture and binary
                                                    types will be loaded.
        :param additional_edges:                    A dict mapping addresses of basic blocks to addresses of
                                                    successors to manually include and analyze forward from.
        :param bool no_construct:                   Skip the construction procedure. Only used in unit-testing.
        :param bool normalize:                      If the CFG as well as all Function graphs should be normalized or
                                                    not.
        :param int max_iterations:                  The maximum number of iterations that each basic block should be
                                                    "executed". 1 by default. Larger numbers of iterations are usually
                                                    required for complex analyses like loop analysis.
        :param iterable address_whitelist:          A list of allowed addresses. Any basic blocks outside of this
                                                    collection of addresses will be ignored.
        :param networkx.DiGraph base_graph:         A basic control flow graph to follow. Each node inside this graph
                                                    must have the following properties: `addr` and `size`. CFG recovery
                                                    will strictly follow nodes and edges shown in the graph, and discard
                                                    any contorl flow that does not follow an existing edge in the base
                                                    graph. For example, you can pass in a Function local transition
                                                    graph as the base graph, and CFGEmulated will traverse nodes and
                                                    edges and extract useful information.
        :param int iropt_level:                     The optimization level of VEX IR (0, 1, 2). The default level will
                                                    be used if `iropt_level` is None.
        :param int max_steps:                       The maximum number of basic blocks to recover forthe longest path
                                                    from each start before pausing the recovery procedure.
        :param state_add_options:                   State options that will be added to the initial state.
        :param state_remove_options:                State options that will be removed from the initial state.
        """
        ForwardAnalysis.__init__(self, order_jobs=True if base_graph is not None else False)
        CFGBase.__init__(self, 'emulated', context_sensitivity_level, normalize=normalize,
                         resolve_indirect_jumps=resolve_indirect_jumps,
                         indirect_jump_resolvers=indirect_jump_resolvers,
                         indirect_jump_target_limit=indirect_jump_target_limit,
                         model=model,
        )

        if start is not None:
            l.warning("`start` is deprecated. Please consider using `starts` instead in your code.")
            self._starts = (start,)
        else:
            if isinstance(starts, (list, set)):
                self._starts = tuple(starts)
            elif isinstance(starts, tuple) or starts is None:
                self._starts = starts
            else:
                raise AngrCFGError('Unsupported type of the `starts` argument.')

        if enable_advanced_backward_slicing or enable_symbolic_back_traversal:
            l.warning("`advanced backward slicing` and `symbolic back traversal` are deprecated.")
            l.warning("Please use `resolve_indirect_jumps` to resolve indirect jumps using different resolvers instead.")

        self._iropt_level = iropt_level
        self._avoid_runs = avoid_runs
        self._enable_function_hints = enable_function_hints
        self._call_depth = call_depth
        self._call_tracing_filter = call_tracing_filter
        self._initial_state = initial_state
        self._keep_state = keep_state
        self._advanced_backward_slicing = enable_advanced_backward_slicing
        self._enable_symbolic_back_traversal = enable_symbolic_back_traversal
        self._additional_edges = additional_edges if additional_edges else {}
        self._max_steps = max_steps
        self._state_add_options = state_add_options if state_add_options is not None else set()
        self._state_remove_options = state_remove_options if state_remove_options is not None else set()
        self._state_add_options.update([o.SYMBOL_FILL_UNCONSTRAINED_MEMORY, o.SYMBOL_FILL_UNCONSTRAINED_REGISTERS])

        # add the track_memory_option if the enable function hint flag is set
        if self._enable_function_hints and o.TRACK_MEMORY_ACTIONS not in self._state_add_options:
            self._state_add_options.add(o.TRACK_MEMORY_ACTIONS)

        # more initialization

        self._symbolic_function_initial_state = {}
        self._function_input_states = None
        self._unresolvable_runs = set()

        # Stores the index for each CFGNode in this CFG after a quasi-topological sort (currently a DFS)
        # TODO: remove it since it's no longer used
        self._quasi_topological_order = {}
        # A copy of all entry points in this CFG. Integers
        self._entry_points = []

        self._max_iterations = max_iterations
        self._address_whitelist = set(address_whitelist) if address_whitelist is not None else None
        self._base_graph = base_graph
        self._node_addr_visiting_order = [ ]

        if self._base_graph:
            sorted_nodes = CFGUtils.quasi_topological_sort_nodes(self._base_graph)
            self._node_addr_visiting_order = [ n.addr for n in sorted_nodes ]

        self._sanitize_parameters()

        self._executable_address_ranges = []
        self._executable_address_ranges = self._executable_memory_regions()

        # These save input states of functions. It will be discarded after the CFG is constructed
        self._function_input_states = {}
        self._loop_back_edges = []
        self._overlapped_loop_headers = []
        self._pending_function_hints = set()
        # A dict to log edges and the jumpkind between each basic block
        self._edge_map = defaultdict(list)

        self._model._iropt_level = self._iropt_level

        self._start_keys = [ ]  # a list of block IDs of all starts

        # For each call, we are always getting two exits: an Ijk_Call that
        # stands for the real call exit, and an Ijk_Ret that is a simulated exit
        # for the retn address. There are certain cases that the control flow
        # never returns to the next instruction of a callsite due to
        # imprecision of the concrete execution. So we save those simulated
        # exits here to increase our code coverage. Of course the real retn from
        # that call always precedes those "fake" retns.
        self._pending_jobs = defaultdict(list) # Dict[BlockID, List[PendingJob]]

        # Counting how many times a basic block is traced into
        self._traced_addrs = defaultdict(lambda: defaultdict(int))

        # A dict that collects essential parameters to properly reconstruct initial state for a block
        self._block_artifacts = {}
        self._analyzed_addrs = set()
        self._non_returning_functions = set()

        self._pending_edges = defaultdict(list)

        if not no_construct:
            self._initialize_cfg()
            self._analyze()
def __init__ ( self , context_sensitivity_level = 1 , start = None , avoid_runs = None , enable_function_hints = False , call_depth = None , call_tracing_filter = None , initial_state = None , starts = None , keep_state = False , indirect_jump_target_limit = 100000 , resolve_indirect_jumps = True , enable_advanced_backward_slicing = False , enable_symbolic_back_traversal = False , indirect_jump_resolvers = None , additional_edges = None , no_construct = False , normalize = False , max_iterations = 1 , address_whitelist = None , base_graph = None , iropt_level = None , max_steps = None , state_add_options = None , state_remove_options = None , model = None , ) : ForwardAnalysis . __init__ ( self , order_jobs = True if base_graph is not None else False ) CFGBase . __init__ ( self , 'emulated' , context_sensitivity_level , normalize = normalize , resolve_indirect_jumps = resolve_indirect_jumps , indirect_jump_resolvers = indirect_jump_resolvers , indirect_jump_target_limit = indirect_jump_target_limit , model = model , ) if start is not None : l . warning ( "`start` is deprecated. Please consider using `starts` instead in your code." ) self . _starts = ( start , ) else : if isinstance ( starts , ( list , set ) ) : self . _starts = tuple ( starts ) elif isinstance ( starts , tuple ) or starts is None : self . _starts = starts else : raise AngrCFGError ( 'Unsupported type of the `starts` argument.' ) if enable_advanced_backward_slicing or enable_symbolic_back_traversal : l . warning ( "`advanced backward slicing` and `symbolic back traversal` are deprecated." ) l . warning ( "Please use `resolve_indirect_jumps` to resolve indirect jumps using different resolvers instead." ) self . _iropt_level = iropt_level self . _avoid_runs = avoid_runs self . _enable_function_hints = enable_function_hints self . _call_depth = call_depth self . _call_tracing_filter = call_tracing_filter self . _initial_state = initial_state self . _keep_state = keep_state self . _advanced_backward_slicing = enable_advanced_backward_slicing self . _enable_symbolic_back_traversal = enable_symbolic_back_traversal self . _additional_edges = additional_edges if additional_edges else { } self . _max_steps = max_steps self . _state_add_options = state_add_options if state_add_options is not None else set ( ) self . _state_remove_options = state_remove_options if state_remove_options is not None else set ( ) self . _state_add_options . update ( [ o . SYMBOL_FILL_UNCONSTRAINED_MEMORY , o . SYMBOL_FILL_UNCONSTRAINED_REGISTERS ] ) # add the track_memory_option if the enable function hint flag is set if self . _enable_function_hints and o . TRACK_MEMORY_ACTIONS not in self . _state_add_options : self . _state_add_options . add ( o . TRACK_MEMORY_ACTIONS ) # more initialization self . _symbolic_function_initial_state = { } self . _function_input_states = None self . _unresolvable_runs = set ( ) # Stores the index for each CFGNode in this CFG after a quasi-topological sort (currently a DFS) # TODO: remove it since it's no longer used self . _quasi_topological_order = { } # A copy of all entry points in this CFG. Integers self . _entry_points = [ ] self . _max_iterations = max_iterations self . _address_whitelist = set ( address_whitelist ) if address_whitelist is not None else None self . _base_graph = base_graph self . _node_addr_visiting_order = [ ] if self . _base_graph : sorted_nodes = CFGUtils . quasi_topological_sort_nodes ( self . _base_graph ) self . _node_addr_visiting_order = [ n . addr for n in sorted_nodes ] self . _sanitize_parameters ( ) self . _executable_address_ranges = [ ] self . _executable_address_ranges = self . _executable_memory_regions ( ) # These save input states of functions. It will be discarded after the CFG is constructed self . _function_input_states = { } self . _loop_back_edges = [ ] self . _overlapped_loop_headers = [ ] self . _pending_function_hints = set ( ) # A dict to log edges and the jumpkind between each basic block self . _edge_map = defaultdict ( list ) self . _model . _iropt_level = self . _iropt_level self . _start_keys = [ ] # a list of block IDs of all starts # For each call, we are always getting two exits: an Ijk_Call that # stands for the real call exit, and an Ijk_Ret that is a simulated exit # for the retn address. There are certain cases that the control flow # never returns to the next instruction of a callsite due to # imprecision of the concrete execution. So we save those simulated # exits here to increase our code coverage. Of course the real retn from # that call always precedes those "fake" retns. self . _pending_jobs = defaultdict ( list ) # Dict[BlockID, List[PendingJob]] # Counting how many times a basic block is traced into self . _traced_addrs = defaultdict ( lambda : defaultdict ( int ) ) # A dict that collects essential parameters to properly reconstruct initial state for a block self . _block_artifacts = { } self . _analyzed_addrs = set ( ) self . _non_returning_functions = set ( ) self . _pending_edges = defaultdict ( list ) if not no_construct : self . _initialize_cfg ( ) self . _analyze ( )