Esempio n. 1
0
    def calc_cov_heuristic(
        objs, parent_stack: List[str], inpt: str, knowledge: KnowledgeHandling
    ) -> Tuple["HeuristicValue", Set[Tuple[Any, Any]], Set[Tuple[Any, Any]]]:
        """
        Calculates based on the covered lines and the heuristic value of the parent the heurisitic value for the children.
        New heuristic value is: #newly covered lines + 1 - heuristic value of parent. -1 as if no new line is covered the
        heuristic value decreases over time
        :param inpt: The string used in the execution
        :param objs: the covered lines and comparisons
        :param parent_stack: the smallest stack occurred for the parent input
        """
        # Todo also take stackdepth into account (maybe in combination with input length s.t. for longer inputs a small stack is preferred
        # Todo this obviously only works for recursive parsers, but for all others this is more or less a nop
        tmp_events = []
        coverage_events = []
        stack = HeuristicValue.calc_stack(objs)
        all_covered = set()
        # we need to consider the taken branches between the last comparison and the eof comparison
        last_was_real = False
        # cur_idx = -1
        for obj in objs:
            # consider only basic block jumps up until the last "real" comparison
            if Utils.is_real_input_comparison(
                    obj, Utils.max_index -
                    1):  # and cur_idx != int(obj["index"][0]):
                # last_was_eof = False
                coverage_events += tmp_events
                tmp_events = []
                last_was_real = True
                # cur_idx = int(obj["index"][0])
            elif not Utils.is_real_input_comparison(
                    obj, Utils.max_index -
                    1) and obj["type"] == "INPUT_COMPARISON" and last_was_real:
                last_was_real = False
                coverage_events += tmp_events
                tmp_events = []
            # elif obj["type"] == "INPUT_COMPARISON" and obj["operator"] == "eof" and not last_was_eof:
            #     last_was_eof = True
            #     coverage_events += tmp_events
            #     tmp_events = []
            elif obj["type"] == "COVERAGE_EVENT":
                tmp_events.append(obj)
                all_covered.add((obj["old"], obj["new"]))

        cover_counter = 0
        new_covered = 0
        covered = set()
        for event in coverage_events:
            value = (event["old"], event["new"])
            if value not in Utils.valid_covered:
                cover_counter += 2
                new_covered += 1
            else:
                cover_counter += 1 / Utils.valid_covered[value]
            covered.add(value)
        same_path_taken = HeuristicValue.check_same_path_taken(coverage_events)
        return HeuristicValue((new_covered, cover_counter), stack,
                              parent_stack, inpt, same_path_taken,
                              knowledge), covered, all_covered
Esempio n. 2
0
 def _calc_tos_coverage(self, objs, tos):
     is_tos = False
     self.tos_cover_counter = 0
     last_was_eof = False
     cur_idx = -1
     tmp_events = set()
     for obj in objs:
         # consider only basic block jumps up until the last "real" comparison
         if obj["type"] == "INPUT_COMPARISON" and obj["operator"] == "eof":
             tmp_events = set()
         elif obj["type"] == "STACK_EVENT" and len(obj["stack"]) == len(self.min_stack_list) and obj["stack"][-1] == tos:
             is_tos = True
         elif obj["type"] == "STACK_EVENT" and obj["stack"] and obj["stack"][-1] != tos:
             is_tos = False
         elif Utils.is_real_input_comparison(obj, Utils.max_index - 1) and cur_idx != obj["index"][0]:
             last_was_eof = False
             self.tos_branches.update(tmp_events)
             tmp_events = set()
             cur_idx = int(obj["index"][0])
         elif obj["type"] == "INPUT_COMPARISON" and obj["operator"] == "eof" and not last_was_eof:
             last_was_eof = True
             self.tos_branches.update(tmp_events)
             tmp_events = set()
         elif is_tos and obj["type"] == "COVERAGE_EVENT":
             tmp_events.add((obj["old"], obj["new"]))
     self.tos_cover_counter = len(self.tos_branches - Utils.valid_covered.keys())
Esempio n. 3
0
def check_no_new_branches(objs):
    """
    Checks if a list of 11 comparisons on different characters has no coverage event in between.
    If this happens the generator is stuck in a loop which is not able to proceed usefully.
    :param objs:
    """
    seen_indexes = set()
    for obj in objs:
        if Utils.is_real_input_comparison(obj, Utils.max_index - 1):
            seen_indexes.add(tuple(obj["index"]))
            if len(seen_indexes) >= 10:
                return True
        else:
            seen_indexes = set()
    return False
Esempio n. 4
0
 def calc_stack(objs) -> List[str]:
     """
     Returns the smallest stack in which a comparison with the last character was done
     :param objs:
     :return:
     """
     robjs = reversed(objs)
     stack = []
     ident = -1
     for obj in robjs:
         real_input_comparison = Utils.is_real_input_comparison(obj, Utils.max_index - 1)
         if ident == -1 and real_input_comparison:
             ident = int(obj["index"][0])
         if ident != -1 and real_input_comparison:
             if ident in obj["index"]:
                 stack = stack if stack and len(stack) < len(obj["stack"]) else obj["stack"]
             else:
                 return stack
     return stack