/*
 * Copyright 2013, 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 <sys/stat.h>
#include <stdio.h>
#include <stdlib.h>
#include <iostream>

#include <cstdarg>
#include <cctype>

#include <algorithm>
#include <sstream>
#include <string>
#include <utility>

#include "os_sep.h"
#include "slang_rs_context.h"
#include "slang_rs_export_var.h"
#include "slang_rs_export_foreach.h"
#include "slang_rs_export_func.h"
#include "slang_rs_reflect_utils.h"
#include "slang_version.h"
#include "slang_utils.h"

#include "slang_rs_reflection_cpp.h"

using namespace std;

namespace slang {

#define RS_TYPE_ITEM_CLASS_NAME "Item"

#define RS_ELEM_PREFIX "__rs_elem_"

static const char *GetMatrixTypeName(const RSExportMatrixType *EMT) {
  static const char *MatrixTypeCNameMap[] = {
      "rs_matrix2x2", "rs_matrix3x3", "rs_matrix4x4",
  };
  unsigned Dim = EMT->getDim();

  if ((Dim - 2) < (sizeof(MatrixTypeCNameMap) / sizeof(const char *)))
    return MatrixTypeCNameMap[EMT->getDim() - 2];

  slangAssert(false && "GetMatrixTypeName : Unsupported matrix dimension");
  return NULL;
}

static std::string GetTypeName(const RSExportType *ET, bool Brackets = true) {
  switch (ET->getClass()) {
  case RSExportType::ExportClassPrimitive: {
    const RSExportPrimitiveType *EPT =
        static_cast<const RSExportPrimitiveType *>(ET);
    if (EPT->isRSObjectType()) {
      return std::string("android::RSC::sp<const android::RSC::") +
             RSExportPrimitiveType::getRSReflectionType(EPT)->c_name + ">";
    } else {
      return RSExportPrimitiveType::getRSReflectionType(EPT)->c_name;
    }
  }
  case RSExportType::ExportClassPointer: {
    const RSExportType *PointeeType =
        static_cast<const RSExportPointerType *>(ET)->getPointeeType();

    if (PointeeType->getClass() != RSExportType::ExportClassRecord)
      return "android::RSC::sp<android::RSC::Allocation>";
    else
      return PointeeType->getElementName();
  }
  case RSExportType::ExportClassVector: {
    const RSExportVectorType *EVT = static_cast<const RSExportVectorType *>(ET);
    std::stringstream VecName;
    VecName << EVT->getRSReflectionType(EVT)->rs_c_vector_prefix
            << EVT->getNumElement();
    return VecName.str();
  }
  case RSExportType::ExportClassMatrix: {
    return GetMatrixTypeName(static_cast<const RSExportMatrixType *>(ET));
  }
  case RSExportType::ExportClassConstantArray: {
    // TODO: Fix this for C arrays!
    const RSExportConstantArrayType *CAT =
        static_cast<const RSExportConstantArrayType *>(ET);
    std::string ElementTypeName = GetTypeName(CAT->getElementType());
    if (Brackets) {
      ElementTypeName.append("[]");
    }
    return ElementTypeName;
  }
  case RSExportType::ExportClassRecord: {
    // TODO: Fix for C structs!
    return ET->getElementName() + "." RS_TYPE_ITEM_CLASS_NAME;
  }
  default: { slangAssert(false && "Unknown class of type"); }
  }

  return "";
}

RSReflectionCpp::RSReflectionCpp(const RSContext *Context,
                                 const string &OutputDirectory,
                                 const string &RSSourceFileName,
                                 const string &BitCodeFileName)
    : mRSContext(Context), mRSSourceFilePath(RSSourceFileName),
      mBitCodeFilePath(BitCodeFileName), mOutputDirectory(OutputDirectory),
      mNextExportVarSlot(0), mNextExportFuncSlot(0), mNextExportForEachSlot(0) {
  mCleanedRSFileName = RootNameFromRSFileName(mRSSourceFilePath);
  mClassName = "ScriptC_" + mCleanedRSFileName;
}

RSReflectionCpp::~RSReflectionCpp() {}

bool RSReflectionCpp::reflect() {
  writeHeaderFile();
  writeImplementationFile();

  return true;
}

#define RS_TYPE_CLASS_NAME_PREFIX "ScriptField_"

bool RSReflectionCpp::writeHeaderFile() {
  // Create the file and write the license note.
  if (!mOut.startFile(mOutputDirectory, mClassName + ".h", mRSSourceFilePath,
                      mRSContext->getLicenseNote(), false,
                      mRSContext->getVerbose())) {
    return false;
  }

  mOut.indent() << "#include \"RenderScript.h\"\n\n";
  mOut.indent() << "using namespace android::RSC;\n\n";

  mOut.comment("This class encapsulates access to the exported elements of the script.  "
               "Typically, you would instantiate this class once, call the set_* methods "
               "for each of the exported global variables you want to change, then call "
               "one of the forEach_ methods to invoke a kernel.");
  mOut.indent() << "class " << mClassName << " : public android::RSC::ScriptC";
  mOut.startBlock();

  mOut.decreaseIndent();
  mOut.indent() << "private:\n";
  mOut.increaseIndent();

  genFieldsToStoreExportVariableValues();
  genTypeInstancesUsedInForEach();
  genFieldsForAllocationTypeVerification();

  mOut.decreaseIndent();
  mOut.indent() << "public:\n";
  mOut.increaseIndent();

  // Generate the constructor and destructor declarations.
  mOut.indent() << mClassName << "(android::RSC::sp<android::RSC::RS> rs);\n";
  mOut.indent() << "virtual ~" << mClassName << "();\n\n";

  genExportVariablesGetterAndSetter();
  genForEachDeclarations();
  genExportFunctionDeclarations();

  mOut.endBlock(true);
  mOut.closeFile();
  return true;
}

void RSReflectionCpp::genTypeInstancesUsedInForEach() {
  for (RSContext::const_export_foreach_iterator
           I = mRSContext->export_foreach_begin(),
           E = mRSContext->export_foreach_end();
       I != E; I++) {
    const RSExportForEach *EF = *I;
    const RSExportType *OET = EF->getOutType();

    if (OET) {
      genTypeInstanceFromPointer(OET);
    }

    const RSExportForEach::InTypeVec &InTypes = EF->getInTypes();

    for (RSExportForEach::InTypeIter BI = InTypes.begin(),
         EI = InTypes.end(); BI != EI; BI++) {

      genTypeInstanceFromPointer(*BI);
    }
  }
}

void RSReflectionCpp::genFieldsForAllocationTypeVerification() {
  bool CommentAdded = false;
  for (std::set<std::string>::iterator I = mTypesToCheck.begin(),
                                       E = mTypesToCheck.end();
       I != E; I++) {
    if (!CommentAdded) {
      mOut.comment("The following elements are used to verify the types of "
                   "allocations passed to kernels.");
      CommentAdded = true;
    }
    mOut.indent() << "android::RSC::sp<const android::RSC::Element> "
                  << RS_ELEM_PREFIX << *I << ";\n";
  }
}

void RSReflectionCpp::genFieldsToStoreExportVariableValues() {
  bool CommentAdded = false;
  for (RSContext::const_export_var_iterator I = mRSContext->export_vars_begin(),
                                            E = mRSContext->export_vars_end();
       I != E; I++) {
    const RSExportVar *ev = *I;
    if (ev->isConst()) {
      continue;
    }
    if (!CommentAdded) {
      mOut.comment("For each non-const variable exported by the script, we "
                   "have an equivalent field.  This field contains the last "
                   "value this variable was set to using the set_ method.  "
                   "This may not be current value of the variable in the "
                   "script, as the script is free to modify its internal "
                   "variable without changing this field.  If the script "
                   "initializes the exported variable, the constructor will "
                   "initialize this field to the same value.");
      CommentAdded = true;
    }
    mOut.indent() << GetTypeName(ev->getType()) << " " RS_EXPORT_VAR_PREFIX
                  << ev->getName() << ";\n";
  }
}

void RSReflectionCpp::genForEachDeclarations() {
  bool CommentAdded = false;
  for (RSContext::const_export_foreach_iterator
           I = mRSContext->export_foreach_begin(),
           E = mRSContext->export_foreach_end();
       I != E; I++) {
    const RSExportForEach *ForEach = *I;

    if (ForEach->isDummyRoot()) {
      mOut.indent() << "// No forEach_root(...)\n";
      continue;
    }

    if (!CommentAdded) {
      mOut.comment("For each kernel of the script corresponds one method.  "
                   "That method queues the kernel for execution.  The kernel "
                   "may not have completed nor even started by the time this "
                   "function returns.  Calls that extract the data out of the "
                   "output allocation will wait for the kernels to complete.");
      CommentAdded = true;
    }

    std::string FunctionStart = "void forEach_" + ForEach->getName() + "(";
    mOut.indent() << FunctionStart;

    ArgumentList Arguments;
    const RSExportForEach::InVec &Ins = ForEach->getIns();
    for (RSExportForEach::InIter BI = Ins.begin(), EI = Ins.end();
         BI != EI; BI++) {

      Arguments.push_back(std::make_pair(
        "android::RSC::sp<const android::RSC::Allocation>", (*BI)->getName()));
    }

    if (ForEach->hasOut() || ForEach->hasReturn()) {
      Arguments.push_back(std::make_pair(
          "android::RSC::sp<const android::RSC::Allocation>", "aout"));
    }

    const RSExportRecordType *ERT = ForEach->getParamPacketType();
    if (ERT) {
      for (RSExportForEach::const_param_iterator i = ForEach->params_begin(),
                                                 e = ForEach->params_end();
           i != e; i++) {
        RSReflectionTypeData rtd;
        (*i)->getType()->convertToRTD(&rtd);
        Arguments.push_back(std::make_pair(rtd.type->c_name, (*i)->getName()));
      }
    }
    genArguments(Arguments, FunctionStart.length());
    mOut << ");\n";
  }
}

void RSReflectionCpp::genExportFunctionDeclarations() {
  for (RSContext::const_export_func_iterator
           I = mRSContext->export_funcs_begin(),
           E = mRSContext->export_funcs_end();
       I != E; I++) {
    const RSExportFunc *ef = *I;

    makeFunctionSignature(false, ef);
  }
}

bool RSReflectionCpp::genEncodedBitCode() {
  FILE *pfin = fopen(mBitCodeFilePath.c_str(), "rb");
  if (pfin == NULL) {
    fprintf(stderr, "Error: could not read file %s\n",
            mBitCodeFilePath.c_str());
    return false;
  }

  unsigned char buf[16];
  int read_length;
  mOut.indent() << "static const unsigned char __txt[] =";
  mOut.startBlock();
  while ((read_length = fread(buf, 1, sizeof(buf), pfin)) > 0) {
    mOut.indent();
    for (int i = 0; i < read_length; i++) {
      char buf2[16];
      snprintf(buf2, sizeof(buf2), "0x%02x,", buf[i]);
      mOut << buf2;
    }
    mOut << "\n";
  }
  mOut.endBlock(true);
  mOut << "\n";
  return true;
}

bool RSReflectionCpp::writeImplementationFile() {
  if (!mOut.startFile(mOutputDirectory, mClassName + ".cpp", mRSSourceFilePath,
                      mRSContext->getLicenseNote(), false,
                      mRSContext->getVerbose())) {
    return false;
  }

  mOut.indent() << "#include \"" << mClassName << ".h\"\n\n";

  genEncodedBitCode();
  mOut.indent() << "\n\n";

  const std::string &packageName = mRSContext->getReflectJavaPackageName();
  mOut.indent() << mClassName << "::" << mClassName
                << "(android::RSC::sp<android::RSC::RS> rs):\n"
                   "        ScriptC(rs, __txt, sizeof(__txt), \""
                << mCleanedRSFileName << "\", " << mCleanedRSFileName.length()
                << ", \"/data/data/" << packageName << "/app\", sizeof(\""
                << packageName << "\"))";
  mOut.startBlock();
  for (std::set<std::string>::iterator I = mTypesToCheck.begin(),
                                       E = mTypesToCheck.end();
       I != E; I++) {
    mOut.indent() << RS_ELEM_PREFIX << *I << " = android::RSC::Element::" << *I
                  << "(mRS);\n";
  }

  for (RSContext::const_export_var_iterator I = mRSContext->export_vars_begin(),
                                            E = mRSContext->export_vars_end();
       I != E; I++) {
    const RSExportVar *EV = *I;
    if (!EV->getInit().isUninit()) {
      genInitExportVariable(EV->getType(), EV->getName(), EV->getInit());
    } else {
      genZeroInitExportVariable(EV->getName());
    }
  }
  mOut.endBlock();

  mOut.indent() << mClassName << "::~" << mClassName << "()";
  mOut.startBlock();
  mOut.endBlock();

  // Reflect export for each functions
  uint32_t slot = 0;
  for (RSContext::const_export_foreach_iterator
           I = mRSContext->export_foreach_begin(),
           E = mRSContext->export_foreach_end();
       I != E; I++, slot++) {
    const RSExportForEach *ef = *I;
    if (ef->isDummyRoot()) {
      mOut.indent() << "// No forEach_root(...)\n";
      continue;
    }

    ArgumentList Arguments;
    std::string FunctionStart =
        "void " + mClassName + "::forEach_" + ef->getName() + "(";
    mOut.indent() << FunctionStart;

    if (ef->hasIns()) {
      // FIXME: Add support for kernels with multiple inputs.
      assert(ef->getIns().size() == 1);
      Arguments.push_back(std::make_pair(
          "android::RSC::sp<const android::RSC::Allocation>", "ain"));
    }

    if (ef->hasOut() || ef->hasReturn()) {
      Arguments.push_back(std::make_pair(
          "android::RSC::sp<const android::RSC::Allocation>", "aout"));
    }

    const RSExportRecordType *ERT = ef->getParamPacketType();
    if (ERT) {
      for (RSExportForEach::const_param_iterator i = ef->params_begin(),
                                                 e = ef->params_end();
           i != e; i++) {
        RSReflectionTypeData rtd;
        (*i)->getType()->convertToRTD(&rtd);
        Arguments.push_back(std::make_pair(rtd.type->c_name, (*i)->getName()));
      }
    }
    genArguments(Arguments, FunctionStart.length());
    mOut << ")";
    mOut.startBlock();

    const RSExportType *OET = ef->getOutType();
    const RSExportForEach::InTypeVec &InTypes = ef->getInTypes();
    if (ef->hasIns()) {
      // FIXME: Add support for kernels with multiple inputs.
      assert(ef->getIns().size() == 1);
      genTypeCheck(InTypes[0], "ain");
    }
    if (OET) {
      genTypeCheck(OET, "aout");
    }

    // TODO Add the appropriate dimension checking code, as seen in
    // slang_rs_reflection.cpp.

    std::string FieldPackerName = ef->getName() + "_fp";
    if (ERT) {
      if (genCreateFieldPacker(ERT, FieldPackerName.c_str())) {
        genPackVarOfType(ERT, NULL, FieldPackerName.c_str());
      }
    }
    mOut.indent() << "forEach(" << slot << ", ";

    if (ef->hasIns()) {
      // FIXME: Add support for kernels with multiple inputs.
      assert(ef->getIns().size() == 1);
      mOut << "ain, ";
    } else {
      mOut << "NULL, ";
    }

    if (ef->hasOut() || ef->hasReturn()) {
      mOut << "aout, ";
    } else {
      mOut << "NULL, ";
    }

    // FIXME (no support for usrData with C++ kernels)
    mOut << "NULL, 0);\n";
    mOut.endBlock();
  }

  slot = 0;
  // Reflect export function
  for (RSContext::const_export_func_iterator
           I = mRSContext->export_funcs_begin(),
           E = mRSContext->export_funcs_end();
       I != E; I++) {
    const RSExportFunc *ef = *I;

    makeFunctionSignature(true, ef);
    mOut.startBlock();
    const RSExportRecordType *params = ef->getParamPacketType();
    size_t param_len = 0;
    if (params) {
      param_len = params->getAllocSize();
      if (genCreateFieldPacker(params, "__fp")) {
        genPackVarOfType(params, NULL, "__fp");
      }
    }

    mOut.indent() << "invoke(" << slot;
    if (params) {
      mOut << ", __fp.getData(), " << param_len << ");\n";
    } else {
      mOut << ", NULL, 0);\n";
    }
    mOut.endBlock();

    slot++;
  }

  mOut.closeFile();
  return true;
}

void RSReflectionCpp::genExportVariablesGetterAndSetter() {
  mOut.comment("Methods to set and get the variables exported by the script. "
               "Const variables will not have a setter.\n\n"
               "Note that the value returned by the getter may not be the "
               "current value of the variable in the script.  The getter will "
               "return the initial value of the variable (as defined in the "
               "script) or the the last value set by using the setter method.  "
               "The script is free to modify its value independently.");
  for (RSContext::const_export_var_iterator I = mRSContext->export_vars_begin(),
                                            E = mRSContext->export_vars_end();
       I != E; I++) {
    const RSExportVar *EV = *I;
    const RSExportType *ET = EV->getType();

    switch (ET->getClass()) {
    case RSExportType::ExportClassPrimitive: {
      genGetterAndSetter(static_cast<const RSExportPrimitiveType *>(ET), EV);
      break;
    }
    case RSExportType::ExportClassPointer: {
      // TODO Deprecate this.
      genPointerTypeExportVariable(EV);
      break;
    }
    case RSExportType::ExportClassVector: {
      genGetterAndSetter(static_cast<const RSExportVectorType *>(ET), EV);
      break;
    }
    case RSExportType::ExportClassMatrix: {
      genMatrixTypeExportVariable(EV);
      break;
    }
    case RSExportType::ExportClassConstantArray: {
      genGetterAndSetter(static_cast<const RSExportConstantArrayType *>(ET),
                         EV);
      break;
    }
    case RSExportType::ExportClassRecord: {
      genGetterAndSetter(static_cast<const RSExportRecordType *>(ET), EV);
      break;
    }
    default: { slangAssert(false && "Unknown class of type"); }
    }
  }
}

void RSReflectionCpp::genGetterAndSetter(const RSExportPrimitiveType *EPT,
                                         const RSExportVar *EV) {
  RSReflectionTypeData rtd;
  EPT->convertToRTD(&rtd);
  std::string TypeName = GetTypeName(EPT, false);

  if (!EV->isConst()) {
    mOut.indent() << "void set_" << EV->getName() << "(" << TypeName << " v)";
    mOut.startBlock();
    mOut.indent() << "setVar(" << getNextExportVarSlot() << ", ";
    if (EPT->isRSObjectType()) {
      mOut << "v";
    } else {
      mOut << "&v, sizeof(v)";
    }
    mOut << ");\n";
    mOut.indent() << RS_EXPORT_VAR_PREFIX << EV->getName() << " = v;\n";
    mOut.endBlock();
  }
  mOut.indent() << TypeName << " get_" << EV->getName() << "() const";
  mOut.startBlock();
  if (EV->isConst()) {
    const clang::APValue &val = EV->getInit();
    bool isBool = !strcmp(TypeName.c_str(), "bool");
    mOut.indent() << "return ";
    genInitValue(val, isBool);
    mOut << ";\n";
  } else {
    mOut.indent() << "return " << RS_EXPORT_VAR_PREFIX << EV->getName()
                  << ";\n";
  }
  mOut.endBlock();
}

void RSReflectionCpp::genPointerTypeExportVariable(const RSExportVar *EV) {
  const RSExportType *ET = EV->getType();

  slangAssert((ET->getClass() == RSExportType::ExportClassPointer) &&
              "Variable should be type of pointer here");

  std::string TypeName = GetTypeName(ET);
  std::string VarName = EV->getName();

  RSReflectionTypeData rtd;
  EV->getType()->convertToRTD(&rtd);
  uint32_t slot = getNextExportVarSlot();

  if (!EV->isConst()) {
    mOut.indent() << "void bind_" << VarName << "(" << TypeName << " v)";
    mOut.startBlock();
    mOut.indent() << "bindAllocation(v, " << slot << ");\n";
    mOut.indent() << RS_EXPORT_VAR_PREFIX << VarName << " = v;\n";
    mOut.endBlock();
  }
  mOut.indent() << TypeName << " get_" << VarName << "() const";
  mOut.startBlock();
  if (EV->isConst()) {
    const clang::APValue &val = EV->getInit();
    bool isBool = !strcmp(TypeName.c_str(), "bool");
    mOut.indent() << "return ";
    genInitValue(val, isBool);
    mOut << ";\n";
  } else {
    mOut.indent() << "return " << RS_EXPORT_VAR_PREFIX << VarName << ";\n";
  }
  mOut.endBlock();
}

void RSReflectionCpp::genGetterAndSetter(const RSExportVectorType *EVT,
                                         const RSExportVar *EV) {
  slangAssert(EVT != NULL);

  RSReflectionTypeData rtd;
  EVT->convertToRTD(&rtd);

  if (!EV->isConst()) {
    mOut.indent() << "void set_" << EV->getName() << "("
                  << rtd.type->rs_c_vector_prefix << EVT->getNumElement()
                  << " v)";
    mOut.startBlock();
    mOut.indent() << "setVar(" << getNextExportVarSlot()
                  << ", &v, sizeof(v));\n";
    mOut.indent() << RS_EXPORT_VAR_PREFIX << EV->getName() << " = v;\n";
    mOut.endBlock();
  }
  mOut.indent() << rtd.type->rs_c_vector_prefix << EVT->getNumElement()
                << " get_" << EV->getName() << "() const";
  mOut.startBlock();
  if (EV->isConst()) {
    const clang::APValue &val = EV->getInit();
    mOut.indent() << "return ";
    genInitValue(val, false);
    mOut << ";\n";
  } else {
    mOut.indent() << "return " << RS_EXPORT_VAR_PREFIX << EV->getName()
                  << ";\n";
  }
  mOut.endBlock();
}

void RSReflectionCpp::genMatrixTypeExportVariable(const RSExportVar *EV) {
  slangAssert(false);
}

void RSReflectionCpp::genGetterAndSetter(const RSExportConstantArrayType *AT,
                                         const RSExportVar *EV) {
  slangAssert(false);
}

void RSReflectionCpp::genGetterAndSetter(const RSExportRecordType *ERT,
                                         const RSExportVar *EV) {
  slangAssert(false);
}

void RSReflectionCpp::makeFunctionSignature(bool isDefinition,
                                            const RSExportFunc *ef) {
  mOut.indent() << "void ";
  if (isDefinition) {
    mOut << mClassName << "::";
  }
  mOut << "invoke_" << ef->getName() << "(";

  if (ef->getParamPacketType()) {
    bool FirstArg = true;
    for (RSExportFunc::const_param_iterator i = ef->params_begin(),
                                            e = ef->params_end();
         i != e; i++) {
      RSReflectionTypeData rtd;
      (*i)->getType()->convertToRTD(&rtd);
      if (!FirstArg) {
        mOut << ", ";
      } else {
        FirstArg = false;
      }
      mOut << rtd.type->c_name << " " << (*i)->getName();
    }
  }

  if (isDefinition) {
    mOut << ")";
  } else {
    mOut << ");\n";
  }
}

void RSReflectionCpp::genArguments(const ArgumentList &Arguments, int Offset) {
  bool FirstArg = true;

  for (ArgumentList::const_iterator I = Arguments.begin(), E = Arguments.end();
       I != E; I++) {
    if (!FirstArg) {
      mOut << ",\n";
      mOut.indent() << string(Offset, ' ');
    } else {
      FirstArg = false;
    }

    mOut << I->first << " " << I->second;
  }
}

bool RSReflectionCpp::genCreateFieldPacker(const RSExportType *ET,
                                           const char *FieldPackerName) {
  size_t AllocSize = ET->getAllocSize();

  if (AllocSize > 0) {
    mOut.indent() << "android::RSC::FieldPacker " << FieldPackerName << "("
                  << AllocSize << ");\n";
    return true;
  }

  return false;
}

void RSReflectionCpp::genPackVarOfType(const RSExportType *ET,
                                       const char *VarName,
                                       const char *FieldPackerName) {
  switch (ET->getClass()) {
  case RSExportType::ExportClassPrimitive:
  case RSExportType::ExportClassVector:
  case RSExportType::ExportClassPointer:
  case RSExportType::ExportClassMatrix: {
    mOut.indent() << FieldPackerName << ".add(" << VarName << ");\n";
    break;
  }
  case RSExportType::ExportClassConstantArray: {
    /*const RSExportConstantArrayType *ECAT =
        static_cast<const RSExportConstantArrayType *>(ET);

    // TODO(zonr): more elegant way. Currently, we obtain the unique index
    //             variable (this method involves recursive call which means
    //             we may have more than one level loop, therefore we can't
    //             always use the same index variable name here) name given
    //             in the for-loop from counting the '.' in @VarName.
    unsigned Level = 0;
    size_t LastDotPos = 0;
    std::string ElementVarName(VarName);

  while (LastDotPos != std::string::npos) {
    LastDotPos = ElementVarName.find_first_of('.', LastDotPos + 1);
    Level++;
  }
  std::string IndexVarName("ct");
  IndexVarName.append(llvm::utostr_32(Level));

  C.indent() << "for (int " << IndexVarName << " = 0; " <<
                      IndexVarName << " < " << ECAT->getSize() << "; " <<
                      IndexVarName << "++)";
  C.startBlock();

  ElementVarName.append("[" + IndexVarName + "]");
  genPackVarOfType(C, ECAT->getElementType(), ElementVarName.c_str(),
                   FieldPackerName);

  C.endBlock();*/
    break;
  }
  case RSExportType::ExportClassRecord: {
    const RSExportRecordType *ERT = static_cast<const RSExportRecordType *>(ET);
    // Relative pos from now on in field packer
    unsigned Pos = 0;

    for (RSExportRecordType::const_field_iterator I = ERT->fields_begin(),
                                                  E = ERT->fields_end();
         I != E; I++) {
      const RSExportRecordType::Field *F = *I;
      std::string FieldName;
      size_t FieldOffset = F->getOffsetInParent();
      const RSExportType *T = F->getType();
      size_t FieldStoreSize = T->getStoreSize();
      size_t FieldAllocSize = T->getAllocSize();

      if (VarName != NULL)
        FieldName = VarName + ("." + F->getName());
      else
        FieldName = F->getName();

      if (FieldOffset > Pos) {
        mOut.indent() << FieldPackerName << ".skip(" << (FieldOffset - Pos)
                      << ");\n";
      }

      genPackVarOfType(F->getType(), FieldName.c_str(), FieldPackerName);

      // There is padding in the field type
      if (FieldAllocSize > FieldStoreSize) {
        mOut.indent() << FieldPackerName << ".skip("
                      << (FieldAllocSize - FieldStoreSize) << ");\n";
      }

      Pos = FieldOffset + FieldAllocSize;
    }

    // There maybe some padding after the struct
    if (ERT->getAllocSize() > Pos) {
      mOut.indent() << FieldPackerName << ".skip(" << ERT->getAllocSize() - Pos
                    << ");\n";
    }
    break;
  }
  default: { slangAssert(false && "Unknown class of type"); }
  }
}

