Exemplo n.º 1
0
    def __init__(self, get_repository, config):
        """Set the paramaters of the model - i.e. the weights and features.

    For some explanation of why the paramaters were set this way see these docs:
      https://docs.google.com/a/google.com/document/d/1TdDEDlUJX81-5yvB9IfdJFq5-kJBb_DwAgDH9cGfNao/edit?usp=sharing
      https://docs.google.com/a/google.com/document/d/1FHaghBX_FANjtiUP7D1pihZGxzEYdXA3Y7t0rSA4bWU/edit?usp=sharing
    As well as the following CLs:
      https://chromium-review.googlesource.com/c/599071
      https://chromium-review.googlesource.com/c/585784
    """
        super(PredatorForUMASamplingProfiler,
              self).__init__(get_repository, config)
        meta_weight = MetaWeight({
            'TouchCrashedFileMeta':
            MetaWeight({
                'MinDistance': Weight(2.),
                'TopFrameIndex': Weight(0.),
                'TouchCrashedFile': Weight(1.),
            })
        })

        min_distance_feature = MinDistanceFeature(get_repository)
        top_frame_index_feature = TopFrameIndexFeature()
        touch_crashed_file_feature = TouchCrashedFileFeature()
        meta_feature = WrapperMetaFeature([
            TouchCrashedFileMetaFeature([
                min_distance_feature, top_frame_index_feature,
                touch_crashed_file_feature
            ],
                                        include_renamed_paths=True)
        ])

        self._predator = Predator(
            ChangelistClassifier(get_repository, meta_feature, meta_weight),
            self._component_classifier, self._project_classifier)
Exemplo n.º 2
0
    def __init__(self, get_repository, config):
        super(PredatorForClusterfuzz, self).__init__(get_repository, config)
        meta_weight = MetaWeight({
            'TouchCrashedFileMeta':
            MetaWeight({
                'MinDistance': Weight(2.),
                'TopFrameIndex': Weight(1.),
                'TouchCrashedFile': Weight(1.),
            }),
            'TouchCrashedDirectory':
            Weight(1.),
            'TouchCrashedComponent':
            Weight(1.),
            'NumberOfTouchedFiles':
            Weight(0.5),
        })

        min_distance_feature = MinDistanceFeature(get_repository)
        top_frame_index_feature = TopFrameIndexFeature()
        touch_crashed_file_feature = TouchCrashedFileFeature()

        meta_feature = WrapperMetaFeature([
            TouchCrashedFileMetaFeature([
                min_distance_feature, top_frame_index_feature,
                touch_crashed_file_feature
            ],
                                        options=config.feature_options.get(
                                            'TouchCrashedFileMetaFeature')),
            TouchCrashedDirectoryFeature(
                options=config.feature_options['TouchCrashedDirectory']),
            TouchCrashedComponentFeature(
                self._component_classifier,
                options=config.feature_options['TouchCrashedComponent']),
            NumberOfTouchedFilesFeature()
        ])

        self._predator = Predator(
            ChangelistClassifier(get_repository, meta_feature, meta_weight),
            self._component_classifier, self._project_classifier)
    def __init__(self, get_repository, config):
        super(FinditForClusterfuzz, self).__init__(get_repository, config)
        meta_weight = MetaWeight({
            'TouchCrashedFileMeta':
            MetaWeight({
                'MinDistance': Weight(1.),
                'TopFrameIndex': Weight(1.),
                'TouchCrashedFile': Weight(1.),
            }),
            'TouchCrashedDirectory':
            Weight(1.),
            'TouchCrashedComponent':
            Weight(1.)
        })
        meta_feature = WrapperMetaFeature([
            TouchCrashedFileMetaFeature(get_repository),
            TouchCrashedDirectoryFeature(),
            TouchCrashedComponentFeature(self._component_classifier)
        ])

        self._predator = Predator(
            ChangelistClassifier(get_repository, meta_feature, meta_weight),
            self._component_classifier, self._project_classifier)
