# Copyright 2020 Google LLC
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
#      http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
"""Runs a specific OSS-Fuzz project's fuzzers for CI tools."""
import logging
import sys

import config_utils
import docker
import run_fuzzers

# pylint: disable=c-extension-no-member
# pylint gets confused because of the relative import of cifuzz.

logging.basicConfig(
    format='%(asctime)s - %(name)s - %(levelname)s - %(message)s',
    level=logging.DEBUG)


def delete_unneeded_docker_images(config):
  """Deletes unneeded docker images if running in an environment with low
  disk space."""
  if not config.low_disk_space:
    return
  logging.info('Deleting builder docker images to save disk space.')
  project_image = docker.get_project_image_name(config.oss_fuzz_project_name)
  images = [
      project_image,
      docker.BASE_BUILDER_TAG,
      docker.BASE_BUILDER_TAG + ':xenial',
      docker.BASE_BUILDER_TAG + '-go',
      docker.BASE_BUILDER_TAG + '-jvm',
      docker.BASE_BUILDER_TAG + '-python',
      docker.BASE_BUILDER_TAG + '-rust',
      docker.BASE_BUILDER_TAG + '-swift',
  ]
  docker.delete_images(images)


def run_fuzzers_entrypoint():
  """This is the entrypoint for the run_fuzzers github action.
  This action can be added to any OSS-Fuzz project's workflow that uses
  Github."""
  config = config_utils.RunFuzzersConfig()
  # The default return code when an error occurs.
  returncode = 1
  if config.dry_run:
    # Sets the default return code on error to success.
    returncode = 0

  delete_unneeded_docker_images(config)
  # Run the specified project's fuzzers from the build.
  result = run_fuzzers.run_fuzzers(config)
  if result == run_fuzzers.RunFuzzersResult.ERROR:
    logging.error('Error occurred while running in workspace %s.',
                  config.workspace)
    return returncode
  if result == run_fuzzers.RunFuzzersResult.BUG_FOUND:
    logging.info('Bug found.')
    if not config.dry_run:
      # Return 2 when a bug was found by a fuzzer causing the CI to fail.
      return 2
  return 0


def main():
  """Runs project's fuzzers for CI tools.
  This is the entrypoint for the run_fuzzers github action.

  NOTE: libFuzzer binaries must be located in the ${GITHUB_WORKSPACE}/out
  directory in order for this action to be used. This action will only fuzz the
  binaries that are located in that directory. It is recommended that you add
  the build_fuzzers action preceding this one.

  NOTE: Any crash report will be in the filepath:
  ${GITHUB_WORKSPACE}/out/testcase
  This can be used in parallel with the upload-artifact action to surface the
  logs.

  Required environment variables:
    FUZZ_SECONDS: The length of time in seconds that fuzzers are to be run.
    GITHUB_WORKSPACE: The shared volume directory where input artifacts are.
    DRY_RUN: If true, no failures will surface.
    OSS_FUZZ_PROJECT_NAME: The name of the relevant OSS-Fuzz project.
    SANITIZER: The sanitizer to use when running fuzzers.

  Returns:
    0 on success or nonzero on failure.
  """
  return run_fuzzers_entrypoint()


if __name__ == '__main__':
  sys.exit(main())