void RSReflectionCpp::genTypeCheck(const RSExportType *ET,
                                   const char *VarName) {
  mOut.indent() << "// Type check for " << VarName << "\n";

  if (ET->getClass() == RSExportType::ExportClassPointer) {
    const RSExportPointerType *EPT =
        static_cast<const RSExportPointerType *>(ET);
    ET = EPT->getPointeeType();
  }

  std::string TypeName;
  switch (ET->getClass()) {
  case RSExportType::ExportClassPrimitive:
  case RSExportType::ExportClassVector:
  case RSExportType::ExportClassRecord: {
    TypeName = ET->getElementName();
    break;
  }

  default:
    break;
  }

  if (!TypeName.empty()) {
    mOut.indent() << "if (!" << VarName
                  << "->getType()->getElement()->isCompatible("
                  << RS_ELEM_PREFIX << TypeName << "))";
    mOut.startBlock();
    mOut.indent() << "mRS->throwError(RS_ERROR_RUNTIME_ERROR, "
                     "\"Incompatible type\");\n";
    mOut.indent() << "return;\n";
    mOut.endBlock();
  }
}

void RSReflectionCpp::genTypeInstanceFromPointer(const RSExportType *ET) {
  if (ET->getClass() == RSExportType::ExportClassPointer) {
    // For pointer parameters to original forEach kernels.
    const RSExportPointerType *EPT =
        static_cast<const RSExportPointerType *>(ET);
    genTypeInstance(EPT->getPointeeType());
  } else {
    // For handling pass-by-value kernel parameters.
    genTypeInstance(ET);
  }
}