Exemplo n.º 4
0
class PredatorForClusterfuzz(PredatorApp):
    @classmethod
    def _ClientID(cls):
        return CrashClient.CLUSTERFUZZ

    def __init__(self, get_repository, config):
        super(PredatorForClusterfuzz, self).__init__(get_repository, config)
        meta_weight = MetaWeight({
            'TouchCrashedFileMeta':
            MetaWeight({
                'MinDistance': Weight(2.),
                'TopFrameIndex': Weight(1.),
                'TouchCrashedFile': Weight(1.),
            }),
            'TouchCrashedDirectory':
            Weight(1.),
            'TouchCrashedComponent':
            Weight(1.),
            'NumberOfTouchedFiles':
            Weight(0.5),
        })

        min_distance_feature = MinDistanceFeature(get_repository)
        top_frame_index_feature = TopFrameIndexFeature()
        touch_crashed_file_feature = TouchCrashedFileFeature()

        meta_feature = WrapperMetaFeature([
            TouchCrashedFileMetaFeature([
                min_distance_feature, top_frame_index_feature,
                touch_crashed_file_feature
            ],
                                        options=config.feature_options.get(
                                            'TouchCrashedFileMetaFeature')),
            TouchCrashedDirectoryFeature(
                options=config.feature_options['TouchCrashedDirectory']),
            TouchCrashedComponentFeature(
                self._component_classifier,
                options=config.feature_options['TouchCrashedComponent']),
            NumberOfTouchedFilesFeature()
        ])

        self._predator = Predator(
            ChangelistClassifier(get_repository, meta_feature, meta_weight),
            self._component_classifier, self._project_classifier)

    def _Predator(self):  # pragma: no cover
        return self._predator

    def CreateAnalysis(self, crash_identifiers):
        """Creates ``ClusterfuzzAnalysis`` with crash_identifiers as key."""
        return ClusterfuzzAnalysis.Create(crash_identifiers)

    def GetAnalysis(self, crash_identifiers):
        """Gets ``ClusterfuzzAnalysis`` using crash_identifiers."""
        return ClusterfuzzAnalysis.Get(crash_identifiers)

    def GetCrashData(self, raw_crash_data):
        """Gets ``ClusterfuzzData`` from ``raw_crash_data``."""
        return ClusterfuzzData(raw_crash_data,
                               self._get_repository,
                               top_n_frames=self.client_config['top_n'])

    def ResultMessageToClient(self, crash_identifiers):
        """Converts culprit into publishable result to client.

    Args:
      crash_identifiers (dict): Dict containing identifiers that can uniquely
        identify CrashAnalysis entity.

    Returns:
      A dict of the given ``crash_identifiers``, this model's
      ``client_id``, and a publishable version of this model's ``result``.
    """
        message = super(PredatorForClusterfuzz,
                        self).ResultMessageToClient(crash_identifiers)
        result = message['result']
        if 'regression_range' in result:
            del result['regression_range']

        return message

    def MessageToTryBot(self, analysis):
        """Gets log to push to try bot topic."""
        regression_ranges = []
        dep_rolls = (analysis.dependency_rolls.itervalues()
                     if analysis.dependency_rolls else [])
        for dep_roll in dep_rolls:
            repository = self._get_repository(dep_roll.repo_url)
            regression_range = dep_roll.ToDict()
            regression_range.update({
                'commits':
                repository.GetCommitsBetweenRevisions(dep_roll.old_revision,
                                                      dep_roll.new_revision)
            })
            regression_ranges.append(regression_range)

        message = {
            'regression_ranges': regression_ranges,
            'testcase_id': analysis.testcase_id,
            'feedback_url': analysis.feedback_url,
        }
        if 'suspected_cls' in analysis.result:
            message['suspected_cls'] = analysis.result['suspected_cls']

        return message

    def PublishResultToTryBot(self, crash_identifiers):
        """Publishes heuristic results to try bot."""
        analysis = self.GetAnalysis(crash_identifiers)
        if not analysis.regression_range:
            logging.info(
                'Skipping this testcase because it does not have regression '
                'range.')
            return

        supported_platforms = self.client_config['try_bot_supported_platforms']
        if not analysis.platform in supported_platforms:
            logging.info(
                'Skipping testcase because %s is not a supported platform.'
                ' Supported platforms: %s.', analysis.platform,
                repr(supported_platforms))
            return

        message = self.MessageToTryBot(analysis)
        topic = self.client_config['try_bot_topic']
        pubsub_util.PublishMessagesToTopic([json.dumps(message)], topic)
        logging.info('Publish result for %s to try-bot %s:\n%s',
                     repr(analysis.identifiers), topic,
                     json.dumps(message, sort_keys=True, indent=4))

    def PublishResult(self, crash_identifiers):
        """Publish results to clusterfuzz and try bot."""
        self.PublishResultToClient(crash_identifiers)
        self.PublishResultToTryBot(crash_identifiers)

    def RedefineClassifierIfLargeRegressionRange(self, analysis):
        """Disable features for revisions in regression range > 100 commits.

    For crash with big regression range, it's easy to get false positives if we
    enable TouchCrashedComponentFeature and TouchCrashedDirectoryFeature,
    Because it has a big chance to hit these features and cause false positives.
    So we should disable these 2 features.
    """
        if (analysis.commit_count_in_regression_range <
                _BIG_REGRESSION_RANGE_COMMITS_THRESHOLD):
            return

        get_repository = self._predator.changelist_classifier._get_repository
        meta_weight = MetaWeight({
            'TouchCrashedFileMeta':
            MetaWeight({
                'MinDistance': Weight(1.),
                'TopFrameIndex': Weight(1.),
                'TouchCrashedFile': Weight(1.),
            }),
        })

        meta_feature = WrapperMetaFeature([
            TouchCrashedFileMetaFeature([
                MinDistanceFeature(get_repository),
                TopFrameIndexFeature(),
                TouchCrashedFileFeature()
            ])
        ])

        self._predator.changelist_classifier = ChangelistClassifier(
            get_repository, meta_feature, meta_weight)

    def FindCulprit(self, analysis):
        """Given a crash_identifiers, returns a ``Culprit``."""
        self.RedefineClassifierIfLargeRegressionRange(analysis)
        return self._predator.FindCulprit(analysis.ToCrashReport())

    def UpdateMetrics(self, analysis):
        super(PredatorForClusterfuzz, self).UpdateMetrics(analysis)
        monitoring.clusterfuzz_reports.increment({
            'found_suspects':
            analysis.found_suspects,
            'has_regression_range':
            analysis.has_regression_range,
            'crash_type':
            analysis.crash_type,
            'security':
            analysis.security_flag,
            'platform':
            analysis.platform,
            'job_type':
            analysis.job_type,
        })
Exemplo n.º 5
0
 def _Predator(self):
   return Predator(MockChangelistClassifier(get_repository, None, None),
                   self._component_classifier,
                   self._project_classifier)