The Mother-of-All code review:
1. Fix AllowRSPrefix bug
2. Remove member mRS*Pragma in class RSContext
3. No longer only support 2x2, 3x3, 4x4 arrays
4. Fix Export All code for victorhsieh
5. Improve readability and maintainability
6. size_t -> int in calculating padding
Change-Id: I772aebd1440af66a89e2d2e688b193e500f38d69
diff --git a/slang.cpp b/slang.cpp
index fec213b..77e8467 100644
--- a/slang.cpp
+++ b/slang.cpp
@@ -1,9 +1,6 @@
#include "slang.hpp"
-#include "slang_rs_export_func.hpp"
-
-#include <stdlib.h> /* for getenv */
-
#include "libslang.h"
+#include "slang_rs_export_func.hpp"
#include "llvm/Target/TargetSelect.h" /* for function LLVMInitialize[ARM|X86][TargetInfo|Target|AsmPrinter]() */
@@ -19,102 +16,114 @@
#include "clang/Parse/ParseAST.h" /* for function clang::ParseAST() */
+#include <stdlib.h>
+
+using namespace slang;
+
#if defined(__arm__)
# define DEFAULT_TARGET_TRIPLE_STRING "armv7-none-linux-gnueabi"
#elif defined(__x86_64__)
# define DEFAULT_TARGET_TRIPLE_STRING "x86_64-unknown-linux"
#else
-# define DEFAULT_TARGET_TRIPLE_STRING "i686-unknown-linux" // let's use x86 as default target
+// let's use x86 as default target
+# define DEFAULT_TARGET_TRIPLE_STRING "i686-unknown-linux"
#endif
-namespace slang {
-
bool Slang::GlobalInitialized = false;
-/* Language option (define the language feature for compiler such as C99) */
-LangOptions Slang::LangOpts;
+// Language option (define the language feature for compiler such as C99)
+clang::LangOptions Slang::LangOpts;
/* Code generation option for the compiler */
-CodeGenOptions Slang::CodeGenOpts;
+clang::CodeGenOptions Slang::CodeGenOpts;
const std::string Slang::TargetDescription = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-a0:0:64-n32";
-/* The named of metadata node that pragma resides (should be synced with bcc.cpp) */
+// The named of metadata node that pragma resides (should be synced with
+// bcc.cpp)
const llvm::StringRef Slang::PragmaMetadataName = "#pragma";
void Slang::GlobalInitialization() {
- if(!GlobalInitialized) {
- /* We only support x86, x64 and ARM target */
+ if (!GlobalInitialized) {
+ // We only support x86, x64 and ARM target
- /* For ARM */
- LLVMInitializeARMTargetInfo();
- LLVMInitializeARMTarget();
- LLVMInitializeARMAsmPrinter();
+ // For ARM
+ LLVMInitializeARMTargetInfo();
+ LLVMInitializeARMTarget();
+ LLVMInitializeARMAsmPrinter();
- /* For x86 and x64 */
- LLVMInitializeX86TargetInfo();
- LLVMInitializeX86Target();
- LLVMInitializeX86AsmPrinter();
+ // For x86 and x64
+ LLVMInitializeX86TargetInfo();
+ LLVMInitializeX86Target();
+ LLVMInitializeX86AsmPrinter();
- /* Please refer to clang/include/clang/Basic/LangOptions.h for setting up the options */
- LangOpts.RTTI = 0; /* turn off the RTTI information support */
- LangOpts.NeXTRuntime = 0; /* turn off the NeXT runtime uses */
- LangOpts.Bool = 1; /* turn on 'bool', 'true', 'false' keywords. */
+ // Please refer to clang/include/clang/Basic/LangOptions.h to set up
+ // the options.
+ LangOpts.RTTI = 0; // Turn off the RTTI information support
+ LangOpts.NeXTRuntime = 0; // Turn off the NeXT runtime uses
+ LangOpts.Bool = 1; // Turn on 'bool', 'true', 'false' keywords
- CodeGenOpts.OptimizationLevel = 3; /* -O3 */
+ CodeGenOpts.OptimizationLevel = 3; /* -O3 */
- GlobalInitialized = true;
- }
+ GlobalInitialized = true;
+ }
- return;
+ return;
}
void Slang::LLVMErrorHandler(void *UserData, const std::string &Message) {
- Diagnostic* Diags = static_cast<Diagnostic*>(UserData);
- Diags->Report(clang::diag::err_fe_error_backend) << Message;
- exit(1);
+ clang::Diagnostic* Diags = static_cast<clang::Diagnostic*>(UserData);
+ Diags->Report(clang::diag::err_fe_error_backend) << Message;
+ exit(1);
}
-void Slang::createTarget(const char* Triple, const char* CPU, const char** Features) {
- if(Triple != NULL)
- mTargetOpts.Triple = Triple;
- else
- mTargetOpts.Triple = DEFAULT_TARGET_TRIPLE_STRING;
+void Slang::createTarget(const char* Triple, const char* CPU,
+ const char** Features) {
+ if (Triple != NULL)
+ mTargetOpts.Triple = Triple;
+ else
+ mTargetOpts.Triple = DEFAULT_TARGET_TRIPLE_STRING;
- if(CPU != NULL)
- mTargetOpts.CPU = CPU;
+ if (CPU != NULL)
+ mTargetOpts.CPU = CPU;
- mTarget.reset(TargetInfo::CreateTargetInfo(*mDiagnostics, mTargetOpts));
+ mTarget.reset(clang::TargetInfo::CreateTargetInfo(*mDiagnostics,
+ mTargetOpts));
- if(Features != NULL)
- for(int i=0;Features[i]!=NULL;i++)
- mTargetOpts.Features.push_back(Features[i]);
+ if (Features != NULL)
+ for (int i = 0; Features[i]!=NULL; i++)
+ mTargetOpts.Features.push_back(Features[i]);
return;
}
void Slang::createPreprocessor() {
- HeaderSearch* HS = new HeaderSearch(*mFileMgr); /* Default only search header file in current dir */
+ // Default only search header file in current dir
+ clang::HeaderSearch *HS = new clang::HeaderSearch(*mFileMgr);
- mPP.reset(new Preprocessor( *mDiagnostics,
- LangOpts,
- *mTarget,
- *mSourceMgr,
- *HS,
- NULL,
- true /* OwnsHeaderSearch */));
- /* Initialize the prepocessor */
+ mPP.reset(new clang::Preprocessor(*mDiagnostics,
+ LangOpts,
+ *mTarget,
+ *mSourceMgr,
+ *HS,
+ NULL,
+ /* OwnsHeaderSearch */true));
+ // Initialize the prepocessor
mPragmas.clear();
mPP->AddPragmaHandler(new PragmaRecorder(mPragmas));
std::string inclFiles("#include \"rs_types.rsh\"");
mPP->setPredefines(inclFiles + "\n" + "#include \"rs_math.rsh\"" + "\n");
- std::vector<DirectoryLookup> SearchList;
- for (int i = 0; i < mIncludePaths.size(); ++i) {
- if (const DirectoryEntry *DE = mFileMgr->getDirectory(mIncludePaths[i])) {
- SearchList.push_back(DirectoryLookup(DE, SrcMgr::C_System, false, false));
- }
+ std::vector<clang::DirectoryLookup> SearchList;
+ for (unsigned i = 0; i < mIncludePaths.size(); ++i) {
+ if (const clang::DirectoryEntry *DE =
+ mFileMgr->getDirectory(mIncludePaths[i])) {
+ SearchList.push_back(clang::DirectoryLookup(DE,
+ clang::SrcMgr::C_System,
+ false,
+ false));
+ }
}
HS->SetSearchPaths(SearchList, 1, false);
@@ -122,200 +131,210 @@
return;
}
-Slang::Slang(const char* Triple, const char* CPU, const char** Features) :
+Slang::Slang(const char *Triple, const char *CPU, const char **Features) :
mOutputType(SlangCompilerOutput_Default),
mAllowRSPrefix(false)
{
- GlobalInitialization();
+ GlobalInitialization();
- createDiagnostic();
- llvm::install_fatal_error_handler(LLVMErrorHandler, mDiagnostics.get());
+ createDiagnostic();
+ llvm::install_fatal_error_handler(LLVMErrorHandler, mDiagnostics.get());
- createTarget(Triple, CPU, Features);
- createFileManager();
- createSourceManager();
+ createTarget(Triple, CPU, Features);
+ createFileManager();
+ createSourceManager();
- return;
+ return;
}
-bool Slang::setInputSource(llvm::StringRef inputFile, const char* text, size_t textLength) {
- mInputFileName = inputFile.str();
+bool Slang::setInputSource(llvm::StringRef inputFile, const char *text, size_t textLength) {
+ mInputFileName = inputFile.str();
- /* Reset the ID tables if we are reusing the SourceManager */
- mSourceMgr->clearIDTables();
+ // Reset the ID tables if we are reusing the SourceManager
+ mSourceMgr->clearIDTables();
- /* Load the source */
- llvm::MemoryBuffer *SB = llvm::MemoryBuffer::getMemBuffer(text, text + textLength);
- mSourceMgr->createMainFileIDForMemBuffer(SB);
+ // Load the source
+ llvm::MemoryBuffer *SB = llvm::MemoryBuffer::getMemBuffer(text, text + textLength);
+ mSourceMgr->createMainFileIDForMemBuffer(SB);
- if(mSourceMgr->getMainFileID().isInvalid()) {
- mDiagnostics->Report(clang::diag::err_fe_error_reading) << inputFile;
- return false;
- }
- return true;
+ if (mSourceMgr->getMainFileID().isInvalid()) {
+ mDiagnostics->Report(clang::diag::err_fe_error_reading) << inputFile;
+ return false;
+ }
+ return true;
}
bool Slang::setInputSource(llvm::StringRef inputFile) {
- mInputFileName = inputFile.str();
+ mInputFileName = inputFile.str();
- mSourceMgr->clearIDTables();
+ mSourceMgr->clearIDTables();
- const FileEntry* File = mFileMgr->getFile(inputFile);
- if(File)
- mSourceMgr->createMainFileID(File);
+ const clang::FileEntry *File = mFileMgr->getFile(inputFile);
+ if (File)
+ mSourceMgr->createMainFileID(File);
- if(mSourceMgr->getMainFileID().isInvalid()) {
- mDiagnostics->Report(clang::diag::err_fe_error_reading) << inputFile;
- return false;
- }
+ if (mSourceMgr->getMainFileID().isInvalid()) {
+ mDiagnostics->Report(clang::diag::err_fe_error_reading) << inputFile;
+ return false;
+ }
- return true;
+ return true;
}
-void Slang::addIncludePath(const char* path) {
- mIncludePaths.push_back(path);
+void Slang::addIncludePath(const char *path) {
+ mIncludePaths.push_back(path);
}
void Slang::setOutputType(SlangCompilerOutputTy outputType) {
- mOutputType = outputType;
- if( mOutputType != SlangCompilerOutput_Assembly &&
- mOutputType != SlangCompilerOutput_LL &&
- mOutputType != SlangCompilerOutput_Bitcode &&
- mOutputType != SlangCompilerOutput_Nothing &&
- mOutputType != SlangCompilerOutput_Obj)
- mOutputType = SlangCompilerOutput_Default;
- return;
+ mOutputType = outputType;
+ if ( mOutputType != SlangCompilerOutput_Assembly &&
+ mOutputType != SlangCompilerOutput_LL &&
+ mOutputType != SlangCompilerOutput_Bitcode &&
+ mOutputType != SlangCompilerOutput_Nothing &&
+ mOutputType != SlangCompilerOutput_Obj)
+ mOutputType = SlangCompilerOutput_Default;
+ return;
}
static void _mkdir_given_a_file(const char *file) {
- char buf[256];
- char *tmp, *p = NULL;
- size_t len = strlen(file);
+ char buf[256];
+ char *tmp, *p = NULL;
+ size_t len = strlen(file);
- if (len + 1 <= sizeof(buf))
- tmp = buf;
- else
- tmp = new char [len + 1];
+ if (len + 1 <= sizeof(buf))
+ tmp = buf;
+ else
+ tmp = new char [len + 1];
- strcpy(tmp, file);
+ strcpy(tmp, file);
- if (tmp[len - 1] == '/')
- tmp[len - 1] = 0;
+ if (tmp[len - 1] == '/')
+ tmp[len - 1] = 0;
- for (p = tmp + 1; *p; p++) {
- if (*p == '/') {
- *p = 0;
- mkdir(tmp, S_IRWXU);
- *p = '/';
- }
+ for (p = tmp + 1; *p; p++) {
+ if (*p == '/') {
+ *p = 0;
+ mkdir(tmp, S_IRWXU);
+ *p = '/';
}
+ }
- if (tmp != buf)
- delete[] tmp;
+ if (tmp != buf)
+ delete[] tmp;
}
-bool Slang::setOutput(const char* outputFile) {
- std::string Error;
+bool Slang::setOutput(const char *outputFile) {
+ std::string Error;
- _mkdir_given_a_file(outputFile);
+ _mkdir_given_a_file(outputFile);
- switch(mOutputType) {
- case SlangCompilerOutput_Assembly:
- case SlangCompilerOutput_LL:
- mOS.reset( new llvm::raw_fd_ostream(outputFile, Error, 0) );
- break;
-
- case SlangCompilerOutput_Nothing:
- mOS.reset();
- break;
-
- case SlangCompilerOutput_Obj:
- case SlangCompilerOutput_Bitcode:
- default:
- mOS.reset( new llvm::raw_fd_ostream(outputFile, Error, llvm::raw_fd_ostream::F_Binary) );
- break;
+ switch (mOutputType) {
+ case SlangCompilerOutput_Assembly:
+ case SlangCompilerOutput_LL: {
+ mOS.reset( new llvm::raw_fd_ostream(outputFile, Error, 0) );
+ break;
}
-
- if(!Error.empty()) {
- mOS.reset();
- mDiagnostics->Report(clang::diag::err_fe_error_opening) << outputFile << Error;
- return false;
+ case SlangCompilerOutput_Nothing: {
+ mOS.reset();
+ break;
}
+ case SlangCompilerOutput_Obj:
+ case SlangCompilerOutput_Bitcode:
+ default: {
+ mOS.reset(new llvm::raw_fd_ostream(outputFile,
+ Error,
+ llvm::raw_fd_ostream::F_Binary));
+ break;
+ }
+ }
- mOutputFileName = outputFile;
+ if (!Error.empty()) {
+ mOS.reset();
+ mDiagnostics->Report(clang::diag::err_fe_error_opening) << outputFile
+ << Error;
+ return false;
+ }
- return true;
+ mOutputFileName = outputFile;
+
+ return true;
}
int Slang::compile() {
- if((mDiagnostics->getNumErrors() > 0) || (mOS.get() == NULL))
- return mDiagnostics->getNumErrors();
-
- /* Here is per-compilation needed initialization */
- createPreprocessor();
- createASTContext();
- createRSContext();
- //createBackend();
- createRSBackend();
-
- /* Inform the diagnostic client we are processing a source file */
- mDiagClient->BeginSourceFile(LangOpts, mPP.get());
-
- /* The core of the slang compiler */
- ParseAST(*mPP, mBackend.get(), *mASTContext);
-
- /* The compilation ended, clear up */
- mBackend.reset();
- // Can't reset yet because the reflection later on still needs mRSContext
- // mRSContext.reset();
- mASTContext.reset();
- mPP.reset();
-
- /* Inform the diagnostic client we are done with previous source file */
- mDiagClient->EndSourceFile();
-
+ if ((mDiagnostics->getNumErrors() > 0) || (mOS.get() == NULL))
return mDiagnostics->getNumErrors();
+
+ // Here is per-compilation needed initialization
+ createPreprocessor();
+ createASTContext();
+ createRSContext();
+ //createBackend();
+ createRSBackend();
+
+ // Inform the diagnostic client we are processing a source file
+ mDiagClient->BeginSourceFile(LangOpts, mPP.get());
+
+ // The core of the slang compiler
+ ParseAST(*mPP, mBackend.get(), *mASTContext);
+
+ // The compilation ended, clear up
+ mBackend.reset();
+ // Can't reset yet because the reflection later on still needs mRSContext
+ //mRSContext.reset();
+ mASTContext.reset();
+ mPP.reset();
+
+ // Inform the diagnostic client we are done with previous source file
+ mDiagClient->EndSourceFile();
+
+ return mDiagnostics->getNumErrors();
}
-bool Slang::reflectToJava(const char* outputPackageName, char* realPackageName, int bSize) {
- if(mRSContext.get())
- return mRSContext->reflectToJava(outputPackageName, mInputFileName, mOutputFileName,
- realPackageName, bSize);
- else
- return false;
+bool Slang::reflectToJava(const char *outputPackageName,
+ char *realPackageName,
+ int bSize) {
+ if (mRSContext.get())
+ return mRSContext->reflectToJava(outputPackageName,
+ mInputFileName,
+ mOutputFileName,
+ realPackageName,
+ bSize);
+ else
+ return false;
}
-bool Slang::reflectToJavaPath(const char* outputPathName) {
- if(mRSContext.get())
- return mRSContext->reflectToJavaPath(outputPathName);
- else
- return false;
+bool Slang::reflectToJavaPath(const char *outputPathName) {
+ if (mRSContext.get())
+ return mRSContext->reflectToJavaPath(outputPathName);
+ else
+ return false;
}
-void Slang::getPragmas(size_t* actualStringCount, size_t maxStringCount, char** strings) {
- int stringCount = mPragmas.size() * 2;
+void Slang::getPragmas(size_t *actualStringCount,
+ size_t maxStringCount,
+ char **strings) {
+ unsigned stringCount = mPragmas.size() * 2;
- if(actualStringCount)
- *actualStringCount = stringCount;
- if(stringCount > maxStringCount)
- stringCount = maxStringCount;
- if(strings)
- for(PragmaList::const_iterator it = mPragmas.begin();
- stringCount > 0;
- stringCount-=2, it++)
- {
- *strings++ = const_cast<char*>(it->first.c_str());
- *strings++ = const_cast<char*>(it->second.c_str());
- }
+ if (actualStringCount)
+ *actualStringCount = stringCount;
+ if (stringCount > maxStringCount)
+ stringCount = maxStringCount;
+ if (strings)
+ for (PragmaList::const_iterator it = mPragmas.begin();
+ stringCount > 0;
+ stringCount -= 2, it++) {
+ *strings++ = const_cast<char*>(it->first.c_str());
+ *strings++ = const_cast<char*>(it->second.c_str());
+ }
- return;
+ return;
}
typedef std::list<RSExportFunc*> ExportFuncList;
const char* Slang::exportFuncs() {
std::string fNames;
- for (RSContext::const_export_func_iterator I = mRSContext->export_funcs_begin();
+ for (RSContext::const_export_func_iterator I=mRSContext->export_funcs_begin();
I != mRSContext->export_funcs_end();
++I) {
RSExportFunc* func = *I;
@@ -326,8 +345,6 @@
}
Slang::~Slang() {
- llvm::llvm_shutdown();
- return;
+ llvm::llvm_shutdown();
+ return;
}
-
-} /* namespace slang */