void RSReflectionCpp::genTypeInstance(const RSExportType *ET) {
  switch (ET->getClass()) {
  case RSExportType::ExportClassPrimitive:
  case RSExportType::ExportClassVector:
  case RSExportType::ExportClassConstantArray:
  case RSExportType::ExportClassRecord: {
    std::string TypeName = ET->getElementName();
    mTypesToCheck.insert(TypeName);
    break;
  }

  default:
    break;
  }
}

void RSReflectionCpp::genInitExportVariable(const RSExportType *ET,
                                            const std::string &VarName,
                                            const clang::APValue &Val) {
  slangAssert(!Val.isUninit() && "Not a valid initializer");

  switch (ET->getClass()) {
  case RSExportType::ExportClassPrimitive: {
    const RSExportPrimitiveType *EPT =
        static_cast<const RSExportPrimitiveType *>(ET);
    if (EPT->getType() == DataTypeBoolean) {
      genInitBoolExportVariable(VarName, Val);
    } else {
      genInitPrimitiveExportVariable(VarName, Val);
    }
    break;
  }
  case RSExportType::ExportClassPointer: {
    if (!Val.isInt() || Val.getInt().getSExtValue() != 0)
      std::cerr << "Initializer which is non-NULL to pointer type variable "
                   "will be ignored" << std::endl;
    break;
  }
  case RSExportType::ExportClassVector: {
    const RSExportVectorType *EVT = static_cast<const RSExportVectorType *>(ET);
    switch (Val.getKind()) {
    case clang::APValue::Int:
    case clang::APValue::Float: {
      for (unsigned i = 0; i < EVT->getNumElement(); i++) {
        std::string Name = VarName + "." + getVectorAccessor(i);
        genInitPrimitiveExportVariable(Name, Val);
      }
      break;
    }
    case clang::APValue::Vector: {
      unsigned NumElements = std::min(
          static_cast<unsigned>(EVT->getNumElement()), Val.getVectorLength());
      for (unsigned i = 0; i < NumElements; i++) {
        const clang::APValue &ElementVal = Val.getVectorElt(i);
        std::string Name = VarName + "." + getVectorAccessor(i);
        genInitPrimitiveExportVariable(Name, ElementVal);
      }
      break;
    }
    case clang::APValue::MemberPointer:
    case clang::APValue::Uninitialized:
    case clang::APValue::ComplexInt:
    case clang::APValue::ComplexFloat:
    case clang::APValue::LValue:
    case clang::APValue::Array:
    case clang::APValue::Struct:
    case clang::APValue::Union:
    case clang::APValue::AddrLabelDiff: {
      slangAssert(false && "Unexpected type of value of initializer.");
    }
    }
    break;
  }
  case RSExportType::ExportClassMatrix:
  case RSExportType::ExportClassConstantArray:
  case RSExportType::ExportClassRecord: {
    slangAssert(false && "Unsupported initializer for record/matrix/constant "
                         "array type variable currently");
    break;
  }
  default: { slangAssert(false && "Unknown class of type"); }
  }
}

