/* Distributed under the OSI-approved BSD 3-Clause License.  See accompanying
   file LICENSE.rst or https://cmake.org/licensing for details.  */

#pragma once

#include "cmConfigure.h" // IWYU pragma: keep

#include <string>
#include <unordered_map>
#include <vector>

#include <cm/optional>
#include <cm/string_view>

// From cmPkgConfigParser.h, IWYU doesn't like including the header
struct cmPkgConfigEntry;

struct cmPkgConfigCflagsResult
{
  std::string Flagline;
  std::vector<std::string> Includes;
  std::vector<std::string> CompileOptions;
};

struct cmPkgConfigLibsResult
{
  std::string Flagline;
  std::vector<std::string> LibDirs;
  std::vector<std::string> LibNames;
  std::vector<std::string> LinkOptions;
};

struct cmPkgConfigVersionReq
{
  enum
  {
    ANY = 0,
    LT,
    LT_EQ,
    EQ,
    NEQ,
    GT_EQ,
    GT,
  } Operation = ANY;
  std::string Version;

  std::string string() const;
};

struct cmPkgConfigDependency
{
  std::string Name;
  cmPkgConfigVersionReq VerReq;
};

struct cmPkgConfigEnv
{
  cm::optional<std::vector<std::string>> Path;
  cm::optional<std::vector<std::string>> LibDirs;
  cm::optional<std::vector<std::string>> SysCflags;
  cm::optional<std::vector<std::string>> SysLibs;

  cm::optional<std::string> SysrootDir;
  cm::optional<std::string> TopBuildDir;
  std::vector<std::string> search;

  cm::optional<bool> DisableUninstalled;

  bool AllowSysCflags = true;
  bool AllowSysLibs = true;
};

class cmPkgConfigResult
{
public:
  std::unordered_map<std::string, std::string> Keywords;
  std::unordered_map<std::string, std::string> Variables;

  std::string Name();
  std::string Description();
  std::string Version();

  std::vector<cmPkgConfigDependency> Conflicts();
  std::vector<cmPkgConfigDependency> Provides();
  std::vector<cmPkgConfigDependency> Requires(bool priv = false);

  cmPkgConfigCflagsResult Cflags(bool priv = false);
  cmPkgConfigLibsResult Libs(bool priv = false);

  cmPkgConfigEnv* env;

private:
  std::string StrOrDefault(std::string const& key, cm::string_view def = "");
};

class cmPkgConfigResolver
{
  friend class cmPkgConfigResult;

public:
  static cm::optional<cmPkgConfigResult> ResolveStrict(
    std::vector<cmPkgConfigEntry> const& entries, cmPkgConfigEnv env);

  static cm::optional<cmPkgConfigResult> ResolvePermissive(
    std::vector<cmPkgConfigEntry> const& entries, cmPkgConfigEnv env);

  static cmPkgConfigResult ResolveBestEffort(
    std::vector<cmPkgConfigEntry> const& entries, cmPkgConfigEnv env);

  static cmPkgConfigVersionReq ParseVersion(std::string const& version);

  static bool CheckVersion(cmPkgConfigVersionReq const& desired,
                           std::string const& provided);

  static void ReplaceSep(std::string& list);

#ifdef _WIN32
  static char const Sep = ';';
#else
  static char const Sep = ':';
#endif

private:
  static std::string HandleVariablePermissive(
    cmPkgConfigEntry const& entry,
    std::unordered_map<std::string, std::string> const& variables);

  static cm::optional<std::string> HandleVariableStrict(
    cmPkgConfigEntry const& entry,
    std::unordered_map<std::string, std::string> const& variables);

  static std::string HandleKeyword(
    cmPkgConfigEntry const& entry,
    std::unordered_map<std::string, std::string> const& variables);

  static std::vector<cm::string_view> TokenizeFlags(
    std::string const& flagline);

  static cmPkgConfigCflagsResult MangleCflags(
    std::vector<cm::string_view> const& flags);

  static cmPkgConfigCflagsResult MangleCflags(
    std::vector<cm::string_view> const& flags, std::string const& sysroot);

  static cmPkgConfigCflagsResult MangleCflags(
    std::vector<cm::string_view> const& flags,
    std::vector<std::string> const& syspaths);

  static cmPkgConfigCflagsResult MangleCflags(
    std::vector<cm::string_view> const& flags, std::string const& sysroot,
    std::vector<std::string> const& syspaths);

  static cmPkgConfigLibsResult MangleLibs(
    std::vector<cm::string_view> const& flags);

  static cmPkgConfigLibsResult MangleLibs(
    std::vector<cm::string_view> const& flags, std::string const& sysroot);

  static cmPkgConfigLibsResult MangleLibs(
    std::vector<cm::string_view> const& flags,
    std::vector<std::string> const& syspaths);

  static cmPkgConfigLibsResult MangleLibs(
    std::vector<cm::string_view> const& flags, std::string const& sysroot,
    std::vector<std::string> const& syspaths);

  static std::string Reroot(cm::string_view flag, cm::string_view prefix,
                            std::string const& sysroot);

  static cmPkgConfigVersionReq ParseVersion(std::string::const_iterator& cur,
                                            std::string::const_iterator end);

  static std::vector<cmPkgConfigDependency> ParseDependencies(
    std::string const& deps);
};
