// Copyright 2014 The Bazel Authors. All rights reserved.
//
// 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.

#include "src/main/cpp/blaze_util.h"

#include <fcntl.h>
#include <stdarg.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#include <algorithm>
#include <cassert>
#include <iostream>

#include "src/main/cpp/blaze_util_platform.h"
#include "src/main/cpp/util/errors.h"
#include "src/main/cpp/util/exit_code.h"
#include "src/main/cpp/util/file.h"
#include "src/main/cpp/util/logging.h"
#include "src/main/cpp/util/numbers.h"
#include "src/main/cpp/util/path_platform.h"
#include "src/main/cpp/util/port.h"
#include "src/main/cpp/util/strings.h"

namespace blaze {

using std::map;
using std::min;
using std::string;
using std::vector;

const char kServerPidFile[] = "server.pid.txt";

const unsigned int kPostShutdownGracePeriodSeconds = 60;

const unsigned int kPostKillGracePeriodSeconds = 10;

const char* GetUnaryOption(const char *arg,
                           const char *next_arg,
                           const char *key) {
  const char *value = blaze_util::var_strprefix(arg, key);
  if (value == nullptr) {
    return nullptr;
  } else if (value[0] == '=') {
    return value + 1;
  } else if (value[0]) {
    return nullptr;  // trailing garbage in key name
  }

  return next_arg;
}

bool GetNullaryOption(const char *arg, const char *key) {
  const char *value = blaze_util::var_strprefix(arg, key);
  if (value == nullptr) {
    return false;
  } else if (value[0] == '=') {
    BAZEL_DIE(blaze_exit_code::BAD_ARGV)
        << "In argument '" << arg << "': option '" << key
        << "' does not take a value.";
  } else if (value[0]) {
    return false;  // trailing garbage in key name
  }

  return true;
}

std::vector<std::string> GetAllUnaryOptionValues(
    const vector<string>& args, const char* key,
    const char* ignore_after_value) {
  vector<std::string> values;
  for (vector<string>::size_type i = 0; i < args.size(); ++i) {
    if (args[i] == "--") {
      // "--" means all remaining args aren't options
      return values;
    }

    const char* next_arg = args[std::min(i + 1, args.size() - 1)].c_str();
    const char* result = GetUnaryOption(args[i].c_str(), next_arg, key);
    if (result != nullptr) {
      // 'key' was found and 'result' has its value.
      values.push_back(result);

      if (ignore_after_value != nullptr &&
          strcmp(result, ignore_after_value) == 0) {
        break;
      }
    }

    // This is a pointer comparison, so equality means that the result must be
    // from the next arg instead of happening to match the value from
    // "--key=<value>" string, in which case we need to advance the index to
    // skip the next arg for later iterations.
    if (result == next_arg) {
      i++;
    }
  }

  return values;
}

const char* SearchUnaryOption(const vector<string>& args,
                              const char *key, bool warn_if_dupe) {
  if (args.empty()) {
    return nullptr;
  }

  const char* value = nullptr;
  bool found_dupe = false;  // true if 'key' was found twice
  vector<string>::size_type i = 0;

  // Examine the first N-1 arguments. (N-1 because we examine the i'th and
  // i+1'th together, in case a flag is defined "--name value" style and not
  // "--name=value" style.)
  for (; i < args.size() - 1; ++i) {
    if (args[i] == "--") {
      // If the current argument is "--", all following args are target names.
      // If 'key' was not found, 'value' is nullptr and we can return that.
      // If 'key' was found exactly once, then 'value' has the value and again
      // we can return that.
      // If 'key' was found more than once then we could not have reached this
      // line, because we would have broken out of the loop when 'key' was found
      // the second time.
      return value;
    }
    const char* result = GetUnaryOption(args[i].c_str(),
                                        args[i + 1].c_str(),
                                        key);
    if (result != nullptr) {
      // 'key' was found and 'result' has its value.
      if (value) {
        // 'key' was found once before, because 'value' is not empty.
        found_dupe = true;
        break;
      } else {
        // 'key' was not found before, so store the value in 'value'.
        value = result;
      }
    }
  }

  if (value) {
    // 'value' is not empty, so 'key' was found at least once in the first N-1
    // arguments.
    if (warn_if_dupe) {
      if (!found_dupe) {
        // We did not find a duplicate in the first N-1 arguments. Examine the
        // last argument, it may be a duplicate.
        found_dupe = (GetUnaryOption(args[i].c_str(), nullptr, key) != nullptr);
      }
      if (found_dupe) {
        BAZEL_LOG(WARNING) << key << " is given more than once, "
                           << "only the first occurrence is used";
      }
    }
    return value;
  } else {
    // 'value' is empty, so 'key' was not yet found in the first N-1 arguments.
    // If 'key' is in the last argument, we'll parse and return the value from
    // that, and if it isn't, we'll return NULL.
    return GetUnaryOption(args[i].c_str(), nullptr, key);
  }
}

bool SearchNullaryOption(const vector<string>& args,
                         const string& flag_name,
                         const bool default_value) {
  const string positive_flag = "--" + flag_name;
  const string negative_flag = "--no" + flag_name;
  bool result = default_value;
  for (vector<string>::size_type i = 0; i < args.size(); i++) {
    if (args[i] == "--") {
      break;
    }
    if (GetNullaryOption(args[i].c_str(), positive_flag.c_str())) {
      result = true;
    } else if (GetNullaryOption(args[i].c_str(), negative_flag.c_str())) {
      result = false;
    }
  }
  return result;
}

bool IsArg(const string& arg) {
  return blaze_util::starts_with(arg, "-") && (arg != "--help")
      && (arg != "-help") && (arg != "-h");
}

std::string AbsolutePathFromFlag(const std::string& value) {
  if (value.empty()) {
    return blaze_util::GetCwd();
  } else if (!value.empty() && value[0] == '~') {
    return blaze_util::JoinPath(GetHomeDir(), value.substr(1));
  } else {
    return blaze_util::MakeAbsolute(value);
  }
}

void LogWait(unsigned int elapsed_seconds, unsigned int wait_seconds) {
  SigPrintf("WARNING: Waiting for server process to terminate "
            "(waited %d seconds, waiting at most %d)\n",
            elapsed_seconds, wait_seconds);
}

bool AwaitServerProcessTermination(int pid, const blaze_util::Path& output_base,
                                   unsigned int wait_seconds) {
  uint64_t st = GetMillisecondsMonotonic();
  const unsigned int first_seconds = 5;
  bool logged_first = false;
  const unsigned int second_seconds = 10;
  bool logged_second = false;
  const unsigned int third_seconds = 30;
  bool logged_third = false;

  while (VerifyServerProcess(pid, output_base)) {
    TrySleep(100);
    uint64_t elapsed_millis = GetMillisecondsMonotonic() - st;
    if (!logged_first && elapsed_millis > first_seconds * 1000) {
      LogWait(first_seconds, wait_seconds);
      logged_first = true;
    }
    if (!logged_second && elapsed_millis > second_seconds * 1000) {
      LogWait(second_seconds, wait_seconds);
      logged_second = true;
    }
    if (!logged_third && elapsed_millis > third_seconds * 1000) {
      LogWait(third_seconds, wait_seconds);
      logged_third = true;
    }
    if (elapsed_millis > wait_seconds * 1000) {
      SigPrintf("INFO: Waited %d seconds for server process (pid=%d) to"
                " terminate.\n",
                wait_seconds, pid);
      return false;
    }
  }
  return true;
}

// For now, we don't have the client set up to log to a file. If --client_debug
// is passed, however, all BAZEL_LOG statements will be output to stderr.
// If/when we switch to logging these to a file, care will have to be taken to
// either log to both stderr and the file in the case of --client_debug, or be
// ok that these log lines will only go to one stream.
void SetDebugLog(bool enabled) {
  if (enabled) {
    blaze_util::SetLoggingOutputStreamToStderr();
  } else {
    blaze_util::SetLoggingOutputStream(nullptr);
  }
}

bool IsRunningWithinTest() { return ExistsEnv("TEST_TMPDIR"); }

void WithEnvVars::SetEnvVars(const map<string, EnvVarValue>& vars) {
  for (const auto& var : vars) {
    switch (var.second.action) {
      case EnvVarAction::UNSET:
        UnsetEnv(var.first);
        break;

      case EnvVarAction::SET:
        SetEnv(var.first, var.second.value);
        break;

      default:
        assert(false);
    }
  }
}

WithEnvVars::WithEnvVars(const map<string, EnvVarValue>& vars) {
  for (const auto& v : vars) {
    if (ExistsEnv(v.first)) {
      _old_values[v.first] = EnvVarValue(EnvVarAction::SET, GetEnv(v.first));
    } else {
      _old_values[v.first] = EnvVarValue(EnvVarAction::UNSET, "");
    }
  }

  SetEnvVars(vars);
}

WithEnvVars::~WithEnvVars() {
  SetEnvVars(_old_values);
}

}  // namespace blaze
