/*
 * Copyright (C) 2016 The Android Open Source Project
 *
 * 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 <iostream>
#include <sstream>
#include <type_traits>
#include <ios>
#include <algorithm>
#include <string>

// Art Offset file dependencies
#define DEFINE_INCLUDE_DEPENDENCIES
#include "offsets_all.def"

std::string to_upper(std::string input) {
  std::transform(input.begin(), input.end(), input.begin(), ::toupper);
  return input;
}

template <typename T, typename = void>
typename std::enable_if<!std::is_signed<T>::value, std::string>::type
pretty_format(T value) {
  // Print most values as hex.
  std::stringstream ss;
  ss << std::showbase << std::hex << value;
  return ss.str();
}

template <typename T, typename = void>
typename std::enable_if<std::is_signed<T>::value, std::string>::type
pretty_format(T value) {
  // Print "signed" values as decimal so that the negativity doesn't get lost.
  std::stringstream ss;

  // For negative values add a (). Omit it from positive values for conciseness.
  if (value < 0) {
    ss << "(";
  }

  ss << value;

  if (value < 0) {
    ss << ")";
  }
  return ss.str();
}

template <typename T>
void cpp_define(std::string name, T value) {
  std::cout << "#define " << name << " " << pretty_format(value) << std::endl;
}

template <typename T>
void emit_check_eq(T value, std::string expr) {
  std::cout << "DEFINE_CHECK_EQ(" << value << ", (" << expr << "))" << std::endl;
}

const char *kFileHeader = /* // NOLINT [readability/multiline_string] [5] */ R"L1C3NS3(
/*
 * Copyright (C) 2016 The Android Open Source Project
 *
 * 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.
 */

#ifndef ART_RUNTIME_GENERATED_ASM_SUPPORT_GEN_H_
#define ART_RUNTIME_GENERATED_ASM_SUPPORT_GEN_H_

// This file has been auto-generated by cpp-define-generator; do not edit directly.
)L1C3NS3";  // NOLINT [readability/multiline_string] [5]

const char *kFileFooter = /* // NOLINT [readability/multiline_string] [5] */ R"F00T3R(
#endif  // ART_RUNTIME_GENERATED_ASM_SUPPORT_GEN_H_
)F00T3R";  // NOLINT [readability/multiline_string] [5]

#define MACROIZE(holder_type, field_name) to_upper(#holder_type "_" #field_name "_OFFSET")

int main() {
  std::cout << kFileHeader << std::endl;

  std::string z = "";

  // Print every constant expression to stdout as a #define or a CHECK_EQ
#define DEFINE_EXPR(macro_name, field_type, expr) \
  cpp_define(to_upper(#macro_name), static_cast<field_type>(expr)); \
  emit_check_eq(z + "static_cast<" #field_type ">(" + to_upper(#macro_name) + ")", \
                "static_cast<" #field_type ">(" #expr ")");
#include "offsets_all.def"

  std::cout << kFileFooter << std::endl;
  return 0;
}
