//===-- sanitizer_flags.cpp -----------------------------------------------===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//
//
// This file is a part of ThreadSanitizer/AddressSanitizer runtime.
//
//===----------------------------------------------------------------------===//

#include "sanitizer_flags.h"

#include "sanitizer_common.h"
#include "sanitizer_libc.h"
#include "sanitizer_list.h"
#include "sanitizer_flag_parser.h"

namespace __sanitizer {

CommonFlags common_flags_dont_use;

void CommonFlags::SetDefaults() {
#define COMMON_FLAG(Type, Name, DefaultValue, Description) Name = DefaultValue;
#include "sanitizer_flags.inc"
#undef COMMON_FLAG
}

void CommonFlags::CopyFrom(const CommonFlags &other) {
  internal_memcpy(this, &other, sizeof(*this));
}

// Copy the string from "s" to "out", making the following substitutions:
// %b = binary basename
// %p = pid
void SubstituteForFlagValue(const char *s, char *out, uptr out_size) {
  char *out_end = out + out_size;
  while (*s && out < out_end - 1) {
    if (s[0] != '%') {
      *out++ = *s++;
      continue;
    }
    switch (s[1]) {
      case 'b': {
        const char *base = GetProcessName();
        CHECK(base);
        while (*base && out < out_end - 1)
          *out++ = *base++;
        s += 2; // skip "%b"
        break;
      }
      case 'p': {
        int pid = internal_getpid();
        char buf[32];
        char *buf_pos = buf + 32;
        do {
          *--buf_pos = (pid % 10) + '0';
          pid /= 10;
        } while (pid);
        while (buf_pos < buf + 32 && out < out_end - 1)
          *out++ = *buf_pos++;
        s += 2; // skip "%p"
        break;
      }
      default:
        *out++ = *s++;
        break;
    }
  }
  CHECK(out < out_end - 1);
  *out = '\0';
}

class FlagHandlerInclude : public FlagHandlerBase {
  FlagParser *parser_;
  bool ignore_missing_;
  const char *original_path_;

 public:
  explicit FlagHandlerInclude(FlagParser *parser, bool ignore_missing)
      : parser_(parser), ignore_missing_(ignore_missing), original_path_("") {}
  bool Parse(const char *value) final {
    original_path_ = value;
    if (internal_strchr(value, '%')) {
      char *buf = (char *)MmapOrDie(kMaxPathLength, "FlagHandlerInclude");
      SubstituteForFlagValue(value, buf, kMaxPathLength);
      bool res = parser_->ParseFile(buf, ignore_missing_);
      UnmapOrDie(buf, kMaxPathLength);
      return res;
    }
    return parser_->ParseFile(value, ignore_missing_);
  }
  bool Format(char *buffer, uptr size) {
    // Note `original_path_` isn't actually what's parsed due to `%`
    // substitutions. Printing the substituted path would require holding onto
    // mmap'ed memory.
    return FormatString(buffer, size, original_path_);
  }
};

void RegisterIncludeFlags(FlagParser *parser, CommonFlags *cf) {
  FlagHandlerInclude *fh_include = new (FlagParser::Alloc)
      FlagHandlerInclude(parser, /*ignore_missing*/ false);
  parser->RegisterHandler("include", fh_include,
                          "read more options from the given file");
  FlagHandlerInclude *fh_include_if_exists = new (FlagParser::Alloc)
      FlagHandlerInclude(parser, /*ignore_missing*/ true);
  parser->RegisterHandler(
      "include_if_exists", fh_include_if_exists,
      "read more options from the given file (if it exists)");
}

void RegisterCommonFlags(FlagParser *parser, CommonFlags *cf) {
#define COMMON_FLAG(Type, Name, DefaultValue, Description) \
  RegisterFlag(parser, #Name, Description, &cf->Name);
#include "sanitizer_flags.inc"
#undef COMMON_FLAG

  RegisterIncludeFlags(parser, cf);
}

void InitializeCommonFlags(CommonFlags *cf) {
  // need to record coverage to generate coverage report.
  cf->coverage |= cf->html_cov_report;
  SetVerbosity(cf->verbosity);
}

}  // namespace __sanitizer