const char *RSReflectionCpp::getVectorAccessor(unsigned Index) {
  static const char *VectorAccessorMap[] = {/* 0 */ "x",
                                            /* 1 */ "y",
                                            /* 2 */ "z",
                                            /* 3 */ "w",
  };

  slangAssert((Index < (sizeof(VectorAccessorMap) / sizeof(const char *))) &&
              "Out-of-bound index to access vector member");

  return VectorAccessorMap[Index];
}

void RSReflectionCpp::genZeroInitExportVariable(const std::string &VarName) {
  mOut.indent() << "memset(&" << RS_EXPORT_VAR_PREFIX << VarName
                << ", 0, sizeof(" << RS_EXPORT_VAR_PREFIX << VarName << "));\n";
}

void
RSReflectionCpp::genInitPrimitiveExportVariable(const std::string &VarName,
                                                const clang::APValue &Val) {
  slangAssert(!Val.isUninit() && "Not a valid initializer");

  mOut.indent() << RS_EXPORT_VAR_PREFIX << VarName << " = ";
  genInitValue(Val);
  mOut << ";\n";
}

void RSReflectionCpp::genInitValue(const clang::APValue &Val, bool asBool) {
  switch (Val.getKind()) {
  case clang::APValue::Int: {
    llvm::APInt api = Val.getInt();
    if (asBool) {
      mOut << ((api.getSExtValue() == 0) ? "false" : "true");
    } else {
      // TODO: Handle unsigned correctly for C++
      mOut << api.getSExtValue();
      if (api.getBitWidth() > 32) {
        mOut << "L";
      }
    }
    break;
  }

  case clang::APValue::Float: {
    llvm::APFloat apf = Val.getFloat();
    llvm::SmallString<30> s;
    apf.toString(s);
    mOut << s.c_str();
    if (&apf.getSemantics() == &llvm::APFloat::IEEEsingle) {
      if (s.count('.') == 0) {
        mOut << ".f";
      } else {
        mOut << "f";
      }
    }
    break;
  }

  case clang::APValue::ComplexInt:
  case clang::APValue::ComplexFloat:
  case clang::APValue::LValue:
  case clang::APValue::Vector: {
    slangAssert(false && "Primitive type cannot have such kind of initializer");
    break;
  }

  default: { slangAssert(false && "Unknown kind of initializer"); }
  }
}

void RSReflectionCpp::genInitBoolExportVariable(const std::string &VarName,
                                                const clang::APValue &Val) {
  slangAssert(!Val.isUninit() && "Not a valid initializer");
  slangAssert((Val.getKind() == clang::APValue::Int) &&
              "Bool type has wrong initial APValue");

  mOut.indent() << RS_EXPORT_VAR_PREFIX << VarName << " = "
                << ((Val.getInt().getSExtValue() == 0) ? "false" : "true")
                << ";";
}

} // namespace slang
